OSDN Git Service

91c4571ee49164af175bf830d6fce49a519e14bf
[android-x86/frameworks-base.git] / services / core / java / com / android / server / am / ActivityManagerService.java
1 /*
2  * Copyright (C) 2006-2008 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
17 package com.android.server.am;
18
19 import com.android.internal.telephony.TelephonyIntents;
20 import com.google.android.collect.Lists;
21 import com.google.android.collect.Maps;
22 import com.android.internal.R;
23 import com.android.internal.annotations.GuardedBy;
24 import com.android.internal.app.AssistUtils;
25 import com.android.internal.app.DumpHeapActivity;
26 import com.android.internal.app.IAppOpsCallback;
27 import com.android.internal.app.IAppOpsService;
28 import com.android.internal.app.IVoiceInteractor;
29 import com.android.internal.app.ProcessMap;
30 import com.android.internal.app.SystemUserHomeActivity;
31 import com.android.internal.app.procstats.ProcessStats;
32 import com.android.internal.os.BackgroundThread;
33 import com.android.internal.os.BatteryStatsImpl;
34 import com.android.internal.os.IResultReceiver;
35 import com.android.internal.os.ProcessCpuTracker;
36 import com.android.internal.os.TransferPipe;
37 import com.android.internal.os.Zygote;
38 import com.android.internal.os.InstallerConnection.InstallerException;
39 import com.android.internal.util.ArrayUtils;
40 import com.android.internal.util.FastPrintWriter;
41 import com.android.internal.util.FastXmlSerializer;
42 import com.android.internal.util.MemInfoReader;
43 import com.android.internal.util.Preconditions;
44 import com.android.server.AppOpsService;
45 import com.android.server.AttributeCache;
46 import com.android.server.DeviceIdleController;
47 import com.android.server.IntentResolver;
48 import com.android.server.LocalServices;
49 import com.android.server.LockGuard;
50 import com.android.server.ServiceThread;
51 import com.android.server.SystemService;
52 import com.android.server.SystemServiceManager;
53 import com.android.server.Watchdog;
54 import com.android.server.am.ActivityStack.ActivityState;
55 import com.android.server.firewall.IntentFirewall;
56 import com.android.server.pm.Installer;
57 import com.android.server.statusbar.StatusBarManagerInternal;
58 import com.android.server.vr.VrManagerInternal;
59 import com.android.server.wm.WindowManagerService;
60
61 import org.xmlpull.v1.XmlPullParser;
62 import org.xmlpull.v1.XmlPullParserException;
63 import org.xmlpull.v1.XmlSerializer;
64
65 import android.Manifest;
66 import android.Manifest.permission;
67 import android.annotation.NonNull;
68 import android.annotation.UserIdInt;
69 import android.app.Activity;
70 import android.app.ActivityManager;
71 import android.app.ActivityManager.RunningTaskInfo;
72 import android.app.ActivityManager.StackId;
73 import android.app.ActivityManager.StackInfo;
74 import android.app.ActivityManager.TaskThumbnailInfo;
75 import android.app.ActivityManagerInternal;
76 import android.app.ActivityManagerInternal.SleepToken;
77 import android.app.ActivityManagerNative;
78 import android.app.ActivityOptions;
79 import android.app.ActivityThread;
80 import android.app.AlertDialog;
81 import android.app.AppGlobals;
82 import android.app.AppOpsManager;
83 import android.app.ApplicationErrorReport;
84 import android.app.ApplicationThreadNative;
85 import android.app.BroadcastOptions;
86 import android.app.Dialog;
87 import android.app.IActivityContainer;
88 import android.app.IActivityContainerCallback;
89 import android.app.IActivityController;
90 import android.app.IAppTask;
91 import android.app.IApplicationThread;
92 import android.app.IInstrumentationWatcher;
93 import android.app.INotificationManager;
94 import android.app.IProcessObserver;
95 import android.app.IServiceConnection;
96 import android.app.IStopUserCallback;
97 import android.app.ITaskStackListener;
98 import android.app.IUiAutomationConnection;
99 import android.app.IUidObserver;
100 import android.app.IUserSwitchObserver;
101 import android.app.Instrumentation;
102 import android.app.Notification;
103 import android.app.NotificationManager;
104 import android.app.PendingIntent;
105 import android.app.ProfilerInfo;
106 import android.app.admin.DevicePolicyManager;
107 import android.app.assist.AssistContent;
108 import android.app.assist.AssistStructure;
109 import android.app.backup.IBackupManager;
110 import android.app.usage.UsageEvents;
111 import android.app.usage.UsageStatsManagerInternal;
112 import android.appwidget.AppWidgetManager;
113 import android.content.ActivityNotFoundException;
114 import android.content.BroadcastReceiver;
115 import android.content.ClipData;
116 import android.content.ComponentCallbacks2;
117 import android.content.ComponentName;
118 import android.content.ContentProvider;
119 import android.content.ContentResolver;
120 import android.content.Context;
121 import android.content.DialogInterface;
122 import android.content.IContentProvider;
123 import android.content.IIntentReceiver;
124 import android.content.IIntentSender;
125 import android.content.Intent;
126 import android.content.IntentFilter;
127 import android.content.IntentSender;
128 import android.content.pm.ActivityInfo;
129 import android.content.pm.ApplicationInfo;
130 import android.content.pm.ConfigurationInfo;
131 import android.content.pm.IPackageDataObserver;
132 import android.content.pm.IPackageManager;
133 import android.content.pm.InstrumentationInfo;
134 import android.content.pm.PackageInfo;
135 import android.content.pm.PackageManager;
136 import android.content.pm.PackageManager.NameNotFoundException;
137 import android.content.pm.PackageManagerInternal;
138 import android.content.pm.ParceledListSlice;
139 import android.content.pm.PathPermission;
140 import android.content.pm.PermissionInfo;
141 import android.content.pm.ProviderInfo;
142 import android.content.pm.ResolveInfo;
143 import android.content.pm.ServiceInfo;
144 import android.content.pm.UserInfo;
145 import android.content.res.CompatibilityInfo;
146 import android.content.res.Configuration;
147 import android.content.res.Resources;
148 import android.database.ContentObserver;
149 import android.graphics.Bitmap;
150 import android.graphics.Point;
151 import android.graphics.Rect;
152 import android.location.LocationManager;
153 import android.net.Proxy;
154 import android.net.ProxyInfo;
155 import android.net.Uri;
156 import android.os.BatteryStats;
157 import android.os.Binder;
158 import android.os.Build;
159 import android.os.Bundle;
160 import android.os.Debug;
161 import android.os.DropBoxManager;
162 import android.os.Environment;
163 import android.os.FactoryTest;
164 import android.os.FileObserver;
165 import android.os.FileUtils;
166 import android.os.Handler;
167 import android.os.IBinder;
168 import android.os.IPermissionController;
169 import android.os.IProcessInfoService;
170 import android.os.IProgressListener;
171 import android.os.LocaleList;
172 import android.os.Looper;
173 import android.os.Message;
174 import android.os.Parcel;
175 import android.os.ParcelFileDescriptor;
176 import android.os.PersistableBundle;
177 import android.os.PowerManager;
178 import android.os.PowerManagerInternal;
179 import android.os.Process;
180 import android.os.RemoteCallbackList;
181 import android.os.RemoteException;
182 import android.os.ResultReceiver;
183 import android.os.ServiceManager;
184 import android.os.StrictMode;
185 import android.os.SystemClock;
186 import android.os.SystemProperties;
187 import android.os.Trace;
188 import android.os.TransactionTooLargeException;
189 import android.os.UpdateLock;
190 import android.os.UserHandle;
191 import android.os.UserManager;
192 import android.os.WorkSource;
193 import android.provider.Downloads;
194 import android.os.storage.IMountService;
195 import android.os.storage.MountServiceInternal;
196 import android.os.storage.StorageManager;
197 import android.provider.Settings;
198 import android.service.voice.IVoiceInteractionSession;
199 import android.service.voice.VoiceInteractionManagerInternal;
200 import android.service.voice.VoiceInteractionSession;
201 import android.telecom.TelecomManager;
202 import android.text.format.DateUtils;
203 import android.text.format.Time;
204 import android.text.style.SuggestionSpan;
205 import android.util.ArrayMap;
206 import android.util.ArraySet;
207 import android.util.AtomicFile;
208 import android.util.DebugUtils;
209 import android.util.DisplayMetrics;
210 import android.util.EventLog;
211 import android.util.Log;
212 import android.util.Pair;
213 import android.util.PrintWriterPrinter;
214 import android.util.Slog;
215 import android.util.SparseArray;
216 import android.util.TimeUtils;
217 import android.util.Xml;
218 import android.view.Display;
219 import android.view.Gravity;
220 import android.view.LayoutInflater;
221 import android.view.View;
222 import android.view.WindowManager;
223
224 import java.io.File;
225 import java.io.FileDescriptor;
226 import java.io.FileInputStream;
227 import java.io.FileNotFoundException;
228 import java.io.FileOutputStream;
229 import java.io.IOException;
230 import java.io.InputStreamReader;
231 import java.io.PrintWriter;
232 import java.io.StringWriter;
233 import java.lang.ref.WeakReference;
234 import java.nio.charset.StandardCharsets;
235 import java.util.ArrayList;
236 import java.util.Arrays;
237 import java.util.Collections;
238 import java.util.Comparator;
239 import java.util.HashMap;
240 import java.util.HashSet;
241 import java.util.Iterator;
242 import java.util.List;
243 import java.util.Locale;
244 import java.util.Map;
245 import java.util.Objects;
246 import java.util.Set;
247 import java.util.concurrent.atomic.AtomicBoolean;
248 import java.util.concurrent.atomic.AtomicLong;
249
250 import dalvik.system.VMRuntime;
251
252 import libcore.io.IoUtils;
253 import libcore.util.EmptyArray;
254
255 import static android.Manifest.permission.INTERACT_ACROSS_USERS;
256 import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL;
257 import static android.Manifest.permission.MANAGE_ACTIVITY_STACKS;
258 import static android.Manifest.permission.START_TASKS_FROM_RECENTS;
259 import static android.app.ActivityManager.DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT;
260 import static android.app.ActivityManager.RESIZE_MODE_PRESERVE_WINDOW;
261 import static android.app.ActivityManager.StackId.DOCKED_STACK_ID;
262 import static android.app.ActivityManager.StackId.FREEFORM_WORKSPACE_STACK_ID;
263 import static android.app.ActivityManager.StackId.FULLSCREEN_WORKSPACE_STACK_ID;
264 import static android.app.ActivityManager.StackId.HOME_STACK_ID;
265 import static android.app.ActivityManager.StackId.INVALID_STACK_ID;
266 import static android.app.ActivityManager.StackId.PINNED_STACK_ID;
267 import static android.content.pm.PackageManager.FEATURE_FREEFORM_WINDOW_MANAGEMENT;
268 import static android.content.pm.PackageManager.FEATURE_LEANBACK_ONLY;
269 import static android.content.pm.PackageManager.FEATURE_PICTURE_IN_PICTURE;
270 import static android.content.pm.PackageManager.GET_PROVIDERS;
271 import static android.content.pm.PackageManager.MATCH_DEBUG_TRIAGED_MISSING;
272 import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_AWARE;
273 import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE;
274 import static android.content.pm.PackageManager.MATCH_SYSTEM_ONLY;
275 import static android.content.pm.PackageManager.MATCH_UNINSTALLED_PACKAGES;
276 import static android.content.pm.PackageManager.PERMISSION_GRANTED;
277 import static android.content.res.Configuration.UI_MODE_TYPE_TELEVISION;
278 import static android.os.Process.PROC_CHAR;
279 import static android.os.Process.PROC_OUT_LONG;
280 import static android.os.Process.PROC_PARENS;
281 import static android.os.Process.PROC_SPACE_TERM;
282 import static android.provider.Settings.Global.ALWAYS_FINISH_ACTIVITIES;
283 import static android.provider.Settings.Global.DEBUG_APP;
284 import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT;
285 import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES;
286 import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RTL;
287 import static android.provider.Settings.Global.LENIENT_BACKGROUND_CHECK;
288 import static android.provider.Settings.Global.WAIT_FOR_DEBUGGER;
289 import static android.provider.Settings.System.FONT_SCALE;
290 import static com.android.internal.util.XmlUtils.readBooleanAttribute;
291 import static com.android.internal.util.XmlUtils.readIntAttribute;
292 import static com.android.internal.util.XmlUtils.readLongAttribute;
293 import static com.android.internal.util.XmlUtils.writeBooleanAttribute;
294 import static com.android.internal.util.XmlUtils.writeIntAttribute;
295 import static com.android.internal.util.XmlUtils.writeLongAttribute;
296 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ALL;
297 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ANR;
298 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BACKUP;
299 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST;
300 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_BACKGROUND;
301 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_LIGHT;
302 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CLEANUP;
303 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CONFIGURATION;
304 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_FOCUS;
305 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_IMMERSIVE;
306 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKSCREEN;
307 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKTASK;
308 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LRU;
309 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_MU;
310 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_OOM_ADJ;
311 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PERMISSIONS_REVIEW;
312 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER;
313 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER_QUICK;
314 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESSES;
315 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESS_OBSERVERS;
316 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROVIDER;
317 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PSS;
318 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_RECENTS;
319 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SERVICE;
320 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_STACK;
321 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SWITCH;
322 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_TASKS;
323 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_UID_OBSERVERS;
324 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_URI_PERMISSION;
325 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_USAGE_STATS;
326 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBILITY;
327 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBLE_BEHIND;
328 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_WHITELISTS;
329 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BACKUP;
330 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BROADCAST;
331 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CLEANUP;
332 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CONFIGURATION;
333 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_FOCUS;
334 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_IMMERSIVE;
335 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKSCREEN;
336 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKTASK;
337 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LRU;
338 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_MU;
339 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_OOM_ADJ;
340 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_POWER;
341 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESSES;
342 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESS_OBSERVERS;
343 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROVIDER;
344 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PSS;
345 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_RECENTS;
346 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SERVICE;
347 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_STACK;
348 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SWITCH;
349 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_UID_OBSERVERS;
350 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_URI_PERMISSION;
351 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBILITY;
352 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBLE_BEHIND;
353 import static com.android.server.am.ActivityManagerDebugConfig.TAG_AM;
354 import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME;
355 import static com.android.server.am.ActivityRecord.RECENTS_ACTIVITY_TYPE;
356 import static com.android.server.am.ActivityStackSupervisor.ActivityContainer.FORCE_NEW_TASK_FLAGS;
357 import static com.android.server.am.ActivityStackSupervisor.DEFER_RESUME;
358 import static com.android.server.am.ActivityStackSupervisor.FORCE_FOCUS;
359 import static com.android.server.am.ActivityStackSupervisor.ON_TOP;
360 import static com.android.server.am.ActivityStackSupervisor.PRESERVE_WINDOWS;
361 import static com.android.server.am.ActivityStackSupervisor.RESTORE_FROM_RECENTS;
362 import static com.android.server.am.TaskRecord.INVALID_TASK_ID;
363 import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_DONT_LOCK;
364 import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_LAUNCHABLE_PRIV;
365 import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_PINNABLE;
366 import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_OPEN;
367 import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_RELAUNCH;
368 import static com.android.server.wm.AppTransition.TRANSIT_TASK_IN_PLACE;
369 import static com.android.server.wm.AppTransition.TRANSIT_TASK_OPEN;
370 import static com.android.server.wm.AppTransition.TRANSIT_TASK_TO_FRONT;
371 import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT;
372 import static org.xmlpull.v1.XmlPullParser.START_TAG;
373
374 public final class ActivityManagerService extends ActivityManagerNative
375         implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback {
376
377     private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityManagerService" : TAG_AM;
378     private static final String TAG_BACKUP = TAG + POSTFIX_BACKUP;
379     private static final String TAG_BROADCAST = TAG + POSTFIX_BROADCAST;
380     private static final String TAG_CLEANUP = TAG + POSTFIX_CLEANUP;
381     private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION;
382     private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS;
383     private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE;
384     private static final String TAG_LOCKSCREEN = TAG + POSTFIX_LOCKSCREEN;
385     private static final String TAG_LOCKTASK = TAG + POSTFIX_LOCKTASK;
386     private static final String TAG_LRU = TAG + POSTFIX_LRU;
387     private static final String TAG_MU = TAG + POSTFIX_MU;
388     private static final String TAG_OOM_ADJ = TAG + POSTFIX_OOM_ADJ;
389     private static final String TAG_POWER = TAG + POSTFIX_POWER;
390     private static final String TAG_PROCESS_OBSERVERS = TAG + POSTFIX_PROCESS_OBSERVERS;
391     private static final String TAG_PROCESSES = TAG + POSTFIX_PROCESSES;
392     private static final String TAG_PROVIDER = TAG + POSTFIX_PROVIDER;
393     private static final String TAG_PSS = TAG + POSTFIX_PSS;
394     private static final String TAG_RECENTS = TAG + POSTFIX_RECENTS;
395     private static final String TAG_SERVICE = TAG + POSTFIX_SERVICE;
396     private static final String TAG_STACK = TAG + POSTFIX_STACK;
397     private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH;
398     private static final String TAG_UID_OBSERVERS = TAG + POSTFIX_UID_OBSERVERS;
399     private static final String TAG_URI_PERMISSION = TAG + POSTFIX_URI_PERMISSION;
400     private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY;
401     private static final String TAG_VISIBLE_BEHIND = TAG + POSTFIX_VISIBLE_BEHIND;
402
403     // Mock "pretend we're idle now" broadcast action to the job scheduler; declared
404     // here so that while the job scheduler can depend on AMS, the other way around
405     // need not be the case.
406     public static final String ACTION_TRIGGER_IDLE = "com.android.server.ACTION_TRIGGER_IDLE";
407
408     /** Control over CPU and battery monitoring */
409     // write battery stats every 30 minutes.
410     static final long BATTERY_STATS_TIME = 30 * 60 * 1000;
411     static final boolean MONITOR_CPU_USAGE = true;
412     // don't sample cpu less than every 5 seconds.
413     static final long MONITOR_CPU_MIN_TIME = 5 * 1000;
414     // wait possibly forever for next cpu sample.
415     static final long MONITOR_CPU_MAX_TIME = 0x0fffffff;
416     static final boolean MONITOR_THREAD_CPU_USAGE = false;
417
418     // The flags that are set for all calls we make to the package manager.
419     static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES;
420
421     static final String SYSTEM_DEBUGGABLE = "ro.debuggable";
422
423     static final boolean IS_USER_BUILD = "user".equals(Build.TYPE);
424
425     // Amount of time after a call to stopAppSwitches() during which we will
426     // prevent further untrusted switches from happening.
427     static final long APP_SWITCH_DELAY_TIME = 5*1000;
428
429     // How long we wait for a launched process to attach to the activity manager
430     // before we decide it's never going to come up for real.
431     static final int PROC_START_TIMEOUT = 10*1000;
432     // How long we wait for an attached process to publish its content providers
433     // before we decide it must be hung.
434     static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT = 10*1000;
435
436     // How long we will retain processes hosting content providers in the "last activity"
437     // state before allowing them to drop down to the regular cached LRU list.  This is
438     // to avoid thrashing of provider processes under low memory situations.
439     static final int CONTENT_PROVIDER_RETAIN_TIME = 20*1000;
440
441     // How long we wait for a launched process to attach to the activity manager
442     // before we decide it's never going to come up for real, when the process was
443     // started with a wrapper for instrumentation (such as Valgrind) because it
444     // could take much longer than usual.
445     static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000;
446
447     // How long to wait after going idle before forcing apps to GC.
448     static final int GC_TIMEOUT = 5*1000;
449
450     // The minimum amount of time between successive GC requests for a process.
451     static final int GC_MIN_INTERVAL = 60*1000;
452
453     // The minimum amount of time between successive PSS requests for a process.
454     static final int FULL_PSS_MIN_INTERVAL = 10*60*1000;
455
456     // The minimum amount of time between successive PSS requests for a process
457     // when the request is due to the memory state being lowered.
458     static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000;
459
460     // The rate at which we check for apps using excessive power -- 15 mins.
461     static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000;
462
463     // The minimum sample duration we will allow before deciding we have
464     // enough data on wake locks to start killing things.
465     static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000;
466
467     // The minimum sample duration we will allow before deciding we have
468     // enough data on CPU usage to start killing things.
469     static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000;
470
471     // How long we allow a receiver to run before giving up on it.
472     static final int BROADCAST_FG_TIMEOUT = 10*1000;
473     static final int BROADCAST_BG_TIMEOUT = 60*1000;
474
475     // How long we wait until we timeout on key dispatching.
476     static final int KEY_DISPATCHING_TIMEOUT = 5*1000;
477
478     // How long we wait until we timeout on key dispatching during instrumentation.
479     static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000;
480
481     // This is the amount of time an app needs to be running a foreground service before
482     // we will consider it to be doing interaction for usage stats.
483     static final int SERVICE_USAGE_INTERACTION_TIME = 30*60*1000;
484
485     // Maximum amount of time we will allow to elapse before re-reporting usage stats
486     // interaction with foreground processes.
487     static final long USAGE_STATS_INTERACTION_INTERVAL = 24*60*60*1000L;
488
489     // This is the amount of time we allow an app to settle after it goes into the background,
490     // before we start restricting what it can do.
491     static final int BACKGROUND_SETTLE_TIME = 1*60*1000;
492
493     // How long to wait in getAssistContextExtras for the activity and foreground services
494     // to respond with the result.
495     static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500;
496
497     // How long top wait when going through the modern assist (which doesn't need to block
498     // on getting this result before starting to launch its UI).
499     static final int PENDING_ASSIST_EXTRAS_LONG_TIMEOUT = 2000;
500
501     // Maximum number of persisted Uri grants a package is allowed
502     static final int MAX_PERSISTED_URI_GRANTS = 128;
503
504     static final int MY_PID = Process.myPid();
505
506     static final String[] EMPTY_STRING_ARRAY = new String[0];
507
508     // How many bytes to write into the dropbox log before truncating
509     static final int DROPBOX_MAX_SIZE = 192 * 1024;
510     // Assumes logcat entries average around 100 bytes; that's not perfect stack traces count
511     // as one line, but close enough for now.
512     static final int RESERVED_BYTES_PER_LOGCAT_LINE = 100;
513
514     // Access modes for handleIncomingUser.
515     static final int ALLOW_NON_FULL = 0;
516     static final int ALLOW_NON_FULL_IN_PROFILE = 1;
517     static final int ALLOW_FULL_ONLY = 2;
518
519     // Delay in notifying task stack change listeners (in millis)
520     static final int NOTIFY_TASK_STACK_CHANGE_LISTENERS_DELAY = 100;
521
522     // Necessary ApplicationInfo flags to mark an app as persistent
523     private static final int PERSISTENT_MASK =
524             ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT;
525
526     // Intent sent when remote bugreport collection has been completed
527     private static final String INTENT_REMOTE_BUGREPORT_FINISHED =
528             "android.intent.action.REMOTE_BUGREPORT_FINISHED";
529
530     // Delay to disable app launch boost
531     static final int APP_BOOST_MESSAGE_DELAY = 3000;
532     // Lower delay than APP_BOOST_MESSAGE_DELAY to disable the boost
533     static final int APP_BOOST_TIMEOUT = 2500;
534
535     // Used to indicate that a task is removed it should also be removed from recents.
536     private static final boolean REMOVE_FROM_RECENTS = true;
537     // Used to indicate that an app transition should be animated.
538     static final boolean ANIMATE = true;
539
540     // Determines whether to take full screen screenshots
541     static final boolean TAKE_FULLSCREEN_SCREENSHOTS = true;
542     public static final float FULLSCREEN_SCREENSHOT_SCALE = 0.6f;
543
544     private static native int nativeMigrateToBoost();
545     private static native int nativeMigrateFromBoost();
546     private boolean mIsBoosted = false;
547     private long mBoostStartTime = 0;
548
549     /** All system services */
550     SystemServiceManager mSystemServiceManager;
551
552     private Installer mInstaller;
553
554     /** Run all ActivityStacks through this */
555     final ActivityStackSupervisor mStackSupervisor;
556
557     final ActivityStarter mActivityStarter;
558
559     /** Task stack change listeners. */
560     private final RemoteCallbackList<ITaskStackListener> mTaskStackListeners =
561             new RemoteCallbackList<ITaskStackListener>();
562
563     final InstrumentationReporter mInstrumentationReporter = new InstrumentationReporter();
564
565     public IntentFirewall mIntentFirewall;
566
567     // Whether we should show our dialogs (ANR, crash, etc) or just perform their
568     // default actuion automatically.  Important for devices without direct input
569     // devices.
570     private boolean mShowDialogs = true;
571     private boolean mInVrMode = false;
572
573     // Whether we should use SCHED_FIFO for UI and RenderThreads.
574     private boolean mUseFifoUiScheduling = false;
575
576     BroadcastQueue mFgBroadcastQueue;
577     BroadcastQueue mBgBroadcastQueue;
578     // Convenient for easy iteration over the queues. Foreground is first
579     // so that dispatch of foreground broadcasts gets precedence.
580     final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2];
581
582     BroadcastStats mLastBroadcastStats;
583     BroadcastStats mCurBroadcastStats;
584
585     BroadcastQueue broadcastQueueForIntent(Intent intent) {
586         final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0;
587         if (DEBUG_BROADCAST_BACKGROUND) Slog.i(TAG_BROADCAST,
588                 "Broadcast intent " + intent + " on "
589                 + (isFg ? "foreground" : "background") + " queue");
590         return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue;
591     }
592
593     /**
594      * Activity we have told the window manager to have key focus.
595      */
596     ActivityRecord mFocusedActivity = null;
597
598     /**
599      * User id of the last activity mFocusedActivity was set to.
600      */
601     private int mLastFocusedUserId;
602
603     /**
604      * If non-null, we are tracking the time the user spends in the currently focused app.
605      */
606     private AppTimeTracker mCurAppTimeTracker;
607
608     /**
609      * List of intents that were used to start the most recent tasks.
610      */
611     final RecentTasks mRecentTasks;
612
613     /**
614      * For addAppTask: cached of the last activity component that was added.
615      */
616     ComponentName mLastAddedTaskComponent;
617
618     /**
619      * For addAppTask: cached of the last activity uid that was added.
620      */
621     int mLastAddedTaskUid;
622
623     /**
624      * For addAppTask: cached of the last ActivityInfo that was added.
625      */
626     ActivityInfo mLastAddedTaskActivity;
627
628     /**
629      * List of packages whitelisted by DevicePolicyManager for locktask. Indexed by userId.
630      */
631     SparseArray<String[]> mLockTaskPackages = new SparseArray<>();
632
633     /**
634      * The package name of the DeviceOwner. This package is not permitted to have its data cleared.
635      */
636     String mDeviceOwnerName;
637
638     final UserController mUserController;
639
640     final AppErrors mAppErrors;
641
642     boolean mDoingSetFocusedActivity;
643
644     public boolean canShowErrorDialogs() {
645         return mShowDialogs && !mSleeping && !mShuttingDown
646                 && mLockScreenShown != LOCK_SCREEN_SHOWN;
647     }
648
649     private static final class PriorityState {
650         // Acts as counter for number of synchronized region that needs to acquire 'this' as a lock
651         // the current thread is currently in. When it drops down to zero, we will no longer boost
652         // the thread's priority.
653         private int regionCounter = 0;
654
655         // The thread's previous priority before boosting.
656         private int prevPriority = Integer.MIN_VALUE;
657     }
658
659     static ThreadLocal<PriorityState> sThreadPriorityState = new ThreadLocal<PriorityState>() {
660         @Override protected PriorityState initialValue() {
661             return new PriorityState();
662         }
663     };
664
665     static void boostPriorityForLockedSection() {
666         int tid = Process.myTid();
667         int prevPriority = Process.getThreadPriority(tid);
668         PriorityState state = sThreadPriorityState.get();
669         if (state.regionCounter == 0 && prevPriority > -2) {
670             state.prevPriority = prevPriority;
671             Process.setThreadPriority(tid, -2);
672         }
673         state.regionCounter++;
674     }
675
676     static void resetPriorityAfterLockedSection() {
677         PriorityState state = sThreadPriorityState.get();
678         state.regionCounter--;
679         if (state.regionCounter == 0 && state.prevPriority > -2) {
680             Process.setThreadPriority(Process.myTid(), state.prevPriority);
681         }
682     }
683
684     public class PendingAssistExtras extends Binder implements Runnable {
685         public final ActivityRecord activity;
686         public final Bundle extras;
687         public final Intent intent;
688         public final String hint;
689         public final IResultReceiver receiver;
690         public final int userHandle;
691         public boolean haveResult = false;
692         public Bundle result = null;
693         public AssistStructure structure = null;
694         public AssistContent content = null;
695         public Bundle receiverExtras;
696
697         public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent,
698                 String _hint, IResultReceiver _receiver, Bundle _receiverExtras, int _userHandle) {
699             activity = _activity;
700             extras = _extras;
701             intent = _intent;
702             hint = _hint;
703             receiver = _receiver;
704             receiverExtras = _receiverExtras;
705             userHandle = _userHandle;
706         }
707         @Override
708         public void run() {
709             Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity);
710             synchronized (this) {
711                 haveResult = true;
712                 notifyAll();
713             }
714             pendingAssistExtrasTimedOut(this);
715         }
716     }
717
718     final ArrayList<PendingAssistExtras> mPendingAssistExtras
719             = new ArrayList<PendingAssistExtras>();
720
721     /**
722      * Process management.
723      */
724     final ProcessList mProcessList = new ProcessList();
725
726     /**
727      * All of the applications we currently have running organized by name.
728      * The keys are strings of the application package name (as
729      * returned by the package manager), and the keys are ApplicationRecord
730      * objects.
731      */
732     final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>();
733
734     /**
735      * Tracking long-term execution of processes to look for abuse and other
736      * bad app behavior.
737      */
738     final ProcessStatsService mProcessStats;
739
740     /**
741      * The currently running isolated processes.
742      */
743     final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>();
744
745     /**
746      * Counter for assigning isolated process uids, to avoid frequently reusing the
747      * same ones.
748      */
749     int mNextIsolatedProcessUid = 0;
750
751     /**
752      * The currently running heavy-weight process, if any.
753      */
754     ProcessRecord mHeavyWeightProcess = null;
755
756     /**
757      * All of the processes we currently have running organized by pid.
758      * The keys are the pid running the application.
759      *
760      * <p>NOTE: This object is protected by its own lock, NOT the global
761      * activity manager lock!
762      */
763     final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>();
764
765     /**
766      * All of the processes that have been forced to be foreground.  The key
767      * is the pid of the caller who requested it (we hold a death
768      * link on it).
769      */
770     abstract class ForegroundToken implements IBinder.DeathRecipient {
771         int pid;
772         IBinder token;
773     }
774     final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>();
775
776     /**
777      * List of records for processes that someone had tried to start before the
778      * system was ready.  We don't start them at that point, but ensure they
779      * are started by the time booting is complete.
780      */
781     final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>();
782
783     /**
784      * List of persistent applications that are in the process
785      * of being started.
786      */
787     final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>();
788
789     /**
790      * Processes that are being forcibly torn down.
791      */
792     final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>();
793
794     /**
795      * List of running applications, sorted by recent usage.
796      * The first entry in the list is the least recently used.
797      */
798     final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>();
799
800     /**
801      * Where in mLruProcesses that the processes hosting activities start.
802      */
803     int mLruProcessActivityStart = 0;
804
805     /**
806      * Where in mLruProcesses that the processes hosting services start.
807      * This is after (lower index) than mLruProcessesActivityStart.
808      */
809     int mLruProcessServiceStart = 0;
810
811     /**
812      * List of processes that should gc as soon as things are idle.
813      */
814     final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>();
815
816     /**
817      * Processes we want to collect PSS data from.
818      */
819     final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>();
820
821     private boolean mBinderTransactionTrackingEnabled = false;
822
823     /**
824      * Last time we requested PSS data of all processes.
825      */
826     long mLastFullPssTime = SystemClock.uptimeMillis();
827
828     /**
829      * If set, the next time we collect PSS data we should do a full collection
830      * with data from native processes and the kernel.
831      */
832     boolean mFullPssPending = false;
833
834     /**
835      * This is the process holding what we currently consider to be
836      * the "home" activity.
837      */
838     ProcessRecord mHomeProcess;
839
840     /**
841      * This is the process holding the activity the user last visited that
842      * is in a different process from the one they are currently in.
843      */
844     ProcessRecord mPreviousProcess;
845
846     /**
847      * The time at which the previous process was last visible.
848      */
849     long mPreviousProcessVisibleTime;
850
851     /**
852      * Track all uids that have actively running processes.
853      */
854     final SparseArray<UidRecord> mActiveUids = new SparseArray<>();
855
856     /**
857      * This is for verifying the UID report flow.
858      */
859     static final boolean VALIDATE_UID_STATES = true;
860     final SparseArray<UidRecord> mValidateUids = new SparseArray<>();
861
862     /**
863      * Packages that the user has asked to have run in screen size
864      * compatibility mode instead of filling the screen.
865      */
866     final CompatModePackages mCompatModePackages;
867
868     /**
869      * Set of IntentSenderRecord objects that are currently active.
870      */
871     final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords
872             = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>();
873
874     /**
875      * Fingerprints (hashCode()) of stack traces that we've
876      * already logged DropBox entries for.  Guarded by itself.  If
877      * something (rogue user app) forces this over
878      * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared.
879      */
880     private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>();
881     private static final int MAX_DUP_SUPPRESSED_STACKS = 5000;
882
883     /**
884      * Strict Mode background batched logging state.
885      *
886      * The string buffer is guarded by itself, and its lock is also
887      * used to determine if another batched write is already
888      * in-flight.
889      */
890     private final StringBuilder mStrictModeBuffer = new StringBuilder();
891
892     /**
893      * Keeps track of all IIntentReceivers that have been registered for broadcasts.
894      * Hash keys are the receiver IBinder, hash value is a ReceiverList.
895      */
896     final HashMap<IBinder, ReceiverList> mRegisteredReceivers = new HashMap<>();
897
898     /**
899      * Resolver for broadcast intents to registered receivers.
900      * Holds BroadcastFilter (subclass of IntentFilter).
901      */
902     final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver
903             = new IntentResolver<BroadcastFilter, BroadcastFilter>() {
904         @Override
905         protected boolean allowFilterResult(
906                 BroadcastFilter filter, List<BroadcastFilter> dest) {
907             IBinder target = filter.receiverList.receiver.asBinder();
908             for (int i = dest.size() - 1; i >= 0; i--) {
909                 if (dest.get(i).receiverList.receiver.asBinder() == target) {
910                     return false;
911                 }
912             }
913             return true;
914         }
915
916         @Override
917         protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) {
918             if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL
919                     || userId == filter.owningUserId) {
920                 return super.newResult(filter, match, userId);
921             }
922             return null;
923         }
924
925         @Override
926         protected BroadcastFilter[] newArray(int size) {
927             return new BroadcastFilter[size];
928         }
929
930         @Override
931         protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) {
932             return packageName.equals(filter.packageName);
933         }
934     };
935
936     /**
937      * State of all active sticky broadcasts per user.  Keys are the action of the
938      * sticky Intent, values are an ArrayList of all broadcasted intents with
939      * that action (which should usually be one).  The SparseArray is keyed
940      * by the user ID the sticky is for, and can include UserHandle.USER_ALL
941      * for stickies that are sent to all users.
942      */
943     final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts =
944             new SparseArray<ArrayMap<String, ArrayList<Intent>>>();
945
946     final ActiveServices mServices;
947
948     final static class Association {
949         final int mSourceUid;
950         final String mSourceProcess;
951         final int mTargetUid;
952         final ComponentName mTargetComponent;
953         final String mTargetProcess;
954
955         int mCount;
956         long mTime;
957
958         int mNesting;
959         long mStartTime;
960
961         // states of the source process when the bind occurred.
962         int mLastState = ActivityManager.MAX_PROCESS_STATE + 1;
963         long mLastStateUptime;
964         long[] mStateTimes = new long[ActivityManager.MAX_PROCESS_STATE
965                 - ActivityManager.MIN_PROCESS_STATE+1];
966
967         Association(int sourceUid, String sourceProcess, int targetUid,
968                 ComponentName targetComponent, String targetProcess) {
969             mSourceUid = sourceUid;
970             mSourceProcess = sourceProcess;
971             mTargetUid = targetUid;
972             mTargetComponent = targetComponent;
973             mTargetProcess = targetProcess;
974         }
975     }
976
977     /**
978      * When service association tracking is enabled, this is all of the associations we
979      * have seen.  Mapping is target uid -> target component -> source uid -> source process name
980      * -> association data.
981      */
982     final SparseArray<ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>>>
983             mAssociations = new SparseArray<>();
984     boolean mTrackingAssociations;
985
986     /**
987      * Backup/restore process management
988      */
989     String mBackupAppName = null;
990     BackupRecord mBackupTarget = null;
991
992     final ProviderMap mProviderMap;
993
994     /**
995      * List of content providers who have clients waiting for them.  The
996      * application is currently being launched and the provider will be
997      * removed from this list once it is published.
998      */
999     final ArrayList<ContentProviderRecord> mLaunchingProviders
1000             = new ArrayList<ContentProviderRecord>();
1001
1002     /**
1003      * File storing persisted {@link #mGrantedUriPermissions}.
1004      */
1005     private final AtomicFile mGrantFile;
1006
1007     /** XML constants used in {@link #mGrantFile} */
1008     private static final String TAG_URI_GRANTS = "uri-grants";
1009     private static final String TAG_URI_GRANT = "uri-grant";
1010     private static final String ATTR_USER_HANDLE = "userHandle";
1011     private static final String ATTR_SOURCE_USER_ID = "sourceUserId";
1012     private static final String ATTR_TARGET_USER_ID = "targetUserId";
1013     private static final String ATTR_SOURCE_PKG = "sourcePkg";
1014     private static final String ATTR_TARGET_PKG = "targetPkg";
1015     private static final String ATTR_URI = "uri";
1016     private static final String ATTR_MODE_FLAGS = "modeFlags";
1017     private static final String ATTR_CREATED_TIME = "createdTime";
1018     private static final String ATTR_PREFIX = "prefix";
1019
1020     /**
1021      * Global set of specific {@link Uri} permissions that have been granted.
1022      * This optimized lookup structure maps from {@link UriPermission#targetUid}
1023      * to {@link UriPermission#uri} to {@link UriPermission}.
1024      */
1025     @GuardedBy("this")
1026     private final SparseArray<ArrayMap<GrantUri, UriPermission>>
1027             mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>();
1028
1029     public static class GrantUri {
1030         public final int sourceUserId;
1031         public final Uri uri;
1032         public boolean prefix;
1033
1034         public GrantUri(int sourceUserId, Uri uri, boolean prefix) {
1035             this.sourceUserId = sourceUserId;
1036             this.uri = uri;
1037             this.prefix = prefix;
1038         }
1039
1040         @Override
1041         public int hashCode() {
1042             int hashCode = 1;
1043             hashCode = 31 * hashCode + sourceUserId;
1044             hashCode = 31 * hashCode + uri.hashCode();
1045             hashCode = 31 * hashCode + (prefix ? 1231 : 1237);
1046             return hashCode;
1047         }
1048
1049         @Override
1050         public boolean equals(Object o) {
1051             if (o instanceof GrantUri) {
1052                 GrantUri other = (GrantUri) o;
1053                 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId)
1054                         && prefix == other.prefix;
1055             }
1056             return false;
1057         }
1058
1059         @Override
1060         public String toString() {
1061             String result = Integer.toString(sourceUserId) + " @ " + uri.toString();
1062             if (prefix) result += " [prefix]";
1063             return result;
1064         }
1065
1066         public String toSafeString() {
1067             String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString();
1068             if (prefix) result += " [prefix]";
1069             return result;
1070         }
1071
1072         public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) {
1073             return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle),
1074                     ContentProvider.getUriWithoutUserId(uri), false);
1075         }
1076     }
1077
1078     CoreSettingsObserver mCoreSettingsObserver;
1079
1080     FontScaleSettingObserver mFontScaleSettingObserver;
1081
1082     private final class FontScaleSettingObserver extends ContentObserver {
1083         private final Uri mFontScaleUri = Settings.System.getUriFor(FONT_SCALE);
1084
1085         public FontScaleSettingObserver() {
1086             super(mHandler);
1087             ContentResolver resolver = mContext.getContentResolver();
1088             resolver.registerContentObserver(mFontScaleUri, false, this, UserHandle.USER_ALL);
1089         }
1090
1091         @Override
1092         public void onChange(boolean selfChange, Uri uri, @UserIdInt int userId) {
1093             if (mFontScaleUri.equals(uri)) {
1094                 updateFontScaleIfNeeded(userId);
1095             }
1096         }
1097     }
1098
1099     /**
1100      * Thread-local storage used to carry caller permissions over through
1101      * indirect content-provider access.
1102      */
1103     private class Identity {
1104         public final IBinder token;
1105         public final int pid;
1106         public final int uid;
1107
1108         Identity(IBinder _token, int _pid, int _uid) {
1109             token = _token;
1110             pid = _pid;
1111             uid = _uid;
1112         }
1113     }
1114
1115     private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>();
1116
1117     /**
1118      * All information we have collected about the runtime performance of
1119      * any user id that can impact battery performance.
1120      */
1121     final BatteryStatsService mBatteryStatsService;
1122
1123     /**
1124      * Information about component usage
1125      */
1126     UsageStatsManagerInternal mUsageStatsService;
1127
1128     /**
1129      * Access to DeviceIdleController service.
1130      */
1131     DeviceIdleController.LocalService mLocalDeviceIdleController;
1132
1133     /**
1134      * Information about and control over application operations
1135      */
1136     final AppOpsService mAppOpsService;
1137
1138     /**
1139      * Current configuration information.  HistoryRecord objects are given
1140      * a reference to this object to indicate which configuration they are
1141      * currently running in, so this object must be kept immutable.
1142      */
1143     Configuration mConfiguration = new Configuration();
1144
1145     /**
1146      * Current sequencing integer of the configuration, for skipping old
1147      * configurations.
1148      */
1149     int mConfigurationSeq = 0;
1150
1151     boolean mSuppressResizeConfigChanges = false;
1152
1153     /**
1154      * Hardware-reported OpenGLES version.
1155      */
1156     final int GL_ES_VERSION;
1157
1158     /**
1159      * List of initialization arguments to pass to all processes when binding applications to them.
1160      * For example, references to the commonly used services.
1161      */
1162     HashMap<String, IBinder> mAppBindArgs;
1163     HashMap<String, IBinder> mIsolatedAppBindArgs;
1164
1165     /**
1166      * Temporary to avoid allocations.  Protected by main lock.
1167      */
1168     final StringBuilder mStringBuilder = new StringBuilder(256);
1169
1170     /**
1171      * Used to control how we initialize the service.
1172      */
1173     ComponentName mTopComponent;
1174     String mTopAction = Intent.ACTION_MAIN;
1175     String mTopData;
1176
1177     volatile boolean mProcessesReady = false;
1178     volatile boolean mSystemReady = false;
1179     volatile boolean mOnBattery = false;
1180     volatile int mFactoryTest;
1181
1182     @GuardedBy("this") boolean mBooting = false;
1183     @GuardedBy("this") boolean mCallFinishBooting = false;
1184     @GuardedBy("this") boolean mBootAnimationComplete = false;
1185     @GuardedBy("this") boolean mLaunchWarningShown = false;
1186     @GuardedBy("this") boolean mCheckedForSetup = false;
1187
1188     Context mContext;
1189
1190     /**
1191      * The time at which we will allow normal application switches again,
1192      * after a call to {@link #stopAppSwitches()}.
1193      */
1194     long mAppSwitchesAllowedTime;
1195
1196     /**
1197      * This is set to true after the first switch after mAppSwitchesAllowedTime
1198      * is set; any switches after that will clear the time.
1199      */
1200     boolean mDidAppSwitch;
1201
1202     /**
1203      * Last time (in realtime) at which we checked for power usage.
1204      */
1205     long mLastPowerCheckRealtime;
1206
1207     /**
1208      * Last time (in uptime) at which we checked for power usage.
1209      */
1210     long mLastPowerCheckUptime;
1211
1212     /**
1213      * Set while we are wanting to sleep, to prevent any
1214      * activities from being started/resumed.
1215      *
1216      * TODO(b/33594039): Clarify the actual state transitions represented by mSleeping.
1217      *
1218      * Currently mSleeping is set to true when transitioning into the sleep state, and remains true
1219      * while in the sleep state until there is a pending transition out of sleep, in which case
1220      * mSleeping is set to false, and remains false while awake.
1221      *
1222      * Whether mSleeping can quickly toggled between true/false without the device actually
1223      * display changing states is undefined.
1224      */
1225     private boolean mSleeping = false;
1226
1227     /**
1228      * The process state used for processes that are running the top activities.
1229      * This changes between TOP and TOP_SLEEPING to following mSleeping.
1230      */
1231     int mTopProcessState = ActivityManager.PROCESS_STATE_TOP;
1232
1233     /**
1234      * Set while we are running a voice interaction.  This overrides
1235      * sleeping while it is active.
1236      */
1237     private IVoiceInteractionSession mRunningVoice;
1238
1239     /**
1240      * For some direct access we need to power manager.
1241      */
1242     PowerManagerInternal mLocalPowerManager;
1243
1244     /**
1245      * We want to hold a wake lock while running a voice interaction session, since
1246      * this may happen with the screen off and we need to keep the CPU running to
1247      * be able to continue to interact with the user.
1248      */
1249     PowerManager.WakeLock mVoiceWakeLock;
1250
1251     /**
1252      * State of external calls telling us if the device is awake or asleep.
1253      */
1254     private int mWakefulness = PowerManagerInternal.WAKEFULNESS_AWAKE;
1255
1256     /**
1257      * A list of tokens that cause the top activity to be put to sleep.
1258      * They are used by components that may hide and block interaction with underlying
1259      * activities.
1260      */
1261     final ArrayList<SleepToken> mSleepTokens = new ArrayList<SleepToken>();
1262
1263     static final int LOCK_SCREEN_HIDDEN = 0;
1264     static final int LOCK_SCREEN_LEAVING = 1;
1265     static final int LOCK_SCREEN_SHOWN = 2;
1266     /**
1267      * State of external call telling us if the lock screen is shown.
1268      */
1269     int mLockScreenShown = LOCK_SCREEN_HIDDEN;
1270
1271     /**
1272      * Set if we are shutting down the system, similar to sleeping.
1273      */
1274     boolean mShuttingDown = false;
1275
1276     /**
1277      * Current sequence id for oom_adj computation traversal.
1278      */
1279     int mAdjSeq = 0;
1280
1281     /**
1282      * Current sequence id for process LRU updating.
1283      */
1284     int mLruSeq = 0;
1285
1286     /**
1287      * Keep track of the non-cached/empty process we last found, to help
1288      * determine how to distribute cached/empty processes next time.
1289      */
1290     int mNumNonCachedProcs = 0;
1291
1292     /**
1293      * Keep track of the number of cached hidden procs, to balance oom adj
1294      * distribution between those and empty procs.
1295      */
1296     int mNumCachedHiddenProcs = 0;
1297
1298     /**
1299      * Keep track of the number of service processes we last found, to
1300      * determine on the next iteration which should be B services.
1301      */
1302     int mNumServiceProcs = 0;
1303     int mNewNumAServiceProcs = 0;
1304     int mNewNumServiceProcs = 0;
1305
1306     /**
1307      * Allow the current computed overall memory level of the system to go down?
1308      * This is set to false when we are killing processes for reasons other than
1309      * memory management, so that the now smaller process list will not be taken as
1310      * an indication that memory is tighter.
1311      */
1312     boolean mAllowLowerMemLevel = false;
1313
1314     /**
1315      * The last computed memory level, for holding when we are in a state that
1316      * processes are going away for other reasons.
1317      */
1318     int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL;
1319
1320     /**
1321      * The last total number of process we have, to determine if changes actually look
1322      * like a shrinking number of process due to lower RAM.
1323      */
1324     int mLastNumProcesses;
1325
1326     /**
1327      * The uptime of the last time we performed idle maintenance.
1328      */
1329     long mLastIdleTime = SystemClock.uptimeMillis();
1330
1331     /**
1332      * Total time spent with RAM that has been added in the past since the last idle time.
1333      */
1334     long mLowRamTimeSinceLastIdle = 0;
1335
1336     /**
1337      * If RAM is currently low, when that horrible situation started.
1338      */
1339     long mLowRamStartTime = 0;
1340
1341     /**
1342      * For reporting to battery stats the current top application.
1343      */
1344     private String mCurResumedPackage = null;
1345     private int mCurResumedUid = -1;
1346
1347     /**
1348      * For reporting to battery stats the apps currently running foreground
1349      * service.  The ProcessMap is package/uid tuples; each of these contain
1350      * an array of the currently foreground processes.
1351      */
1352     final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages
1353             = new ProcessMap<ArrayList<ProcessRecord>>();
1354
1355     /**
1356      * This is set if we had to do a delayed dexopt of an app before launching
1357      * it, to increase the ANR timeouts in that case.
1358      */
1359     boolean mDidDexOpt;
1360
1361     /**
1362      * Set if the systemServer made a call to enterSafeMode.
1363      */
1364     boolean mSafeMode;
1365
1366     /**
1367      * If true, we are running under a test environment so will sample PSS from processes
1368      * much more rapidly to try to collect better data when the tests are rapidly
1369      * running through apps.
1370      */
1371     boolean mTestPssMode = false;
1372
1373     String mDebugApp = null;
1374     boolean mWaitForDebugger = false;
1375     boolean mDebugTransient = false;
1376     String mOrigDebugApp = null;
1377     boolean mOrigWaitForDebugger = false;
1378     boolean mAlwaysFinishActivities = false;
1379     boolean mLenientBackgroundCheck = false;
1380     boolean mForceResizableActivities;
1381     boolean mSupportsMultiWindow;
1382     boolean mSupportsFreeformWindowManagement;
1383     boolean mSupportsPictureInPicture;
1384     boolean mSupportsLeanbackOnly;
1385     Rect mDefaultPinnedStackBounds;
1386     IActivityController mController = null;
1387     boolean mControllerIsAMonkey = false;
1388     String mProfileApp = null;
1389     ProcessRecord mProfileProc = null;
1390     String mProfileFile;
1391     ParcelFileDescriptor mProfileFd;
1392     int mSamplingInterval = 0;
1393     boolean mAutoStopProfiler = false;
1394     int mProfileType = 0;
1395     final ProcessMap<Pair<Long, String>> mMemWatchProcesses = new ProcessMap<>();
1396     String mMemWatchDumpProcName;
1397     String mMemWatchDumpFile;
1398     int mMemWatchDumpPid;
1399     int mMemWatchDumpUid;
1400     String mTrackAllocationApp = null;
1401     String mNativeDebuggingApp = null;
1402
1403     final long[] mTmpLong = new long[2];
1404
1405     static final class ProcessChangeItem {
1406         static final int CHANGE_ACTIVITIES = 1<<0;
1407         static final int CHANGE_PROCESS_STATE = 1<<1;
1408         int changes;
1409         int uid;
1410         int pid;
1411         int processState;
1412         boolean foregroundActivities;
1413     }
1414
1415     final RemoteCallbackList<IProcessObserver> mProcessObservers = new RemoteCallbackList<>();
1416     ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5];
1417
1418     final ArrayList<ProcessChangeItem> mPendingProcessChanges = new ArrayList<>();
1419     final ArrayList<ProcessChangeItem> mAvailProcessChanges = new ArrayList<>();
1420
1421     final RemoteCallbackList<IUidObserver> mUidObservers = new RemoteCallbackList<>();
1422     UidRecord.ChangeItem[] mActiveUidChanges = new UidRecord.ChangeItem[5];
1423
1424     final ArrayList<UidRecord.ChangeItem> mPendingUidChanges = new ArrayList<>();
1425     final ArrayList<UidRecord.ChangeItem> mAvailUidChanges = new ArrayList<>();
1426
1427     /**
1428      * Runtime CPU use collection thread.  This object's lock is used to
1429      * perform synchronization with the thread (notifying it to run).
1430      */
1431     final Thread mProcessCpuThread;
1432
1433     /**
1434      * Used to collect per-process CPU use for ANRs, battery stats, etc.
1435      * Must acquire this object's lock when accessing it.
1436      * NOTE: this lock will be held while doing long operations (trawling
1437      * through all processes in /proc), so it should never be acquired by
1438      * any critical paths such as when holding the main activity manager lock.
1439      */
1440     final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker(
1441             MONITOR_THREAD_CPU_USAGE);
1442     final AtomicLong mLastCpuTime = new AtomicLong(0);
1443     final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true);
1444
1445     long mLastWriteTime = 0;
1446
1447     /**
1448      * Used to retain an update lock when the foreground activity is in
1449      * immersive mode.
1450      */
1451     final UpdateLock mUpdateLock = new UpdateLock("immersive");
1452
1453     /**
1454      * Set to true after the system has finished booting.
1455      */
1456     boolean mBooted = false;
1457
1458     int mProcessLimit = ProcessList.MAX_CACHED_APPS;
1459     int mProcessLimitOverride = -1;
1460
1461     WindowManagerService mWindowManager;
1462     final ActivityThread mSystemThread;
1463
1464     private final class AppDeathRecipient implements IBinder.DeathRecipient {
1465         final ProcessRecord mApp;
1466         final int mPid;
1467         final IApplicationThread mAppThread;
1468
1469         AppDeathRecipient(ProcessRecord app, int pid,
1470                 IApplicationThread thread) {
1471             if (DEBUG_ALL) Slog.v(
1472                 TAG, "New death recipient " + this
1473                 + " for thread " + thread.asBinder());
1474             mApp = app;
1475             mPid = pid;
1476             mAppThread = thread;
1477         }
1478
1479         @Override
1480         public void binderDied() {
1481             if (DEBUG_ALL) Slog.v(
1482                 TAG, "Death received in " + this
1483                 + " for thread " + mAppThread.asBinder());
1484             synchronized(ActivityManagerService.this) {
1485                 appDiedLocked(mApp, mPid, mAppThread, true);
1486             }
1487         }
1488     }
1489
1490     static final int SHOW_ERROR_UI_MSG = 1;
1491     static final int SHOW_NOT_RESPONDING_UI_MSG = 2;
1492     static final int SHOW_FACTORY_ERROR_UI_MSG = 3;
1493     static final int UPDATE_CONFIGURATION_MSG = 4;
1494     static final int GC_BACKGROUND_PROCESSES_MSG = 5;
1495     static final int WAIT_FOR_DEBUGGER_UI_MSG = 6;
1496     static final int SERVICE_TIMEOUT_MSG = 12;
1497     static final int UPDATE_TIME_ZONE = 13;
1498     static final int SHOW_UID_ERROR_UI_MSG = 14;
1499     static final int SHOW_FINGERPRINT_ERROR_UI_MSG = 15;
1500     static final int PROC_START_TIMEOUT_MSG = 20;
1501     static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21;
1502     static final int KILL_APPLICATION_MSG = 22;
1503     static final int FINALIZE_PENDING_INTENT_MSG = 23;
1504     static final int POST_HEAVY_NOTIFICATION_MSG = 24;
1505     static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25;
1506     static final int SHOW_STRICT_MODE_VIOLATION_UI_MSG = 26;
1507     static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27;
1508     static final int CLEAR_DNS_CACHE_MSG = 28;
1509     static final int UPDATE_HTTP_PROXY_MSG = 29;
1510     static final int SHOW_COMPAT_MODE_DIALOG_UI_MSG = 30;
1511     static final int DISPATCH_PROCESSES_CHANGED_UI_MSG = 31;
1512     static final int DISPATCH_PROCESS_DIED_UI_MSG = 32;
1513     static final int REPORT_MEM_USAGE_MSG = 33;
1514     static final int REPORT_USER_SWITCH_MSG = 34;
1515     static final int CONTINUE_USER_SWITCH_MSG = 35;
1516     static final int USER_SWITCH_TIMEOUT_MSG = 36;
1517     static final int IMMERSIVE_MODE_LOCK_MSG = 37;
1518     static final int PERSIST_URI_GRANTS_MSG = 38;
1519     static final int REQUEST_ALL_PSS_MSG = 39;
1520     static final int START_PROFILES_MSG = 40;
1521     static final int UPDATE_TIME = 41;
1522     static final int SYSTEM_USER_START_MSG = 42;
1523     static final int SYSTEM_USER_CURRENT_MSG = 43;
1524     static final int ENTER_ANIMATION_COMPLETE_MSG = 44;
1525     static final int FINISH_BOOTING_MSG = 45;
1526     static final int START_USER_SWITCH_UI_MSG = 46;
1527     static final int SEND_LOCALE_TO_MOUNT_DAEMON_MSG = 47;
1528     static final int DISMISS_DIALOG_UI_MSG = 48;
1529     static final int NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG = 49;
1530     static final int NOTIFY_CLEARTEXT_NETWORK_MSG = 50;
1531     static final int POST_DUMP_HEAP_NOTIFICATION_MSG = 51;
1532     static final int DELETE_DUMPHEAP_MSG = 52;
1533     static final int FOREGROUND_PROFILE_CHANGED_MSG = 53;
1534     static final int DISPATCH_UIDS_CHANGED_UI_MSG = 54;
1535     static final int REPORT_TIME_TRACKER_MSG = 55;
1536     static final int REPORT_USER_SWITCH_COMPLETE_MSG = 56;
1537     static final int SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG = 57;
1538     static final int APP_BOOST_DEACTIVATE_MSG = 58;
1539     static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG = 59;
1540     static final int IDLE_UIDS_MSG = 60;
1541     static final int SYSTEM_USER_UNLOCK_MSG = 61;
1542     static final int LOG_STACK_STATE = 62;
1543     static final int VR_MODE_CHANGE_MSG = 63;
1544     static final int NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG = 64;
1545     static final int NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG = 65;
1546     static final int NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG = 66;
1547     static final int NOTIFY_FORCED_RESIZABLE_MSG = 67;
1548     static final int NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG = 68;
1549     static final int SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG = 69;
1550     static final int NOTIFY_VR_SLEEPING_MSG = 70;
1551
1552     static final int FIRST_ACTIVITY_STACK_MSG = 100;
1553     static final int FIRST_BROADCAST_QUEUE_MSG = 200;
1554     static final int FIRST_COMPAT_MODE_MSG = 300;
1555     static final int FIRST_SUPERVISOR_STACK_MSG = 100;
1556
1557     static ServiceThread sKillThread = null;
1558     static KillHandler sKillHandler = null;
1559
1560     CompatModeDialog mCompatModeDialog;
1561     UnsupportedDisplaySizeDialog mUnsupportedDisplaySizeDialog;
1562     long mLastMemUsageReportTime = 0;
1563
1564     /**
1565      * Flag whether the current user is a "monkey", i.e. whether
1566      * the UI is driven by a UI automation tool.
1567      */
1568     private boolean mUserIsMonkey;
1569
1570     /** Flag whether the device has a Recents UI */
1571     boolean mHasRecents;
1572
1573     /** The dimensions of the thumbnails in the Recents UI. */
1574     int mThumbnailWidth;
1575     int mThumbnailHeight;
1576     float mFullscreenThumbnailScale;
1577
1578     final ServiceThread mHandlerThread;
1579     final MainHandler mHandler;
1580     final UiHandler mUiHandler;
1581
1582     PackageManagerInternal mPackageManagerInt;
1583
1584     // VoiceInteraction session ID that changes for each new request except when
1585     // being called for multiwindow assist in a single session.
1586     private int mViSessionId = 1000;
1587
1588     final boolean mPermissionReviewRequired;
1589
1590     final class KillHandler extends Handler {
1591         static final int KILL_PROCESS_GROUP_MSG = 4000;
1592
1593         public KillHandler(Looper looper) {
1594             super(looper, null, true);
1595         }
1596
1597         @Override
1598         public void handleMessage(Message msg) {
1599             switch (msg.what) {
1600                 case KILL_PROCESS_GROUP_MSG:
1601                 {
1602                     Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "killProcessGroup");
1603                     Process.killProcessGroup(msg.arg1 /* uid */, msg.arg2 /* pid */);
1604                     Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
1605                 }
1606                 break;
1607
1608                 default:
1609                     super.handleMessage(msg);
1610             }
1611         }
1612     }
1613
1614     final class UiHandler extends Handler {
1615         public UiHandler() {
1616             super(com.android.server.UiThread.get().getLooper(), null, true);
1617         }
1618
1619         @Override
1620         public void handleMessage(Message msg) {
1621             switch (msg.what) {
1622             case SHOW_ERROR_UI_MSG: {
1623                 mAppErrors.handleShowAppErrorUi(msg);
1624                 ensureBootCompleted();
1625             } break;
1626             case SHOW_NOT_RESPONDING_UI_MSG: {
1627                 mAppErrors.handleShowAnrUi(msg);
1628                 ensureBootCompleted();
1629             } break;
1630             case SHOW_STRICT_MODE_VIOLATION_UI_MSG: {
1631                 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj;
1632                 synchronized (ActivityManagerService.this) {
1633                     ProcessRecord proc = (ProcessRecord) data.get("app");
1634                     if (proc == null) {
1635                         Slog.e(TAG, "App not found when showing strict mode dialog.");
1636                         break;
1637                     }
1638                     if (proc.crashDialog != null) {
1639                         Slog.e(TAG, "App already has strict mode dialog: " + proc);
1640                         return;
1641                     }
1642                     AppErrorResult res = (AppErrorResult) data.get("result");
1643                     if (mShowDialogs && !mSleeping && !mShuttingDown) {
1644                         Dialog d = new StrictModeViolationDialog(mContext,
1645                                 ActivityManagerService.this, res, proc);
1646                         d.show();
1647                         proc.crashDialog = d;
1648                     } else {
1649                         // The device is asleep, so just pretend that the user
1650                         // saw a crash dialog and hit "force quit".
1651                         res.set(0);
1652                     }
1653                 }
1654                 ensureBootCompleted();
1655             } break;
1656             case SHOW_FACTORY_ERROR_UI_MSG: {
1657                 Dialog d = new FactoryErrorDialog(
1658                     mContext, msg.getData().getCharSequence("msg"));
1659                 d.show();
1660                 ensureBootCompleted();
1661             } break;
1662             case WAIT_FOR_DEBUGGER_UI_MSG: {
1663                 synchronized (ActivityManagerService.this) {
1664                     ProcessRecord app = (ProcessRecord)msg.obj;
1665                     if (msg.arg1 != 0) {
1666                         if (!app.waitedForDebugger) {
1667                             Dialog d = new AppWaitingForDebuggerDialog(
1668                                     ActivityManagerService.this,
1669                                     mContext, app);
1670                             app.waitDialog = d;
1671                             app.waitedForDebugger = true;
1672                             d.show();
1673                         }
1674                     } else {
1675                         if (app.waitDialog != null) {
1676                             app.waitDialog.dismiss();
1677                             app.waitDialog = null;
1678                         }
1679                     }
1680                 }
1681             } break;
1682             case SHOW_UID_ERROR_UI_MSG: {
1683                 if (mShowDialogs) {
1684                     AlertDialog d = new BaseErrorDialog(mContext);
1685                     d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
1686                     d.setCancelable(false);
1687                     d.setTitle(mContext.getText(R.string.android_system_label));
1688                     d.setMessage(mContext.getText(R.string.system_error_wipe_data));
1689                     d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok),
1690                             obtainMessage(DISMISS_DIALOG_UI_MSG, d));
1691                     d.show();
1692                 }
1693             } break;
1694             case SHOW_FINGERPRINT_ERROR_UI_MSG: {
1695                 if (mShowDialogs) {
1696                     AlertDialog d = new BaseErrorDialog(mContext);
1697                     d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR);
1698                     d.setCancelable(false);
1699                     d.setTitle(mContext.getText(R.string.android_system_label));
1700                     d.setMessage(mContext.getText(R.string.system_error_manufacturer));
1701                     d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok),
1702                             obtainMessage(DISMISS_DIALOG_UI_MSG, d));
1703                     d.show();
1704                 }
1705             } break;
1706             case SHOW_COMPAT_MODE_DIALOG_UI_MSG: {
1707                 synchronized (ActivityManagerService.this) {
1708                     ActivityRecord ar = (ActivityRecord) msg.obj;
1709                     if (mCompatModeDialog != null) {
1710                         if (mCompatModeDialog.mAppInfo.packageName.equals(
1711                                 ar.info.applicationInfo.packageName)) {
1712                             return;
1713                         }
1714                         mCompatModeDialog.dismiss();
1715                         mCompatModeDialog = null;
1716                     }
1717                     if (ar != null && false) {
1718                         if (mCompatModePackages.getPackageAskCompatModeLocked(
1719                                 ar.packageName)) {
1720                             int mode = mCompatModePackages.computeCompatModeLocked(
1721                                     ar.info.applicationInfo);
1722                             if (mode == ActivityManager.COMPAT_MODE_DISABLED
1723                                     || mode == ActivityManager.COMPAT_MODE_ENABLED) {
1724                                 mCompatModeDialog = new CompatModeDialog(
1725                                         ActivityManagerService.this, mContext,
1726                                         ar.info.applicationInfo);
1727                                 mCompatModeDialog.show();
1728                             }
1729                         }
1730                     }
1731                 }
1732                 break;
1733             }
1734             case SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG: {
1735                 synchronized (ActivityManagerService.this) {
1736                     final ActivityRecord ar = (ActivityRecord) msg.obj;
1737                     if (mUnsupportedDisplaySizeDialog != null) {
1738                         mUnsupportedDisplaySizeDialog.dismiss();
1739                         mUnsupportedDisplaySizeDialog = null;
1740                     }
1741                     if (ar != null && mCompatModePackages.getPackageNotifyUnsupportedZoomLocked(
1742                             ar.packageName)) {
1743                         mUnsupportedDisplaySizeDialog = new UnsupportedDisplaySizeDialog(
1744                                 ActivityManagerService.this, mContext, ar.info.applicationInfo);
1745                         mUnsupportedDisplaySizeDialog.show();
1746                     }
1747                 }
1748                 break;
1749             }
1750             case START_USER_SWITCH_UI_MSG: {
1751                 mUserController.showUserSwitchDialog((Pair<UserInfo, UserInfo>) msg.obj);
1752                 break;
1753             }
1754             case DISMISS_DIALOG_UI_MSG: {
1755                 final Dialog d = (Dialog) msg.obj;
1756                 d.dismiss();
1757                 break;
1758             }
1759             case DISPATCH_PROCESSES_CHANGED_UI_MSG: {
1760                 dispatchProcessesChanged();
1761                 break;
1762             }
1763             case DISPATCH_PROCESS_DIED_UI_MSG: {
1764                 final int pid = msg.arg1;
1765                 final int uid = msg.arg2;
1766                 dispatchProcessDied(pid, uid);
1767                 break;
1768             }
1769             case DISPATCH_UIDS_CHANGED_UI_MSG: {
1770                 dispatchUidsChanged();
1771             } break;
1772             }
1773         }
1774     }
1775
1776     final class MainHandler extends Handler {
1777         public MainHandler(Looper looper) {
1778             super(looper, null, true);
1779         }
1780
1781         @Override
1782         public void handleMessage(Message msg) {
1783             switch (msg.what) {
1784             case UPDATE_CONFIGURATION_MSG: {
1785                 final ContentResolver resolver = mContext.getContentResolver();
1786                 Settings.System.putConfigurationForUser(resolver, (Configuration) msg.obj,
1787                         msg.arg1);
1788             } break;
1789             case GC_BACKGROUND_PROCESSES_MSG: {
1790                 synchronized (ActivityManagerService.this) {
1791                     performAppGcsIfAppropriateLocked();
1792                 }
1793             } break;
1794             case SERVICE_TIMEOUT_MSG: {
1795                 if (mDidDexOpt) {
1796                     mDidDexOpt = false;
1797                     Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG);
1798                     nmsg.obj = msg.obj;
1799                     mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT);
1800                     return;
1801                 }
1802                 mServices.serviceTimeout((ProcessRecord)msg.obj);
1803             } break;
1804             case UPDATE_TIME_ZONE: {
1805                 synchronized (ActivityManagerService.this) {
1806                     for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
1807                         ProcessRecord r = mLruProcesses.get(i);
1808                         if (r.thread != null) {
1809                             try {
1810                                 r.thread.updateTimeZone();
1811                             } catch (RemoteException ex) {
1812                                 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName);
1813                             }
1814                         }
1815                     }
1816                 }
1817             } break;
1818             case CLEAR_DNS_CACHE_MSG: {
1819                 synchronized (ActivityManagerService.this) {
1820                     for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
1821                         ProcessRecord r = mLruProcesses.get(i);
1822                         if (r.thread != null) {
1823                             try {
1824                                 r.thread.clearDnsCache();
1825                             } catch (RemoteException ex) {
1826                                 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName);
1827                             }
1828                         }
1829                     }
1830                 }
1831             } break;
1832             case UPDATE_HTTP_PROXY_MSG: {
1833                 ProxyInfo proxy = (ProxyInfo)msg.obj;
1834                 String host = "";
1835                 String port = "";
1836                 String exclList = "";
1837                 Uri pacFileUrl = Uri.EMPTY;
1838                 if (proxy != null) {
1839                     host = proxy.getHost();
1840                     port = Integer.toString(proxy.getPort());
1841                     exclList = proxy.getExclusionListAsString();
1842                     pacFileUrl = proxy.getPacFileUrl();
1843                 }
1844                 synchronized (ActivityManagerService.this) {
1845                     for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
1846                         ProcessRecord r = mLruProcesses.get(i);
1847                         if (r.thread != null) {
1848                             try {
1849                                 r.thread.setHttpProxy(host, port, exclList, pacFileUrl);
1850                             } catch (RemoteException ex) {
1851                                 Slog.w(TAG, "Failed to update http proxy for: " +
1852                                         r.info.processName);
1853                             }
1854                         }
1855                     }
1856                 }
1857             } break;
1858             case PROC_START_TIMEOUT_MSG: {
1859                 if (mDidDexOpt) {
1860                     mDidDexOpt = false;
1861                     Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG);
1862                     nmsg.obj = msg.obj;
1863                     mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT);
1864                     return;
1865                 }
1866                 ProcessRecord app = (ProcessRecord)msg.obj;
1867                 synchronized (ActivityManagerService.this) {
1868                     processStartTimedOutLocked(app);
1869                 }
1870             } break;
1871             case CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG: {
1872                 ProcessRecord app = (ProcessRecord)msg.obj;
1873                 synchronized (ActivityManagerService.this) {
1874                     processContentProviderPublishTimedOutLocked(app);
1875                 }
1876             } break;
1877             case DO_PENDING_ACTIVITY_LAUNCHES_MSG: {
1878                 synchronized (ActivityManagerService.this) {
1879                     mActivityStarter.doPendingActivityLaunchesLocked(true);
1880                 }
1881             } break;
1882             case KILL_APPLICATION_MSG: {
1883                 synchronized (ActivityManagerService.this) {
1884                     final int appId = msg.arg1;
1885                     final int userId = msg.arg2;
1886                     Bundle bundle = (Bundle)msg.obj;
1887                     String pkg = bundle.getString("pkg");
1888                     String reason = bundle.getString("reason");
1889                     forceStopPackageLocked(pkg, appId, false, false, true, false,
1890                             false, userId, reason);
1891                 }
1892             } break;
1893             case FINALIZE_PENDING_INTENT_MSG: {
1894                 ((PendingIntentRecord)msg.obj).completeFinalize();
1895             } break;
1896             case POST_HEAVY_NOTIFICATION_MSG: {
1897                 INotificationManager inm = NotificationManager.getService();
1898                 if (inm == null) {
1899                     return;
1900                 }
1901
1902                 ActivityRecord root = (ActivityRecord)msg.obj;
1903                 ProcessRecord process = root.app;
1904                 if (process == null) {
1905                     return;
1906                 }
1907
1908                 try {
1909                     Context context = mContext.createPackageContext(process.info.packageName, 0);
1910                     String text = mContext.getString(R.string.heavy_weight_notification,
1911                             context.getApplicationInfo().loadLabel(context.getPackageManager()));
1912                     Notification notification = new Notification.Builder(context)
1913                             .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb)
1914                             .setWhen(0)
1915                             .setOngoing(true)
1916                             .setTicker(text)
1917                             .setColor(mContext.getColor(
1918                                     com.android.internal.R.color.system_notification_accent_color))
1919                             .setContentTitle(text)
1920                             .setContentText(
1921                                     mContext.getText(R.string.heavy_weight_notification_detail))
1922                             .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0,
1923                                     root.intent, PendingIntent.FLAG_CANCEL_CURRENT, null,
1924                                     new UserHandle(root.userId)))
1925                             .build();
1926                     try {
1927                         int[] outId = new int[1];
1928                         inm.enqueueNotificationWithTag("android", "android", null,
1929                                 R.string.heavy_weight_notification,
1930                                 notification, outId, root.userId);
1931                     } catch (RuntimeException e) {
1932                         Slog.w(ActivityManagerService.TAG,
1933                                 "Error showing notification for heavy-weight app", e);
1934                     } catch (RemoteException e) {
1935                     }
1936                 } catch (NameNotFoundException e) {
1937                     Slog.w(TAG, "Unable to create context for heavy notification", e);
1938                 }
1939             } break;
1940             case CANCEL_HEAVY_NOTIFICATION_MSG: {
1941                 INotificationManager inm = NotificationManager.getService();
1942                 if (inm == null) {
1943                     return;
1944                 }
1945                 try {
1946                     inm.cancelNotificationWithTag("android", null,
1947                             R.string.heavy_weight_notification,  msg.arg1);
1948                 } catch (RuntimeException e) {
1949                     Slog.w(ActivityManagerService.TAG,
1950                             "Error canceling notification for service", e);
1951                 } catch (RemoteException e) {
1952                 }
1953             } break;
1954             case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: {
1955                 synchronized (ActivityManagerService.this) {
1956                     checkExcessivePowerUsageLocked(true);
1957                     removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG);
1958                     Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG);
1959                     sendMessageDelayed(nmsg, POWER_CHECK_DELAY);
1960                 }
1961             } break;
1962             case REPORT_MEM_USAGE_MSG: {
1963                 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj;
1964                 Thread thread = new Thread() {
1965                     @Override public void run() {
1966                         reportMemUsage(memInfos);
1967                     }
1968                 };
1969                 thread.start();
1970                 break;
1971             }
1972             case REPORT_USER_SWITCH_MSG: {
1973                 mUserController.dispatchUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2);
1974                 break;
1975             }
1976             case CONTINUE_USER_SWITCH_MSG: {
1977                 mUserController.continueUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2);
1978                 break;
1979             }
1980             case USER_SWITCH_TIMEOUT_MSG: {
1981                 mUserController.timeoutUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2);
1982                 break;
1983             }
1984             case IMMERSIVE_MODE_LOCK_MSG: {
1985                 final boolean nextState = (msg.arg1 != 0);
1986                 if (mUpdateLock.isHeld() != nextState) {
1987                     if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE,
1988                             "Applying new update lock state '" + nextState
1989                             + "' for " + (ActivityRecord)msg.obj);
1990                     if (nextState) {
1991                         mUpdateLock.acquire();
1992                     } else {
1993                         mUpdateLock.release();
1994                     }
1995                 }
1996                 break;
1997             }
1998             case PERSIST_URI_GRANTS_MSG: {
1999                 writeGrantedUriPermissions();
2000                 break;
2001             }
2002             case REQUEST_ALL_PSS_MSG: {
2003                 synchronized (ActivityManagerService.this) {
2004                     requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false);
2005                 }
2006                 break;
2007             }
2008             case START_PROFILES_MSG: {
2009                 synchronized (ActivityManagerService.this) {
2010                     mUserController.startProfilesLocked();
2011                 }
2012                 break;
2013             }
2014             case UPDATE_TIME: {
2015                 synchronized (ActivityManagerService.this) {
2016                     for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
2017                         ProcessRecord r = mLruProcesses.get(i);
2018                         if (r.thread != null) {
2019                             try {
2020                                 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true);
2021                             } catch (RemoteException ex) {
2022                                 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName);
2023                             }
2024                         }
2025                     }
2026                 }
2027                 break;
2028             }
2029             case SYSTEM_USER_START_MSG: {
2030                 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START,
2031                         Integer.toString(msg.arg1), msg.arg1);
2032                 mSystemServiceManager.startUser(msg.arg1);
2033                 break;
2034             }
2035             case SYSTEM_USER_UNLOCK_MSG: {
2036                 final int userId = msg.arg1;
2037                 mSystemServiceManager.unlockUser(userId);
2038                 synchronized (ActivityManagerService.this) {
2039                     mRecentTasks.loadUserRecentsLocked(userId);
2040                 }
2041                 if (userId == UserHandle.USER_SYSTEM) {
2042                     startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_UNAWARE);
2043                 }
2044                 installEncryptionUnawareProviders(userId);
2045                 mUserController.finishUserUnlocked((UserState) msg.obj);
2046                 break;
2047             }
2048             case SYSTEM_USER_CURRENT_MSG: {
2049                 mBatteryStatsService.noteEvent(
2050                         BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH,
2051                         Integer.toString(msg.arg2), msg.arg2);
2052                 mBatteryStatsService.noteEvent(
2053                         BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START,
2054                         Integer.toString(msg.arg1), msg.arg1);
2055                 mSystemServiceManager.switchUser(msg.arg1);
2056                 break;
2057             }
2058             case ENTER_ANIMATION_COMPLETE_MSG: {
2059                 synchronized (ActivityManagerService.this) {
2060                     ActivityRecord r = ActivityRecord.forTokenLocked((IBinder) msg.obj);
2061                     if (r != null && r.app != null && r.app.thread != null) {
2062                         try {
2063                             r.app.thread.scheduleEnterAnimationComplete(r.appToken);
2064                         } catch (RemoteException e) {
2065                         }
2066                     }
2067                 }
2068                 break;
2069             }
2070             case FINISH_BOOTING_MSG: {
2071                 if (msg.arg1 != 0) {
2072                     Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting");
2073                     finishBooting();
2074                     Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
2075                 }
2076                 if (msg.arg2 != 0) {
2077                     enableScreenAfterBoot();
2078                 }
2079                 break;
2080             }
2081             case SEND_LOCALE_TO_MOUNT_DAEMON_MSG: {
2082                 try {
2083                     Locale l = (Locale) msg.obj;
2084                     IBinder service = ServiceManager.getService("mount");
2085                     IMountService mountService = IMountService.Stub.asInterface(service);
2086                     Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI");
2087                     mountService.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag());
2088                 } catch (RemoteException e) {
2089                     Log.e(TAG, "Error storing locale for decryption UI", e);
2090                 }
2091                 break;
2092             }
2093             case NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG: {
2094                 synchronized (ActivityManagerService.this) {
2095                     for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
2096                         try {
2097                             // Make a one-way callback to the listener
2098                             mTaskStackListeners.getBroadcastItem(i).onTaskStackChanged();
2099                         } catch (RemoteException e){
2100                             // Handled by the RemoteCallbackList
2101                         }
2102                     }
2103                     mTaskStackListeners.finishBroadcast();
2104                 }
2105                 break;
2106             }
2107             case NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG: {
2108                 synchronized (ActivityManagerService.this) {
2109                     for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
2110                         try {
2111                             // Make a one-way callback to the listener
2112                             mTaskStackListeners.getBroadcastItem(i).onActivityPinned();
2113                         } catch (RemoteException e){
2114                             // Handled by the RemoteCallbackList
2115                         }
2116                     }
2117                     mTaskStackListeners.finishBroadcast();
2118                 }
2119                 break;
2120             }
2121             case NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG: {
2122                 synchronized (ActivityManagerService.this) {
2123                     for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
2124                         try {
2125                             // Make a one-way callback to the listener
2126                             mTaskStackListeners.getBroadcastItem(i).onPinnedActivityRestartAttempt();
2127                         } catch (RemoteException e){
2128                             // Handled by the RemoteCallbackList
2129                         }
2130                     }
2131                     mTaskStackListeners.finishBroadcast();
2132                 }
2133                 break;
2134             }
2135             case NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG: {
2136                 synchronized (ActivityManagerService.this) {
2137                     for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
2138                         try {
2139                             // Make a one-way callback to the listener
2140                             mTaskStackListeners.getBroadcastItem(i).onPinnedStackAnimationEnded();
2141                         } catch (RemoteException e){
2142                             // Handled by the RemoteCallbackList
2143                         }
2144                     }
2145                     mTaskStackListeners.finishBroadcast();
2146                 }
2147                 break;
2148             }
2149             case NOTIFY_FORCED_RESIZABLE_MSG: {
2150                 synchronized (ActivityManagerService.this) {
2151                     for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
2152                         try {
2153                             // Make a one-way callback to the listener
2154                             mTaskStackListeners.getBroadcastItem(i).onActivityForcedResizable(
2155                                     (String) msg.obj, msg.arg1);
2156                         } catch (RemoteException e){
2157                             // Handled by the RemoteCallbackList
2158                         }
2159                     }
2160                     mTaskStackListeners.finishBroadcast();
2161                 }
2162                 break;
2163             }
2164                 case NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG: {
2165                     synchronized (ActivityManagerService.this) {
2166                         for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) {
2167                             try {
2168                                 // Make a one-way callback to the listener
2169                                 mTaskStackListeners.getBroadcastItem(i)
2170                                         .onActivityDismissingDockedStack();
2171                             } catch (RemoteException e){
2172                                 // Handled by the RemoteCallbackList
2173                             }
2174                         }
2175                         mTaskStackListeners.finishBroadcast();
2176                     }
2177                     break;
2178                 }
2179             case NOTIFY_CLEARTEXT_NETWORK_MSG: {
2180                 final int uid = msg.arg1;
2181                 final byte[] firstPacket = (byte[]) msg.obj;
2182
2183                 synchronized (mPidsSelfLocked) {
2184                     for (int i = 0; i < mPidsSelfLocked.size(); i++) {
2185                         final ProcessRecord p = mPidsSelfLocked.valueAt(i);
2186                         if (p.uid == uid) {
2187                             try {
2188                                 p.thread.notifyCleartextNetwork(firstPacket);
2189                             } catch (RemoteException ignored) {
2190                             }
2191                         }
2192                     }
2193                 }
2194                 break;
2195             }
2196             case POST_DUMP_HEAP_NOTIFICATION_MSG: {
2197                 final String procName;
2198                 final int uid;
2199                 final long memLimit;
2200                 final String reportPackage;
2201                 synchronized (ActivityManagerService.this) {
2202                     procName = mMemWatchDumpProcName;
2203                     uid = mMemWatchDumpUid;
2204                     Pair<Long, String> val = mMemWatchProcesses.get(procName, uid);
2205                     if (val == null) {
2206                         val = mMemWatchProcesses.get(procName, 0);
2207                     }
2208                     if (val != null) {
2209                         memLimit = val.first;
2210                         reportPackage = val.second;
2211                     } else {
2212                         memLimit = 0;
2213                         reportPackage = null;
2214                     }
2215                 }
2216                 if (procName == null) {
2217                     return;
2218                 }
2219
2220                 if (DEBUG_PSS) Slog.d(TAG_PSS,
2221                         "Showing dump heap notification from " + procName + "/" + uid);
2222
2223                 INotificationManager inm = NotificationManager.getService();
2224                 if (inm == null) {
2225                     return;
2226                 }
2227
2228                 String text = mContext.getString(R.string.dump_heap_notification, procName);
2229
2230
2231                 Intent deleteIntent = new Intent();
2232                 deleteIntent.setAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP);
2233                 Intent intent = new Intent();
2234                 intent.setClassName("android", DumpHeapActivity.class.getName());
2235                 intent.putExtra(DumpHeapActivity.KEY_PROCESS, procName);
2236                 intent.putExtra(DumpHeapActivity.KEY_SIZE, memLimit);
2237                 if (reportPackage != null) {
2238                     intent.putExtra(DumpHeapActivity.KEY_DIRECT_LAUNCH, reportPackage);
2239                 }
2240                 int userId = UserHandle.getUserId(uid);
2241                 Notification notification = new Notification.Builder(mContext)
2242                         .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb)
2243                         .setWhen(0)
2244                         .setOngoing(true)
2245                         .setAutoCancel(true)
2246                         .setTicker(text)
2247                         .setColor(mContext.getColor(
2248                                 com.android.internal.R.color.system_notification_accent_color))
2249                         .setContentTitle(text)
2250                         .setContentText(
2251                                 mContext.getText(R.string.dump_heap_notification_detail))
2252                         .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0,
2253                                 intent, PendingIntent.FLAG_CANCEL_CURRENT, null,
2254                                 new UserHandle(userId)))
2255                         .setDeleteIntent(PendingIntent.getBroadcastAsUser(mContext, 0,
2256                                 deleteIntent, 0, UserHandle.SYSTEM))
2257                         .build();
2258
2259                 try {
2260                     int[] outId = new int[1];
2261                     inm.enqueueNotificationWithTag("android", "android", null,
2262                             R.string.dump_heap_notification,
2263                             notification, outId, userId);
2264                 } catch (RuntimeException e) {
2265                     Slog.w(ActivityManagerService.TAG,
2266                             "Error showing notification for dump heap", e);
2267                 } catch (RemoteException e) {
2268                 }
2269             } break;
2270             case DELETE_DUMPHEAP_MSG: {
2271                 revokeUriPermission(ActivityThread.currentActivityThread().getApplicationThread(),
2272                         DumpHeapActivity.JAVA_URI,
2273                         Intent.FLAG_GRANT_READ_URI_PERMISSION
2274                                 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION,
2275                         UserHandle.myUserId());
2276                 synchronized (ActivityManagerService.this) {
2277                     mMemWatchDumpFile = null;
2278                     mMemWatchDumpProcName = null;
2279                     mMemWatchDumpPid = -1;
2280                     mMemWatchDumpUid = -1;
2281                 }
2282             } break;
2283             case FOREGROUND_PROFILE_CHANGED_MSG: {
2284                 mUserController.dispatchForegroundProfileChanged(msg.arg1);
2285             } break;
2286             case REPORT_TIME_TRACKER_MSG: {
2287                 AppTimeTracker tracker = (AppTimeTracker)msg.obj;
2288                 tracker.deliverResult(mContext);
2289             } break;
2290             case REPORT_USER_SWITCH_COMPLETE_MSG: {
2291                 mUserController.dispatchUserSwitchComplete(msg.arg1);
2292             } break;
2293             case SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG: {
2294                 IUiAutomationConnection connection = (IUiAutomationConnection) msg.obj;
2295                 try {
2296                     connection.shutdown();
2297                 } catch (RemoteException e) {
2298                     Slog.w(TAG, "Error shutting down UiAutomationConnection");
2299                 }
2300                 // Only a UiAutomation can set this flag and now that
2301                 // it is finished we make sure it is reset to its default.
2302                 mUserIsMonkey = false;
2303             } break;
2304             case APP_BOOST_DEACTIVATE_MSG: {
2305                 synchronized(ActivityManagerService.this) {
2306                     if (mIsBoosted) {
2307                         if (mBoostStartTime < (SystemClock.uptimeMillis() - APP_BOOST_TIMEOUT)) {
2308                             nativeMigrateFromBoost();
2309                             mIsBoosted = false;
2310                             mBoostStartTime = 0;
2311                         } else {
2312                             Message newmsg = mHandler.obtainMessage(APP_BOOST_DEACTIVATE_MSG);
2313                             mHandler.sendMessageDelayed(newmsg, APP_BOOST_TIMEOUT);
2314                         }
2315                     }
2316                 }
2317             } break;
2318             case IDLE_UIDS_MSG: {
2319                 idleUids();
2320             } break;
2321             case LOG_STACK_STATE: {
2322                 synchronized (ActivityManagerService.this) {
2323                     mStackSupervisor.logStackState();
2324                 }
2325             } break;
2326             case VR_MODE_CHANGE_MSG: {
2327                 VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class);
2328                 if (vrService == null) {
2329                     break;
2330                 }
2331                 final ActivityRecord r = (ActivityRecord) msg.obj;
2332                 boolean vrMode;
2333                 ComponentName requestedPackage;
2334                 ComponentName callingPackage;
2335                 int userId;
2336                 synchronized (ActivityManagerService.this) {
2337                     vrMode = r.requestedVrComponent != null;
2338                     requestedPackage = r.requestedVrComponent;
2339                     userId = r.userId;
2340                     callingPackage = r.info.getComponentName();
2341                     if (mInVrMode != vrMode) {
2342                         mInVrMode = vrMode;
2343                         mShowDialogs = shouldShowDialogs(mConfiguration, mInVrMode);
2344                         if (r.app != null) {
2345                             ProcessRecord proc = r.app;
2346                             if (proc.vrThreadTid > 0) {
2347                                 if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) {
2348                                     try {
2349                                         if (mInVrMode == true) {
2350                                             Process.setThreadScheduler(proc.vrThreadTid,
2351                                                 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1);
2352                                         } else {
2353                                             Process.setThreadScheduler(proc.vrThreadTid,
2354                                                 Process.SCHED_OTHER, 0);
2355                                         }
2356                                     } catch (IllegalArgumentException e) {
2357                                         Slog.w(TAG, "Failed to set scheduling policy, thread does"
2358                                                 + " not exist:\n" + e);
2359                                     }
2360                                 }
2361                             }
2362                         }
2363                     }
2364                 }
2365                 vrService.setVrMode(vrMode, requestedPackage, userId, callingPackage);
2366             } case NOTIFY_VR_SLEEPING_MSG: {
2367                 notifyVrManagerOfSleepState(msg.arg1 != 0);
2368             } break;
2369             }
2370         }
2371     };
2372
2373     static final int COLLECT_PSS_BG_MSG = 1;
2374
2375     final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) {
2376         @Override
2377         public void handleMessage(Message msg) {
2378             switch (msg.what) {
2379             case COLLECT_PSS_BG_MSG: {
2380                 long start = SystemClock.uptimeMillis();
2381                 MemInfoReader memInfo = null;
2382                 synchronized (ActivityManagerService.this) {
2383                     if (mFullPssPending) {
2384                         mFullPssPending = false;
2385                         memInfo = new MemInfoReader();
2386                     }
2387                 }
2388                 if (memInfo != null) {
2389                     updateCpuStatsNow();
2390                     long nativeTotalPss = 0;
2391                     final List<ProcessCpuTracker.Stats> stats;
2392                     synchronized (mProcessCpuTracker) {
2393                         stats = mProcessCpuTracker.getStats( (st)-> {
2394                             return st.vsize > 0 && st.uid < Process.FIRST_APPLICATION_UID;
2395                         });
2396                     }
2397                     final int N = stats.size();
2398                     for (int j = 0; j < N; j++) {
2399                         synchronized (mPidsSelfLocked) {
2400                             if (mPidsSelfLocked.indexOfKey(stats.get(j).pid) >= 0) {
2401                                 // This is one of our own processes; skip it.
2402                                 continue;
2403                             }
2404                         }
2405                         nativeTotalPss += Debug.getPss(stats.get(j).pid, null, null);
2406                     }
2407                     memInfo.readMemInfo();
2408                     synchronized (ActivityManagerService.this) {
2409                         if (DEBUG_PSS) Slog.d(TAG_PSS, "Collected native and kernel memory in "
2410                                 + (SystemClock.uptimeMillis()-start) + "ms");
2411                         final long cachedKb = memInfo.getCachedSizeKb();
2412                         final long freeKb = memInfo.getFreeSizeKb();
2413                         final long zramKb = memInfo.getZramTotalSizeKb();
2414                         final long kernelKb = memInfo.getKernelUsedSizeKb();
2415                         EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024,
2416                                 kernelKb*1024, nativeTotalPss*1024);
2417                         mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb,
2418                                 nativeTotalPss);
2419                     }
2420                 }
2421
2422                 int num = 0;
2423                 long[] tmp = new long[2];
2424                 do {
2425                     ProcessRecord proc;
2426                     int procState;
2427                     int pid;
2428                     long lastPssTime;
2429                     synchronized (ActivityManagerService.this) {
2430                         if (mPendingPssProcesses.size() <= 0) {
2431                             if (mTestPssMode || DEBUG_PSS) Slog.d(TAG_PSS,
2432                                     "Collected PSS of " + num + " processes in "
2433                                     + (SystemClock.uptimeMillis() - start) + "ms");
2434                             mPendingPssProcesses.clear();
2435                             return;
2436                         }
2437                         proc = mPendingPssProcesses.remove(0);
2438                         procState = proc.pssProcState;
2439                         lastPssTime = proc.lastPssTime;
2440                         if (proc.thread != null && procState == proc.setProcState
2441                                 && (lastPssTime+ProcessList.PSS_SAFE_TIME_FROM_STATE_CHANGE)
2442                                         < SystemClock.uptimeMillis()) {
2443                             pid = proc.pid;
2444                         } else {
2445                             proc = null;
2446                             pid = 0;
2447                         }
2448                     }
2449                     if (proc != null) {
2450                         long pss = Debug.getPss(pid, tmp, null);
2451                         synchronized (ActivityManagerService.this) {
2452                             if (pss != 0 && proc.thread != null && proc.setProcState == procState
2453                                     && proc.pid == pid && proc.lastPssTime == lastPssTime) {
2454                                 num++;
2455                                 recordPssSampleLocked(proc, procState, pss, tmp[0], tmp[1],
2456                                         SystemClock.uptimeMillis());
2457                             }
2458                         }
2459                     }
2460                 } while (true);
2461             }
2462             }
2463         }
2464     };
2465
2466     public void setSystemProcess() {
2467         try {
2468             ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true);
2469             ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats);
2470             ServiceManager.addService("meminfo", new MemBinder(this));
2471             ServiceManager.addService("gfxinfo", new GraphicsBinder(this));
2472             ServiceManager.addService("dbinfo", new DbBinder(this));
2473             if (MONITOR_CPU_USAGE) {
2474                 ServiceManager.addService("cpuinfo", new CpuBinder(this));
2475             }
2476             ServiceManager.addService("permission", new PermissionController(this));
2477             ServiceManager.addService("processinfo", new ProcessInfoService(this));
2478
2479             ApplicationInfo info = mContext.getPackageManager().getApplicationInfo(
2480                     "android", STOCK_PM_FLAGS | MATCH_SYSTEM_ONLY);
2481             mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader());
2482
2483             synchronized (this) {
2484                 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0);
2485                 app.persistent = true;
2486                 app.pid = MY_PID;
2487                 app.maxAdj = ProcessList.SYSTEM_ADJ;
2488                 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats);
2489                 synchronized (mPidsSelfLocked) {
2490                     mPidsSelfLocked.put(app.pid, app);
2491                 }
2492                 updateLruProcessLocked(app, false, null);
2493                 updateOomAdjLocked();
2494             }
2495         } catch (PackageManager.NameNotFoundException e) {
2496             throw new RuntimeException(
2497                     "Unable to find android system package", e);
2498         }
2499     }
2500
2501     public void setWindowManager(WindowManagerService wm) {
2502         mWindowManager = wm;
2503         mStackSupervisor.setWindowManager(wm);
2504         mActivityStarter.setWindowManager(wm);
2505     }
2506
2507     public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) {
2508         mUsageStatsService = usageStatsManager;
2509     }
2510
2511     public void startObservingNativeCrashes() {
2512         final NativeCrashListener ncl = new NativeCrashListener(this);
2513         ncl.start();
2514     }
2515
2516     public IAppOpsService getAppOpsService() {
2517         return mAppOpsService;
2518     }
2519
2520     static class MemBinder extends Binder {
2521         ActivityManagerService mActivityManagerService;
2522         MemBinder(ActivityManagerService activityManagerService) {
2523             mActivityManagerService = activityManagerService;
2524         }
2525
2526         @Override
2527         protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
2528             if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP)
2529                     != PackageManager.PERMISSION_GRANTED) {
2530                 pw.println("Permission Denial: can't dump meminfo from from pid="
2531                         + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid()
2532                         + " without permission " + android.Manifest.permission.DUMP);
2533                 return;
2534             }
2535
2536             mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, "  ", args, false, null);
2537         }
2538     }
2539
2540     static class GraphicsBinder extends Binder {
2541         ActivityManagerService mActivityManagerService;
2542         GraphicsBinder(ActivityManagerService activityManagerService) {
2543             mActivityManagerService = activityManagerService;
2544         }
2545
2546         @Override
2547         protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
2548             if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP)
2549                     != PackageManager.PERMISSION_GRANTED) {
2550                 pw.println("Permission Denial: can't dump gfxinfo from from pid="
2551                         + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid()
2552                         + " without permission " + android.Manifest.permission.DUMP);
2553                 return;
2554             }
2555
2556             mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args);
2557         }
2558     }
2559
2560     static class DbBinder extends Binder {
2561         ActivityManagerService mActivityManagerService;
2562         DbBinder(ActivityManagerService activityManagerService) {
2563             mActivityManagerService = activityManagerService;
2564         }
2565
2566         @Override
2567         protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
2568             if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP)
2569                     != PackageManager.PERMISSION_GRANTED) {
2570                 pw.println("Permission Denial: can't dump dbinfo from from pid="
2571                         + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid()
2572                         + " without permission " + android.Manifest.permission.DUMP);
2573                 return;
2574             }
2575
2576             mActivityManagerService.dumpDbInfo(fd, pw, args);
2577         }
2578     }
2579
2580     static class CpuBinder extends Binder {
2581         ActivityManagerService mActivityManagerService;
2582         CpuBinder(ActivityManagerService activityManagerService) {
2583             mActivityManagerService = activityManagerService;
2584         }
2585
2586         @Override
2587         protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
2588             if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP)
2589                     != PackageManager.PERMISSION_GRANTED) {
2590                 pw.println("Permission Denial: can't dump cpuinfo from from pid="
2591                         + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid()
2592                         + " without permission " + android.Manifest.permission.DUMP);
2593                 return;
2594             }
2595
2596             synchronized (mActivityManagerService.mProcessCpuTracker) {
2597                 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad());
2598                 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState(
2599                         SystemClock.uptimeMillis()));
2600             }
2601         }
2602     }
2603
2604     public static final class Lifecycle extends SystemService {
2605         private final ActivityManagerService mService;
2606
2607         public Lifecycle(Context context) {
2608             super(context);
2609             mService = new ActivityManagerService(context);
2610         }
2611
2612         @Override
2613         public void onStart() {
2614             mService.start();
2615         }
2616
2617         public ActivityManagerService getService() {
2618             return mService;
2619         }
2620     }
2621
2622     // Note: This method is invoked on the main thread but may need to attach various
2623     // handlers to other threads.  So take care to be explicit about the looper.
2624     public ActivityManagerService(Context systemContext) {
2625         mContext = systemContext;
2626         mFactoryTest = FactoryTest.getMode();
2627         mSystemThread = ActivityThread.currentActivityThread();
2628
2629         Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass());
2630
2631         mPermissionReviewRequired = mContext.getResources().getBoolean(
2632                 com.android.internal.R.bool.config_permissionReviewRequired);
2633
2634         mHandlerThread = new ServiceThread(TAG,
2635                 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/);
2636         mHandlerThread.start();
2637         mHandler = new MainHandler(mHandlerThread.getLooper());
2638         mUiHandler = new UiHandler();
2639
2640         /* static; one-time init here */
2641         if (sKillHandler == null) {
2642             sKillThread = new ServiceThread(TAG + ":kill",
2643                     android.os.Process.THREAD_PRIORITY_BACKGROUND, true /* allowIo */);
2644             sKillThread.start();
2645             sKillHandler = new KillHandler(sKillThread.getLooper());
2646         }
2647
2648         mFgBroadcastQueue = new BroadcastQueue(this, mHandler,
2649                 "foreground", BROADCAST_FG_TIMEOUT, false);
2650         mBgBroadcastQueue = new BroadcastQueue(this, mHandler,
2651                 "background", BROADCAST_BG_TIMEOUT, true);
2652         mBroadcastQueues[0] = mFgBroadcastQueue;
2653         mBroadcastQueues[1] = mBgBroadcastQueue;
2654
2655         mServices = new ActiveServices(this);
2656         mProviderMap = new ProviderMap(this);
2657         mAppErrors = new AppErrors(mContext, this);
2658
2659         // TODO: Move creation of battery stats service outside of activity manager service.
2660         File dataDir = Environment.getDataDirectory();
2661         File systemDir = new File(dataDir, "system");
2662         systemDir.mkdirs();
2663         mBatteryStatsService = new BatteryStatsService(systemDir, mHandler);
2664         mBatteryStatsService.getActiveStatistics().readLocked();
2665         mBatteryStatsService.scheduleWriteToDisk();
2666         mOnBattery = DEBUG_POWER ? true
2667                 : mBatteryStatsService.getActiveStatistics().getIsOnBattery();
2668         mBatteryStatsService.getActiveStatistics().setCallback(this);
2669
2670         mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats"));
2671
2672         mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler);
2673         mAppOpsService.startWatchingMode(AppOpsManager.OP_RUN_IN_BACKGROUND, null,
2674                 new IAppOpsCallback.Stub() {
2675                     @Override public void opChanged(int op, int uid, String packageName) {
2676                         if (op == AppOpsManager.OP_RUN_IN_BACKGROUND && packageName != null) {
2677                             if (mAppOpsService.checkOperation(op, uid, packageName)
2678                                     != AppOpsManager.MODE_ALLOWED) {
2679                                 runInBackgroundDisabled(uid);
2680                             }
2681                         }
2682                     }
2683                 });
2684
2685         mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml"));
2686
2687         mUserController = new UserController(this);
2688
2689         GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version",
2690             ConfigurationInfo.GL_ES_VERSION_UNDEFINED);
2691
2692         if (SystemProperties.getInt("sys.use_fifo_ui", 0) != 0) {
2693             mUseFifoUiScheduling = true;
2694         }
2695
2696         mTrackingAssociations = "1".equals(SystemProperties.get("debug.track-associations"));
2697
2698         mConfiguration.setToDefaults();
2699         mConfiguration.setLocales(LocaleList.getDefault());
2700
2701         mConfigurationSeq = mConfiguration.seq = 1;
2702         mProcessCpuTracker.init();
2703
2704         mCompatModePackages = new CompatModePackages(this, systemDir, mHandler);
2705         mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler);
2706         mStackSupervisor = new ActivityStackSupervisor(this);
2707         mActivityStarter = new ActivityStarter(this, mStackSupervisor);
2708         mRecentTasks = new RecentTasks(this, mStackSupervisor);
2709
2710         mProcessCpuThread = new Thread("CpuTracker") {
2711             @Override
2712             public void run() {
2713                 while (true) {
2714                     try {
2715                         try {
2716                             synchronized(this) {
2717                                 final long now = SystemClock.uptimeMillis();
2718                                 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now;
2719                                 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now;
2720                                 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay
2721                                 //        + ", write delay=" + nextWriteDelay);
2722                                 if (nextWriteDelay < nextCpuDelay) {
2723                                     nextCpuDelay = nextWriteDelay;
2724                                 }
2725                                 if (nextCpuDelay > 0) {
2726                                     mProcessCpuMutexFree.set(true);
2727                                     this.wait(nextCpuDelay);
2728                                 }
2729                             }
2730                         } catch (InterruptedException e) {
2731                         }
2732                         updateCpuStatsNow();
2733                     } catch (Exception e) {
2734                         Slog.e(TAG, "Unexpected exception collecting process stats", e);
2735                     }
2736                 }
2737             }
2738         };
2739
2740         Watchdog.getInstance().addMonitor(this);
2741         Watchdog.getInstance().addThread(mHandler);
2742     }
2743
2744     public void setSystemServiceManager(SystemServiceManager mgr) {
2745         mSystemServiceManager = mgr;
2746     }
2747
2748     public void setInstaller(Installer installer) {
2749         mInstaller = installer;
2750     }
2751
2752     private void start() {
2753         Process.removeAllProcessGroups();
2754         mProcessCpuThread.start();
2755
2756         mBatteryStatsService.publish(mContext);
2757         mAppOpsService.publish(mContext);
2758         Slog.d("AppOps", "AppOpsService published");
2759         LocalServices.addService(ActivityManagerInternal.class, new LocalService());
2760     }
2761
2762     void onUserStoppedLocked(int userId) {
2763         mRecentTasks.unloadUserDataFromMemoryLocked(userId);
2764     }
2765
2766     public void initPowerManagement() {
2767         mStackSupervisor.initPowerManagement();
2768         mBatteryStatsService.initPowerManagement();
2769         mLocalPowerManager = LocalServices.getService(PowerManagerInternal.class);
2770         PowerManager pm = (PowerManager)mContext.getSystemService(Context.POWER_SERVICE);
2771         mVoiceWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "*voice*");
2772         mVoiceWakeLock.setReferenceCounted(false);
2773     }
2774
2775     @Override
2776     public boolean onTransact(int code, Parcel data, Parcel reply, int flags)
2777             throws RemoteException {
2778         if (code == SYSPROPS_TRANSACTION) {
2779             // We need to tell all apps about the system property change.
2780             ArrayList<IBinder> procs = new ArrayList<IBinder>();
2781             synchronized(this) {
2782                 final int NP = mProcessNames.getMap().size();
2783                 for (int ip=0; ip<NP; ip++) {
2784                     SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
2785                     final int NA = apps.size();
2786                     for (int ia=0; ia<NA; ia++) {
2787                         ProcessRecord app = apps.valueAt(ia);
2788                         if (app.thread != null) {
2789                             procs.add(app.thread.asBinder());
2790                         }
2791                     }
2792                 }
2793             }
2794
2795             int N = procs.size();
2796             for (int i=0; i<N; i++) {
2797                 Parcel data2 = Parcel.obtain();
2798                 try {
2799                     procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0);
2800                 } catch (RemoteException e) {
2801                 }
2802                 data2.recycle();
2803             }
2804         }
2805         try {
2806             return super.onTransact(code, data, reply, flags);
2807         } catch (RuntimeException e) {
2808             // The activity manager only throws security exceptions, so let's
2809             // log all others.
2810             if (!(e instanceof SecurityException)) {
2811                 Slog.wtf(TAG, "Activity Manager Crash", e);
2812             }
2813             throw e;
2814         }
2815     }
2816
2817     void updateCpuStats() {
2818         final long now = SystemClock.uptimeMillis();
2819         if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) {
2820             return;
2821         }
2822         if (mProcessCpuMutexFree.compareAndSet(true, false)) {
2823             synchronized (mProcessCpuThread) {
2824                 mProcessCpuThread.notify();
2825             }
2826         }
2827     }
2828
2829     void updateCpuStatsNow() {
2830         synchronized (mProcessCpuTracker) {
2831             mProcessCpuMutexFree.set(false);
2832             final long now = SystemClock.uptimeMillis();
2833             boolean haveNewCpuStats = false;
2834
2835             if (MONITOR_CPU_USAGE &&
2836                     mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) {
2837                 mLastCpuTime.set(now);
2838                 mProcessCpuTracker.update();
2839                 if (mProcessCpuTracker.hasGoodLastStats()) {
2840                     haveNewCpuStats = true;
2841                     //Slog.i(TAG, mProcessCpu.printCurrentState());
2842                     //Slog.i(TAG, "Total CPU usage: "
2843                     //        + mProcessCpu.getTotalCpuPercent() + "%");
2844
2845                     // Slog the cpu usage if the property is set.
2846                     if ("true".equals(SystemProperties.get("events.cpu"))) {
2847                         int user = mProcessCpuTracker.getLastUserTime();
2848                         int system = mProcessCpuTracker.getLastSystemTime();
2849                         int iowait = mProcessCpuTracker.getLastIoWaitTime();
2850                         int irq = mProcessCpuTracker.getLastIrqTime();
2851                         int softIrq = mProcessCpuTracker.getLastSoftIrqTime();
2852                         int idle = mProcessCpuTracker.getLastIdleTime();
2853
2854                         int total = user + system + iowait + irq + softIrq + idle;
2855                         if (total == 0) total = 1;
2856
2857                         EventLog.writeEvent(EventLogTags.CPU,
2858                                 ((user+system+iowait+irq+softIrq) * 100) / total,
2859                                 (user * 100) / total,
2860                                 (system * 100) / total,
2861                                 (iowait * 100) / total,
2862                                 (irq * 100) / total,
2863                                 (softIrq * 100) / total);
2864                     }
2865                 }
2866             }
2867
2868             final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics();
2869             synchronized(bstats) {
2870                 synchronized(mPidsSelfLocked) {
2871                     if (haveNewCpuStats) {
2872                         if (bstats.startAddingCpuLocked()) {
2873                             int totalUTime = 0;
2874                             int totalSTime = 0;
2875                             final int N = mProcessCpuTracker.countStats();
2876                             for (int i=0; i<N; i++) {
2877                                 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i);
2878                                 if (!st.working) {
2879                                     continue;
2880                                 }
2881                                 ProcessRecord pr = mPidsSelfLocked.get(st.pid);
2882                                 totalUTime += st.rel_utime;
2883                                 totalSTime += st.rel_stime;
2884                                 if (pr != null) {
2885                                     BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats;
2886                                     if (ps == null || !ps.isActive()) {
2887                                         pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked(
2888                                                 pr.info.uid, pr.processName);
2889                                     }
2890                                     ps.addCpuTimeLocked(st.rel_utime, st.rel_stime);
2891                                     pr.curCpuTime += st.rel_utime + st.rel_stime;
2892                                 } else {
2893                                     BatteryStatsImpl.Uid.Proc ps = st.batteryStats;
2894                                     if (ps == null || !ps.isActive()) {
2895                                         st.batteryStats = ps = bstats.getProcessStatsLocked(
2896                                                 bstats.mapUid(st.uid), st.name);
2897                                     }
2898                                     ps.addCpuTimeLocked(st.rel_utime, st.rel_stime);
2899                                 }
2900                             }
2901                             final int userTime = mProcessCpuTracker.getLastUserTime();
2902                             final int systemTime = mProcessCpuTracker.getLastSystemTime();
2903                             final int iowaitTime = mProcessCpuTracker.getLastIoWaitTime();
2904                             final int irqTime = mProcessCpuTracker.getLastIrqTime();
2905                             final int softIrqTime = mProcessCpuTracker.getLastSoftIrqTime();
2906                             final int idleTime = mProcessCpuTracker.getLastIdleTime();
2907                             bstats.finishAddingCpuLocked(totalUTime, totalSTime, userTime,
2908                                     systemTime, iowaitTime, irqTime, softIrqTime, idleTime);
2909                         }
2910                     }
2911                 }
2912
2913                 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) {
2914                     mLastWriteTime = now;
2915                     mBatteryStatsService.scheduleWriteToDisk();
2916                 }
2917             }
2918         }
2919     }
2920
2921     @Override
2922     public void batteryNeedsCpuUpdate() {
2923         updateCpuStatsNow();
2924     }
2925
2926     @Override
2927     public void batteryPowerChanged(boolean onBattery) {
2928         // When plugging in, update the CPU stats first before changing
2929         // the plug state.
2930         updateCpuStatsNow();
2931         synchronized (this) {
2932             synchronized(mPidsSelfLocked) {
2933                 mOnBattery = DEBUG_POWER ? true : onBattery;
2934             }
2935         }
2936     }
2937
2938     @Override
2939     public void batterySendBroadcast(Intent intent) {
2940         broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null,
2941                 AppOpsManager.OP_NONE, null, false, false,
2942                 -1, Process.SYSTEM_UID, UserHandle.USER_ALL);
2943     }
2944
2945     /**
2946      * Initialize the application bind args. These are passed to each
2947      * process when the bindApplication() IPC is sent to the process. They're
2948      * lazily setup to make sure the services are running when they're asked for.
2949      */
2950     private HashMap<String, IBinder> getCommonServicesLocked(boolean isolated) {
2951         // Isolated processes won't get this optimization, so that we don't
2952         // violate the rules about which services they have access to.
2953         if (isolated) {
2954             if (mIsolatedAppBindArgs == null) {
2955                 mIsolatedAppBindArgs = new HashMap<>();
2956                 mIsolatedAppBindArgs.put("package", ServiceManager.getService("package"));
2957             }
2958             return mIsolatedAppBindArgs;
2959         }
2960
2961         if (mAppBindArgs == null) {
2962             mAppBindArgs = new HashMap<>();
2963
2964             // Setup the application init args
2965             mAppBindArgs.put("package", ServiceManager.getService("package"));
2966             mAppBindArgs.put("window", ServiceManager.getService("window"));
2967             mAppBindArgs.put(Context.ALARM_SERVICE,
2968                     ServiceManager.getService(Context.ALARM_SERVICE));
2969         }
2970         return mAppBindArgs;
2971     }
2972
2973     boolean setFocusedActivityLocked(ActivityRecord r, String reason) {
2974         if (r == null || mFocusedActivity == r) {
2975             return false;
2976         }
2977
2978         if (!r.isFocusable()) {
2979             if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedActivityLocked: unfocusable r=" + r);
2980             return false;
2981         }
2982
2983         if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedActivityLocked: r=" + r);
2984
2985         final boolean wasDoingSetFocusedActivity = mDoingSetFocusedActivity;
2986         if (wasDoingSetFocusedActivity) Slog.w(TAG,
2987                 "setFocusedActivityLocked: called recursively, r=" + r + ", reason=" + reason);
2988         mDoingSetFocusedActivity = true;
2989
2990         final ActivityRecord last = mFocusedActivity;
2991         mFocusedActivity = r;
2992         if (r.task.isApplicationTask()) {
2993             if (mCurAppTimeTracker != r.appTimeTracker) {
2994                 // We are switching app tracking.  Complete the current one.
2995                 if (mCurAppTimeTracker != null) {
2996                     mCurAppTimeTracker.stop();
2997                     mHandler.obtainMessage(
2998                             REPORT_TIME_TRACKER_MSG, mCurAppTimeTracker).sendToTarget();
2999                     mStackSupervisor.clearOtherAppTimeTrackers(r.appTimeTracker);
3000                     mCurAppTimeTracker = null;
3001                 }
3002                 if (r.appTimeTracker != null) {
3003                     mCurAppTimeTracker = r.appTimeTracker;
3004                     startTimeTrackingFocusedActivityLocked();
3005                 }
3006             } else {
3007                 startTimeTrackingFocusedActivityLocked();
3008             }
3009         } else {
3010             r.appTimeTracker = null;
3011         }
3012         // TODO: VI Maybe r.task.voiceInteractor || r.voiceInteractor != null
3013         // TODO: Probably not, because we don't want to resume voice on switching
3014         // back to this activity
3015         if (r.task.voiceInteractor != null) {
3016             startRunningVoiceLocked(r.task.voiceSession, r.info.applicationInfo.uid);
3017         } else {
3018             finishRunningVoiceLocked();
3019             IVoiceInteractionSession session;
3020             if (last != null && ((session = last.task.voiceSession) != null
3021                     || (session = last.voiceSession) != null)) {
3022                 // We had been in a voice interaction session, but now focused has
3023                 // move to something different.  Just finish the session, we can't
3024                 // return to it and retain the proper state and synchronization with
3025                 // the voice interaction service.
3026                 finishVoiceTask(session);
3027             }
3028         }
3029         if (mStackSupervisor.moveActivityStackToFront(r, reason + " setFocusedActivity")) {
3030             mWindowManager.setFocusedApp(r.appToken, true);
3031         }
3032         applyUpdateLockStateLocked(r);
3033         applyUpdateVrModeLocked(r);
3034         if (mFocusedActivity.userId != mLastFocusedUserId) {
3035             mHandler.removeMessages(FOREGROUND_PROFILE_CHANGED_MSG);
3036             mHandler.obtainMessage(
3037                     FOREGROUND_PROFILE_CHANGED_MSG, mFocusedActivity.userId, 0).sendToTarget();
3038             mLastFocusedUserId = mFocusedActivity.userId;
3039         }
3040
3041         // Log a warning if the focused app is changed during the process. This could
3042         // indicate a problem of the focus setting logic!
3043         if (mFocusedActivity != r) Slog.w(TAG,
3044                 "setFocusedActivityLocked: r=" + r + " but focused to " + mFocusedActivity);
3045         mDoingSetFocusedActivity = wasDoingSetFocusedActivity;
3046
3047         EventLogTags.writeAmFocusedActivity(
3048                 mFocusedActivity == null ? -1 : mFocusedActivity.userId,
3049                 mFocusedActivity == null ? "NULL" : mFocusedActivity.shortComponentName,
3050                 reason);
3051         return true;
3052     }
3053
3054     final void resetFocusedActivityIfNeededLocked(ActivityRecord goingAway) {
3055         if (mFocusedActivity != goingAway) {
3056             return;
3057         }
3058
3059         final ActivityStack focusedStack = mStackSupervisor.getFocusedStack();
3060         if (focusedStack != null) {
3061             final ActivityRecord top = focusedStack.topActivity();
3062             if (top != null && top.userId != mLastFocusedUserId) {
3063                 mHandler.removeMessages(FOREGROUND_PROFILE_CHANGED_MSG);
3064                 mHandler.sendMessage(
3065                         mHandler.obtainMessage(FOREGROUND_PROFILE_CHANGED_MSG, top.userId, 0));
3066                 mLastFocusedUserId = top.userId;
3067             }
3068         }
3069
3070         // Try to move focus to another activity if possible.
3071         if (setFocusedActivityLocked(
3072                 focusedStack.topRunningActivityLocked(), "resetFocusedActivityIfNeeded")) {
3073             return;
3074         }
3075
3076         if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "resetFocusedActivityIfNeeded: Setting focus to NULL "
3077                 + "prev mFocusedActivity=" + mFocusedActivity + " goingAway=" + goingAway);
3078         mFocusedActivity = null;
3079         EventLogTags.writeAmFocusedActivity(-1, "NULL", "resetFocusedActivityIfNeeded");
3080     }
3081
3082     @Override
3083     public void setFocusedStack(int stackId) {
3084         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedStack()");
3085         if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedStack: stackId=" + stackId);
3086         final long callingId = Binder.clearCallingIdentity();
3087         try {
3088             synchronized (this) {
3089                 final ActivityStack stack = mStackSupervisor.getStack(stackId);
3090                 if (stack == null) {
3091                     return;
3092                 }
3093                 final ActivityRecord r = stack.topRunningActivityLocked();
3094                 if (setFocusedActivityLocked(r, "setFocusedStack")) {
3095                     mStackSupervisor.resumeFocusedStackTopActivityLocked();
3096                 }
3097             }
3098         } finally {
3099             Binder.restoreCallingIdentity(callingId);
3100         }
3101     }
3102
3103     @Override
3104     public void setFocusedTask(int taskId) {
3105         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedTask()");
3106         if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedTask: taskId=" + taskId);
3107         final long callingId = Binder.clearCallingIdentity();
3108         try {
3109             synchronized (this) {
3110                 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
3111                 if (task == null) {
3112                     return;
3113                 }
3114                 if (mUserController.shouldConfirmCredentials(task.userId)) {
3115                     mActivityStarter.showConfirmDeviceCredential(task.userId);
3116                     if (task.stack != null && task.stack.mStackId == FREEFORM_WORKSPACE_STACK_ID) {
3117                         mStackSupervisor.moveTaskToStackLocked(task.taskId,
3118                                 FULLSCREEN_WORKSPACE_STACK_ID, !ON_TOP, !FORCE_FOCUS,
3119                                 "setFocusedTask", ANIMATE);
3120                     }
3121                     return;
3122                 }
3123                 final ActivityRecord r = task.topRunningActivityLocked();
3124                 if (setFocusedActivityLocked(r, "setFocusedTask")) {
3125                     mStackSupervisor.resumeFocusedStackTopActivityLocked();
3126                 }
3127             }
3128         } finally {
3129             Binder.restoreCallingIdentity(callingId);
3130         }
3131     }
3132
3133     /** Sets the task stack listener that gets callbacks when a task stack changes. */
3134     @Override
3135     public void registerTaskStackListener(ITaskStackListener listener) throws RemoteException {
3136         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "registerTaskStackListener()");
3137         synchronized (this) {
3138             if (listener != null) {
3139                 mTaskStackListeners.register(listener);
3140             }
3141         }
3142     }
3143
3144     @Override
3145     public void notifyActivityDrawn(IBinder token) {
3146         if (DEBUG_VISIBILITY) Slog.d(TAG_VISIBILITY, "notifyActivityDrawn: token=" + token);
3147         synchronized (this) {
3148             ActivityRecord r = mStackSupervisor.isInAnyStackLocked(token);
3149             if (r != null) {
3150                 r.task.stack.notifyActivityDrawnLocked(r);
3151             }
3152         }
3153     }
3154
3155     final void applyUpdateLockStateLocked(ActivityRecord r) {
3156         // Modifications to the UpdateLock state are done on our handler, outside
3157         // the activity manager's locks.  The new state is determined based on the
3158         // state *now* of the relevant activity record.  The object is passed to
3159         // the handler solely for logging detail, not to be consulted/modified.
3160         final boolean nextState = r != null && r.immersive;
3161         mHandler.sendMessage(
3162                 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r));
3163     }
3164
3165     final void applyUpdateVrModeLocked(ActivityRecord r) {
3166         mHandler.sendMessage(
3167                 mHandler.obtainMessage(VR_MODE_CHANGE_MSG, 0, 0, r));
3168     }
3169
3170     private void sendNotifyVrManagerOfSleepState(boolean isSleeping) {
3171         mHandler.sendMessage(
3172                 mHandler.obtainMessage(NOTIFY_VR_SLEEPING_MSG, isSleeping ? 1 : 0, 0));
3173     }
3174
3175     private void notifyVrManagerOfSleepState(boolean isSleeping) {
3176         final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class);
3177         if (vrService == null) {
3178             return;
3179         }
3180         vrService.onSleepStateChanged(isSleeping);
3181     }
3182
3183     final void showAskCompatModeDialogLocked(ActivityRecord r) {
3184         Message msg = Message.obtain();
3185         msg.what = SHOW_COMPAT_MODE_DIALOG_UI_MSG;
3186         msg.obj = r.task.askedCompatMode ? null : r;
3187         mUiHandler.sendMessage(msg);
3188     }
3189
3190     final void showUnsupportedZoomDialogIfNeededLocked(ActivityRecord r) {
3191         if (mConfiguration.densityDpi != DisplayMetrics.DENSITY_DEVICE_STABLE
3192                 && r.appInfo.requiresSmallestWidthDp > mConfiguration.smallestScreenWidthDp) {
3193             final Message msg = Message.obtain();
3194             msg.what = SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG;
3195             msg.obj = r;
3196             mUiHandler.sendMessage(msg);
3197         }
3198     }
3199
3200     private int updateLruProcessInternalLocked(ProcessRecord app, long now, int index,
3201             String what, Object obj, ProcessRecord srcApp) {
3202         app.lastActivityTime = now;
3203
3204         if (app.activities.size() > 0) {
3205             // Don't want to touch dependent processes that are hosting activities.
3206             return index;
3207         }
3208
3209         int lrui = mLruProcesses.lastIndexOf(app);
3210         if (lrui < 0) {
3211             Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: "
3212                     + what + " " + obj + " from " + srcApp);
3213             return index;
3214         }
3215
3216         if (lrui >= index) {
3217             // Don't want to cause this to move dependent processes *back* in the
3218             // list as if they were less frequently used.
3219             return index;
3220         }
3221
3222         if (lrui >= mLruProcessActivityStart) {
3223             // Don't want to touch dependent processes that are hosting activities.
3224             return index;
3225         }
3226
3227         mLruProcesses.remove(lrui);
3228         if (index > 0) {
3229             index--;
3230         }
3231         if (DEBUG_LRU) Slog.d(TAG_LRU, "Moving dep from " + lrui + " to " + index
3232                 + " in LRU list: " + app);
3233         mLruProcesses.add(index, app);
3234         return index;
3235     }
3236
3237     static void killProcessGroup(int uid, int pid) {
3238         if (sKillHandler != null) {
3239             sKillHandler.sendMessage(
3240                     sKillHandler.obtainMessage(KillHandler.KILL_PROCESS_GROUP_MSG, uid, pid));
3241         } else {
3242             Slog.w(TAG, "Asked to kill process group before system bringup!");
3243             Process.killProcessGroup(uid, pid);
3244         }
3245     }
3246
3247     final void removeLruProcessLocked(ProcessRecord app) {
3248         int lrui = mLruProcesses.lastIndexOf(app);
3249         if (lrui >= 0) {
3250             if (!app.killed) {
3251                 Slog.wtfStack(TAG, "Removing process that hasn't been killed: " + app);
3252                 Process.killProcessQuiet(app.pid);
3253                 killProcessGroup(app.uid, app.pid);
3254             }
3255             if (lrui <= mLruProcessActivityStart) {
3256                 mLruProcessActivityStart--;
3257             }
3258             if (lrui <= mLruProcessServiceStart) {
3259                 mLruProcessServiceStart--;
3260             }
3261             mLruProcesses.remove(lrui);
3262         }
3263     }
3264
3265     final void updateLruProcessLocked(ProcessRecord app, boolean activityChange,
3266             ProcessRecord client) {
3267         final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities
3268                 || app.treatLikeActivity;
3269         final boolean hasService = false; // not impl yet. app.services.size() > 0;
3270         if (!activityChange && hasActivity) {
3271             // The process has activities, so we are only allowing activity-based adjustments
3272             // to move it.  It should be kept in the front of the list with other
3273             // processes that have activities, and we don't want those to change their
3274             // order except due to activity operations.
3275             return;
3276         }
3277
3278         mLruSeq++;
3279         final long now = SystemClock.uptimeMillis();
3280         app.lastActivityTime = now;
3281
3282         // First a quick reject: if the app is already at the position we will
3283         // put it, then there is nothing to do.
3284         if (hasActivity) {
3285             final int N = mLruProcesses.size();
3286             if (N > 0 && mLruProcesses.get(N-1) == app) {
3287                 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top activity: " + app);
3288                 return;
3289             }
3290         } else {
3291             if (mLruProcessServiceStart > 0
3292                     && mLruProcesses.get(mLruProcessServiceStart-1) == app) {
3293                 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top other: " + app);
3294                 return;
3295             }
3296         }
3297
3298         int lrui = mLruProcesses.lastIndexOf(app);
3299
3300         if (app.persistent && lrui >= 0) {
3301             // We don't care about the position of persistent processes, as long as
3302             // they are in the list.
3303             if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, persistent: " + app);
3304             return;
3305         }
3306
3307         /* In progress: compute new position first, so we can avoid doing work
3308            if the process is not actually going to move.  Not yet working.
3309         int addIndex;
3310         int nextIndex;
3311         boolean inActivity = false, inService = false;
3312         if (hasActivity) {
3313             // Process has activities, put it at the very tipsy-top.
3314             addIndex = mLruProcesses.size();
3315             nextIndex = mLruProcessServiceStart;
3316             inActivity = true;
3317         } else if (hasService) {
3318             // Process has services, put it at the top of the service list.
3319             addIndex = mLruProcessActivityStart;
3320             nextIndex = mLruProcessServiceStart;
3321             inActivity = true;
3322             inService = true;
3323         } else  {
3324             // Process not otherwise of interest, it goes to the top of the non-service area.
3325             addIndex = mLruProcessServiceStart;
3326             if (client != null) {
3327                 int clientIndex = mLruProcesses.lastIndexOf(client);
3328                 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating "
3329                         + app);
3330                 if (clientIndex >= 0 && addIndex > clientIndex) {
3331                     addIndex = clientIndex;
3332                 }
3333             }
3334             nextIndex = addIndex > 0 ? addIndex-1 : addIndex;
3335         }
3336
3337         Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act="
3338                 + mLruProcessActivityStart + "): " + app);
3339         */
3340
3341         if (lrui >= 0) {
3342             if (lrui < mLruProcessActivityStart) {
3343                 mLruProcessActivityStart--;
3344             }
3345             if (lrui < mLruProcessServiceStart) {
3346                 mLruProcessServiceStart--;
3347             }
3348             /*
3349             if (addIndex > lrui) {
3350                 addIndex--;
3351             }
3352             if (nextIndex > lrui) {
3353                 nextIndex--;
3354             }
3355             */
3356             mLruProcesses.remove(lrui);
3357         }
3358
3359         /*
3360         mLruProcesses.add(addIndex, app);
3361         if (inActivity) {
3362             mLruProcessActivityStart++;
3363         }
3364         if (inService) {
3365             mLruProcessActivityStart++;
3366         }
3367         */
3368
3369         int nextIndex;
3370         if (hasActivity) {
3371             final int N = mLruProcesses.size();
3372             if (app.activities.size() == 0 && mLruProcessActivityStart < (N - 1)) {
3373                 // Process doesn't have activities, but has clients with
3374                 // activities...  move it up, but one below the top (the top
3375                 // should always have a real activity).
3376                 if (DEBUG_LRU) Slog.d(TAG_LRU,
3377                         "Adding to second-top of LRU activity list: " + app);
3378                 mLruProcesses.add(N - 1, app);
3379                 // To keep it from spamming the LRU list (by making a bunch of clients),
3380                 // we will push down any other entries owned by the app.
3381                 final int uid = app.info.uid;
3382                 for (int i = N - 2; i > mLruProcessActivityStart; i--) {
3383                     ProcessRecord subProc = mLruProcesses.get(i);
3384                     if (subProc.info.uid == uid) {
3385                         // We want to push this one down the list.  If the process after
3386                         // it is for the same uid, however, don't do so, because we don't
3387                         // want them internally to be re-ordered.
3388                         if (mLruProcesses.get(i - 1).info.uid != uid) {
3389                             if (DEBUG_LRU) Slog.d(TAG_LRU,
3390                                     "Pushing uid " + uid + " swapping at " + i + ": "
3391                                     + mLruProcesses.get(i) + " : " + mLruProcesses.get(i - 1));
3392                             ProcessRecord tmp = mLruProcesses.get(i);
3393                             mLruProcesses.set(i, mLruProcesses.get(i - 1));
3394                             mLruProcesses.set(i - 1, tmp);
3395                             i--;
3396                         }
3397                     } else {
3398                         // A gap, we can stop here.
3399                         break;
3400                     }
3401                 }
3402             } else {
3403                 // Process has activities, put it at the very tipsy-top.
3404                 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU activity list: " + app);
3405                 mLruProcesses.add(app);
3406             }
3407             nextIndex = mLruProcessServiceStart;
3408         } else if (hasService) {
3409             // Process has services, put it at the top of the service list.
3410             if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU service list: " + app);
3411             mLruProcesses.add(mLruProcessActivityStart, app);
3412             nextIndex = mLruProcessServiceStart;
3413             mLruProcessActivityStart++;
3414         } else  {
3415             // Process not otherwise of interest, it goes to the top of the non-service area.
3416             int index = mLruProcessServiceStart;
3417             if (client != null) {
3418                 // If there is a client, don't allow the process to be moved up higher
3419                 // in the list than that client.
3420                 int clientIndex = mLruProcesses.lastIndexOf(client);
3421                 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG_LRU, "Unknown client " + client
3422                         + " when updating " + app);
3423                 if (clientIndex <= lrui) {
3424                     // Don't allow the client index restriction to push it down farther in the
3425                     // list than it already is.
3426                     clientIndex = lrui;
3427                 }
3428                 if (clientIndex >= 0 && index > clientIndex) {
3429                     index = clientIndex;
3430                 }
3431             }
3432             if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding at " + index + " of LRU list: " + app);
3433             mLruProcesses.add(index, app);
3434             nextIndex = index-1;
3435             mLruProcessActivityStart++;
3436             mLruProcessServiceStart++;
3437         }
3438
3439         // If the app is currently using a content provider or service,
3440         // bump those processes as well.
3441         for (int j=app.connections.size()-1; j>=0; j--) {
3442             ConnectionRecord cr = app.connections.valueAt(j);
3443             if (cr.binding != null && !cr.serviceDead && cr.binding.service != null
3444                     && cr.binding.service.app != null
3445                     && cr.binding.service.app.lruSeq != mLruSeq
3446                     && !cr.binding.service.app.persistent) {
3447                 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex,
3448                         "service connection", cr, app);
3449             }
3450         }
3451         for (int j=app.conProviders.size()-1; j>=0; j--) {
3452             ContentProviderRecord cpr = app.conProviders.get(j).provider;
3453             if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) {
3454                 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex,
3455                         "provider reference", cpr, app);
3456             }
3457         }
3458     }
3459
3460     final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) {
3461         if (uid == Process.SYSTEM_UID) {
3462             // The system gets to run in any process.  If there are multiple
3463             // processes with the same uid, just pick the first (this
3464             // should never happen).
3465             SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName);
3466             if (procs == null) return null;
3467             final int procCount = procs.size();
3468             for (int i = 0; i < procCount; i++) {
3469                 final int procUid = procs.keyAt(i);
3470                 if (UserHandle.isApp(procUid) || !UserHandle.isSameUser(procUid, uid)) {
3471                     // Don't use an app process or different user process for system component.
3472                     continue;
3473                 }
3474                 return procs.valueAt(i);
3475             }
3476         }
3477         ProcessRecord proc = mProcessNames.get(processName, uid);
3478         if (false && proc != null && !keepIfLarge
3479                 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY
3480                 && proc.lastCachedPss >= 4000) {
3481             // Turn this condition on to cause killing to happen regularly, for testing.
3482             if (proc.baseProcessTracker != null) {
3483                 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss);
3484             }
3485             proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true);
3486         } else if (proc != null && !keepIfLarge
3487                 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL
3488                 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) {
3489             if (DEBUG_PSS) Slog.d(TAG_PSS, "May not keep " + proc + ": pss=" + proc.lastCachedPss);
3490             if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) {
3491                 if (proc.baseProcessTracker != null) {
3492                     proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss);
3493                 }
3494                 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true);
3495             }
3496         }
3497         return proc;
3498     }
3499
3500     void notifyPackageUse(String packageName, int reason) {
3501         IPackageManager pm = AppGlobals.getPackageManager();
3502         try {
3503             pm.notifyPackageUse(packageName, reason);
3504         } catch (RemoteException e) {
3505         }
3506     }
3507
3508     boolean isNextTransitionForward() {
3509         int transit = mWindowManager.getPendingAppTransition();
3510         return transit == TRANSIT_ACTIVITY_OPEN
3511                 || transit == TRANSIT_TASK_OPEN
3512                 || transit == TRANSIT_TASK_TO_FRONT;
3513     }
3514
3515     int startIsolatedProcess(String entryPoint, String[] entryPointArgs,
3516             String processName, String abiOverride, int uid, Runnable crashHandler) {
3517         synchronized(this) {
3518             ApplicationInfo info = new ApplicationInfo();
3519             // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid.
3520             // For isolated processes, the former contains the parent's uid and the latter the
3521             // actual uid of the isolated process.
3522             // In the special case introduced by this method (which is, starting an isolated
3523             // process directly from the SystemServer without an actual parent app process) the
3524             // closest thing to a parent's uid is SYSTEM_UID.
3525             // The only important thing here is to keep AI.uid != PR.uid, in order to trigger
3526             // the |isolated| logic in the ProcessRecord constructor.
3527             info.uid = Process.SYSTEM_UID;
3528             info.processName = processName;
3529             info.className = entryPoint;
3530             info.packageName = "android";
3531             ProcessRecord proc = startProcessLocked(processName, info /* info */,
3532                     false /* knownToBeDead */, 0 /* intentFlags */, ""  /* hostingType */,
3533                     null /* hostingName */, true /* allowWhileBooting */, true /* isolated */,
3534                     uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs,
3535                     crashHandler);
3536             return proc != null ? proc.pid : 0;
3537         }
3538     }
3539
3540     final ProcessRecord startProcessLocked(String processName,
3541             ApplicationInfo info, boolean knownToBeDead, int intentFlags,
3542             String hostingType, ComponentName hostingName, boolean allowWhileBooting,
3543             boolean isolated, boolean keepIfLarge) {
3544         return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType,
3545                 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge,
3546                 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */,
3547                 null /* crashHandler */);
3548     }
3549
3550     final ProcessRecord startProcessLocked(String processName, ApplicationInfo info,
3551             boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName,
3552             boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge,
3553             String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) {
3554         long startTime = SystemClock.elapsedRealtime();
3555         ProcessRecord app;
3556         if (!isolated) {
3557             app = getProcessRecordLocked(processName, info.uid, keepIfLarge);
3558             checkTime(startTime, "startProcess: after getProcessRecord");
3559
3560             if ((intentFlags & Intent.FLAG_FROM_BACKGROUND) != 0) {
3561                 // If we are in the background, then check to see if this process
3562                 // is bad.  If so, we will just silently fail.
3563                 if (mAppErrors.isBadProcessLocked(info)) {
3564                     if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid
3565                             + "/" + info.processName);
3566                     return null;
3567                 }
3568             } else {
3569                 // When the user is explicitly starting a process, then clear its
3570                 // crash count so that we won't make it bad until they see at
3571                 // least one crash dialog again, and make the process good again
3572                 // if it had been bad.
3573                 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid
3574                         + "/" + info.processName);
3575                 mAppErrors.resetProcessCrashTimeLocked(info);
3576                 if (mAppErrors.isBadProcessLocked(info)) {
3577                     EventLog.writeEvent(EventLogTags.AM_PROC_GOOD,
3578                             UserHandle.getUserId(info.uid), info.uid,
3579                             info.processName);
3580                     mAppErrors.clearBadProcessLocked(info);
3581                     if (app != null) {
3582                         app.bad = false;
3583                     }
3584                 }
3585             }
3586         } else {
3587             // If this is an isolated process, it can't re-use an existing process.
3588             app = null;
3589         }
3590
3591         // app launch boost for big.little configurations
3592         // use cpusets to migrate freshly launched tasks to big cores
3593         nativeMigrateToBoost();
3594         mIsBoosted = true;
3595         mBoostStartTime = SystemClock.uptimeMillis();
3596         Message msg = mHandler.obtainMessage(APP_BOOST_DEACTIVATE_MSG);
3597         mHandler.sendMessageDelayed(msg, APP_BOOST_MESSAGE_DELAY);
3598
3599         // We don't have to do anything more if:
3600         // (1) There is an existing application record; and
3601         // (2) The caller doesn't think it is dead, OR there is no thread
3602         //     object attached to it so we know it couldn't have crashed; and
3603         // (3) There is a pid assigned to it, so it is either starting or
3604         //     already running.
3605         if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "startProcess: name=" + processName
3606                 + " app=" + app + " knownToBeDead=" + knownToBeDead
3607                 + " thread=" + (app != null ? app.thread : null)
3608                 + " pid=" + (app != null ? app.pid : -1));
3609         if (app != null && app.pid > 0) {
3610             if ((!knownToBeDead && !app.killed) || app.thread == null) {
3611                 // We already have the app running, or are waiting for it to
3612                 // come up (we have a pid but not yet its thread), so keep it.
3613                 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "App already running: " + app);
3614                 // If this is a new package in the process, add the package to the list
3615                 app.addPackage(info.packageName, info.versionCode, mProcessStats);
3616                 checkTime(startTime, "startProcess: done, added package to proc");
3617                 return app;
3618             }
3619
3620             // An application record is attached to a previous process,
3621             // clean it up now.
3622             if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_PROCESSES, "App died: " + app);
3623             checkTime(startTime, "startProcess: bad proc running, killing");
3624             killProcessGroup(app.uid, app.pid);
3625             handleAppDiedLocked(app, true, true);
3626             checkTime(startTime, "startProcess: done killing old proc");
3627         }
3628
3629         String hostingNameStr = hostingName != null
3630                 ? hostingName.flattenToShortString() : null;
3631
3632         if (app == null) {
3633             checkTime(startTime, "startProcess: creating new process record");
3634             app = newProcessRecordLocked(info, processName, isolated, isolatedUid);
3635             if (app == null) {
3636                 Slog.w(TAG, "Failed making new process record for "
3637                         + processName + "/" + info.uid + " isolated=" + isolated);
3638                 return null;
3639             }
3640             app.crashHandler = crashHandler;
3641             checkTime(startTime, "startProcess: done creating new process record");
3642         } else {
3643             // If this is a new package in the process, add the package to the list
3644             app.addPackage(info.packageName, info.versionCode, mProcessStats);
3645             checkTime(startTime, "startProcess: added package to existing proc");
3646         }
3647
3648         // If the system is not ready yet, then hold off on starting this
3649         // process until it is.
3650         if (!mProcessesReady
3651                 && !isAllowedWhileBooting(info)
3652                 && !allowWhileBooting) {
3653             if (!mProcessesOnHold.contains(app)) {
3654                 mProcessesOnHold.add(app);
3655             }
3656             if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES,
3657                     "System not ready, putting on hold: " + app);
3658             checkTime(startTime, "startProcess: returning with proc on hold");
3659             return app;
3660         }
3661
3662         checkTime(startTime, "startProcess: stepping in to startProcess");
3663         startProcessLocked(
3664                 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs);
3665         checkTime(startTime, "startProcess: done starting proc!");
3666         return (app.pid != 0) ? app : null;
3667     }
3668
3669     boolean isAllowedWhileBooting(ApplicationInfo ai) {
3670         return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0;
3671     }
3672
3673     private final void startProcessLocked(ProcessRecord app,
3674             String hostingType, String hostingNameStr) {
3675         startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */,
3676                 null /* entryPoint */, null /* entryPointArgs */);
3677     }
3678
3679     private final void startProcessLocked(ProcessRecord app, String hostingType,
3680             String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) {
3681         long startTime = SystemClock.elapsedRealtime();
3682         if (app.pid > 0 && app.pid != MY_PID) {
3683             checkTime(startTime, "startProcess: removing from pids map");
3684             synchronized (mPidsSelfLocked) {
3685                 mPidsSelfLocked.remove(app.pid);
3686                 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
3687             }
3688             checkTime(startTime, "startProcess: done removing from pids map");
3689             app.setPid(0);
3690         }
3691
3692         if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES,
3693                 "startProcessLocked removing on hold: " + app);
3694         mProcessesOnHold.remove(app);
3695
3696         checkTime(startTime, "startProcess: starting to update cpu stats");
3697         updateCpuStats();
3698         checkTime(startTime, "startProcess: done updating cpu stats");
3699
3700         try {
3701             try {
3702                 final int userId = UserHandle.getUserId(app.uid);
3703                 AppGlobals.getPackageManager().checkPackageStartable(app.info.packageName, userId);
3704             } catch (RemoteException e) {
3705                 throw e.rethrowAsRuntimeException();
3706             }
3707
3708             int uid = app.uid;
3709             int[] gids = null;
3710             int mountExternal = Zygote.MOUNT_EXTERNAL_NONE;
3711             if (!app.isolated) {
3712                 int[] permGids = null;
3713                 try {
3714                     checkTime(startTime, "startProcess: getting gids from package manager");
3715                     final IPackageManager pm = AppGlobals.getPackageManager();
3716                     permGids = pm.getPackageGids(app.info.packageName,
3717                             MATCH_DEBUG_TRIAGED_MISSING, app.userId);
3718                     MountServiceInternal mountServiceInternal = LocalServices.getService(
3719                             MountServiceInternal.class);
3720                     mountExternal = mountServiceInternal.getExternalStorageMountMode(uid,
3721                             app.info.packageName);
3722                 } catch (RemoteException e) {
3723                     throw e.rethrowAsRuntimeException();
3724                 }
3725
3726                 /*
3727                  * Add shared application and profile GIDs so applications can share some
3728                  * resources like shared libraries and access user-wide resources
3729                  */
3730                 if (ArrayUtils.isEmpty(permGids)) {
3731                     gids = new int[2];
3732                 } else {
3733                     gids = new int[permGids.length + 2];
3734                     System.arraycopy(permGids, 0, gids, 2, permGids.length);
3735                 }
3736                 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid));
3737                 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid));
3738             }
3739             checkTime(startTime, "startProcess: building args");
3740             if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) {
3741                 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL
3742                         && mTopComponent != null
3743                         && app.processName.equals(mTopComponent.getPackageName())) {
3744                     uid = 0;
3745                 }
3746                 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL
3747                         && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) {
3748                     uid = 0;
3749                 }
3750             }
3751             int debugFlags = 0;
3752             if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) {
3753                 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER;
3754                 // Also turn on CheckJNI for debuggable apps. It's quite
3755                 // awkward to turn on otherwise.
3756                 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI;
3757             }
3758             // Run the app in safe mode if its manifest requests so or the
3759             // system is booted in safe mode.
3760             if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 ||
3761                 mSafeMode == true) {
3762                 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE;
3763             }
3764             if ("1".equals(SystemProperties.get("debug.checkjni"))) {
3765                 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI;
3766             }
3767             String genDebugInfoProperty = SystemProperties.get("debug.generate-debug-info");
3768             if ("true".equals(genDebugInfoProperty)) {
3769                 debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO;
3770             }
3771             if ("1".equals(SystemProperties.get("debug.jni.logging"))) {
3772                 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING;
3773             }
3774             if ("1".equals(SystemProperties.get("debug.assert"))) {
3775                 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT;
3776             }
3777             if (mNativeDebuggingApp != null && mNativeDebuggingApp.equals(app.processName)) {
3778                 // Enable all debug flags required by the native debugger.
3779                 debugFlags |= Zygote.DEBUG_ALWAYS_JIT;          // Don't interpret anything
3780                 debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; // Generate debug info
3781                 debugFlags |= Zygote.DEBUG_NATIVE_DEBUGGABLE;   // Disbale optimizations
3782                 mNativeDebuggingApp = null;
3783             }
3784
3785             String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi;
3786             if (requiredAbi == null) {
3787                 requiredAbi = Build.SUPPORTED_ABIS[0];
3788             }
3789
3790             String instructionSet = null;
3791             if (app.info.primaryCpuAbi != null) {
3792                 instructionSet = VMRuntime.getInstructionSet(app.info.primaryCpuAbi);
3793             }
3794
3795             app.gids = gids;
3796             app.requiredAbi = requiredAbi;
3797             app.instructionSet = instructionSet;
3798
3799             // Start the process.  It will either succeed and return a result containing
3800             // the PID of the new process, or else throw a RuntimeException.
3801             boolean isActivityProcess = (entryPoint == null);
3802             if (entryPoint == null) entryPoint = "android.app.ActivityThread";
3803             Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " +
3804                     app.processName);
3805             checkTime(startTime, "startProcess: asking zygote to start proc");
3806             Process.ProcessStartResult startResult = Process.start(entryPoint,
3807                     app.processName, uid, uid, gids, debugFlags, mountExternal,
3808                     app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet,
3809                     app.info.dataDir, entryPointArgs);
3810             checkTime(startTime, "startProcess: returned from zygote!");
3811             Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
3812
3813             mBatteryStatsService.noteProcessStart(app.processName, app.info.uid);
3814             checkTime(startTime, "startProcess: done updating battery stats");
3815
3816             EventLog.writeEvent(EventLogTags.AM_PROC_START,
3817                     UserHandle.getUserId(uid), startResult.pid, uid,
3818                     app.processName, hostingType,
3819                     hostingNameStr != null ? hostingNameStr : "");
3820
3821             try {
3822                 AppGlobals.getPackageManager().logAppProcessStartIfNeeded(app.processName, app.uid,
3823                         app.info.seinfo, app.info.sourceDir, startResult.pid);
3824             } catch (RemoteException ex) {
3825                 // Ignore
3826             }
3827
3828             if (app.persistent) {
3829                 Watchdog.getInstance().processStarted(app.processName, startResult.pid);
3830             }
3831
3832             checkTime(startTime, "startProcess: building log message");
3833             StringBuilder buf = mStringBuilder;
3834             buf.setLength(0);
3835             buf.append("Start proc ");
3836             buf.append(startResult.pid);
3837             buf.append(':');
3838             buf.append(app.processName);
3839             buf.append('/');
3840             UserHandle.formatUid(buf, uid);
3841             if (!isActivityProcess) {
3842                 buf.append(" [");
3843                 buf.append(entryPoint);
3844                 buf.append("]");
3845             }
3846             buf.append(" for ");
3847             buf.append(hostingType);
3848             if (hostingNameStr != null) {
3849                 buf.append(" ");
3850                 buf.append(hostingNameStr);
3851             }
3852             Slog.i(TAG, buf.toString());
3853             app.setPid(startResult.pid);
3854             app.usingWrapper = startResult.usingWrapper;
3855             app.removed = false;
3856             app.killed = false;
3857             app.killedByAm = false;
3858             checkTime(startTime, "startProcess: starting to update pids map");
3859             ProcessRecord oldApp;
3860             synchronized (mPidsSelfLocked) {
3861                 oldApp = mPidsSelfLocked.get(startResult.pid);
3862             }
3863             // If there is already an app occupying that pid that hasn't been cleaned up
3864             if (oldApp != null && !app.isolated) {
3865                 // Clean up anything relating to this pid first
3866                 Slog.w(TAG, "Reusing pid " + startResult.pid
3867                         + " while app is still mapped to it");
3868                 cleanUpApplicationRecordLocked(oldApp, false, false, -1,
3869                         true /*replacingPid*/);
3870             }
3871             synchronized (mPidsSelfLocked) {
3872                 this.mPidsSelfLocked.put(startResult.pid, app);
3873                 if (isActivityProcess) {
3874                     Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG);
3875                     msg.obj = app;
3876                     mHandler.sendMessageDelayed(msg, startResult.usingWrapper
3877                             ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT);
3878                 }
3879             }
3880             checkTime(startTime, "startProcess: done updating pids map");
3881         } catch (RuntimeException e) {
3882             Slog.e(TAG, "Failure starting process " + app.processName, e);
3883
3884             // Something went very wrong while trying to start this process; one
3885             // common case is when the package is frozen due to an active
3886             // upgrade. To recover, clean up any active bookkeeping related to
3887             // starting this process. (We already invoked this method once when
3888             // the package was initially frozen through KILL_APPLICATION_MSG, so
3889             // it doesn't hurt to use it again.)
3890             forceStopPackageLocked(app.info.packageName, UserHandle.getAppId(app.uid), false,
3891                     false, true, false, false, UserHandle.getUserId(app.userId), "start failure");
3892         }
3893     }
3894
3895     void updateUsageStats(ActivityRecord component, boolean resumed) {
3896         if (DEBUG_SWITCH) Slog.d(TAG_SWITCH,
3897                 "updateUsageStats: comp=" + component + "res=" + resumed);
3898         final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
3899         if (resumed) {
3900             if (mUsageStatsService != null) {
3901                 mUsageStatsService.reportEvent(component.realActivity, component.userId,
3902                         UsageEvents.Event.MOVE_TO_FOREGROUND);
3903             }
3904             synchronized (stats) {
3905                 stats.noteActivityResumedLocked(component.app.uid);
3906             }
3907         } else {
3908             if (mUsageStatsService != null) {
3909                 mUsageStatsService.reportEvent(component.realActivity, component.userId,
3910                         UsageEvents.Event.MOVE_TO_BACKGROUND);
3911             }
3912             synchronized (stats) {
3913                 stats.noteActivityPausedLocked(component.app.uid);
3914             }
3915         }
3916     }
3917
3918     Intent getHomeIntent() {
3919         Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
3920         intent.setComponent(mTopComponent);
3921         intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING);
3922         if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
3923             intent.addCategory(Intent.CATEGORY_HOME);
3924         }
3925         return intent;
3926     }
3927
3928     boolean startHomeActivityLocked(int userId, String reason) {
3929         if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL
3930                 && mTopAction == null) {
3931             // We are running in factory test mode, but unable to find
3932             // the factory test app, so just sit around displaying the
3933             // error message and don't try to start anything.
3934             return false;
3935         }
3936         Intent intent = getHomeIntent();
3937         ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId);
3938         if (aInfo != null) {
3939             intent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name));
3940             // Don't do this if the home app is currently being
3941             // instrumented.
3942             aInfo = new ActivityInfo(aInfo);
3943             aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId);
3944             ProcessRecord app = getProcessRecordLocked(aInfo.processName,
3945                     aInfo.applicationInfo.uid, true);
3946             if (app == null || app.instrumentationClass == null) {
3947                 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK);
3948                 mActivityStarter.startHomeActivityLocked(intent, aInfo, reason);
3949             }
3950         } else {
3951             Slog.wtf(TAG, "No home screen found for " + intent, new Throwable());
3952         }
3953
3954         return true;
3955     }
3956
3957     private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) {
3958         ActivityInfo ai = null;
3959         ComponentName comp = intent.getComponent();
3960         try {
3961             if (comp != null) {
3962                 // Factory test.
3963                 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId);
3964             } else {
3965                 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent(
3966                         intent,
3967                         intent.resolveTypeIfNeeded(mContext.getContentResolver()),
3968                         flags, userId);
3969
3970                 if (info != null) {
3971                     ai = info.activityInfo;
3972                 }
3973             }
3974         } catch (RemoteException e) {
3975             // ignore
3976         }
3977
3978         return ai;
3979     }
3980
3981     /**
3982      * Starts the "new version setup screen" if appropriate.
3983      */
3984     void startSetupActivityLocked() {
3985         // Only do this once per boot.
3986         if (mCheckedForSetup) {
3987             return;
3988         }
3989
3990         // We will show this screen if the current one is a different
3991         // version than the last one shown, and we are not running in
3992         // low-level factory test mode.
3993         final ContentResolver resolver = mContext.getContentResolver();
3994         if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL &&
3995                 Settings.Global.getInt(resolver,
3996                         Settings.Global.DEVICE_PROVISIONED, 0) != 0) {
3997             mCheckedForSetup = true;
3998
3999             // See if we should be showing the platform update setup UI.
4000             final Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP);
4001             final List<ResolveInfo> ris = mContext.getPackageManager().queryIntentActivities(intent,
4002                     PackageManager.MATCH_SYSTEM_ONLY | PackageManager.GET_META_DATA);
4003             if (!ris.isEmpty()) {
4004                 final ResolveInfo ri = ris.get(0);
4005                 String vers = ri.activityInfo.metaData != null
4006                         ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION)
4007                         : null;
4008                 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) {
4009                     vers = ri.activityInfo.applicationInfo.metaData.getString(
4010                             Intent.METADATA_SETUP_VERSION);
4011                 }
4012                 String lastVers = Settings.Secure.getString(
4013                         resolver, Settings.Secure.LAST_SETUP_SHOWN);
4014                 if (vers != null && !vers.equals(lastVers)) {
4015                     intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
4016                     intent.setComponent(new ComponentName(
4017                             ri.activityInfo.packageName, ri.activityInfo.name));
4018                     mActivityStarter.startActivityLocked(null, intent, null /*ephemeralIntent*/,
4019                             null, ri.activityInfo, null /*rInfo*/, null, null, null, null, 0, 0, 0,
4020                             null, 0, 0, 0, null, false, false, null, null, null);
4021                 }
4022             }
4023         }
4024     }
4025
4026     CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) {
4027         return mCompatModePackages.compatibilityInfoForPackageLocked(ai);
4028     }
4029
4030     void enforceNotIsolatedCaller(String caller) {
4031         if (UserHandle.isIsolated(Binder.getCallingUid())) {
4032             throw new SecurityException("Isolated process not allowed to call " + caller);
4033         }
4034     }
4035
4036     void enforceShellRestriction(String restriction, int userHandle) {
4037         if (Binder.getCallingUid() == Process.SHELL_UID) {
4038             if (userHandle < 0 || mUserController.hasUserRestriction(restriction, userHandle)) {
4039                 throw new SecurityException("Shell does not have permission to access user "
4040                         + userHandle);
4041             }
4042         }
4043     }
4044
4045     @Override
4046     public int getFrontActivityScreenCompatMode() {
4047         enforceNotIsolatedCaller("getFrontActivityScreenCompatMode");
4048         synchronized (this) {
4049             return mCompatModePackages.getFrontActivityScreenCompatModeLocked();
4050         }
4051     }
4052
4053     @Override
4054     public void setFrontActivityScreenCompatMode(int mode) {
4055         enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4056                 "setFrontActivityScreenCompatMode");
4057         synchronized (this) {
4058             mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode);
4059         }
4060     }
4061
4062     @Override
4063     public int getPackageScreenCompatMode(String packageName) {
4064         enforceNotIsolatedCaller("getPackageScreenCompatMode");
4065         synchronized (this) {
4066             return mCompatModePackages.getPackageScreenCompatModeLocked(packageName);
4067         }
4068     }
4069
4070     @Override
4071     public void setPackageScreenCompatMode(String packageName, int mode) {
4072         enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4073                 "setPackageScreenCompatMode");
4074         synchronized (this) {
4075             mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode);
4076         }
4077     }
4078
4079     @Override
4080     public boolean getPackageAskScreenCompat(String packageName) {
4081         enforceNotIsolatedCaller("getPackageAskScreenCompat");
4082         synchronized (this) {
4083             return mCompatModePackages.getPackageAskCompatModeLocked(packageName);
4084         }
4085     }
4086
4087     @Override
4088     public void setPackageAskScreenCompat(String packageName, boolean ask) {
4089         enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY,
4090                 "setPackageAskScreenCompat");
4091         synchronized (this) {
4092             mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask);
4093         }
4094     }
4095
4096     private boolean hasUsageStatsPermission(String callingPackage) {
4097         final int mode = mAppOpsService.checkOperation(AppOpsManager.OP_GET_USAGE_STATS,
4098                 Binder.getCallingUid(), callingPackage);
4099         if (mode == AppOpsManager.MODE_DEFAULT) {
4100             return checkCallingPermission(Manifest.permission.PACKAGE_USAGE_STATS)
4101                     == PackageManager.PERMISSION_GRANTED;
4102         }
4103         return mode == AppOpsManager.MODE_ALLOWED;
4104     }
4105
4106     @Override
4107     public int getPackageProcessState(String packageName, String callingPackage) {
4108         if (!hasUsageStatsPermission(callingPackage)) {
4109             enforceCallingPermission(android.Manifest.permission.GET_PACKAGE_IMPORTANCE,
4110                     "getPackageProcessState");
4111         }
4112
4113         int procState = ActivityManager.PROCESS_STATE_NONEXISTENT;
4114         synchronized (this) {
4115             for (int i=mLruProcesses.size()-1; i>=0; i--) {
4116                 final ProcessRecord proc = mLruProcesses.get(i);
4117                 if (procState == ActivityManager.PROCESS_STATE_NONEXISTENT
4118                         || procState > proc.setProcState) {
4119                     boolean found = false;
4120                     for (int j=proc.pkgList.size()-1; j>=0 && !found; j--) {
4121                         if (proc.pkgList.keyAt(j).equals(packageName)) {
4122                             procState = proc.setProcState;
4123                             found = true;
4124                         }
4125                     }
4126                     if (proc.pkgDeps != null && !found) {
4127                         for (int j=proc.pkgDeps.size()-1; j>=0; j--) {
4128                             if (proc.pkgDeps.valueAt(j).equals(packageName)) {
4129                                 procState = proc.setProcState;
4130                                 break;
4131                             }
4132                         }
4133                     }
4134                 }
4135             }
4136         }
4137         return procState;
4138     }
4139
4140     @Override
4141     public boolean setProcessMemoryTrimLevel(String process, int userId, int level) {
4142         synchronized (this) {
4143             final ProcessRecord app = findProcessLocked(process, userId, "setProcessMemoryTrimLevel");
4144             if (app == null) {
4145                 return false;
4146             }
4147             if (app.trimMemoryLevel < level && app.thread != null &&
4148                     (level < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN ||
4149                             app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND)) {
4150                 try {
4151                     app.thread.scheduleTrimMemory(level);
4152                     app.trimMemoryLevel = level;
4153                     return true;
4154                 } catch (RemoteException e) {
4155                     // Fallthrough to failure case.
4156                 }
4157             }
4158         }
4159         return false;
4160     }
4161
4162     private void dispatchProcessesChanged() {
4163         int N;
4164         synchronized (this) {
4165             N = mPendingProcessChanges.size();
4166             if (mActiveProcessChanges.length < N) {
4167                 mActiveProcessChanges = new ProcessChangeItem[N];
4168             }
4169             mPendingProcessChanges.toArray(mActiveProcessChanges);
4170             mPendingProcessChanges.clear();
4171             if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
4172                     "*** Delivering " + N + " process changes");
4173         }
4174
4175         int i = mProcessObservers.beginBroadcast();
4176         while (i > 0) {
4177             i--;
4178             final IProcessObserver observer = mProcessObservers.getBroadcastItem(i);
4179             if (observer != null) {
4180                 try {
4181                     for (int j=0; j<N; j++) {
4182                         ProcessChangeItem item = mActiveProcessChanges[j];
4183                         if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) {
4184                             if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
4185                                     "ACTIVITIES CHANGED pid=" + item.pid + " uid="
4186                                     + item.uid + ": " + item.foregroundActivities);
4187                             observer.onForegroundActivitiesChanged(item.pid, item.uid,
4188                                     item.foregroundActivities);
4189                         }
4190                         if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) {
4191                             if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
4192                                     "PROCSTATE CHANGED pid=" + item.pid + " uid=" + item.uid
4193                                     + ": " + item.processState);
4194                             observer.onProcessStateChanged(item.pid, item.uid, item.processState);
4195                         }
4196                     }
4197                 } catch (RemoteException e) {
4198                 }
4199             }
4200         }
4201         mProcessObservers.finishBroadcast();
4202
4203         synchronized (this) {
4204             for (int j=0; j<N; j++) {
4205                 mAvailProcessChanges.add(mActiveProcessChanges[j]);
4206             }
4207         }
4208     }
4209
4210     private void dispatchProcessDied(int pid, int uid) {
4211         int i = mProcessObservers.beginBroadcast();
4212         while (i > 0) {
4213             i--;
4214             final IProcessObserver observer = mProcessObservers.getBroadcastItem(i);
4215             if (observer != null) {
4216                 try {
4217                     observer.onProcessDied(pid, uid);
4218                 } catch (RemoteException e) {
4219                 }
4220             }
4221         }
4222         mProcessObservers.finishBroadcast();
4223     }
4224
4225     private void dispatchUidsChanged() {
4226         int N;
4227         synchronized (this) {
4228             N = mPendingUidChanges.size();
4229             if (mActiveUidChanges.length < N) {
4230                 mActiveUidChanges = new UidRecord.ChangeItem[N];
4231             }
4232             for (int i=0; i<N; i++) {
4233                 final UidRecord.ChangeItem change = mPendingUidChanges.get(i);
4234                 mActiveUidChanges[i] = change;
4235                 if (change.uidRecord != null) {
4236                     change.uidRecord.pendingChange = null;
4237                     change.uidRecord = null;
4238                 }
4239             }
4240             mPendingUidChanges.clear();
4241             if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
4242                     "*** Delivering " + N + " uid changes");
4243         }
4244
4245         if (mLocalPowerManager != null) {
4246             for (int j=0; j<N; j++) {
4247                 UidRecord.ChangeItem item = mActiveUidChanges[j];
4248                 if (item.change == UidRecord.CHANGE_GONE
4249                         || item.change == UidRecord.CHANGE_GONE_IDLE) {
4250                     mLocalPowerManager.uidGone(item.uid);
4251                 } else {
4252                     mLocalPowerManager.updateUidProcState(item.uid, item.processState);
4253                 }
4254             }
4255         }
4256
4257         int i = mUidObservers.beginBroadcast();
4258         while (i > 0) {
4259             i--;
4260             final IUidObserver observer = mUidObservers.getBroadcastItem(i);
4261             final int which = (Integer)mUidObservers.getBroadcastCookie(i);
4262             if (observer != null) {
4263                 try {
4264                     for (int j=0; j<N; j++) {
4265                         UidRecord.ChangeItem item = mActiveUidChanges[j];
4266                         final int change = item.change;
4267                         UidRecord validateUid = null;
4268                         if (VALIDATE_UID_STATES && i == 0) {
4269                             validateUid = mValidateUids.get(item.uid);
4270                             if (validateUid == null && change != UidRecord.CHANGE_GONE
4271                                     && change != UidRecord.CHANGE_GONE_IDLE) {
4272                                 validateUid = new UidRecord(item.uid);
4273                                 mValidateUids.put(item.uid, validateUid);
4274                             }
4275                         }
4276                         if (change == UidRecord.CHANGE_IDLE
4277                                 || change == UidRecord.CHANGE_GONE_IDLE) {
4278                             if ((which & ActivityManager.UID_OBSERVER_IDLE) != 0) {
4279                                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
4280                                         "UID idle uid=" + item.uid);
4281                                 observer.onUidIdle(item.uid);
4282                             }
4283                             if (VALIDATE_UID_STATES && i == 0) {
4284                                 if (validateUid != null) {
4285                                     validateUid.idle = true;
4286                                 }
4287                             }
4288                         } else if (change == UidRecord.CHANGE_ACTIVE) {
4289                             if ((which & ActivityManager.UID_OBSERVER_ACTIVE) != 0) {
4290                                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
4291                                         "UID active uid=" + item.uid);
4292                                 observer.onUidActive(item.uid);
4293                             }
4294                             if (VALIDATE_UID_STATES && i == 0) {
4295                                 validateUid.idle = false;
4296                             }
4297                         }
4298                         if (change == UidRecord.CHANGE_GONE
4299                                 || change == UidRecord.CHANGE_GONE_IDLE) {
4300                             if ((which & ActivityManager.UID_OBSERVER_GONE) != 0) {
4301                                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
4302                                         "UID gone uid=" + item.uid);
4303                                 observer.onUidGone(item.uid);
4304                             }
4305                             if (VALIDATE_UID_STATES && i == 0) {
4306                                 if (validateUid != null) {
4307                                     mValidateUids.remove(item.uid);
4308                                 }
4309                             }
4310                         } else {
4311                             if ((which & ActivityManager.UID_OBSERVER_PROCSTATE) != 0) {
4312                                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
4313                                         "UID CHANGED uid=" + item.uid
4314                                                 + ": " + item.processState);
4315                                 observer.onUidStateChanged(item.uid, item.processState);
4316                             }
4317                             if (VALIDATE_UID_STATES && i == 0) {
4318                                 validateUid.curProcState = validateUid.setProcState
4319                                         = item.processState;
4320                             }
4321                         }
4322                     }
4323                 } catch (RemoteException e) {
4324                 }
4325             }
4326         }
4327         mUidObservers.finishBroadcast();
4328
4329         synchronized (this) {
4330             for (int j=0; j<N; j++) {
4331                 mAvailUidChanges.add(mActiveUidChanges[j]);
4332             }
4333         }
4334     }
4335
4336     @Override
4337     public final int startActivity(IApplicationThread caller, String callingPackage,
4338             Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
4339             int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) {
4340         return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
4341                 resultWho, requestCode, startFlags, profilerInfo, bOptions,
4342                 UserHandle.getCallingUserId());
4343     }
4344
4345     final int startActivity(Intent intent, ActivityStackSupervisor.ActivityContainer container) {
4346         enforceNotIsolatedCaller("ActivityContainer.startActivity");
4347         final int userId = mUserController.handleIncomingUser(Binder.getCallingPid(),
4348                 Binder.getCallingUid(), mStackSupervisor.mCurrentUser, false,
4349                 ActivityManagerService.ALLOW_FULL_ONLY, "ActivityContainer", null);
4350
4351         // TODO: Switch to user app stacks here.
4352         String mimeType = intent.getType();
4353         final Uri data = intent.getData();
4354         if (mimeType == null && data != null && "content".equals(data.getScheme())) {
4355             mimeType = getProviderMimeType(data, userId);
4356         }
4357         container.checkEmbeddedAllowedInner(userId, intent, mimeType);
4358
4359         intent.addFlags(FORCE_NEW_TASK_FLAGS);
4360         return mActivityStarter.startActivityMayWait(null, -1, null, intent, mimeType, null, null, null,
4361                 null, 0, 0, null, null, null, null, false, userId, container, null);
4362     }
4363
4364     @Override
4365     public final int startActivityAsUser(IApplicationThread caller, String callingPackage,
4366             Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
4367             int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) {
4368         enforceNotIsolatedCaller("startActivity");
4369         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
4370                 userId, false, ALLOW_FULL_ONLY, "startActivity", null);
4371         // TODO: Switch to user app stacks here.
4372         return mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent,
4373                 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags,
4374                 profilerInfo, null, null, bOptions, false, userId, null, null);
4375     }
4376
4377     @Override
4378     public final int startActivityAsCaller(IApplicationThread caller, String callingPackage,
4379             Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
4380             int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, boolean ignoreTargetSecurity,
4381             int userId) {
4382
4383         // This is very dangerous -- it allows you to perform a start activity (including
4384         // permission grants) as any app that may launch one of your own activities.  So
4385         // we will only allow this to be done from activities that are part of the core framework,
4386         // and then only when they are running as the system.
4387         final ActivityRecord sourceRecord;
4388         final int targetUid;
4389         final String targetPackage;
4390         synchronized (this) {
4391             if (resultTo == null) {
4392                 throw new SecurityException("Must be called from an activity");
4393             }
4394             sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo);
4395             if (sourceRecord == null) {
4396                 throw new SecurityException("Called with bad activity token: " + resultTo);
4397             }
4398             if (!sourceRecord.info.packageName.equals("android")) {
4399                 throw new SecurityException(
4400                         "Must be called from an activity that is declared in the android package");
4401             }
4402             if (sourceRecord.app == null) {
4403                 throw new SecurityException("Called without a process attached to activity");
4404             }
4405             if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) {
4406                 // This is still okay, as long as this activity is running under the
4407                 // uid of the original calling activity.
4408                 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) {
4409                     throw new SecurityException(
4410                             "Calling activity in uid " + sourceRecord.app.uid
4411                                     + " must be system uid or original calling uid "
4412                                     + sourceRecord.launchedFromUid);
4413                 }
4414             }
4415             if (ignoreTargetSecurity) {
4416                 if (intent.getComponent() == null) {
4417                     throw new SecurityException(
4418                             "Component must be specified with ignoreTargetSecurity");
4419                 }
4420                 if (intent.getSelector() != null) {
4421                     throw new SecurityException(
4422                             "Selector not allowed with ignoreTargetSecurity");
4423                 }
4424             }
4425             targetUid = sourceRecord.launchedFromUid;
4426             targetPackage = sourceRecord.launchedFromPackage;
4427         }
4428
4429         if (userId == UserHandle.USER_NULL) {
4430             userId = UserHandle.getUserId(sourceRecord.app.uid);
4431         }
4432
4433         // TODO: Switch to user app stacks here.
4434         try {
4435             int ret = mActivityStarter.startActivityMayWait(null, targetUid, targetPackage, intent,
4436                     resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null,
4437                     null, null, bOptions, ignoreTargetSecurity, userId, null, null);
4438             return ret;
4439         } catch (SecurityException e) {
4440             // XXX need to figure out how to propagate to original app.
4441             // A SecurityException here is generally actually a fault of the original
4442             // calling activity (such as a fairly granting permissions), so propagate it
4443             // back to them.
4444             /*
4445             StringBuilder msg = new StringBuilder();
4446             msg.append("While launching");
4447             msg.append(intent.toString());
4448             msg.append(": ");
4449             msg.append(e.getMessage());
4450             */
4451             throw e;
4452         }
4453     }
4454
4455     @Override
4456     public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage,
4457             Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
4458             int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) {
4459         enforceNotIsolatedCaller("startActivityAndWait");
4460         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
4461                 userId, false, ALLOW_FULL_ONLY, "startActivityAndWait", null);
4462         WaitResult res = new WaitResult();
4463         // TODO: Switch to user app stacks here.
4464         mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType,
4465                 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null,
4466                 bOptions, false, userId, null, null);
4467         return res;
4468     }
4469
4470     @Override
4471     public final int startActivityWithConfig(IApplicationThread caller, String callingPackage,
4472             Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
4473             int startFlags, Configuration config, Bundle bOptions, int userId) {
4474         enforceNotIsolatedCaller("startActivityWithConfig");
4475         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
4476                 userId, false, ALLOW_FULL_ONLY, "startActivityWithConfig", null);
4477         // TODO: Switch to user app stacks here.
4478         int ret = mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent,
4479                 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags,
4480                 null, null, config, bOptions, false, userId, null, null);
4481         return ret;
4482     }
4483
4484     @Override
4485     public int startActivityIntentSender(IApplicationThread caller, IntentSender intent,
4486             Intent fillInIntent, String resolvedType, IBinder resultTo, String resultWho,
4487             int requestCode, int flagsMask, int flagsValues, Bundle bOptions)
4488             throws TransactionTooLargeException {
4489         enforceNotIsolatedCaller("startActivityIntentSender");
4490         // Refuse possible leaked file descriptors
4491         if (fillInIntent != null && fillInIntent.hasFileDescriptors()) {
4492             throw new IllegalArgumentException("File descriptors passed in Intent");
4493         }
4494
4495         IIntentSender sender = intent.getTarget();
4496         if (!(sender instanceof PendingIntentRecord)) {
4497             throw new IllegalArgumentException("Bad PendingIntent object");
4498         }
4499
4500         PendingIntentRecord pir = (PendingIntentRecord)sender;
4501
4502         synchronized (this) {
4503             // If this is coming from the currently resumed activity, it is
4504             // effectively saying that app switches are allowed at this point.
4505             final ActivityStack stack = getFocusedStack();
4506             if (stack.mResumedActivity != null &&
4507                     stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) {
4508                 mAppSwitchesAllowedTime = 0;
4509             }
4510         }
4511         int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null,
4512                 resultTo, resultWho, requestCode, flagsMask, flagsValues, bOptions, null);
4513         return ret;
4514     }
4515
4516     @Override
4517     public int startVoiceActivity(String callingPackage, int callingPid, int callingUid,
4518             Intent intent, String resolvedType, IVoiceInteractionSession session,
4519             IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo,
4520             Bundle bOptions, int userId) {
4521         if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION)
4522                 != PackageManager.PERMISSION_GRANTED) {
4523             String msg = "Permission Denial: startVoiceActivity() from pid="
4524                     + Binder.getCallingPid()
4525                     + ", uid=" + Binder.getCallingUid()
4526                     + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION;
4527             Slog.w(TAG, msg);
4528             throw new SecurityException(msg);
4529         }
4530         if (session == null || interactor == null) {
4531             throw new NullPointerException("null session or interactor");
4532         }
4533         userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false,
4534                 ALLOW_FULL_ONLY, "startVoiceActivity", null);
4535         // TODO: Switch to user app stacks here.
4536         return mActivityStarter.startActivityMayWait(null, callingUid, callingPackage, intent,
4537                 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null,
4538                 null, bOptions, false, userId, null, null);
4539     }
4540
4541     @Override
4542     public void startLocalVoiceInteraction(IBinder callingActivity, Bundle options)
4543             throws RemoteException {
4544         Slog.i(TAG, "Activity tried to startVoiceInteraction");
4545         synchronized (this) {
4546             ActivityRecord activity = getFocusedStack().topActivity();
4547             if (ActivityRecord.forTokenLocked(callingActivity) != activity) {
4548                 throw new SecurityException("Only focused activity can call startVoiceInteraction");
4549             }
4550             if (mRunningVoice != null || activity.task.voiceSession != null
4551                     || activity.voiceSession != null) {
4552                 Slog.w(TAG, "Already in a voice interaction, cannot start new voice interaction");
4553                 return;
4554             }
4555             if (activity.pendingVoiceInteractionStart) {
4556                 Slog.w(TAG, "Pending start of voice interaction already.");
4557                 return;
4558             }
4559             activity.pendingVoiceInteractionStart = true;
4560         }
4561         LocalServices.getService(VoiceInteractionManagerInternal.class)
4562                 .startLocalVoiceInteraction(callingActivity, options);
4563     }
4564
4565     @Override
4566     public void stopLocalVoiceInteraction(IBinder callingActivity) throws RemoteException {
4567         LocalServices.getService(VoiceInteractionManagerInternal.class)
4568                 .stopLocalVoiceInteraction(callingActivity);
4569     }
4570
4571     @Override
4572     public boolean supportsLocalVoiceInteraction() throws RemoteException {
4573         return LocalServices.getService(VoiceInteractionManagerInternal.class)
4574                 .supportsLocalVoiceInteraction();
4575     }
4576
4577     void onLocalVoiceInteractionStartedLocked(IBinder activity,
4578             IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
4579         ActivityRecord activityToCallback = ActivityRecord.forTokenLocked(activity);
4580         if (activityToCallback == null) return;
4581         activityToCallback.setVoiceSessionLocked(voiceSession);
4582
4583         // Inform the activity
4584         try {
4585             activityToCallback.app.thread.scheduleLocalVoiceInteractionStarted(activity,
4586                     voiceInteractor);
4587             long token = Binder.clearCallingIdentity();
4588             try {
4589                 startRunningVoiceLocked(voiceSession, activityToCallback.appInfo.uid);
4590             } finally {
4591                 Binder.restoreCallingIdentity(token);
4592             }
4593             // TODO: VI Should we cache the activity so that it's easier to find later
4594             // rather than scan through all the stacks and activities?
4595         } catch (RemoteException re) {
4596             activityToCallback.clearVoiceSessionLocked();
4597             // TODO: VI Should this terminate the voice session?
4598         }
4599     }
4600
4601     @Override
4602     public void setVoiceKeepAwake(IVoiceInteractionSession session, boolean keepAwake) {
4603         synchronized (this) {
4604             if (mRunningVoice != null && mRunningVoice.asBinder() == session.asBinder()) {
4605                 if (keepAwake) {
4606                     mVoiceWakeLock.acquire();
4607                 } else {
4608                     mVoiceWakeLock.release();
4609                 }
4610             }
4611         }
4612     }
4613
4614     @Override
4615     public boolean startNextMatchingActivity(IBinder callingActivity,
4616             Intent intent, Bundle bOptions) {
4617         // Refuse possible leaked file descriptors
4618         if (intent != null && intent.hasFileDescriptors() == true) {
4619             throw new IllegalArgumentException("File descriptors passed in Intent");
4620         }
4621         ActivityOptions options = ActivityOptions.fromBundle(bOptions);
4622
4623         synchronized (this) {
4624             final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity);
4625             if (r == null) {
4626                 ActivityOptions.abort(options);
4627                 return false;
4628             }
4629             if (r.app == null || r.app.thread == null) {
4630                 // The caller is not running...  d'oh!
4631                 ActivityOptions.abort(options);
4632                 return false;
4633             }
4634             intent = new Intent(intent);
4635             // The caller is not allowed to change the data.
4636             intent.setDataAndType(r.intent.getData(), r.intent.getType());
4637             // And we are resetting to find the next component...
4638             intent.setComponent(null);
4639
4640             final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0);
4641
4642             ActivityInfo aInfo = null;
4643             try {
4644                 List<ResolveInfo> resolves =
4645                     AppGlobals.getPackageManager().queryIntentActivities(
4646                             intent, r.resolvedType,
4647                             PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS,
4648                             UserHandle.getCallingUserId()).getList();
4649
4650                 // Look for the original activity in the list...
4651                 final int N = resolves != null ? resolves.size() : 0;
4652                 for (int i=0; i<N; i++) {
4653                     ResolveInfo rInfo = resolves.get(i);
4654                     if (rInfo.activityInfo.packageName.equals(r.packageName)
4655                             && rInfo.activityInfo.name.equals(r.info.name)) {
4656                         // We found the current one...  the next matching is
4657                         // after it.
4658                         i++;
4659                         if (i<N) {
4660                             aInfo = resolves.get(i).activityInfo;
4661                         }
4662                         if (debug) {
4663                             Slog.v(TAG, "Next matching activity: found current " + r.packageName
4664                                     + "/" + r.info.name);
4665                             Slog.v(TAG, "Next matching activity: next is " + ((aInfo == null)
4666                                     ? "null" : aInfo.packageName + "/" + aInfo.name));
4667                         }
4668                         break;
4669                     }
4670                 }
4671             } catch (RemoteException e) {
4672             }
4673
4674             if (aInfo == null) {
4675                 // Nobody who is next!
4676                 ActivityOptions.abort(options);
4677                 if (debug) Slog.d(TAG, "Next matching activity: nothing found");
4678                 return false;
4679             }
4680
4681             intent.setComponent(new ComponentName(
4682                     aInfo.applicationInfo.packageName, aInfo.name));
4683             intent.setFlags(intent.getFlags()&~(
4684                     Intent.FLAG_ACTIVITY_FORWARD_RESULT|
4685                     Intent.FLAG_ACTIVITY_CLEAR_TOP|
4686                     Intent.FLAG_ACTIVITY_MULTIPLE_TASK|
4687                     Intent.FLAG_ACTIVITY_NEW_TASK));
4688
4689             // Okay now we need to start the new activity, replacing the
4690             // currently running activity.  This is a little tricky because
4691             // we want to start the new one as if the current one is finished,
4692             // but not finish the current one first so that there is no flicker.
4693             // And thus...
4694             final boolean wasFinishing = r.finishing;
4695             r.finishing = true;
4696
4697             // Propagate reply information over to the new activity.
4698             final ActivityRecord resultTo = r.resultTo;
4699             final String resultWho = r.resultWho;
4700             final int requestCode = r.requestCode;
4701             r.resultTo = null;
4702             if (resultTo != null) {
4703                 resultTo.removeResultsLocked(r, resultWho, requestCode);
4704             }
4705
4706             final long origId = Binder.clearCallingIdentity();
4707             int res = mActivityStarter.startActivityLocked(r.app.thread, intent,
4708                     null /*ephemeralIntent*/, r.resolvedType, aInfo, null /*rInfo*/, null,
4709                     null, resultTo != null ? resultTo.appToken : null, resultWho, requestCode, -1,
4710                     r.launchedFromUid, r.launchedFromPackage, -1, r.launchedFromUid, 0, options,
4711                     false, false, null, null, null);
4712             Binder.restoreCallingIdentity(origId);
4713
4714             r.finishing = wasFinishing;
4715             if (res != ActivityManager.START_SUCCESS) {
4716                 return false;
4717             }
4718             return true;
4719         }
4720     }
4721
4722     @Override
4723     public final int startActivityFromRecents(int taskId, Bundle bOptions) {
4724         if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) {
4725             String msg = "Permission Denial: startActivityFromRecents called without " +
4726                     START_TASKS_FROM_RECENTS;
4727             Slog.w(TAG, msg);
4728             throw new SecurityException(msg);
4729         }
4730         final long origId = Binder.clearCallingIdentity();
4731         try {
4732             synchronized (this) {
4733                 return mStackSupervisor.startActivityFromRecentsInner(taskId, bOptions);
4734             }
4735         } finally {
4736             Binder.restoreCallingIdentity(origId);
4737         }
4738     }
4739
4740     final int startActivityInPackage(int uid, String callingPackage,
4741             Intent intent, String resolvedType, IBinder resultTo,
4742             String resultWho, int requestCode, int startFlags, Bundle bOptions, int userId,
4743             IActivityContainer container, TaskRecord inTask) {
4744
4745         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
4746                 userId, false, ALLOW_FULL_ONLY, "startActivityInPackage", null);
4747
4748         // TODO: Switch to user app stacks here.
4749         int ret = mActivityStarter.startActivityMayWait(null, uid, callingPackage, intent,
4750                 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags,
4751                 null, null, null, bOptions, false, userId, container, inTask);
4752         return ret;
4753     }
4754
4755     @Override
4756     public final int startActivities(IApplicationThread caller, String callingPackage,
4757             Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle bOptions,
4758             int userId) {
4759         enforceNotIsolatedCaller("startActivities");
4760         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
4761                 userId, false, ALLOW_FULL_ONLY, "startActivity", null);
4762         // TODO: Switch to user app stacks here.
4763         int ret = mActivityStarter.startActivities(caller, -1, callingPackage, intents,
4764                 resolvedTypes, resultTo, bOptions, userId);
4765         return ret;
4766     }
4767
4768     final int startActivitiesInPackage(int uid, String callingPackage,
4769             Intent[] intents, String[] resolvedTypes, IBinder resultTo,
4770             Bundle bOptions, int userId) {
4771
4772         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
4773                 userId, false, ALLOW_FULL_ONLY, "startActivityInPackage", null);
4774         // TODO: Switch to user app stacks here.
4775         int ret = mActivityStarter.startActivities(null, uid, callingPackage, intents, resolvedTypes,
4776                 resultTo, bOptions, userId);
4777         return ret;
4778     }
4779
4780     @Override
4781     public void reportActivityFullyDrawn(IBinder token) {
4782         synchronized (this) {
4783             ActivityRecord r = ActivityRecord.isInStackLocked(token);
4784             if (r == null) {
4785                 return;
4786             }
4787             r.reportFullyDrawnLocked();
4788         }
4789     }
4790
4791     @Override
4792     public void setRequestedOrientation(IBinder token, int requestedOrientation) {
4793         synchronized (this) {
4794             ActivityRecord r = ActivityRecord.isInStackLocked(token);
4795             if (r == null) {
4796                 return;
4797             }
4798             TaskRecord task = r.task;
4799             if (task != null && (!task.mFullscreen || !task.stack.mFullscreen)) {
4800                 // Fixed screen orientation isn't supported when activities aren't in full screen
4801                 // mode.
4802                 return;
4803             }
4804             final long origId = Binder.clearCallingIdentity();
4805             mWindowManager.setAppOrientation(r.appToken, requestedOrientation);
4806             Configuration config = mWindowManager.updateOrientationFromAppTokens(
4807                     mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null);
4808             if (config != null) {
4809                 r.frozenBeforeDestroy = true;
4810                 if (!updateConfigurationLocked(config, r, false)) {
4811                     mStackSupervisor.resumeFocusedStackTopActivityLocked();
4812                 }
4813             }
4814             Binder.restoreCallingIdentity(origId);
4815         }
4816     }
4817
4818     @Override
4819     public int getRequestedOrientation(IBinder token) {
4820         synchronized (this) {
4821             ActivityRecord r = ActivityRecord.isInStackLocked(token);
4822             if (r == null) {
4823                 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
4824             }
4825             return mWindowManager.getAppOrientation(r.appToken);
4826         }
4827     }
4828
4829     /**
4830      * This is the internal entry point for handling Activity.finish().
4831      *
4832      * @param token The Binder token referencing the Activity we want to finish.
4833      * @param resultCode Result code, if any, from this Activity.
4834      * @param resultData Result data (Intent), if any, from this Activity.
4835      * @param finishTask Whether to finish the task associated with this Activity.
4836      *
4837      * @return Returns true if the activity successfully finished, or false if it is still running.
4838      */
4839     @Override
4840     public final boolean finishActivity(IBinder token, int resultCode, Intent resultData,
4841             int finishTask) {
4842         // Refuse possible leaked file descriptors
4843         if (resultData != null && resultData.hasFileDescriptors() == true) {
4844             throw new IllegalArgumentException("File descriptors passed in Intent");
4845         }
4846
4847         synchronized(this) {
4848             ActivityRecord r = ActivityRecord.isInStackLocked(token);
4849             if (r == null) {
4850                 return true;
4851             }
4852             // Keep track of the root activity of the task before we finish it
4853             TaskRecord tr = r.task;
4854             ActivityRecord rootR = tr.getRootActivity();
4855             if (rootR == null) {
4856                 Slog.w(TAG, "Finishing task with all activities already finished");
4857             }
4858             // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps can
4859             // finish.
4860             if (tr.mLockTaskAuth != LOCK_TASK_AUTH_LAUNCHABLE_PRIV && rootR == r &&
4861                     mStackSupervisor.isLastLockedTask(tr)) {
4862                 Slog.i(TAG, "Not finishing task in lock task mode");
4863                 mStackSupervisor.showLockTaskToast();
4864                 return false;
4865             }
4866             if (mController != null) {
4867                 // Find the first activity that is not finishing.
4868                 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0);
4869                 if (next != null) {
4870                     // ask watcher if this is allowed
4871                     boolean resumeOK = true;
4872                     try {
4873                         resumeOK = mController.activityResuming(next.packageName);
4874                     } catch (RemoteException e) {
4875                         mController = null;
4876                         Watchdog.getInstance().setActivityController(null);
4877                     }
4878
4879                     if (!resumeOK) {
4880                         Slog.i(TAG, "Not finishing activity because controller resumed");
4881                         return false;
4882                     }
4883                 }
4884             }
4885             final long origId = Binder.clearCallingIdentity();
4886             try {
4887                 boolean res;
4888                 final boolean finishWithRootActivity =
4889                         finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY;
4890                 if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY
4891                         || (finishWithRootActivity && r == rootR)) {
4892                     // If requested, remove the task that is associated to this activity only if it
4893                     // was the root activity in the task. The result code and data is ignored
4894                     // because we don't support returning them across task boundaries. Also, to
4895                     // keep backwards compatibility we remove the task from recents when finishing
4896                     // task with root activity.
4897                     res = removeTaskByIdLocked(tr.taskId, false, finishWithRootActivity);
4898                     if (!res) {
4899                         Slog.i(TAG, "Removing task failed to finish activity");
4900                     }
4901                 } else {
4902                     res = tr.stack.requestFinishActivityLocked(token, resultCode,
4903                             resultData, "app-request", true);
4904                     if (!res) {
4905                         Slog.i(TAG, "Failed to finish by app-request");
4906                     }
4907                 }
4908                 return res;
4909             } finally {
4910                 Binder.restoreCallingIdentity(origId);
4911             }
4912         }
4913     }
4914
4915     @Override
4916     public final void finishHeavyWeightApp() {
4917         if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES)
4918                 != PackageManager.PERMISSION_GRANTED) {
4919             String msg = "Permission Denial: finishHeavyWeightApp() from pid="
4920                     + Binder.getCallingPid()
4921                     + ", uid=" + Binder.getCallingUid()
4922                     + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES;
4923             Slog.w(TAG, msg);
4924             throw new SecurityException(msg);
4925         }
4926
4927         synchronized(this) {
4928             if (mHeavyWeightProcess == null) {
4929                 return;
4930             }
4931
4932             ArrayList<ActivityRecord> activities = new ArrayList<>(mHeavyWeightProcess.activities);
4933             for (int i = 0; i < activities.size(); i++) {
4934                 ActivityRecord r = activities.get(i);
4935                 if (!r.finishing && r.isInStackLocked()) {
4936                     r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED,
4937                             null, "finish-heavy", true);
4938                 }
4939             }
4940
4941             mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG,
4942                     mHeavyWeightProcess.userId, 0));
4943             mHeavyWeightProcess = null;
4944         }
4945     }
4946
4947     @Override
4948     public void crashApplication(int uid, int initialPid, String packageName,
4949             String message) {
4950         if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES)
4951                 != PackageManager.PERMISSION_GRANTED) {
4952             String msg = "Permission Denial: crashApplication() from pid="
4953                     + Binder.getCallingPid()
4954                     + ", uid=" + Binder.getCallingUid()
4955                     + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES;
4956             Slog.w(TAG, msg);
4957             throw new SecurityException(msg);
4958         }
4959
4960         synchronized(this) {
4961             mAppErrors.scheduleAppCrashLocked(uid, initialPid, packageName, message);
4962         }
4963     }
4964
4965     @Override
4966     public final void finishSubActivity(IBinder token, String resultWho,
4967             int requestCode) {
4968         synchronized(this) {
4969             final long origId = Binder.clearCallingIdentity();
4970             ActivityRecord r = ActivityRecord.isInStackLocked(token);
4971             if (r != null) {
4972                 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode);
4973             }
4974             Binder.restoreCallingIdentity(origId);
4975         }
4976     }
4977
4978     @Override
4979     public boolean finishActivityAffinity(IBinder token) {
4980         synchronized(this) {
4981             final long origId = Binder.clearCallingIdentity();
4982             try {
4983                 ActivityRecord r = ActivityRecord.isInStackLocked(token);
4984                 if (r == null) {
4985                     return false;
4986                 }
4987
4988                 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps
4989                 // can finish.
4990                 final TaskRecord task = r.task;
4991                 if (task.mLockTaskAuth != LOCK_TASK_AUTH_LAUNCHABLE_PRIV &&
4992                         mStackSupervisor.isLastLockedTask(task) && task.getRootActivity() == r) {
4993                     mStackSupervisor.showLockTaskToast();
4994                     return false;
4995                 }
4996                 return task.stack.finishActivityAffinityLocked(r);
4997             } finally {
4998                 Binder.restoreCallingIdentity(origId);
4999             }
5000         }
5001     }
5002
5003     @Override
5004     public void finishVoiceTask(IVoiceInteractionSession session) {
5005         synchronized (this) {
5006             final long origId = Binder.clearCallingIdentity();
5007             try {
5008                 // TODO: VI Consider treating local voice interactions and voice tasks
5009                 // differently here
5010                 mStackSupervisor.finishVoiceTask(session);
5011             } finally {
5012                 Binder.restoreCallingIdentity(origId);
5013             }
5014         }
5015
5016     }
5017
5018     @Override
5019     public boolean releaseActivityInstance(IBinder token) {
5020         synchronized(this) {
5021             final long origId = Binder.clearCallingIdentity();
5022             try {
5023                 ActivityRecord r = ActivityRecord.isInStackLocked(token);
5024                 if (r == null) {
5025                     return false;
5026                 }
5027                 return r.task.stack.safelyDestroyActivityLocked(r, "app-req");
5028             } finally {
5029                 Binder.restoreCallingIdentity(origId);
5030             }
5031         }
5032     }
5033
5034     @Override
5035     public void releaseSomeActivities(IApplicationThread appInt) {
5036         synchronized(this) {
5037             final long origId = Binder.clearCallingIdentity();
5038             try {
5039                 ProcessRecord app = getRecordForAppLocked(appInt);
5040                 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem");
5041             } finally {
5042                 Binder.restoreCallingIdentity(origId);
5043             }
5044         }
5045     }
5046
5047     @Override
5048     public boolean willActivityBeVisible(IBinder token) {
5049         synchronized(this) {
5050             ActivityStack stack = ActivityRecord.getStackLocked(token);
5051             if (stack != null) {
5052                 return stack.willActivityBeVisibleLocked(token);
5053             }
5054             return false;
5055         }
5056     }
5057
5058     @Override
5059     public void overridePendingTransition(IBinder token, String packageName,
5060             int enterAnim, int exitAnim) {
5061         synchronized(this) {
5062             ActivityRecord self = ActivityRecord.isInStackLocked(token);
5063             if (self == null) {
5064                 return;
5065             }
5066
5067             final long origId = Binder.clearCallingIdentity();
5068
5069             if (self.state == ActivityState.RESUMED
5070                     || self.state == ActivityState.PAUSING) {
5071                 mWindowManager.overridePendingAppTransition(packageName,
5072                         enterAnim, exitAnim, null);
5073             }
5074
5075             Binder.restoreCallingIdentity(origId);
5076         }
5077     }
5078
5079     /**
5080      * Main function for removing an existing process from the activity manager
5081      * as a result of that process going away.  Clears out all connections
5082      * to the process.
5083      */
5084     private final void handleAppDiedLocked(ProcessRecord app,
5085             boolean restarting, boolean allowRestart) {
5086         int pid = app.pid;
5087         boolean kept = cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1,
5088                 false /*replacingPid*/);
5089         if (!kept && !restarting) {
5090             removeLruProcessLocked(app);
5091             if (pid > 0) {
5092                 ProcessList.remove(pid);
5093             }
5094         }
5095
5096         if (mProfileProc == app) {
5097             clearProfilerLocked();
5098         }
5099
5100         // Remove this application's activities from active lists.
5101         boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app);
5102
5103         app.activities.clear();
5104
5105         if (app.instrumentationClass != null) {
5106             Slog.w(TAG, "Crash of app " + app.processName
5107                   + " running instrumentation " + app.instrumentationClass);
5108             Bundle info = new Bundle();
5109             info.putString("shortMsg", "Process crashed.");
5110             finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info);
5111         }
5112
5113         if (!restarting && hasVisibleActivities
5114                 && !mStackSupervisor.resumeFocusedStackTopActivityLocked()) {
5115             // If there was nothing to resume, and we are not already restarting this process, but
5116             // there is a visible activity that is hosted by the process...  then make sure all
5117             // visible activities are running, taking care of restarting this process.
5118             mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
5119         }
5120     }
5121
5122     private final int getLRURecordIndexForAppLocked(IApplicationThread thread) {
5123         IBinder threadBinder = thread.asBinder();
5124         // Find the application record.
5125         for (int i=mLruProcesses.size()-1; i>=0; i--) {
5126             ProcessRecord rec = mLruProcesses.get(i);
5127             if (rec.thread != null && rec.thread.asBinder() == threadBinder) {
5128                 return i;
5129             }
5130         }
5131         return -1;
5132     }
5133
5134     final ProcessRecord getRecordForAppLocked(
5135             IApplicationThread thread) {
5136         if (thread == null) {
5137             return null;
5138         }
5139
5140         int appIndex = getLRURecordIndexForAppLocked(thread);
5141         return appIndex >= 0 ? mLruProcesses.get(appIndex) : null;
5142     }
5143
5144     final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) {
5145         // If there are no longer any background processes running,
5146         // and the app that died was not running instrumentation,
5147         // then tell everyone we are now low on memory.
5148         boolean haveBg = false;
5149         for (int i=mLruProcesses.size()-1; i>=0; i--) {
5150             ProcessRecord rec = mLruProcesses.get(i);
5151             if (rec.thread != null
5152                     && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) {
5153                 haveBg = true;
5154                 break;
5155             }
5156         }
5157
5158         if (!haveBg) {
5159             boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
5160             if (doReport) {
5161                 long now = SystemClock.uptimeMillis();
5162                 if (now < (mLastMemUsageReportTime+5*60*1000)) {
5163                     doReport = false;
5164                 } else {
5165                     mLastMemUsageReportTime = now;
5166                 }
5167             }
5168             final ArrayList<ProcessMemInfo> memInfos
5169                     = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null;
5170             EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size());
5171             long now = SystemClock.uptimeMillis();
5172             for (int i=mLruProcesses.size()-1; i>=0; i--) {
5173                 ProcessRecord rec = mLruProcesses.get(i);
5174                 if (rec == dyingProc || rec.thread == null) {
5175                     continue;
5176                 }
5177                 if (doReport) {
5178                     memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj,
5179                             rec.setProcState, rec.adjType, rec.makeAdjReason()));
5180                 }
5181                 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) {
5182                     // The low memory report is overriding any current
5183                     // state for a GC request.  Make sure to do
5184                     // heavy/important/visible/foreground processes first.
5185                     if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) {
5186                         rec.lastRequestedGc = 0;
5187                     } else {
5188                         rec.lastRequestedGc = rec.lastLowMemory;
5189                     }
5190                     rec.reportLowMemory = true;
5191                     rec.lastLowMemory = now;
5192                     mProcessesToGc.remove(rec);
5193                     addProcessToGcListLocked(rec);
5194                 }
5195             }
5196             if (doReport) {
5197                 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos);
5198                 mHandler.sendMessage(msg);
5199             }
5200             scheduleAppGcsLocked();
5201         }
5202     }
5203
5204     final void appDiedLocked(ProcessRecord app) {
5205        appDiedLocked(app, app.pid, app.thread, false);
5206     }
5207
5208     final void appDiedLocked(ProcessRecord app, int pid, IApplicationThread thread,
5209             boolean fromBinderDied) {
5210         // First check if this ProcessRecord is actually active for the pid.
5211         synchronized (mPidsSelfLocked) {
5212             ProcessRecord curProc = mPidsSelfLocked.get(pid);
5213             if (curProc != app) {
5214                 Slog.w(TAG, "Spurious death for " + app + ", curProc for " + pid + ": " + curProc);
5215                 return;
5216             }
5217         }
5218
5219         BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
5220         synchronized (stats) {
5221             stats.noteProcessDiedLocked(app.info.uid, pid);
5222         }
5223
5224         if (!app.killed) {
5225             if (!fromBinderDied) {
5226                 Process.killProcessQuiet(pid);
5227             }
5228             killProcessGroup(app.uid, pid);
5229             app.killed = true;
5230         }
5231
5232         // Clean up already done if the process has been re-started.
5233         if (app.pid == pid && app.thread != null &&
5234                 app.thread.asBinder() == thread.asBinder()) {
5235             boolean doLowMem = app.instrumentationClass == null;
5236             boolean doOomAdj = doLowMem;
5237             if (!app.killedByAm) {
5238                 Slog.i(TAG, "Process " + app.processName + " (pid " + pid
5239                         + ") has died");
5240                 mAllowLowerMemLevel = true;
5241             } else {
5242                 // Note that we always want to do oom adj to update our state with the
5243                 // new number of procs.
5244                 mAllowLowerMemLevel = false;
5245                 doLowMem = false;
5246             }
5247             EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName);
5248             if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP,
5249                 "Dying app: " + app + ", pid: " + pid + ", thread: " + thread.asBinder());
5250             handleAppDiedLocked(app, false, true);
5251
5252             if (doOomAdj) {
5253                 updateOomAdjLocked();
5254             }
5255             if (doLowMem) {
5256                 doLowMemReportIfNeededLocked(app);
5257             }
5258         } else if (app.pid != pid) {
5259             // A new process has already been started.
5260             Slog.i(TAG, "Process " + app.processName + " (pid " + pid
5261                     + ") has died and restarted (pid " + app.pid + ").");
5262             EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName);
5263         } else if (DEBUG_PROCESSES) {
5264             Slog.d(TAG_PROCESSES, "Received spurious death notification for thread "
5265                     + thread.asBinder());
5266         }
5267     }
5268
5269     /**
5270      * If a stack trace dump file is configured, dump process stack traces.
5271      * @param clearTraces causes the dump file to be erased prior to the new
5272      *    traces being written, if true; when false, the new traces will be
5273      *    appended to any existing file content.
5274      * @param firstPids of dalvik VM processes to dump stack traces for first
5275      * @param lastPids of dalvik VM processes to dump stack traces for last
5276      * @param nativeProcs optional list of native process names to dump stack crawls
5277      * @return file containing stack traces, or null if no dump file is configured
5278      */
5279     public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids,
5280             ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) {
5281         String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null);
5282         if (tracesPath == null || tracesPath.length() == 0) {
5283             return null;
5284         }
5285
5286         File tracesFile = new File(tracesPath);
5287         try {
5288             if (clearTraces && tracesFile.exists()) tracesFile.delete();
5289             tracesFile.createNewFile();
5290             FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw-
5291         } catch (IOException e) {
5292             Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e);
5293             return null;
5294         }
5295
5296         dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs);
5297         return tracesFile;
5298     }
5299
5300     private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids,
5301             ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) {
5302         // Use a FileObserver to detect when traces finish writing.
5303         // The order of traces is considered important to maintain for legibility.
5304         FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) {
5305             @Override
5306             public synchronized void onEvent(int event, String path) { notify(); }
5307         };
5308
5309         try {
5310             observer.startWatching();
5311
5312             // First collect all of the stacks of the most important pids.
5313             if (firstPids != null) {
5314                 try {
5315                     int num = firstPids.size();
5316                     for (int i = 0; i < num; i++) {
5317                         synchronized (observer) {
5318                             if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for pid "
5319                                     + firstPids.get(i));
5320                             final long sime = SystemClock.elapsedRealtime();
5321                             Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT);
5322                             observer.wait(1000);  // Wait for write-close, give up after 1 sec
5323                             if (DEBUG_ANR) Slog.d(TAG, "Done with pid " + firstPids.get(i)
5324                                     + " in " + (SystemClock.elapsedRealtime()-sime) + "ms");
5325                         }
5326                     }
5327                 } catch (InterruptedException e) {
5328                     Slog.wtf(TAG, e);
5329                 }
5330             }
5331
5332             // Next collect the stacks of the native pids
5333             if (nativeProcs != null) {
5334                 int[] pids = Process.getPidsForCommands(nativeProcs);
5335                 if (pids != null) {
5336                     for (int pid : pids) {
5337                         if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for native pid " + pid);
5338                         final long sime = SystemClock.elapsedRealtime();
5339                         Debug.dumpNativeBacktraceToFile(pid, tracesPath);
5340                         if (DEBUG_ANR) Slog.d(TAG, "Done with native pid " + pid
5341                                 + " in " + (SystemClock.elapsedRealtime()-sime) + "ms");
5342                     }
5343                 }
5344             }
5345
5346             // Lastly, measure CPU usage.
5347             if (processCpuTracker != null) {
5348                 processCpuTracker.init();
5349                 System.gc();
5350                 processCpuTracker.update();
5351                 try {
5352                     synchronized (processCpuTracker) {
5353                         processCpuTracker.wait(500); // measure over 1/2 second.
5354                     }
5355                 } catch (InterruptedException e) {
5356                 }
5357                 processCpuTracker.update();
5358
5359                 // We'll take the stack crawls of just the top apps using CPU.
5360                 final int N = processCpuTracker.countWorkingStats();
5361                 int numProcs = 0;
5362                 for (int i=0; i<N && numProcs<5; i++) {
5363                     ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i);
5364                     if (lastPids.indexOfKey(stats.pid) >= 0) {
5365                         numProcs++;
5366                         try {
5367                             synchronized (observer) {
5368                                 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for extra pid "
5369                                         + stats.pid);
5370                                 final long stime = SystemClock.elapsedRealtime();
5371                                 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT);
5372                                 observer.wait(1000);  // Wait for write-close, give up after 1 sec
5373                                 if (DEBUG_ANR) Slog.d(TAG, "Done with extra pid " + stats.pid
5374                                         + " in " + (SystemClock.elapsedRealtime()-stime) + "ms");
5375                             }
5376                         } catch (InterruptedException e) {
5377                             Slog.wtf(TAG, e);
5378                         }
5379                     } else if (DEBUG_ANR) {
5380                         Slog.d(TAG, "Skipping next CPU consuming process, not a java proc: "
5381                                 + stats.pid);
5382                     }
5383                 }
5384             }
5385         } finally {
5386             observer.stopWatching();
5387         }
5388     }
5389
5390     final void logAppTooSlow(ProcessRecord app, long startTime, String msg) {
5391         if (true || IS_USER_BUILD) {
5392             return;
5393         }
5394         String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null);
5395         if (tracesPath == null || tracesPath.length() == 0) {
5396             return;
5397         }
5398
5399         StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads();
5400         StrictMode.allowThreadDiskWrites();
5401         try {
5402             final File tracesFile = new File(tracesPath);
5403             final File tracesDir = tracesFile.getParentFile();
5404             final File tracesTmp = new File(tracesDir, "__tmp__");
5405             try {
5406                 if (tracesFile.exists()) {
5407                     tracesTmp.delete();
5408                     tracesFile.renameTo(tracesTmp);
5409                 }
5410                 StringBuilder sb = new StringBuilder();
5411                 Time tobj = new Time();
5412                 tobj.set(System.currentTimeMillis());
5413                 sb.append(tobj.format("%Y-%m-%d %H:%M:%S"));
5414                 sb.append(": ");
5415                 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb);
5416                 sb.append(" since ");
5417                 sb.append(msg);
5418                 FileOutputStream fos = new FileOutputStream(tracesFile);
5419                 fos.write(sb.toString().getBytes());
5420                 if (app == null) {
5421                     fos.write("\n*** No application process!".getBytes());
5422                 }
5423                 fos.close();
5424                 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw-
5425             } catch (IOException e) {
5426                 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e);
5427                 return;
5428             }
5429
5430             if (app != null) {
5431                 ArrayList<Integer> firstPids = new ArrayList<Integer>();
5432                 firstPids.add(app.pid);
5433                 dumpStackTraces(tracesPath, firstPids, null, null, null);
5434             }
5435
5436             File lastTracesFile = null;
5437             File curTracesFile = null;
5438             for (int i=9; i>=0; i--) {
5439                 String name = String.format(Locale.US, "slow%02d.txt", i);
5440                 curTracesFile = new File(tracesDir, name);
5441                 if (curTracesFile.exists()) {
5442                     if (lastTracesFile != null) {
5443                         curTracesFile.renameTo(lastTracesFile);
5444                     } else {
5445                         curTracesFile.delete();
5446                     }
5447                 }
5448                 lastTracesFile = curTracesFile;
5449             }
5450             tracesFile.renameTo(curTracesFile);
5451             if (tracesTmp.exists()) {
5452                 tracesTmp.renameTo(tracesFile);
5453             }
5454         } finally {
5455             StrictMode.setThreadPolicy(oldPolicy);
5456         }
5457     }
5458
5459     final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) {
5460         if (!mLaunchWarningShown) {
5461             mLaunchWarningShown = true;
5462             mUiHandler.post(new Runnable() {
5463                 @Override
5464                 public void run() {
5465                     synchronized (ActivityManagerService.this) {
5466                         final Dialog d = new LaunchWarningWindow(mContext, cur, next);
5467                         d.show();
5468                         mUiHandler.postDelayed(new Runnable() {
5469                             @Override
5470                             public void run() {
5471                                 synchronized (ActivityManagerService.this) {
5472                                     d.dismiss();
5473                                     mLaunchWarningShown = false;
5474                                 }
5475                             }
5476                         }, 4000);
5477                     }
5478                 }
5479             });
5480         }
5481     }
5482
5483     @Override
5484     public boolean clearApplicationUserData(final String packageName,
5485             final IPackageDataObserver observer, int userId) {
5486         enforceNotIsolatedCaller("clearApplicationUserData");
5487         int uid = Binder.getCallingUid();
5488         int pid = Binder.getCallingPid();
5489         userId = mUserController.handleIncomingUser(pid, uid, userId, false,
5490                 ALLOW_FULL_ONLY, "clearApplicationUserData", null);
5491
5492
5493         long callingId = Binder.clearCallingIdentity();
5494         try {
5495             IPackageManager pm = AppGlobals.getPackageManager();
5496             int pkgUid = -1;
5497             synchronized(this) {
5498                 if (getPackageManagerInternalLocked().isPackageDataProtected(
5499                         userId, packageName)) {
5500                     throw new SecurityException(
5501                             "Cannot clear data for a protected package: " + packageName);
5502                 }
5503
5504                 try {
5505                     pkgUid = pm.getPackageUid(packageName, MATCH_UNINSTALLED_PACKAGES, userId);
5506                 } catch (RemoteException e) {
5507                 }
5508                 if (pkgUid == -1) {
5509                     Slog.w(TAG, "Invalid packageName: " + packageName);
5510                     if (observer != null) {
5511                         try {
5512                             observer.onRemoveCompleted(packageName, false);
5513                         } catch (RemoteException e) {
5514                             Slog.i(TAG, "Observer no longer exists.");
5515                         }
5516                     }
5517                     return false;
5518                 }
5519                 if (uid == pkgUid || checkComponentPermission(
5520                         android.Manifest.permission.CLEAR_APP_USER_DATA,
5521                         pid, uid, -1, true)
5522                         == PackageManager.PERMISSION_GRANTED) {
5523                     forceStopPackageLocked(packageName, pkgUid, "clear data");
5524                 } else {
5525                     throw new SecurityException("PID " + pid + " does not have permission "
5526                             + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data"
5527                                     + " of package " + packageName);
5528                 }
5529
5530                 // Remove all tasks match the cleared application package and user
5531                 for (int i = mRecentTasks.size() - 1; i >= 0; i--) {
5532                     final TaskRecord tr = mRecentTasks.get(i);
5533                     final String taskPackageName =
5534                             tr.getBaseIntent().getComponent().getPackageName();
5535                     if (tr.userId != userId) continue;
5536                     if (!taskPackageName.equals(packageName)) continue;
5537                     removeTaskByIdLocked(tr.taskId, false, REMOVE_FROM_RECENTS);
5538                 }
5539             }
5540
5541             final int pkgUidF = pkgUid;
5542             final int userIdF = userId;
5543             final IPackageDataObserver localObserver = new IPackageDataObserver.Stub() {
5544                 @Override
5545                 public void onRemoveCompleted(String packageName, boolean succeeded)
5546                         throws RemoteException {
5547                     synchronized (ActivityManagerService.this) {
5548                         finishForceStopPackageLocked(packageName, pkgUidF);
5549                     }
5550
5551                     final Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED,
5552                             Uri.fromParts("package", packageName, null));
5553                     intent.putExtra(Intent.EXTRA_UID, pkgUidF);
5554                     intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(pkgUidF));
5555                     broadcastIntentInPackage("android", Process.SYSTEM_UID, intent,
5556                             null, null, 0, null, null, null, null, false, false, userIdF);
5557
5558                     if (observer != null) {
5559                         observer.onRemoveCompleted(packageName, succeeded);
5560                     }
5561                 }
5562             };
5563
5564             try {
5565                 // Clear application user data
5566                 pm.clearApplicationUserData(packageName, localObserver, userId);
5567
5568                 synchronized(this) {
5569                     // Remove all permissions granted from/to this package
5570                     removeUriPermissionsForPackageLocked(packageName, userId, true);
5571                 }
5572
5573                 // Remove all zen rules created by this package; revoke it's zen access.
5574                 INotificationManager inm = NotificationManager.getService();
5575                 inm.removeAutomaticZenRules(packageName);
5576                 inm.setNotificationPolicyAccessGranted(packageName, false);
5577
5578             } catch (RemoteException e) {
5579             }
5580         } finally {
5581             Binder.restoreCallingIdentity(callingId);
5582         }
5583         return true;
5584     }
5585
5586     @Override
5587     public void killBackgroundProcesses(final String packageName, int userId) {
5588         if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES)
5589                 != PackageManager.PERMISSION_GRANTED &&
5590                 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES)
5591                         != PackageManager.PERMISSION_GRANTED) {
5592             String msg = "Permission Denial: killBackgroundProcesses() from pid="
5593                     + Binder.getCallingPid()
5594                     + ", uid=" + Binder.getCallingUid()
5595                     + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES;
5596             Slog.w(TAG, msg);
5597             throw new SecurityException(msg);
5598         }
5599
5600         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
5601                 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null);
5602         long callingId = Binder.clearCallingIdentity();
5603         try {
5604             IPackageManager pm = AppGlobals.getPackageManager();
5605             synchronized(this) {
5606                 int appId = -1;
5607                 try {
5608                     appId = UserHandle.getAppId(
5609                             pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId));
5610                 } catch (RemoteException e) {
5611                 }
5612                 if (appId == -1) {
5613                     Slog.w(TAG, "Invalid packageName: " + packageName);
5614                     return;
5615                 }
5616                 killPackageProcessesLocked(packageName, appId, userId,
5617                         ProcessList.SERVICE_ADJ, false, true, true, false, "kill background");
5618             }
5619         } finally {
5620             Binder.restoreCallingIdentity(callingId);
5621         }
5622     }
5623
5624     @Override
5625     public void killAllBackgroundProcesses() {
5626         if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES)
5627                 != PackageManager.PERMISSION_GRANTED) {
5628             final String msg = "Permission Denial: killAllBackgroundProcesses() from pid="
5629                     + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid()
5630                     + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES;
5631             Slog.w(TAG, msg);
5632             throw new SecurityException(msg);
5633         }
5634
5635         final long callingId = Binder.clearCallingIdentity();
5636         try {
5637             synchronized (this) {
5638                 final ArrayList<ProcessRecord> procs = new ArrayList<>();
5639                 final int NP = mProcessNames.getMap().size();
5640                 for (int ip = 0; ip < NP; ip++) {
5641                     final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
5642                     final int NA = apps.size();
5643                     for (int ia = 0; ia < NA; ia++) {
5644                         final ProcessRecord app = apps.valueAt(ia);
5645                         if (app.persistent) {
5646                             // We don't kill persistent processes.
5647                             continue;
5648                         }
5649                         if (app.removed) {
5650                             procs.add(app);
5651                         } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) {
5652                             app.removed = true;
5653                             procs.add(app);
5654                         }
5655                     }
5656                 }
5657
5658                 final int N = procs.size();
5659                 for (int i = 0; i < N; i++) {
5660                     removeProcessLocked(procs.get(i), false, true, "kill all background");
5661                 }
5662
5663                 mAllowLowerMemLevel = true;
5664
5665                 updateOomAdjLocked();
5666                 doLowMemReportIfNeededLocked(null);
5667             }
5668         } finally {
5669             Binder.restoreCallingIdentity(callingId);
5670         }
5671     }
5672
5673     /**
5674      * Kills all background processes, except those matching any of the
5675      * specified properties.
5676      *
5677      * @param minTargetSdk the target SDK version at or above which to preserve
5678      *                     processes, or {@code -1} to ignore the target SDK
5679      * @param maxProcState the process state at or below which to preserve
5680      *                     processes, or {@code -1} to ignore the process state
5681      */
5682     private void killAllBackgroundProcessesExcept(int minTargetSdk, int maxProcState) {
5683         if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES)
5684                 != PackageManager.PERMISSION_GRANTED) {
5685             final String msg = "Permission Denial: killAllBackgroundProcessesExcept() from pid="
5686                     + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid()
5687                     + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES;
5688             Slog.w(TAG, msg);
5689             throw new SecurityException(msg);
5690         }
5691
5692         final long callingId = Binder.clearCallingIdentity();
5693         try {
5694             synchronized (this) {
5695                 final ArrayList<ProcessRecord> procs = new ArrayList<>();
5696                 final int NP = mProcessNames.getMap().size();
5697                 for (int ip = 0; ip < NP; ip++) {
5698                     final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
5699                     final int NA = apps.size();
5700                     for (int ia = 0; ia < NA; ia++) {
5701                         final ProcessRecord app = apps.valueAt(ia);
5702                         if (app.removed) {
5703                             procs.add(app);
5704                         } else if ((minTargetSdk < 0 || app.info.targetSdkVersion < minTargetSdk)
5705                                 && (maxProcState < 0 || app.setProcState > maxProcState)) {
5706                             app.removed = true;
5707                             procs.add(app);
5708                         }
5709                     }
5710                 }
5711
5712                 final int N = procs.size();
5713                 for (int i = 0; i < N; i++) {
5714                     removeProcessLocked(procs.get(i), false, true, "kill all background except");
5715                 }
5716             }
5717         } finally {
5718             Binder.restoreCallingIdentity(callingId);
5719         }
5720     }
5721
5722     @Override
5723     public void forceStopPackage(final String packageName, int userId) {
5724         if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES)
5725                 != PackageManager.PERMISSION_GRANTED) {
5726             String msg = "Permission Denial: forceStopPackage() from pid="
5727                     + Binder.getCallingPid()
5728                     + ", uid=" + Binder.getCallingUid()
5729                     + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES;
5730             Slog.w(TAG, msg);
5731             throw new SecurityException(msg);
5732         }
5733         final int callingPid = Binder.getCallingPid();
5734         userId = mUserController.handleIncomingUser(callingPid, Binder.getCallingUid(),
5735                 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null);
5736         long callingId = Binder.clearCallingIdentity();
5737         try {
5738             IPackageManager pm = AppGlobals.getPackageManager();
5739             synchronized(this) {
5740                 int[] users = userId == UserHandle.USER_ALL
5741                         ? mUserController.getUsers() : new int[] { userId };
5742                 for (int user : users) {
5743                     int pkgUid = -1;
5744                     try {
5745                         pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING,
5746                                 user);
5747                     } catch (RemoteException e) {
5748                     }
5749                     if (pkgUid == -1) {
5750                         Slog.w(TAG, "Invalid packageName: " + packageName);
5751                         continue;
5752                     }
5753                     try {
5754                         pm.setPackageStoppedState(packageName, true, user);
5755                     } catch (RemoteException e) {
5756                     } catch (IllegalArgumentException e) {
5757                         Slog.w(TAG, "Failed trying to unstop package "
5758                                 + packageName + ": " + e);
5759                     }
5760                     if (mUserController.isUserRunningLocked(user, 0)) {
5761                         forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid);
5762                         finishForceStopPackageLocked(packageName, pkgUid);
5763                     }
5764                 }
5765             }
5766         } finally {
5767             Binder.restoreCallingIdentity(callingId);
5768         }
5769     }
5770
5771     @Override
5772     public void addPackageDependency(String packageName) {
5773         synchronized (this) {
5774             int callingPid = Binder.getCallingPid();
5775             if (callingPid == Process.myPid()) {
5776                 //  Yeah, um, no.
5777                 return;
5778             }
5779             ProcessRecord proc;
5780             synchronized (mPidsSelfLocked) {
5781                 proc = mPidsSelfLocked.get(Binder.getCallingPid());
5782             }
5783             if (proc != null) {
5784                 if (proc.pkgDeps == null) {
5785                     proc.pkgDeps = new ArraySet<String>(1);
5786                 }
5787                 proc.pkgDeps.add(packageName);
5788             }
5789         }
5790     }
5791
5792     /*
5793      * The pkg name and app id have to be specified.
5794      */
5795     @Override
5796     public void killApplication(String pkg, int appId, int userId, String reason) {
5797         if (pkg == null) {
5798             return;
5799         }
5800         // Make sure the uid is valid.
5801         if (appId < 0) {
5802             Slog.w(TAG, "Invalid appid specified for pkg : " + pkg);
5803             return;
5804         }
5805         int callerUid = Binder.getCallingUid();
5806         // Only the system server can kill an application
5807         if (UserHandle.getAppId(callerUid) == Process.SYSTEM_UID) {
5808             // Post an aysnc message to kill the application
5809             Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG);
5810             msg.arg1 = appId;
5811             msg.arg2 = userId;
5812             Bundle bundle = new Bundle();
5813             bundle.putString("pkg", pkg);
5814             bundle.putString("reason", reason);
5815             msg.obj = bundle;
5816             mHandler.sendMessage(msg);
5817         } else {
5818             throw new SecurityException(callerUid + " cannot kill pkg: " +
5819                     pkg);
5820         }
5821     }
5822
5823     @Override
5824     public void closeSystemDialogs(String reason) {
5825         enforceNotIsolatedCaller("closeSystemDialogs");
5826
5827         final int pid = Binder.getCallingPid();
5828         final int uid = Binder.getCallingUid();
5829         final long origId = Binder.clearCallingIdentity();
5830         try {
5831             synchronized (this) {
5832                 // Only allow this from foreground processes, so that background
5833                 // applications can't abuse it to prevent system UI from being shown.
5834                 if (uid >= Process.FIRST_APPLICATION_UID) {
5835                     ProcessRecord proc;
5836                     synchronized (mPidsSelfLocked) {
5837                         proc = mPidsSelfLocked.get(pid);
5838                     }
5839                     if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) {
5840                         Slog.w(TAG, "Ignoring closeSystemDialogs " + reason
5841                                 + " from background process " + proc);
5842                         return;
5843                     }
5844                 }
5845                 closeSystemDialogsLocked(reason);
5846             }
5847         } finally {
5848             Binder.restoreCallingIdentity(origId);
5849         }
5850     }
5851
5852     void closeSystemDialogsLocked(String reason) {
5853         Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
5854         intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY
5855                 | Intent.FLAG_RECEIVER_FOREGROUND);
5856         if (reason != null) {
5857             intent.putExtra("reason", reason);
5858         }
5859         mWindowManager.closeSystemDialogs(reason);
5860
5861         mStackSupervisor.closeSystemDialogsLocked();
5862
5863         broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null,
5864                 AppOpsManager.OP_NONE, null, false, false,
5865                 -1, Process.SYSTEM_UID, UserHandle.USER_ALL);
5866     }
5867
5868     @Override
5869     public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) {
5870         enforceNotIsolatedCaller("getProcessMemoryInfo");
5871         Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length];
5872         for (int i=pids.length-1; i>=0; i--) {
5873             ProcessRecord proc;
5874             int oomAdj;
5875             synchronized (this) {
5876                 synchronized (mPidsSelfLocked) {
5877                     proc = mPidsSelfLocked.get(pids[i]);
5878                     oomAdj = proc != null ? proc.setAdj : 0;
5879                 }
5880             }
5881             infos[i] = new Debug.MemoryInfo();
5882             Debug.getMemoryInfo(pids[i], infos[i]);
5883             if (proc != null) {
5884                 synchronized (this) {
5885                     if (proc.thread != null && proc.setAdj == oomAdj) {
5886                         // Record this for posterity if the process has been stable.
5887                         proc.baseProcessTracker.addPss(infos[i].getTotalPss(),
5888                                 infos[i].getTotalUss(), false, proc.pkgList);
5889                     }
5890                 }
5891             }
5892         }
5893         return infos;
5894     }
5895
5896     @Override
5897     public long[] getProcessPss(int[] pids) {
5898         enforceNotIsolatedCaller("getProcessPss");
5899         long[] pss = new long[pids.length];
5900         for (int i=pids.length-1; i>=0; i--) {
5901             ProcessRecord proc;
5902             int oomAdj;
5903             synchronized (this) {
5904                 synchronized (mPidsSelfLocked) {
5905                     proc = mPidsSelfLocked.get(pids[i]);
5906                     oomAdj = proc != null ? proc.setAdj : 0;
5907                 }
5908             }
5909             long[] tmpUss = new long[1];
5910             pss[i] = Debug.getPss(pids[i], tmpUss, null);
5911             if (proc != null) {
5912                 synchronized (this) {
5913                     if (proc.thread != null && proc.setAdj == oomAdj) {
5914                         // Record this for posterity if the process has been stable.
5915                         proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList);
5916                     }
5917                 }
5918             }
5919         }
5920         return pss;
5921     }
5922
5923     @Override
5924     public void killApplicationProcess(String processName, int uid) {
5925         if (processName == null) {
5926             return;
5927         }
5928
5929         int callerUid = Binder.getCallingUid();
5930         // Only the system server can kill an application
5931         if (callerUid == Process.SYSTEM_UID) {
5932             synchronized (this) {
5933                 ProcessRecord app = getProcessRecordLocked(processName, uid, true);
5934                 if (app != null && app.thread != null) {
5935                     try {
5936                         app.thread.scheduleSuicide();
5937                     } catch (RemoteException e) {
5938                         // If the other end already died, then our work here is done.
5939                     }
5940                 } else {
5941                     Slog.w(TAG, "Process/uid not found attempting kill of "
5942                             + processName + " / " + uid);
5943                 }
5944             }
5945         } else {
5946             throw new SecurityException(callerUid + " cannot kill app process: " +
5947                     processName);
5948         }
5949     }
5950
5951     private void forceStopPackageLocked(final String packageName, int uid, String reason) {
5952         forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false,
5953                 false, true, false, false, UserHandle.getUserId(uid), reason);
5954     }
5955
5956     private void finishForceStopPackageLocked(final String packageName, int uid) {
5957         Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED,
5958                 Uri.fromParts("package", packageName, null));
5959         if (!mProcessesReady) {
5960             intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY
5961                     | Intent.FLAG_RECEIVER_FOREGROUND);
5962         }
5963         intent.putExtra(Intent.EXTRA_UID, uid);
5964         intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid));
5965         broadcastIntentLocked(null, null, intent,
5966                 null, null, 0, null, null, null, AppOpsManager.OP_NONE,
5967                 null, false, false, MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid));
5968     }
5969
5970
5971     private final boolean killPackageProcessesLocked(String packageName, int appId,
5972             int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart,
5973             boolean doit, boolean evenPersistent, String reason) {
5974         ArrayList<ProcessRecord> procs = new ArrayList<>();
5975
5976         // Remove all processes this package may have touched: all with the
5977         // same UID (except for the system or root user), and all whose name
5978         // matches the package name.
5979         final int NP = mProcessNames.getMap().size();
5980         for (int ip=0; ip<NP; ip++) {
5981             SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
5982             final int NA = apps.size();
5983             for (int ia=0; ia<NA; ia++) {
5984                 ProcessRecord app = apps.valueAt(ia);
5985                 if (app.persistent && !evenPersistent) {
5986                     // we don't kill persistent processes
5987                     continue;
5988                 }
5989                 if (app.removed) {
5990                     if (doit) {
5991                         procs.add(app);
5992                     }
5993                     continue;
5994                 }
5995
5996                 // Skip process if it doesn't meet our oom adj requirement.
5997                 if (app.setAdj < minOomAdj) {
5998                     continue;
5999                 }
6000
6001                 // If no package is specified, we call all processes under the
6002                 // give user id.
6003                 if (packageName == null) {
6004                     if (userId != UserHandle.USER_ALL && app.userId != userId) {
6005                         continue;
6006                     }
6007                     if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) {
6008                         continue;
6009                     }
6010                 // Package has been specified, we want to hit all processes
6011                 // that match it.  We need to qualify this by the processes
6012                 // that are running under the specified app and user ID.
6013                 } else {
6014                     final boolean isDep = app.pkgDeps != null
6015                             && app.pkgDeps.contains(packageName);
6016                     if (!isDep && UserHandle.getAppId(app.uid) != appId) {
6017                         continue;
6018                     }
6019                     if (userId != UserHandle.USER_ALL && app.userId != userId) {
6020                         continue;
6021                     }
6022                     if (!app.pkgList.containsKey(packageName) && !isDep) {
6023                         continue;
6024                     }
6025                 }
6026
6027                 // Process has passed all conditions, kill it!
6028                 if (!doit) {
6029                     return true;
6030                 }
6031                 app.removed = true;
6032                 procs.add(app);
6033             }
6034         }
6035
6036         int N = procs.size();
6037         for (int i=0; i<N; i++) {
6038             removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason);
6039         }
6040         updateOomAdjLocked();
6041         return N > 0;
6042     }
6043
6044     private void cleanupDisabledPackageComponentsLocked(
6045             String packageName, int userId, boolean killProcess, String[] changedClasses) {
6046
6047         Set<String> disabledClasses = null;
6048         boolean packageDisabled = false;
6049         IPackageManager pm = AppGlobals.getPackageManager();
6050
6051         if (changedClasses == null) {
6052             // Nothing changed...
6053             return;
6054         }
6055
6056         // Determine enable/disable state of the package and its components.
6057         int enabled = PackageManager.COMPONENT_ENABLED_STATE_DEFAULT;
6058         for (int i = changedClasses.length - 1; i >= 0; i--) {
6059             final String changedClass = changedClasses[i];
6060
6061             if (changedClass.equals(packageName)) {
6062                 try {
6063                     // Entire package setting changed
6064                     enabled = pm.getApplicationEnabledSetting(packageName,
6065                             (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM);
6066                 } catch (Exception e) {
6067                     // No such package/component; probably racing with uninstall.  In any
6068                     // event it means we have nothing further to do here.
6069                     return;
6070                 }
6071                 packageDisabled = enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED
6072                         && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT;
6073                 if (packageDisabled) {
6074                     // Entire package is disabled.
6075                     // No need to continue to check component states.
6076                     disabledClasses = null;
6077                     break;
6078                 }
6079             } else {
6080                 try {
6081                     enabled = pm.getComponentEnabledSetting(
6082                             new ComponentName(packageName, changedClass),
6083                             (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM);
6084                 } catch (Exception e) {
6085                     // As above, probably racing with uninstall.
6086                     return;
6087                 }
6088                 if (enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED
6089                         && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT) {
6090                     if (disabledClasses == null) {
6091                         disabledClasses = new ArraySet<>(changedClasses.length);
6092                     }
6093                     disabledClasses.add(changedClass);
6094                 }
6095             }
6096         }
6097
6098         if (!packageDisabled && disabledClasses == null) {
6099             // Nothing to do here...
6100             return;
6101         }
6102
6103         // Clean-up disabled activities.
6104         if (mStackSupervisor.finishDisabledPackageActivitiesLocked(
6105                 packageName, disabledClasses, true, false, userId) && mBooted) {
6106             mStackSupervisor.resumeFocusedStackTopActivityLocked();
6107             mStackSupervisor.scheduleIdleLocked();
6108         }
6109
6110         // Clean-up disabled tasks
6111         cleanupDisabledPackageTasksLocked(packageName, disabledClasses, userId);
6112
6113         // Clean-up disabled services.
6114         mServices.bringDownDisabledPackageServicesLocked(
6115                 packageName, disabledClasses, userId, false, killProcess, true);
6116
6117         // Clean-up disabled providers.
6118         ArrayList<ContentProviderRecord> providers = new ArrayList<>();
6119         mProviderMap.collectPackageProvidersLocked(
6120                 packageName, disabledClasses, true, false, userId, providers);
6121         for (int i = providers.size() - 1; i >= 0; i--) {
6122             removeDyingProviderLocked(null, providers.get(i), true);
6123         }
6124
6125         // Clean-up disabled broadcast receivers.
6126         for (int i = mBroadcastQueues.length - 1; i >= 0; i--) {
6127             mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked(
6128                     packageName, disabledClasses, userId, true);
6129         }
6130
6131     }
6132
6133     final boolean clearBroadcastQueueForUserLocked(int userId) {
6134         boolean didSomething = false;
6135         for (int i = mBroadcastQueues.length - 1; i >= 0; i--) {
6136             didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked(
6137                     null, null, userId, true);
6138         }
6139         return didSomething;
6140     }
6141
6142     final boolean forceStopPackageLocked(String packageName, int appId,
6143             boolean callerWillRestart, boolean purgeCache, boolean doit,
6144             boolean evenPersistent, boolean uninstalling, int userId, String reason) {
6145         int i;
6146
6147         if (userId == UserHandle.USER_ALL && packageName == null) {
6148             Slog.w(TAG, "Can't force stop all processes of all users, that is insane!");
6149         }
6150
6151         if (appId < 0 && packageName != null) {
6152             try {
6153                 appId = UserHandle.getAppId(AppGlobals.getPackageManager()
6154                         .getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 0));
6155             } catch (RemoteException e) {
6156             }
6157         }
6158
6159         if (doit) {
6160             if (packageName != null) {
6161                 Slog.i(TAG, "Force stopping " + packageName + " appid=" + appId
6162                         + " user=" + userId + ": " + reason);
6163             } else {
6164                 Slog.i(TAG, "Force stopping u" + userId + ": " + reason);
6165             }
6166
6167             mAppErrors.resetProcessCrashTimeLocked(packageName == null, appId, userId);
6168         }
6169
6170         boolean didSomething = killPackageProcessesLocked(packageName, appId, userId,
6171                 ProcessList.INVALID_ADJ, callerWillRestart, true, doit, evenPersistent,
6172                 packageName == null ? ("stop user " + userId) : ("stop " + packageName));
6173
6174         if (mStackSupervisor.finishDisabledPackageActivitiesLocked(
6175                 packageName, null, doit, evenPersistent, userId)) {
6176             if (!doit) {
6177                 return true;
6178             }
6179             didSomething = true;
6180         }
6181
6182         if (mServices.bringDownDisabledPackageServicesLocked(
6183                 packageName, null, userId, evenPersistent, true, doit)) {
6184             if (!doit) {
6185                 return true;
6186             }
6187             didSomething = true;
6188         }
6189
6190         if (packageName == null) {
6191             // Remove all sticky broadcasts from this user.
6192             mStickyBroadcasts.remove(userId);
6193         }
6194
6195         ArrayList<ContentProviderRecord> providers = new ArrayList<>();
6196         if (mProviderMap.collectPackageProvidersLocked(packageName, null, doit, evenPersistent,
6197                 userId, providers)) {
6198             if (!doit) {
6199                 return true;
6200             }
6201             didSomething = true;
6202         }
6203         for (i = providers.size() - 1; i >= 0; i--) {
6204             removeDyingProviderLocked(null, providers.get(i), true);
6205         }
6206
6207         // Remove transient permissions granted from/to this package/user
6208         removeUriPermissionsForPackageLocked(packageName, userId, false);
6209
6210         if (doit) {
6211             for (i = mBroadcastQueues.length - 1; i >= 0; i--) {
6212                 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked(
6213                         packageName, null, userId, doit);
6214             }
6215         }
6216
6217         if (packageName == null || uninstalling) {
6218             // Remove pending intents.  For now we only do this when force
6219             // stopping users, because we have some problems when doing this
6220             // for packages -- app widgets are not currently cleaned up for
6221             // such packages, so they can be left with bad pending intents.
6222             if (mIntentSenderRecords.size() > 0) {
6223                 Iterator<WeakReference<PendingIntentRecord>> it
6224                         = mIntentSenderRecords.values().iterator();
6225                 while (it.hasNext()) {
6226                     WeakReference<PendingIntentRecord> wpir = it.next();
6227                     if (wpir == null) {
6228                         it.remove();
6229                         continue;
6230                     }
6231                     PendingIntentRecord pir = wpir.get();
6232                     if (pir == null) {
6233                         it.remove();
6234                         continue;
6235                     }
6236                     if (packageName == null) {
6237                         // Stopping user, remove all objects for the user.
6238                         if (pir.key.userId != userId) {
6239                             // Not the same user, skip it.
6240                             continue;
6241                         }
6242                     } else {
6243                         if (UserHandle.getAppId(pir.uid) != appId) {
6244                             // Different app id, skip it.
6245                             continue;
6246                         }
6247                         if (userId != UserHandle.USER_ALL && pir.key.userId != userId) {
6248                             // Different user, skip it.
6249                             continue;
6250                         }
6251                         if (!pir.key.packageName.equals(packageName)) {
6252                             // Different package, skip it.
6253                             continue;
6254                         }
6255                     }
6256                     if (!doit) {
6257                         return true;
6258                     }
6259                     didSomething = true;
6260                     it.remove();
6261                     pir.canceled = true;
6262                     if (pir.key.activity != null && pir.key.activity.pendingResults != null) {
6263                         pir.key.activity.pendingResults.remove(pir.ref);
6264                     }
6265                 }
6266             }
6267         }
6268
6269         if (doit) {
6270             if (purgeCache && packageName != null) {
6271                 AttributeCache ac = AttributeCache.instance();
6272                 if (ac != null) {
6273                     ac.removePackage(packageName);
6274                 }
6275             }
6276             if (mBooted) {
6277                 mStackSupervisor.resumeFocusedStackTopActivityLocked();
6278                 mStackSupervisor.scheduleIdleLocked();
6279             }
6280         }
6281
6282         return didSomething;
6283     }
6284
6285     private final ProcessRecord removeProcessNameLocked(final String name, final int uid) {
6286         return removeProcessNameLocked(name, uid, null);
6287     }
6288
6289     private final ProcessRecord removeProcessNameLocked(final String name, final int uid,
6290             final ProcessRecord expecting) {
6291         ProcessRecord old = mProcessNames.get(name, uid);
6292         // Only actually remove when the currently recorded value matches the
6293         // record that we expected; if it doesn't match then we raced with a
6294         // newly created process and we don't want to destroy the new one.
6295         if ((expecting == null) || (old == expecting)) {
6296             mProcessNames.remove(name, uid);
6297         }
6298         if (old != null && old.uidRecord != null) {
6299             old.uidRecord.numProcs--;
6300             if (old.uidRecord.numProcs == 0) {
6301                 // No more processes using this uid, tell clients it is gone.
6302                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
6303                         "No more processes in " + old.uidRecord);
6304                 enqueueUidChangeLocked(old.uidRecord, -1, UidRecord.CHANGE_GONE);
6305                 mActiveUids.remove(uid);
6306                 noteUidProcessState(uid, ActivityManager.PROCESS_STATE_NONEXISTENT);
6307             }
6308             old.uidRecord = null;
6309         }
6310         mIsolatedProcesses.remove(uid);
6311         return old;
6312     }
6313
6314     private final void addProcessNameLocked(ProcessRecord proc) {
6315         // We shouldn't already have a process under this name, but just in case we
6316         // need to clean up whatever may be there now.
6317         ProcessRecord old = removeProcessNameLocked(proc.processName, proc.uid);
6318         if (old == proc && proc.persistent) {
6319             // We are re-adding a persistent process.  Whatevs!  Just leave it there.
6320             Slog.w(TAG, "Re-adding persistent process " + proc);
6321         } else if (old != null) {
6322             Slog.wtf(TAG, "Already have existing proc " + old + " when adding " + proc);
6323         }
6324         UidRecord uidRec = mActiveUids.get(proc.uid);
6325         if (uidRec == null) {
6326             uidRec = new UidRecord(proc.uid);
6327             // This is the first appearance of the uid, report it now!
6328             if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
6329                     "Creating new process uid: " + uidRec);
6330             mActiveUids.put(proc.uid, uidRec);
6331             noteUidProcessState(uidRec.uid, uidRec.curProcState);
6332             enqueueUidChangeLocked(uidRec, -1, UidRecord.CHANGE_ACTIVE);
6333         }
6334         proc.uidRecord = uidRec;
6335
6336         // Reset render thread tid if it was already set, so new process can set it again.
6337         proc.renderThreadTid = 0;
6338         uidRec.numProcs++;
6339         mProcessNames.put(proc.processName, proc.uid, proc);
6340         if (proc.isolated) {
6341             mIsolatedProcesses.put(proc.uid, proc);
6342         }
6343     }
6344
6345     boolean removeProcessLocked(ProcessRecord app,
6346             boolean callerWillRestart, boolean allowRestart, String reason) {
6347         final String name = app.processName;
6348         final int uid = app.uid;
6349         if (DEBUG_PROCESSES) Slog.d(TAG_PROCESSES,
6350             "Force removing proc " + app.toShortString() + " (" + name + "/" + uid + ")");
6351
6352         ProcessRecord old = mProcessNames.get(name, uid);
6353         if (old != app) {
6354             // This process is no longer active, so nothing to do.
6355             Slog.w(TAG, "Ignoring remove of inactive process: " + app);
6356             return false;
6357         }
6358         removeProcessNameLocked(name, uid);
6359         if (mHeavyWeightProcess == app) {
6360             mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG,
6361                     mHeavyWeightProcess.userId, 0));
6362             mHeavyWeightProcess = null;
6363         }
6364         boolean needRestart = false;
6365         if (app.pid > 0 && app.pid != MY_PID) {
6366             int pid = app.pid;
6367             synchronized (mPidsSelfLocked) {
6368                 mPidsSelfLocked.remove(pid);
6369                 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
6370             }
6371             mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid);
6372             if (app.isolated) {
6373                 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid);
6374             }
6375             boolean willRestart = false;
6376             if (app.persistent && !app.isolated) {
6377                 if (!callerWillRestart) {
6378                     willRestart = true;
6379                 } else {
6380                     needRestart = true;
6381                 }
6382             }
6383             app.kill(reason, true);
6384             handleAppDiedLocked(app, willRestart, allowRestart);
6385             if (willRestart) {
6386                 removeLruProcessLocked(app);
6387                 addAppLocked(app.info, false, null /* ABI override */);
6388             }
6389         } else {
6390             mRemovedProcesses.add(app);
6391         }
6392
6393         return needRestart;
6394     }
6395
6396     private final void processContentProviderPublishTimedOutLocked(ProcessRecord app) {
6397         cleanupAppInLaunchingProvidersLocked(app, true);
6398         removeProcessLocked(app, false, true, "timeout publishing content providers");
6399     }
6400
6401     private final void processStartTimedOutLocked(ProcessRecord app) {
6402         final int pid = app.pid;
6403         boolean gone = false;
6404         synchronized (mPidsSelfLocked) {
6405             ProcessRecord knownApp = mPidsSelfLocked.get(pid);
6406             if (knownApp != null && knownApp.thread == null) {
6407                 mPidsSelfLocked.remove(pid);
6408                 gone = true;
6409             }
6410         }
6411
6412         if (gone) {
6413             Slog.w(TAG, "Process " + app + " failed to attach");
6414             EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId,
6415                     pid, app.uid, app.processName);
6416             removeProcessNameLocked(app.processName, app.uid);
6417             if (mHeavyWeightProcess == app) {
6418                 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG,
6419                         mHeavyWeightProcess.userId, 0));
6420                 mHeavyWeightProcess = null;
6421             }
6422             mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid);
6423             if (app.isolated) {
6424                 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid);
6425             }
6426             // Take care of any launching providers waiting for this process.
6427             cleanupAppInLaunchingProvidersLocked(app, true);
6428             // Take care of any services that are waiting for the process.
6429             mServices.processStartTimedOutLocked(app);
6430             app.kill("start timeout", true);
6431             removeLruProcessLocked(app);
6432             if (mBackupTarget != null && mBackupTarget.app.pid == pid) {
6433                 Slog.w(TAG, "Unattached app died before backup, skipping");
6434                 try {
6435                     IBackupManager bm = IBackupManager.Stub.asInterface(
6436                             ServiceManager.getService(Context.BACKUP_SERVICE));
6437                     bm.agentDisconnected(app.info.packageName);
6438                 } catch (RemoteException e) {
6439                     // Can't happen; the backup manager is local
6440                 }
6441             }
6442             if (isPendingBroadcastProcessLocked(pid)) {
6443                 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping");
6444                 skipPendingBroadcastLocked(pid);
6445             }
6446         } else {
6447             Slog.w(TAG, "Spurious process start timeout - pid not known for " + app);
6448         }
6449     }
6450
6451     private final boolean attachApplicationLocked(IApplicationThread thread,
6452             int pid) {
6453
6454         // Find the application record that is being attached...  either via
6455         // the pid if we are running in multiple processes, or just pull the
6456         // next app record if we are emulating process with anonymous threads.
6457         ProcessRecord app;
6458         long startTime = SystemClock.uptimeMillis();
6459         if (pid != MY_PID && pid >= 0) {
6460             synchronized (mPidsSelfLocked) {
6461                 app = mPidsSelfLocked.get(pid);
6462             }
6463         } else {
6464             app = null;
6465         }
6466
6467         if (app == null) {
6468             Slog.w(TAG, "No pending application record for pid " + pid
6469                     + " (IApplicationThread " + thread + "); dropping process");
6470             EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid);
6471             if (pid > 0 && pid != MY_PID) {
6472                 Process.killProcessQuiet(pid);
6473                 //TODO: killProcessGroup(app.info.uid, pid);
6474             } else {
6475                 try {
6476                     thread.scheduleExit();
6477                 } catch (Exception e) {
6478                     // Ignore exceptions.
6479                 }
6480             }
6481             return false;
6482         }
6483
6484         // If this application record is still attached to a previous
6485         // process, clean it up now.
6486         if (app.thread != null) {
6487             handleAppDiedLocked(app, true, true);
6488         }
6489
6490         // Tell the process all about itself.
6491
6492         if (DEBUG_ALL) Slog.v(
6493                 TAG, "Binding process pid " + pid + " to record " + app);
6494
6495         final String processName = app.processName;
6496         try {
6497             AppDeathRecipient adr = new AppDeathRecipient(
6498                     app, pid, thread);
6499             thread.asBinder().linkToDeath(adr, 0);
6500             app.deathRecipient = adr;
6501         } catch (RemoteException e) {
6502             app.resetPackageList(mProcessStats);
6503             startProcessLocked(app, "link fail", processName);
6504             return false;
6505         }
6506
6507         EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName);
6508
6509         app.makeActive(thread, mProcessStats);
6510         app.curAdj = app.setAdj = app.verifiedAdj = ProcessList.INVALID_ADJ;
6511         app.curSchedGroup = app.setSchedGroup = ProcessList.SCHED_GROUP_DEFAULT;
6512         app.forcingToForeground = null;
6513         updateProcessForegroundLocked(app, false, false);
6514         app.hasShownUi = false;
6515         app.debugging = false;
6516         app.cached = false;
6517         app.killedByAm = false;
6518
6519         // We carefully use the same state that PackageManager uses for
6520         // filtering, since we use this flag to decide if we need to install
6521         // providers when user is unlocked later
6522         app.unlocked = StorageManager.isUserKeyUnlocked(app.userId);
6523
6524         mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
6525
6526         boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info);
6527         List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null;
6528
6529         if (providers != null && checkAppInLaunchingProvidersLocked(app)) {
6530             Message msg = mHandler.obtainMessage(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG);
6531             msg.obj = app;
6532             mHandler.sendMessageDelayed(msg, CONTENT_PROVIDER_PUBLISH_TIMEOUT);
6533         }
6534
6535         checkTime(startTime, "attachApplicationLocked: before bindApplication");
6536         
6537         if (!normalMode) {
6538             Slog.i(TAG, "Launching preboot mode app: " + app);
6539         }
6540
6541         if (DEBUG_ALL) Slog.v(
6542             TAG, "New app record " + app
6543             + " thread=" + thread.asBinder() + " pid=" + pid);
6544         try {
6545             int testMode = IApplicationThread.DEBUG_OFF;
6546             if (mDebugApp != null && mDebugApp.equals(processName)) {
6547                 testMode = mWaitForDebugger
6548                     ? IApplicationThread.DEBUG_WAIT
6549                     : IApplicationThread.DEBUG_ON;
6550                 app.debugging = true;
6551                 if (mDebugTransient) {
6552                     mDebugApp = mOrigDebugApp;
6553                     mWaitForDebugger = mOrigWaitForDebugger;
6554                 }
6555             }
6556             String profileFile = app.instrumentationProfileFile;
6557             ParcelFileDescriptor profileFd = null;
6558             int samplingInterval = 0;
6559             boolean profileAutoStop = false;
6560             if (mProfileApp != null && mProfileApp.equals(processName)) {
6561                 mProfileProc = app;
6562                 profileFile = mProfileFile;
6563                 profileFd = mProfileFd;
6564                 samplingInterval = mSamplingInterval;
6565                 profileAutoStop = mAutoStopProfiler;
6566             }
6567             boolean enableTrackAllocation = false;
6568             if (mTrackAllocationApp != null && mTrackAllocationApp.equals(processName)) {
6569                 enableTrackAllocation = true;
6570                 mTrackAllocationApp = null;
6571             }
6572
6573             // If the app is being launched for restore or full backup, set it up specially
6574             boolean isRestrictedBackupMode = false;
6575             if (mBackupTarget != null && mBackupAppName.equals(processName)) {
6576                 isRestrictedBackupMode = mBackupTarget.appInfo.uid >= Process.FIRST_APPLICATION_UID
6577                         && ((mBackupTarget.backupMode == BackupRecord.RESTORE)
6578                                 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL)
6579                                 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL));
6580             }
6581
6582             if (app.instrumentationClass != null) {
6583                 notifyPackageUse(app.instrumentationClass.getPackageName(),
6584                                  PackageManager.NOTIFY_PACKAGE_USE_INSTRUMENTATION);
6585             }
6586             if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Binding proc "
6587                     + processName + " with config " + mConfiguration);
6588             ApplicationInfo appInfo = app.instrumentationInfo != null
6589                     ? app.instrumentationInfo : app.info;
6590             app.compat = compatibilityInfoForPackageLocked(appInfo);
6591             if (profileFd != null) {
6592                 profileFd = profileFd.dup();
6593             }
6594             ProfilerInfo profilerInfo = profileFile == null ? null
6595                 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop);
6596             checkTime(startTime, "attachApplicationLocked: immediately before bindApplication");
6597             thread.bindApplication(processName, appInfo, providers, app.instrumentationClass,
6598                     profilerInfo, app.instrumentationArguments, app.instrumentationWatcher,
6599                     app.instrumentationUiAutomationConnection, testMode,
6600                     mBinderTransactionTrackingEnabled, enableTrackAllocation,
6601                     isRestrictedBackupMode || !normalMode, app.persistent,
6602                     new Configuration(mConfiguration), app.compat,
6603                     getCommonServicesLocked(app.isolated),
6604                                    mCoreSettingsObserver.getCoreSettingsLocked());
6605             checkTime(startTime, "attachApplicationLocked: immediately after bindApplication");
6606             updateLruProcessLocked(app, false, null);
6607             checkTime(startTime, "attachApplicationLocked: after updateLruProcessLocked");
6608             app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis();
6609         } catch (Exception e) {
6610             // todo: Yikes!  What should we do?  For now we will try to
6611             // start another process, but that could easily get us in
6612             // an infinite loop of restarting processes...
6613             Slog.wtf(TAG, "Exception thrown during bind of " + app, e);
6614
6615             app.resetPackageList(mProcessStats);
6616             app.unlinkDeathRecipient();
6617             startProcessLocked(app, "bind fail", processName);
6618             return false;
6619         }
6620
6621         // Remove this record from the list of starting applications.
6622         mPersistentStartingProcesses.remove(app);
6623         if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES,
6624                 "Attach application locked removing on hold: " + app);
6625         mProcessesOnHold.remove(app);
6626
6627         boolean badApp = false;
6628         boolean didSomething = false;
6629
6630         // See if the top visible activity is waiting to run in this process...
6631         if (normalMode) {
6632             try {
6633                 if (mStackSupervisor.attachApplicationLocked(app)) {
6634                     didSomething = true;
6635                 }
6636             } catch (Exception e) {
6637                 Slog.wtf(TAG, "Exception thrown launching activities in " + app, e);
6638                 badApp = true;
6639             }
6640         }
6641
6642         // Find any services that should be running in this process...
6643         if (!badApp) {
6644             try {
6645                 didSomething |= mServices.attachApplicationLocked(app, processName);
6646                 checkTime(startTime, "attachApplicationLocked: after mServices.attachApplicationLocked");
6647             } catch (Exception e) {
6648                 Slog.wtf(TAG, "Exception thrown starting services in " + app, e);
6649                 badApp = true;
6650             }
6651         }
6652
6653         // Check if a next-broadcast receiver is in this process...
6654         if (!badApp && isPendingBroadcastProcessLocked(pid)) {
6655             try {
6656                 didSomething |= sendPendingBroadcastsLocked(app);
6657                 checkTime(startTime, "attachApplicationLocked: after sendPendingBroadcastsLocked");
6658             } catch (Exception e) {
6659                 // If the app died trying to launch the receiver we declare it 'bad'
6660                 Slog.wtf(TAG, "Exception thrown dispatching broadcasts in " + app, e);
6661                 badApp = true;
6662             }
6663         }
6664
6665         // Check whether the next backup agent is in this process...
6666         if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) {
6667             if (DEBUG_BACKUP) Slog.v(TAG_BACKUP,
6668                     "New app is backup target, launching agent for " + app);
6669             notifyPackageUse(mBackupTarget.appInfo.packageName,
6670                              PackageManager.NOTIFY_PACKAGE_USE_BACKUP);
6671             try {
6672                 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo,
6673                         compatibilityInfoForPackageLocked(mBackupTarget.appInfo),
6674                         mBackupTarget.backupMode);
6675             } catch (Exception e) {
6676                 Slog.wtf(TAG, "Exception thrown creating backup agent in " + app, e);
6677                 badApp = true;
6678             }
6679         }
6680
6681         if (badApp) {
6682             app.kill("error during init", true);
6683             handleAppDiedLocked(app, false, true);
6684             return false;
6685         }
6686
6687         if (!didSomething) {
6688             updateOomAdjLocked();
6689             checkTime(startTime, "attachApplicationLocked: after updateOomAdjLocked");
6690         }
6691
6692         return true;
6693     }
6694
6695     @Override
6696     public final void attachApplication(IApplicationThread thread) {
6697         synchronized (this) {
6698             int callingPid = Binder.getCallingPid();
6699             final long origId = Binder.clearCallingIdentity();
6700             attachApplicationLocked(thread, callingPid);
6701             Binder.restoreCallingIdentity(origId);
6702         }
6703     }
6704
6705     @Override
6706     public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) {
6707         final long origId = Binder.clearCallingIdentity();
6708         synchronized (this) {
6709             ActivityStack stack = ActivityRecord.getStackLocked(token);
6710             if (stack != null) {
6711                 ActivityRecord r =
6712                         mStackSupervisor.activityIdleInternalLocked(token, false, config);
6713                 if (stopProfiling) {
6714                     if ((mProfileProc == r.app) && (mProfileFd != null)) {
6715                         try {
6716                             mProfileFd.close();
6717                         } catch (IOException e) {
6718                         }
6719                         clearProfilerLocked();
6720                     }
6721                 }
6722             }
6723         }
6724         Binder.restoreCallingIdentity(origId);
6725     }
6726
6727     void postFinishBooting(boolean finishBooting, boolean enableScreen) {
6728         mHandler.sendMessage(mHandler.obtainMessage(FINISH_BOOTING_MSG,
6729                 finishBooting ? 1 : 0, enableScreen ? 1 : 0));
6730     }
6731
6732     void enableScreenAfterBoot() {
6733         EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN,
6734                 SystemClock.uptimeMillis());
6735         mWindowManager.enableScreenAfterBoot();
6736
6737         synchronized (this) {
6738             updateEventDispatchingLocked();
6739         }
6740     }
6741
6742     @Override
6743     public void showBootMessage(final CharSequence msg, final boolean always) {
6744         if (Binder.getCallingUid() != Process.myUid()) {
6745             throw new SecurityException();
6746         }
6747         mWindowManager.showBootMessage(msg, always);
6748     }
6749
6750     @Override
6751     public void keyguardWaitingForActivityDrawn() {
6752         enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn");
6753         final long token = Binder.clearCallingIdentity();
6754         try {
6755             synchronized (this) {
6756                 if (DEBUG_LOCKSCREEN) logLockScreen("");
6757                 mWindowManager.keyguardWaitingForActivityDrawn();
6758                 if (mLockScreenShown == LOCK_SCREEN_SHOWN) {
6759                     mLockScreenShown = LOCK_SCREEN_LEAVING;
6760                     updateSleepIfNeededLocked();
6761                 }
6762             }
6763         } finally {
6764             Binder.restoreCallingIdentity(token);
6765         }
6766     }
6767
6768     @Override
6769     public void keyguardGoingAway(int flags) {
6770         enforceNotIsolatedCaller("keyguardGoingAway");
6771         final long token = Binder.clearCallingIdentity();
6772         try {
6773             synchronized (this) {
6774                 if (DEBUG_LOCKSCREEN) logLockScreen("");
6775                 mWindowManager.keyguardGoingAway(flags);
6776                 if (mLockScreenShown == LOCK_SCREEN_SHOWN) {
6777                     mLockScreenShown = LOCK_SCREEN_HIDDEN;
6778                     updateSleepIfNeededLocked();
6779
6780                     // Some stack visibility might change (e.g. docked stack)
6781                     mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
6782                 }
6783             }
6784         } finally {
6785             Binder.restoreCallingIdentity(token);
6786         }
6787     }
6788
6789     final void finishBooting() {
6790         synchronized (this) {
6791             if (!mBootAnimationComplete) {
6792                 mCallFinishBooting = true;
6793                 return;
6794             }
6795             mCallFinishBooting = false;
6796         }
6797
6798         ArraySet<String> completedIsas = new ArraySet<String>();
6799         for (String abi : Build.SUPPORTED_ABIS) {
6800             Process.establishZygoteConnectionForAbi(abi);
6801             final String instructionSet = VMRuntime.getInstructionSet(abi);
6802             if (!completedIsas.contains(instructionSet)) {
6803                 try {
6804                     mInstaller.markBootComplete(VMRuntime.getInstructionSet(abi));
6805                 } catch (InstallerException e) {
6806                     Slog.w(TAG, "Unable to mark boot complete for abi: " + abi + " (" +
6807                             e.getMessage() +")");
6808                 }
6809                 completedIsas.add(instructionSet);
6810             }
6811         }
6812
6813         IntentFilter pkgFilter = new IntentFilter();
6814         pkgFilter.addAction(Intent.ACTION_QUERY_PACKAGE_RESTART);
6815         pkgFilter.addDataScheme("package");
6816         mContext.registerReceiver(new BroadcastReceiver() {
6817             @Override
6818             public void onReceive(Context context, Intent intent) {
6819                 String[] pkgs = intent.getStringArrayExtra(Intent.EXTRA_PACKAGES);
6820                 if (pkgs != null) {
6821                     for (String pkg : pkgs) {
6822                         synchronized (ActivityManagerService.this) {
6823                             if (forceStopPackageLocked(pkg, -1, false, false, false, false, false,
6824                                     0, "query restart")) {
6825                                 setResultCode(Activity.RESULT_OK);
6826                                 return;
6827                             }
6828                         }
6829                     }
6830                 }
6831             }
6832         }, pkgFilter);
6833
6834         IntentFilter dumpheapFilter = new IntentFilter();
6835         dumpheapFilter.addAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP);
6836         mContext.registerReceiver(new BroadcastReceiver() {
6837             @Override
6838             public void onReceive(Context context, Intent intent) {
6839                 if (intent.getBooleanExtra(DumpHeapActivity.EXTRA_DELAY_DELETE, false)) {
6840                     mHandler.sendEmptyMessageDelayed(POST_DUMP_HEAP_NOTIFICATION_MSG, 5*60*1000);
6841                 } else {
6842                     mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG);
6843                 }
6844             }
6845         }, dumpheapFilter);
6846
6847         // Let system services know.
6848         mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED);
6849
6850         synchronized (this) {
6851             // Ensure that any processes we had put on hold are now started
6852             // up.
6853             final int NP = mProcessesOnHold.size();
6854             if (NP > 0) {
6855                 ArrayList<ProcessRecord> procs =
6856                     new ArrayList<ProcessRecord>(mProcessesOnHold);
6857                 for (int ip=0; ip<NP; ip++) {
6858                     if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "Starting process on hold: "
6859                             + procs.get(ip));
6860                     startProcessLocked(procs.get(ip), "on-hold", null);
6861                 }
6862             }
6863
6864             if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
6865                 // Start looking for apps that are abusing wake locks.
6866                 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG);
6867                 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY);
6868                 // Tell anyone interested that we are done booting!
6869                 SystemProperties.set("sys.boot_completed", "1");
6870
6871                 // And trigger dev.bootcomplete if we are not showing encryption progress
6872                 if (!"trigger_restart_min_framework".equals(SystemProperties.get("vold.decrypt"))
6873                     || "".equals(SystemProperties.get("vold.encrypt_progress"))) {
6874                     SystemProperties.set("dev.bootcomplete", "1");
6875                 }
6876                 mUserController.sendBootCompletedLocked(
6877                         new IIntentReceiver.Stub() {
6878                             @Override
6879                             public void performReceive(Intent intent, int resultCode,
6880                                     String data, Bundle extras, boolean ordered,
6881                                     boolean sticky, int sendingUser) {
6882                                 synchronized (ActivityManagerService.this) {
6883                                     requestPssAllProcsLocked(SystemClock.uptimeMillis(),
6884                                             true, false);
6885                                 }
6886                             }
6887                         });
6888                 scheduleStartProfilesLocked();
6889             }
6890         }
6891     }
6892
6893     @Override
6894     public void bootAnimationComplete() {
6895         final boolean callFinishBooting;
6896         synchronized (this) {
6897             callFinishBooting = mCallFinishBooting;
6898             mBootAnimationComplete = true;
6899         }
6900         if (callFinishBooting) {
6901             Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting");
6902             finishBooting();
6903             Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
6904         }
6905     }
6906
6907     final void ensureBootCompleted() {
6908         boolean booting;
6909         boolean enableScreen;
6910         synchronized (this) {
6911             booting = mBooting;
6912             mBooting = false;
6913             enableScreen = !mBooted;
6914             mBooted = true;
6915         }
6916
6917         if (booting) {
6918             Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting");
6919             finishBooting();
6920             Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
6921         }
6922
6923         if (enableScreen) {
6924             enableScreenAfterBoot();
6925         }
6926     }
6927
6928     @Override
6929     public final void activityResumed(IBinder token) {
6930         final long origId = Binder.clearCallingIdentity();
6931         synchronized(this) {
6932             ActivityStack stack = ActivityRecord.getStackLocked(token);
6933             if (stack != null) {
6934                 stack.activityResumedLocked(token);
6935             }
6936         }
6937         Binder.restoreCallingIdentity(origId);
6938     }
6939
6940     @Override
6941     public final void activityPaused(IBinder token) {
6942         final long origId = Binder.clearCallingIdentity();
6943         synchronized(this) {
6944             ActivityStack stack = ActivityRecord.getStackLocked(token);
6945             if (stack != null) {
6946                 stack.activityPausedLocked(token, false);
6947             }
6948         }
6949         Binder.restoreCallingIdentity(origId);
6950     }
6951
6952     @Override
6953     public final void activityStopped(IBinder token, Bundle icicle,
6954             PersistableBundle persistentState, CharSequence description) {
6955         if (DEBUG_ALL) Slog.v(TAG, "Activity stopped: token=" + token);
6956
6957         // Refuse possible leaked file descriptors
6958         if (icicle != null && icicle.hasFileDescriptors()) {
6959             throw new IllegalArgumentException("File descriptors passed in Bundle");
6960         }
6961
6962         final long origId = Binder.clearCallingIdentity();
6963
6964         synchronized (this) {
6965             ActivityRecord r = ActivityRecord.isInStackLocked(token);
6966             if (r != null) {
6967                 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description);
6968             }
6969         }
6970
6971         trimApplications();
6972
6973         Binder.restoreCallingIdentity(origId);
6974     }
6975
6976     @Override
6977     public final void activityDestroyed(IBinder token) {
6978         if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "ACTIVITY DESTROYED: " + token);
6979         synchronized (this) {
6980             ActivityStack stack = ActivityRecord.getStackLocked(token);
6981             if (stack != null) {
6982                 stack.activityDestroyedLocked(token, "activityDestroyed");
6983             }
6984         }
6985     }
6986
6987     @Override
6988     public final void activityRelaunched(IBinder token) {
6989         final long origId = Binder.clearCallingIdentity();
6990         synchronized (this) {
6991             mStackSupervisor.activityRelaunchedLocked(token);
6992         }
6993         Binder.restoreCallingIdentity(origId);
6994     }
6995
6996     @Override
6997     public void reportSizeConfigurations(IBinder token, int[] horizontalSizeConfiguration,
6998             int[] verticalSizeConfigurations, int[] smallestSizeConfigurations) {
6999         if (DEBUG_CONFIGURATION) Slog.v(TAG, "Report configuration: " + token + " "
7000                 + horizontalSizeConfiguration + " " + verticalSizeConfigurations);
7001         synchronized (this) {
7002             ActivityRecord record = ActivityRecord.isInStackLocked(token);
7003             if (record == null) {
7004                 throw new IllegalArgumentException("reportSizeConfigurations: ActivityRecord not "
7005                         + "found for: " + token);
7006             }
7007             record.setSizeConfigurations(horizontalSizeConfiguration,
7008                     verticalSizeConfigurations, smallestSizeConfigurations);
7009         }
7010     }
7011
7012     @Override
7013     public final void backgroundResourcesReleased(IBinder token) {
7014         final long origId = Binder.clearCallingIdentity();
7015         try {
7016             synchronized (this) {
7017                 ActivityStack stack = ActivityRecord.getStackLocked(token);
7018                 if (stack != null) {
7019                     stack.backgroundResourcesReleased();
7020                 }
7021             }
7022         } finally {
7023             Binder.restoreCallingIdentity(origId);
7024         }
7025     }
7026
7027     @Override
7028     public final void notifyLaunchTaskBehindComplete(IBinder token) {
7029         mStackSupervisor.scheduleLaunchTaskBehindComplete(token);
7030     }
7031
7032     @Override
7033     public final void notifyEnterAnimationComplete(IBinder token) {
7034         mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token));
7035     }
7036
7037     @Override
7038     public String getCallingPackage(IBinder token) {
7039         synchronized (this) {
7040             ActivityRecord r = getCallingRecordLocked(token);
7041             return r != null ? r.info.packageName : null;
7042         }
7043     }
7044
7045     @Override
7046     public ComponentName getCallingActivity(IBinder token) {
7047         synchronized (this) {
7048             ActivityRecord r = getCallingRecordLocked(token);
7049             return r != null ? r.intent.getComponent() : null;
7050         }
7051     }
7052
7053     private ActivityRecord getCallingRecordLocked(IBinder token) {
7054         ActivityRecord r = ActivityRecord.isInStackLocked(token);
7055         if (r == null) {
7056             return null;
7057         }
7058         return r.resultTo;
7059     }
7060
7061     @Override
7062     public ComponentName getActivityClassForToken(IBinder token) {
7063         synchronized(this) {
7064             ActivityRecord r = ActivityRecord.isInStackLocked(token);
7065             if (r == null) {
7066                 return null;
7067             }
7068             return r.intent.getComponent();
7069         }
7070     }
7071
7072     @Override
7073     public String getPackageForToken(IBinder token) {
7074         synchronized(this) {
7075             ActivityRecord r = ActivityRecord.isInStackLocked(token);
7076             if (r == null) {
7077                 return null;
7078             }
7079             return r.packageName;
7080         }
7081     }
7082
7083     @Override
7084     public boolean isRootVoiceInteraction(IBinder token) {
7085         synchronized(this) {
7086             ActivityRecord r = ActivityRecord.isInStackLocked(token);
7087             if (r == null) {
7088                 return false;
7089             }
7090             return r.rootVoiceInteraction;
7091         }
7092     }
7093
7094     @Override
7095     public IIntentSender getIntentSender(int type,
7096             String packageName, IBinder token, String resultWho,
7097             int requestCode, Intent[] intents, String[] resolvedTypes,
7098             int flags, Bundle bOptions, int userId) {
7099         enforceNotIsolatedCaller("getIntentSender");
7100         // Refuse possible leaked file descriptors
7101         if (intents != null) {
7102             if (intents.length < 1) {
7103                 throw new IllegalArgumentException("Intents array length must be >= 1");
7104             }
7105             for (int i=0; i<intents.length; i++) {
7106                 Intent intent = intents[i];
7107                 if (intent != null) {
7108                     if (intent.hasFileDescriptors()) {
7109                         throw new IllegalArgumentException("File descriptors passed in Intent");
7110                     }
7111                     if (type == ActivityManager.INTENT_SENDER_BROADCAST &&
7112                             (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) {
7113                         throw new IllegalArgumentException(
7114                                 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here");
7115                     }
7116                     intents[i] = new Intent(intent);
7117                 }
7118             }
7119             if (resolvedTypes != null && resolvedTypes.length != intents.length) {
7120                 throw new IllegalArgumentException(
7121                         "Intent array length does not match resolvedTypes length");
7122             }
7123         }
7124         if (bOptions != null) {
7125             if (bOptions.hasFileDescriptors()) {
7126                 throw new IllegalArgumentException("File descriptors passed in options");
7127             }
7128         }
7129
7130         synchronized(this) {
7131             int callingUid = Binder.getCallingUid();
7132             int origUserId = userId;
7133             userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId,
7134                     type == ActivityManager.INTENT_SENDER_BROADCAST,
7135                     ALLOW_NON_FULL, "getIntentSender", null);
7136             if (origUserId == UserHandle.USER_CURRENT) {
7137                 // We don't want to evaluate this until the pending intent is
7138                 // actually executed.  However, we do want to always do the
7139                 // security checking for it above.
7140                 userId = UserHandle.USER_CURRENT;
7141             }
7142             try {
7143                 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) {
7144                     final int uid = AppGlobals.getPackageManager().getPackageUid(packageName,
7145                             MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getUserId(callingUid));
7146                     if (!UserHandle.isSameApp(callingUid, uid)) {
7147                         String msg = "Permission Denial: getIntentSender() from pid="
7148                             + Binder.getCallingPid()
7149                             + ", uid=" + Binder.getCallingUid()
7150                             + ", (need uid=" + uid + ")"
7151                             + " is not allowed to send as package " + packageName;
7152                         Slog.w(TAG, msg);
7153                         throw new SecurityException(msg);
7154                     }
7155                 }
7156
7157                 return getIntentSenderLocked(type, packageName, callingUid, userId,
7158                         token, resultWho, requestCode, intents, resolvedTypes, flags, bOptions);
7159
7160             } catch (RemoteException e) {
7161                 throw new SecurityException(e);
7162             }
7163         }
7164     }
7165
7166     IIntentSender getIntentSenderLocked(int type, String packageName,
7167             int callingUid, int userId, IBinder token, String resultWho,
7168             int requestCode, Intent[] intents, String[] resolvedTypes, int flags,
7169             Bundle bOptions) {
7170         if (DEBUG_MU) Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid);
7171         ActivityRecord activity = null;
7172         if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) {
7173             activity = ActivityRecord.isInStackLocked(token);
7174             if (activity == null) {
7175                 Slog.w(TAG, "Failed createPendingResult: activity " + token + " not in any stack");
7176                 return null;
7177             }
7178             if (activity.finishing) {
7179                 Slog.w(TAG, "Failed createPendingResult: activity " + activity + " is finishing");
7180                 return null;
7181             }
7182         }
7183
7184         // We're going to be splicing together extras before sending, so we're
7185         // okay poking into any contained extras.
7186         if (intents != null) {
7187             for (int i = 0; i < intents.length; i++) {
7188                 intents[i].setDefusable(true);
7189             }
7190         }
7191         Bundle.setDefusable(bOptions, true);
7192
7193         final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0;
7194         final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0;
7195         final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0;
7196         flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT
7197                 |PendingIntent.FLAG_UPDATE_CURRENT);
7198
7199         PendingIntentRecord.Key key = new PendingIntentRecord.Key(
7200                 type, packageName, activity, resultWho,
7201                 requestCode, intents, resolvedTypes, flags, bOptions, userId);
7202         WeakReference<PendingIntentRecord> ref;
7203         ref = mIntentSenderRecords.get(key);
7204         PendingIntentRecord rec = ref != null ? ref.get() : null;
7205         if (rec != null) {
7206             if (!cancelCurrent) {
7207                 if (updateCurrent) {
7208                     if (rec.key.requestIntent != null) {
7209                         rec.key.requestIntent.replaceExtras(intents != null ?
7210                                 intents[intents.length - 1] : null);
7211                     }
7212                     if (intents != null) {
7213                         intents[intents.length-1] = rec.key.requestIntent;
7214                         rec.key.allIntents = intents;
7215                         rec.key.allResolvedTypes = resolvedTypes;
7216                     } else {
7217                         rec.key.allIntents = null;
7218                         rec.key.allResolvedTypes = null;
7219                     }
7220                 }
7221                 return rec;
7222             }
7223             rec.canceled = true;
7224             mIntentSenderRecords.remove(key);
7225         }
7226         if (noCreate) {
7227             return rec;
7228         }
7229         rec = new PendingIntentRecord(this, key, callingUid);
7230         mIntentSenderRecords.put(key, rec.ref);
7231         if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) {
7232             if (activity.pendingResults == null) {
7233                 activity.pendingResults
7234                         = new HashSet<WeakReference<PendingIntentRecord>>();
7235             }
7236             activity.pendingResults.add(rec.ref);
7237         }
7238         return rec;
7239     }
7240
7241     @Override
7242     public int sendIntentSender(IIntentSender target, int code, Intent intent, String resolvedType,
7243             IIntentReceiver finishedReceiver, String requiredPermission, Bundle options) {
7244         if (target instanceof PendingIntentRecord) {
7245             return ((PendingIntentRecord)target).sendWithResult(code, intent, resolvedType,
7246                     finishedReceiver, requiredPermission, options);
7247         } else {
7248             if (intent == null) {
7249                 // Weird case: someone has given us their own custom IIntentSender, and now
7250                 // they have someone else trying to send to it but of course this isn't
7251                 // really a PendingIntent, so there is no base Intent, and the caller isn't
7252                 // supplying an Intent... but we never want to dispatch a null Intent to
7253                 // a receiver, so um...  let's make something up.
7254                 Slog.wtf(TAG, "Can't use null intent with direct IIntentSender call");
7255                 intent = new Intent(Intent.ACTION_MAIN);
7256             }
7257             try {
7258                 target.send(code, intent, resolvedType, null, requiredPermission, options);
7259             } catch (RemoteException e) {
7260             }
7261             // Platform code can rely on getting a result back when the send is done, but if
7262             // this intent sender is from outside of the system we can't rely on it doing that.
7263             // So instead we don't give it the result receiver, and instead just directly
7264             // report the finish immediately.
7265             if (finishedReceiver != null) {
7266                 try {
7267                     finishedReceiver.performReceive(intent, 0,
7268                             null, null, false, false, UserHandle.getCallingUserId());
7269                 } catch (RemoteException e) {
7270                 }
7271             }
7272             return 0;
7273         }
7274     }
7275
7276     /**
7277      * Whitelists {@code targetUid} to temporarily bypass Power Save mode.
7278      *
7279      * <p>{@code callerUid} must be allowed to request such whitelist by calling
7280      * {@link #addTempPowerSaveWhitelistGrantorUid(int)}.
7281      */
7282     void tempWhitelistAppForPowerSave(int callerPid, int callerUid, int targetUid, long duration) {
7283         if (DEBUG_WHITELISTS) {
7284             Slog.d(TAG, "tempWhitelistAppForPowerSave(" + callerPid + ", " + callerUid + ", "
7285                     + targetUid + ", " + duration + ")");
7286         }
7287         synchronized (mPidsSelfLocked) {
7288             final ProcessRecord pr = mPidsSelfLocked.get(callerPid);
7289             if (pr == null) {
7290                 Slog.w(TAG, "tempWhitelistAppForPowerSave() no ProcessRecord for pid " + callerPid);
7291                 return;
7292             }
7293             if (!pr.whitelistManager) {
7294                 if (DEBUG_WHITELISTS) {
7295                     Slog.d(TAG, "tempWhitelistAppForPowerSave() for target " + targetUid + ": pid "
7296                             + callerPid + " is not allowed");
7297                 }
7298                 return;
7299             }
7300         }
7301
7302         final long token = Binder.clearCallingIdentity();
7303         try {
7304             mLocalDeviceIdleController.addPowerSaveTempWhitelistAppDirect(targetUid, duration,
7305                     true, "pe from uid:" + callerUid);
7306         } finally {
7307             Binder.restoreCallingIdentity(token);
7308         }
7309     }
7310
7311     @Override
7312     public void cancelIntentSender(IIntentSender sender) {
7313         if (!(sender instanceof PendingIntentRecord)) {
7314             return;
7315         }
7316         synchronized(this) {
7317             PendingIntentRecord rec = (PendingIntentRecord)sender;
7318             try {
7319                 final int uid = AppGlobals.getPackageManager().getPackageUid(rec.key.packageName,
7320                         MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getCallingUserId());
7321                 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) {
7322                     String msg = "Permission Denial: cancelIntentSender() from pid="
7323                         + Binder.getCallingPid()
7324                         + ", uid=" + Binder.getCallingUid()
7325                         + " is not allowed to cancel packges "
7326                         + rec.key.packageName;
7327                     Slog.w(TAG, msg);
7328                     throw new SecurityException(msg);
7329                 }
7330             } catch (RemoteException e) {
7331                 throw new SecurityException(e);
7332             }
7333             cancelIntentSenderLocked(rec, true);
7334         }
7335     }
7336
7337     void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) {
7338         rec.canceled = true;
7339         mIntentSenderRecords.remove(rec.key);
7340         if (cleanActivity && rec.key.activity != null) {
7341             rec.key.activity.pendingResults.remove(rec.ref);
7342         }
7343     }
7344
7345     @Override
7346     public String getPackageForIntentSender(IIntentSender pendingResult) {
7347         if (!(pendingResult instanceof PendingIntentRecord)) {
7348             return null;
7349         }
7350         try {
7351             PendingIntentRecord res = (PendingIntentRecord)pendingResult;
7352             return res.key.packageName;
7353         } catch (ClassCastException e) {
7354         }
7355         return null;
7356     }
7357
7358     @Override
7359     public int getUidForIntentSender(IIntentSender sender) {
7360         if (sender instanceof PendingIntentRecord) {
7361             try {
7362                 PendingIntentRecord res = (PendingIntentRecord)sender;
7363                 return res.uid;
7364             } catch (ClassCastException e) {
7365             }
7366         }
7367         return -1;
7368     }
7369
7370     @Override
7371     public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) {
7372         if (!(pendingResult instanceof PendingIntentRecord)) {
7373             return false;
7374         }
7375         try {
7376             PendingIntentRecord res = (PendingIntentRecord)pendingResult;
7377             if (res.key.allIntents == null) {
7378                 return false;
7379             }
7380             for (int i=0; i<res.key.allIntents.length; i++) {
7381                 Intent intent = res.key.allIntents[i];
7382                 if (intent.getPackage() != null && intent.getComponent() != null) {
7383                     return false;
7384                 }
7385             }
7386             return true;
7387         } catch (ClassCastException e) {
7388         }
7389         return false;
7390     }
7391
7392     @Override
7393     public boolean isIntentSenderAnActivity(IIntentSender pendingResult) {
7394         if (!(pendingResult instanceof PendingIntentRecord)) {
7395             return false;
7396         }
7397         try {
7398             PendingIntentRecord res = (PendingIntentRecord)pendingResult;
7399             if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) {
7400                 return true;
7401             }
7402             return false;
7403         } catch (ClassCastException e) {
7404         }
7405         return false;
7406     }
7407
7408     @Override
7409     public Intent getIntentForIntentSender(IIntentSender pendingResult) {
7410         enforceCallingPermission(Manifest.permission.GET_INTENT_SENDER_INTENT,
7411                 "getIntentForIntentSender()");
7412         if (!(pendingResult instanceof PendingIntentRecord)) {
7413             return null;
7414         }
7415         try {
7416             PendingIntentRecord res = (PendingIntentRecord)pendingResult;
7417             return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null;
7418         } catch (ClassCastException e) {
7419         }
7420         return null;
7421     }
7422
7423     @Override
7424     public String getTagForIntentSender(IIntentSender pendingResult, String prefix) {
7425         if (!(pendingResult instanceof PendingIntentRecord)) {
7426             return null;
7427         }
7428         try {
7429             PendingIntentRecord res = (PendingIntentRecord)pendingResult;
7430             synchronized (this) {
7431                 return getTagForIntentSenderLocked(res, prefix);
7432             }
7433         } catch (ClassCastException e) {
7434         }
7435         return null;
7436     }
7437
7438     String getTagForIntentSenderLocked(PendingIntentRecord res, String prefix) {
7439         final Intent intent = res.key.requestIntent;
7440         if (intent != null) {
7441             if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null
7442                     || res.lastTagPrefix.equals(prefix))) {
7443                 return res.lastTag;
7444             }
7445             res.lastTagPrefix = prefix;
7446             final StringBuilder sb = new StringBuilder(128);
7447             if (prefix != null) {
7448                 sb.append(prefix);
7449             }
7450             if (intent.getAction() != null) {
7451                 sb.append(intent.getAction());
7452             } else if (intent.getComponent() != null) {
7453                 intent.getComponent().appendShortString(sb);
7454             } else {
7455                 sb.append("?");
7456             }
7457             return res.lastTag = sb.toString();
7458         }
7459         return null;
7460     }
7461
7462     @Override
7463     public void setProcessLimit(int max) {
7464         enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT,
7465                 "setProcessLimit()");
7466         synchronized (this) {
7467             mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max;
7468             mProcessLimitOverride = max;
7469         }
7470         trimApplications();
7471     }
7472
7473     @Override
7474     public int getProcessLimit() {
7475         synchronized (this) {
7476             return mProcessLimitOverride;
7477         }
7478     }
7479
7480     void foregroundTokenDied(ForegroundToken token) {
7481         synchronized (ActivityManagerService.this) {
7482             synchronized (mPidsSelfLocked) {
7483                 ForegroundToken cur
7484                     = mForegroundProcesses.get(token.pid);
7485                 if (cur != token) {
7486                     return;
7487                 }
7488                 mForegroundProcesses.remove(token.pid);
7489                 ProcessRecord pr = mPidsSelfLocked.get(token.pid);
7490                 if (pr == null) {
7491                     return;
7492                 }
7493                 pr.forcingToForeground = null;
7494                 updateProcessForegroundLocked(pr, false, false);
7495             }
7496             updateOomAdjLocked();
7497         }
7498     }
7499
7500     @Override
7501     public void setProcessForeground(IBinder token, int pid, boolean isForeground) {
7502         enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT,
7503                 "setProcessForeground()");
7504         synchronized(this) {
7505             boolean changed = false;
7506
7507             synchronized (mPidsSelfLocked) {
7508                 ProcessRecord pr = mPidsSelfLocked.get(pid);
7509                 if (pr == null && isForeground) {
7510                     Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid);
7511                     return;
7512                 }
7513                 ForegroundToken oldToken = mForegroundProcesses.get(pid);
7514                 if (oldToken != null) {
7515                     oldToken.token.unlinkToDeath(oldToken, 0);
7516                     mForegroundProcesses.remove(pid);
7517                     if (pr != null) {
7518                         pr.forcingToForeground = null;
7519                     }
7520                     changed = true;
7521                 }
7522                 if (isForeground && token != null) {
7523                     ForegroundToken newToken = new ForegroundToken() {
7524                         @Override
7525                         public void binderDied() {
7526                             foregroundTokenDied(this);
7527                         }
7528                     };
7529                     newToken.pid = pid;
7530                     newToken.token = token;
7531                     try {
7532                         token.linkToDeath(newToken, 0);
7533                         mForegroundProcesses.put(pid, newToken);
7534                         pr.forcingToForeground = token;
7535                         changed = true;
7536                     } catch (RemoteException e) {
7537                         // If the process died while doing this, we will later
7538                         // do the cleanup with the process death link.
7539                     }
7540                 }
7541             }
7542
7543             if (changed) {
7544                 updateOomAdjLocked();
7545             }
7546         }
7547     }
7548
7549     @Override
7550     public boolean isAppForeground(int uid) throws RemoteException {
7551         synchronized (this) {
7552             UidRecord uidRec = mActiveUids.get(uid);
7553             if (uidRec == null || uidRec.idle) {
7554                 return false;
7555             }
7556             return uidRec.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND;
7557         }
7558     }
7559
7560     // NOTE: this is an internal method used by the OnShellCommand implementation only and should
7561     // be guarded by permission checking.
7562     int getUidState(int uid) {
7563         synchronized (this) {
7564             UidRecord uidRec = mActiveUids.get(uid);
7565             return uidRec == null ? ActivityManager.PROCESS_STATE_NONEXISTENT : uidRec.curProcState;
7566         }
7567     }
7568
7569     @Override
7570     public boolean isInMultiWindowMode(IBinder token) {
7571         final long origId = Binder.clearCallingIdentity();
7572         try {
7573             synchronized(this) {
7574                 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
7575                 if (r == null) {
7576                     return false;
7577                 }
7578                 // An activity is consider to be in multi-window mode if its task isn't fullscreen.
7579                 return !r.task.mFullscreen;
7580             }
7581         } finally {
7582             Binder.restoreCallingIdentity(origId);
7583         }
7584     }
7585
7586     @Override
7587     public boolean isInPictureInPictureMode(IBinder token) {
7588         final long origId = Binder.clearCallingIdentity();
7589         try {
7590             synchronized(this) {
7591                 final ActivityStack stack = ActivityRecord.getStackLocked(token);
7592                 if (stack == null) {
7593                     return false;
7594                 }
7595                 return stack.mStackId == PINNED_STACK_ID;
7596             }
7597         } finally {
7598             Binder.restoreCallingIdentity(origId);
7599         }
7600     }
7601
7602     @Override
7603     public void enterPictureInPictureMode(IBinder token) {
7604         final long origId = Binder.clearCallingIdentity();
7605         try {
7606             synchronized(this) {
7607                 if (!mSupportsPictureInPicture) {
7608                     throw new IllegalStateException("enterPictureInPictureMode: "
7609                             + "Device doesn't support picture-in-picture mode.");
7610                 }
7611
7612                 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
7613
7614                 if (r == null) {
7615                     throw new IllegalStateException("enterPictureInPictureMode: "
7616                             + "Can't find activity for token=" + token);
7617                 }
7618
7619                 if (!r.supportsPictureInPicture()) {
7620                     throw new IllegalArgumentException("enterPictureInPictureMode: "
7621                             + "Picture-In-Picture not supported for r=" + r);
7622                 }
7623
7624                 // Use the default launch bounds for pinned stack if it doesn't exist yet or use the
7625                 // current bounds.
7626                 final ActivityStack pinnedStack = mStackSupervisor.getStack(PINNED_STACK_ID);
7627                 final Rect bounds = (pinnedStack != null)
7628                         ? pinnedStack.mBounds : mDefaultPinnedStackBounds;
7629
7630                 mStackSupervisor.moveActivityToPinnedStackLocked(
7631                         r, "enterPictureInPictureMode", bounds);
7632             }
7633         } finally {
7634             Binder.restoreCallingIdentity(origId);
7635         }
7636     }
7637
7638     // =========================================================
7639     // PROCESS INFO
7640     // =========================================================
7641
7642     static class ProcessInfoService extends IProcessInfoService.Stub {
7643         final ActivityManagerService mActivityManagerService;
7644         ProcessInfoService(ActivityManagerService activityManagerService) {
7645             mActivityManagerService = activityManagerService;
7646         }
7647
7648         @Override
7649         public void getProcessStatesFromPids(/*in*/ int[] pids, /*out*/ int[] states) {
7650             mActivityManagerService.getProcessStatesAndOomScoresForPIDs(
7651                     /*in*/ pids, /*out*/ states, null);
7652         }
7653
7654         @Override
7655         public void getProcessStatesAndOomScoresFromPids(
7656                 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) {
7657             mActivityManagerService.getProcessStatesAndOomScoresForPIDs(
7658                     /*in*/ pids, /*out*/ states, /*out*/ scores);
7659         }
7660     }
7661
7662     /**
7663      * For each PID in the given input array, write the current process state
7664      * for that process into the states array, or -1 to indicate that no
7665      * process with the given PID exists. If scores array is provided, write
7666      * the oom score for the process into the scores array, with INVALID_ADJ
7667      * indicating the PID doesn't exist.
7668      */
7669     public void getProcessStatesAndOomScoresForPIDs(
7670             /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) {
7671         if (scores != null) {
7672             enforceCallingPermission(android.Manifest.permission.GET_PROCESS_STATE_AND_OOM_SCORE,
7673                     "getProcessStatesAndOomScoresForPIDs()");
7674         }
7675
7676         if (pids == null) {
7677             throw new NullPointerException("pids");
7678         } else if (states == null) {
7679             throw new NullPointerException("states");
7680         } else if (pids.length != states.length) {
7681             throw new IllegalArgumentException("pids and states arrays have different lengths!");
7682         } else if (scores != null && pids.length != scores.length) {
7683             throw new IllegalArgumentException("pids and scores arrays have different lengths!");
7684         }
7685
7686         synchronized (mPidsSelfLocked) {
7687             for (int i = 0; i < pids.length; i++) {
7688                 ProcessRecord pr = mPidsSelfLocked.get(pids[i]);
7689                 states[i] = (pr == null) ? ActivityManager.PROCESS_STATE_NONEXISTENT :
7690                         pr.curProcState;
7691                 if (scores != null) {
7692                     scores[i] = (pr == null) ? ProcessList.INVALID_ADJ : pr.curAdj;
7693                 }
7694             }
7695         }
7696     }
7697
7698     // =========================================================
7699     // PERMISSIONS
7700     // =========================================================
7701
7702     static class PermissionController extends IPermissionController.Stub {
7703         ActivityManagerService mActivityManagerService;
7704         PermissionController(ActivityManagerService activityManagerService) {
7705             mActivityManagerService = activityManagerService;
7706         }
7707
7708         @Override
7709         public boolean checkPermission(String permission, int pid, int uid) {
7710             return mActivityManagerService.checkPermission(permission, pid,
7711                     uid) == PackageManager.PERMISSION_GRANTED;
7712         }
7713
7714         @Override
7715         public String[] getPackagesForUid(int uid) {
7716             return mActivityManagerService.mContext.getPackageManager()
7717                     .getPackagesForUid(uid);
7718         }
7719
7720         @Override
7721         public boolean isRuntimePermission(String permission) {
7722             try {
7723                 PermissionInfo info = mActivityManagerService.mContext.getPackageManager()
7724                         .getPermissionInfo(permission, 0);
7725                 return info.protectionLevel == PermissionInfo.PROTECTION_DANGEROUS;
7726             } catch (NameNotFoundException nnfe) {
7727                 Slog.e(TAG, "No such permission: "+ permission, nnfe);
7728             }
7729             return false;
7730         }
7731     }
7732
7733     class IntentFirewallInterface implements IntentFirewall.AMSInterface {
7734         @Override
7735         public int checkComponentPermission(String permission, int pid, int uid,
7736                 int owningUid, boolean exported) {
7737             return ActivityManagerService.this.checkComponentPermission(permission, pid, uid,
7738                     owningUid, exported);
7739         }
7740
7741         @Override
7742         public Object getAMSLock() {
7743             return ActivityManagerService.this;
7744         }
7745     }
7746
7747     /**
7748      * This can be called with or without the global lock held.
7749      */
7750     int checkComponentPermission(String permission, int pid, int uid,
7751             int owningUid, boolean exported) {
7752         if (pid == MY_PID) {
7753             return PackageManager.PERMISSION_GRANTED;
7754         }
7755         return ActivityManager.checkComponentPermission(permission, uid,
7756                 owningUid, exported);
7757     }
7758
7759     /**
7760      * As the only public entry point for permissions checking, this method
7761      * can enforce the semantic that requesting a check on a null global
7762      * permission is automatically denied.  (Internally a null permission
7763      * string is used when calling {@link #checkComponentPermission} in cases
7764      * when only uid-based security is needed.)
7765      *
7766      * This can be called with or without the global lock held.
7767      */
7768     @Override
7769     public int checkPermission(String permission, int pid, int uid) {
7770         if (permission == null) {
7771             return PackageManager.PERMISSION_DENIED;
7772         }
7773         return checkComponentPermission(permission, pid, uid, -1, true);
7774     }
7775
7776     @Override
7777     public int checkPermissionWithToken(String permission, int pid, int uid, IBinder callerToken) {
7778         if (permission == null) {
7779             return PackageManager.PERMISSION_DENIED;
7780         }
7781
7782         // We might be performing an operation on behalf of an indirect binder
7783         // invocation, e.g. via {@link #openContentUri}.  Check and adjust the
7784         // client identity accordingly before proceeding.
7785         Identity tlsIdentity = sCallerIdentity.get();
7786         if (tlsIdentity != null && tlsIdentity.token == callerToken) {
7787             Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {"
7788                     + tlsIdentity.pid + "," + tlsIdentity.uid + "}");
7789             uid = tlsIdentity.uid;
7790             pid = tlsIdentity.pid;
7791         }
7792
7793         return checkComponentPermission(permission, pid, uid, -1, true);
7794     }
7795
7796     /**
7797      * Binder IPC calls go through the public entry point.
7798      * This can be called with or without the global lock held.
7799      */
7800     int checkCallingPermission(String permission) {
7801         return checkPermission(permission,
7802                 Binder.getCallingPid(),
7803                 UserHandle.getAppId(Binder.getCallingUid()));
7804     }
7805
7806     /**
7807      * This can be called with or without the global lock held.
7808      */
7809     void enforceCallingPermission(String permission, String func) {
7810         if (checkCallingPermission(permission)
7811                 == PackageManager.PERMISSION_GRANTED) {
7812             return;
7813         }
7814
7815         String msg = "Permission Denial: " + func + " from pid="
7816                 + Binder.getCallingPid()
7817                 + ", uid=" + Binder.getCallingUid()
7818                 + " requires " + permission;
7819         Slog.w(TAG, msg);
7820         throw new SecurityException(msg);
7821     }
7822
7823     /**
7824      * Determine if UID is holding permissions required to access {@link Uri} in
7825      * the given {@link ProviderInfo}. Final permission checking is always done
7826      * in {@link ContentProvider}.
7827      */
7828     private final boolean checkHoldingPermissionsLocked(
7829             IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) {
7830         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
7831                 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid);
7832         if (UserHandle.getUserId(uid) != grantUri.sourceUserId) {
7833             if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true)
7834                     != PERMISSION_GRANTED) {
7835                 return false;
7836             }
7837         }
7838         return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true);
7839     }
7840
7841     private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi,
7842             GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) {
7843         if (pi.applicationInfo.uid == uid) {
7844             return true;
7845         } else if (!pi.exported) {
7846             return false;
7847         }
7848
7849         boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0;
7850         boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0;
7851         try {
7852             // check if target holds top-level <provider> permissions
7853             if (!readMet && pi.readPermission != null && considerUidPermissions
7854                     && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) {
7855                 readMet = true;
7856             }
7857             if (!writeMet && pi.writePermission != null && considerUidPermissions
7858                     && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) {
7859                 writeMet = true;
7860             }
7861
7862             // track if unprotected read/write is allowed; any denied
7863             // <path-permission> below removes this ability
7864             boolean allowDefaultRead = pi.readPermission == null;
7865             boolean allowDefaultWrite = pi.writePermission == null;
7866
7867             // check if target holds any <path-permission> that match uri
7868             final PathPermission[] pps = pi.pathPermissions;
7869             if (pps != null) {
7870                 final String path = grantUri.uri.getPath();
7871                 int i = pps.length;
7872                 while (i > 0 && (!readMet || !writeMet)) {
7873                     i--;
7874                     PathPermission pp = pps[i];
7875                     if (pp.match(path)) {
7876                         if (!readMet) {
7877                             final String pprperm = pp.getReadPermission();
7878                             if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
7879                                     "Checking read perm for " + pprperm + " for " + pp.getPath()
7880                                     + ": match=" + pp.match(path)
7881                                     + " check=" + pm.checkUidPermission(pprperm, uid));
7882                             if (pprperm != null) {
7883                                 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid)
7884                                         == PERMISSION_GRANTED) {
7885                                     readMet = true;
7886                                 } else {
7887                                     allowDefaultRead = false;
7888                                 }
7889                             }
7890                         }
7891                         if (!writeMet) {
7892                             final String ppwperm = pp.getWritePermission();
7893                             if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
7894                                     "Checking write perm " + ppwperm + " for " + pp.getPath()
7895                                     + ": match=" + pp.match(path)
7896                                     + " check=" + pm.checkUidPermission(ppwperm, uid));
7897                             if (ppwperm != null) {
7898                                 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid)
7899                                         == PERMISSION_GRANTED) {
7900                                     writeMet = true;
7901                                 } else {
7902                                     allowDefaultWrite = false;
7903                                 }
7904                             }
7905                         }
7906                     }
7907                 }
7908             }
7909
7910             // grant unprotected <provider> read/write, if not blocked by
7911             // <path-permission> above
7912             if (allowDefaultRead) readMet = true;
7913             if (allowDefaultWrite) writeMet = true;
7914
7915         } catch (RemoteException e) {
7916             return false;
7917         }
7918
7919         return readMet && writeMet;
7920     }
7921
7922     public int getAppStartMode(int uid, String packageName) {
7923         synchronized (this) {
7924             return checkAllowBackgroundLocked(uid, packageName, -1, true);
7925         }
7926     }
7927
7928     int checkAllowBackgroundLocked(int uid, String packageName, int callingPid,
7929             boolean allowWhenForeground) {
7930         UidRecord uidRec = mActiveUids.get(uid);
7931         if (!mLenientBackgroundCheck) {
7932             if (!allowWhenForeground || uidRec == null
7933                     || uidRec.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) {
7934                 if (mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, uid,
7935                         packageName) != AppOpsManager.MODE_ALLOWED) {
7936                     return ActivityManager.APP_START_MODE_DELAYED;
7937                 }
7938             }
7939
7940         } else if (uidRec == null || uidRec.idle) {
7941             if (callingPid >= 0) {
7942                 ProcessRecord proc;
7943                 synchronized (mPidsSelfLocked) {
7944                     proc = mPidsSelfLocked.get(callingPid);
7945                 }
7946                 if (proc != null && proc.curProcState < ActivityManager.PROCESS_STATE_RECEIVER) {
7947                     // Whoever is instigating this is in the foreground, so we will allow it
7948                     // to go through.
7949                     return ActivityManager.APP_START_MODE_NORMAL;
7950                 }
7951             }
7952             if (mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, uid, packageName)
7953                     != AppOpsManager.MODE_ALLOWED) {
7954                 return ActivityManager.APP_START_MODE_DELAYED;
7955             }
7956         }
7957         return ActivityManager.APP_START_MODE_NORMAL;
7958     }
7959
7960     private ProviderInfo getProviderInfoLocked(String authority, int userHandle, int pmFlags) {
7961         ProviderInfo pi = null;
7962         ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle);
7963         if (cpr != null) {
7964             pi = cpr.info;
7965         } else {
7966             try {
7967                 pi = AppGlobals.getPackageManager().resolveContentProvider(
7968                         authority, PackageManager.GET_URI_PERMISSION_PATTERNS | pmFlags,
7969                         userHandle);
7970             } catch (RemoteException ex) {
7971             }
7972         }
7973         return pi;
7974     }
7975
7976     private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) {
7977         final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid);
7978         if (targetUris != null) {
7979             return targetUris.get(grantUri);
7980         }
7981         return null;
7982     }
7983
7984     private UriPermission findOrCreateUriPermissionLocked(String sourcePkg,
7985             String targetPkg, int targetUid, GrantUri grantUri) {
7986         ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid);
7987         if (targetUris == null) {
7988             targetUris = Maps.newArrayMap();
7989             mGrantedUriPermissions.put(targetUid, targetUris);
7990         }
7991
7992         UriPermission perm = targetUris.get(grantUri);
7993         if (perm == null) {
7994             perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri);
7995             targetUris.put(grantUri, perm);
7996         }
7997
7998         return perm;
7999     }
8000
8001     private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid,
8002             final int modeFlags) {
8003         final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0;
8004         final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE
8005                 : UriPermission.STRENGTH_OWNED;
8006
8007         // Root gets to do everything.
8008         if (uid == 0) {
8009             return true;
8010         }
8011
8012         final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid);
8013         if (perms == null) return false;
8014
8015         // First look for exact match
8016         final UriPermission exactPerm = perms.get(grantUri);
8017         if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) {
8018             return true;
8019         }
8020
8021         // No exact match, look for prefixes
8022         final int N = perms.size();
8023         for (int i = 0; i < N; i++) {
8024             final UriPermission perm = perms.valueAt(i);
8025             if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri)
8026                     && perm.getStrength(modeFlags) >= minStrength) {
8027                 return true;
8028             }
8029         }
8030
8031         return false;
8032     }
8033
8034     /**
8035      * @param uri This uri must NOT contain an embedded userId.
8036      * @param userId The userId in which the uri is to be resolved.
8037      */
8038     @Override
8039     public int checkUriPermission(Uri uri, int pid, int uid,
8040             final int modeFlags, int userId, IBinder callerToken) {
8041         enforceNotIsolatedCaller("checkUriPermission");
8042
8043         // Another redirected-binder-call permissions check as in
8044         // {@link checkPermissionWithToken}.
8045         Identity tlsIdentity = sCallerIdentity.get();
8046         if (tlsIdentity != null && tlsIdentity.token == callerToken) {
8047             uid = tlsIdentity.uid;
8048             pid = tlsIdentity.pid;
8049         }
8050
8051         // Our own process gets to do everything.
8052         if (pid == MY_PID) {
8053             return PackageManager.PERMISSION_GRANTED;
8054         }
8055         synchronized (this) {
8056             return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags)
8057                     ? PackageManager.PERMISSION_GRANTED
8058                     : PackageManager.PERMISSION_DENIED;
8059         }
8060     }
8061
8062     /**
8063      * Check if the targetPkg can be granted permission to access uri by
8064      * the callingUid using the given modeFlags.  Throws a security exception
8065      * if callingUid is not allowed to do this.  Returns the uid of the target
8066      * if the URI permission grant should be performed; returns -1 if it is not
8067      * needed (for example targetPkg already has permission to access the URI).
8068      * If you already know the uid of the target, you can supply it in
8069      * lastTargetUid else set that to -1.
8070      */
8071     int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri,
8072             final int modeFlags, int lastTargetUid) {
8073         if (!Intent.isAccessUriMode(modeFlags)) {
8074             return -1;
8075         }
8076
8077         if (targetPkg != null) {
8078             if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8079                     "Checking grant " + targetPkg + " permission to " + grantUri);
8080         }
8081
8082         final IPackageManager pm = AppGlobals.getPackageManager();
8083
8084         // If this is not a content: uri, we can't do anything with it.
8085         if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) {
8086             if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8087                     "Can't grant URI permission for non-content URI: " + grantUri);
8088             return -1;
8089         }
8090
8091         final String authority = grantUri.uri.getAuthority();
8092         final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId,
8093                 MATCH_DEBUG_TRIAGED_MISSING);
8094         if (pi == null) {
8095             Slog.w(TAG, "No content provider found for permission check: " +
8096                     grantUri.uri.toSafeString());
8097             return -1;
8098         }
8099
8100         int targetUid = lastTargetUid;
8101         if (targetUid < 0 && targetPkg != null) {
8102             try {
8103                 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING,
8104                         UserHandle.getUserId(callingUid));
8105                 if (targetUid < 0) {
8106                     if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8107                             "Can't grant URI permission no uid for: " + targetPkg);
8108                     return -1;
8109                 }
8110             } catch (RemoteException ex) {
8111                 return -1;
8112             }
8113         }
8114
8115         if (targetUid >= 0) {
8116             // First...  does the target actually need this permission?
8117             if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) {
8118                 // No need to grant the target this permission.
8119                 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8120                         "Target " + targetPkg + " already has full permission to " + grantUri);
8121                 return -1;
8122             }
8123         } else {
8124             // First...  there is no target package, so can anyone access it?
8125             boolean allowed = pi.exported;
8126             if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) {
8127                 if (pi.readPermission != null) {
8128                     allowed = false;
8129                 }
8130             }
8131             if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) {
8132                 if (pi.writePermission != null) {
8133                     allowed = false;
8134                 }
8135             }
8136             if (allowed) {
8137                 return -1;
8138             }
8139         }
8140
8141         /* There is a special cross user grant if:
8142          * - The target is on another user.
8143          * - Apps on the current user can access the uri without any uid permissions.
8144          * In this case, we grant a uri permission, even if the ContentProvider does not normally
8145          * grant uri permissions.
8146          */
8147         boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId
8148                 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid,
8149                 modeFlags, false /*without considering the uid permissions*/);
8150
8151         // Second...  is the provider allowing granting of URI permissions?
8152         if (!specialCrossUserGrant) {
8153             if (!pi.grantUriPermissions) {
8154                 throw new SecurityException("Provider " + pi.packageName
8155                         + "/" + pi.name
8156                         + " does not allow granting of Uri permissions (uri "
8157                         + grantUri + ")");
8158             }
8159             if (pi.uriPermissionPatterns != null) {
8160                 final int N = pi.uriPermissionPatterns.length;
8161                 boolean allowed = false;
8162                 for (int i=0; i<N; i++) {
8163                     if (pi.uriPermissionPatterns[i] != null
8164                             && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) {
8165                         allowed = true;
8166                         break;
8167                     }
8168                 }
8169                 if (!allowed) {
8170                     throw new SecurityException("Provider " + pi.packageName
8171                             + "/" + pi.name
8172                             + " does not allow granting of permission to path of Uri "
8173                             + grantUri);
8174                 }
8175             }
8176         }
8177
8178         // Third...  does the caller itself have permission to access
8179         // this uri?
8180         if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) {
8181             if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) {
8182                 // Require they hold a strong enough Uri permission
8183                 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) {
8184                     throw new SecurityException("Uid " + callingUid
8185                             + " does not have permission to uri " + grantUri);
8186                 }
8187             }
8188         }
8189         return targetUid;
8190     }
8191
8192     /**
8193      * @param uri This uri must NOT contain an embedded userId.
8194      * @param userId The userId in which the uri is to be resolved.
8195      */
8196     @Override
8197     public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri,
8198             final int modeFlags, int userId) {
8199         enforceNotIsolatedCaller("checkGrantUriPermission");
8200         synchronized(this) {
8201             return checkGrantUriPermissionLocked(callingUid, targetPkg,
8202                     new GrantUri(userId, uri, false), modeFlags, -1);
8203         }
8204     }
8205
8206     void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri,
8207             final int modeFlags, UriPermissionOwner owner) {
8208         if (!Intent.isAccessUriMode(modeFlags)) {
8209             return;
8210         }
8211
8212         // So here we are: the caller has the assumed permission
8213         // to the uri, and the target doesn't.  Let's now give this to
8214         // the target.
8215
8216         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8217                 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri);
8218
8219         final String authority = grantUri.uri.getAuthority();
8220         final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId,
8221                 MATCH_DEBUG_TRIAGED_MISSING);
8222         if (pi == null) {
8223             Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString());
8224             return;
8225         }
8226
8227         if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) {
8228             grantUri.prefix = true;
8229         }
8230         final UriPermission perm = findOrCreateUriPermissionLocked(
8231                 pi.packageName, targetPkg, targetUid, grantUri);
8232         perm.grantModes(modeFlags, owner);
8233     }
8234
8235     void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri,
8236             final int modeFlags, UriPermissionOwner owner, int targetUserId) {
8237         if (targetPkg == null) {
8238             throw new NullPointerException("targetPkg");
8239         }
8240         int targetUid;
8241         final IPackageManager pm = AppGlobals.getPackageManager();
8242         try {
8243             targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, targetUserId);
8244         } catch (RemoteException ex) {
8245             return;
8246         }
8247
8248         targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags,
8249                 targetUid);
8250         if (targetUid < 0) {
8251             return;
8252         }
8253
8254         grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags,
8255                 owner);
8256     }
8257
8258     static class NeededUriGrants extends ArrayList<GrantUri> {
8259         final String targetPkg;
8260         final int targetUid;
8261         final int flags;
8262
8263         NeededUriGrants(String targetPkg, int targetUid, int flags) {
8264             this.targetPkg = targetPkg;
8265             this.targetUid = targetUid;
8266             this.flags = flags;
8267         }
8268     }
8269
8270     /**
8271      * Like checkGrantUriPermissionLocked, but takes an Intent.
8272      */
8273     NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid,
8274             String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) {
8275         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8276                 "Checking URI perm to data=" + (intent != null ? intent.getData() : null)
8277                 + " clip=" + (intent != null ? intent.getClipData() : null)
8278                 + " from " + intent + "; flags=0x"
8279                 + Integer.toHexString(intent != null ? intent.getFlags() : 0));
8280
8281         if (targetPkg == null) {
8282             throw new NullPointerException("targetPkg");
8283         }
8284
8285         if (intent == null) {
8286             return null;
8287         }
8288         Uri data = intent.getData();
8289         ClipData clip = intent.getClipData();
8290         if (data == null && clip == null) {
8291             return null;
8292         }
8293         // Default userId for uris in the intent (if they don't specify it themselves)
8294         int contentUserHint = intent.getContentUserHint();
8295         if (contentUserHint == UserHandle.USER_CURRENT) {
8296             contentUserHint = UserHandle.getUserId(callingUid);
8297         }
8298         final IPackageManager pm = AppGlobals.getPackageManager();
8299         int targetUid;
8300         if (needed != null) {
8301             targetUid = needed.targetUid;
8302         } else {
8303             try {
8304                 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING,
8305                         targetUserId);
8306             } catch (RemoteException ex) {
8307                 return null;
8308             }
8309             if (targetUid < 0) {
8310                 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8311                         "Can't grant URI permission no uid for: " + targetPkg
8312                         + " on user " + targetUserId);
8313                 return null;
8314             }
8315         }
8316         if (data != null) {
8317             GrantUri grantUri = GrantUri.resolve(contentUserHint, data);
8318             targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode,
8319                     targetUid);
8320             if (targetUid > 0) {
8321                 if (needed == null) {
8322                     needed = new NeededUriGrants(targetPkg, targetUid, mode);
8323                 }
8324                 needed.add(grantUri);
8325             }
8326         }
8327         if (clip != null) {
8328             for (int i=0; i<clip.getItemCount(); i++) {
8329                 Uri uri = clip.getItemAt(i).getUri();
8330                 if (uri != null) {
8331                     GrantUri grantUri = GrantUri.resolve(contentUserHint, uri);
8332                     targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode,
8333                             targetUid);
8334                     if (targetUid > 0) {
8335                         if (needed == null) {
8336                             needed = new NeededUriGrants(targetPkg, targetUid, mode);
8337                         }
8338                         needed.add(grantUri);
8339                     }
8340                 } else {
8341                     Intent clipIntent = clip.getItemAt(i).getIntent();
8342                     if (clipIntent != null) {
8343                         NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked(
8344                                 callingUid, targetPkg, clipIntent, mode, needed, targetUserId);
8345                         if (newNeeded != null) {
8346                             needed = newNeeded;
8347                         }
8348                     }
8349                 }
8350             }
8351         }
8352
8353         return needed;
8354     }
8355
8356     /**
8357      * Like grantUriPermissionUncheckedLocked, but takes an Intent.
8358      */
8359     void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed,
8360             UriPermissionOwner owner) {
8361         if (needed != null) {
8362             for (int i=0; i<needed.size(); i++) {
8363                 GrantUri grantUri = needed.get(i);
8364                 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg,
8365                         grantUri, needed.flags, owner);
8366             }
8367         }
8368     }
8369
8370     void grantUriPermissionFromIntentLocked(int callingUid,
8371             String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) {
8372         NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg,
8373                 intent, intent != null ? intent.getFlags() : 0, null, targetUserId);
8374         if (needed == null) {
8375             return;
8376         }
8377
8378         grantUriPermissionUncheckedFromIntentLocked(needed, owner);
8379     }
8380
8381     /**
8382      * @param uri This uri must NOT contain an embedded userId.
8383      * @param userId The userId in which the uri is to be resolved.
8384      */
8385     @Override
8386     public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri,
8387             final int modeFlags, int userId) {
8388         enforceNotIsolatedCaller("grantUriPermission");
8389         GrantUri grantUri = new GrantUri(userId, uri, false);
8390         synchronized(this) {
8391             final ProcessRecord r = getRecordForAppLocked(caller);
8392             if (r == null) {
8393                 throw new SecurityException("Unable to find app for caller "
8394                         + caller
8395                         + " when granting permission to uri " + grantUri);
8396             }
8397             if (targetPkg == null) {
8398                 throw new IllegalArgumentException("null target");
8399             }
8400             if (grantUri == null) {
8401                 throw new IllegalArgumentException("null uri");
8402             }
8403
8404             Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION
8405                     | Intent.FLAG_GRANT_WRITE_URI_PERMISSION
8406                     | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION
8407                     | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION);
8408
8409             grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null,
8410                     UserHandle.getUserId(r.uid));
8411         }
8412     }
8413
8414     void removeUriPermissionIfNeededLocked(UriPermission perm) {
8415         if (perm.modeFlags == 0) {
8416             final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(
8417                     perm.targetUid);
8418             if (perms != null) {
8419                 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8420                         "Removing " + perm.targetUid + " permission to " + perm.uri);
8421
8422                 perms.remove(perm.uri);
8423                 if (perms.isEmpty()) {
8424                     mGrantedUriPermissions.remove(perm.targetUid);
8425                 }
8426             }
8427         }
8428     }
8429
8430     private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) {
8431         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8432                 "Revoking all granted permissions to " + grantUri);
8433
8434         final IPackageManager pm = AppGlobals.getPackageManager();
8435         final String authority = grantUri.uri.getAuthority();
8436         final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId,
8437                 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE);
8438         if (pi == null) {
8439             Slog.w(TAG, "No content provider found for permission revoke: "
8440                     + grantUri.toSafeString());
8441             return;
8442         }
8443
8444         // Does the caller have this permission on the URI?
8445         if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) {
8446             // If they don't have direct access to the URI, then revoke any
8447             // ownerless URI permissions that have been granted to them.
8448             final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid);
8449             if (perms != null) {
8450                 boolean persistChanged = false;
8451                 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) {
8452                     final UriPermission perm = it.next();
8453                     if (perm.uri.sourceUserId == grantUri.sourceUserId
8454                             && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) {
8455                         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8456                                 "Revoking non-owned " + perm.targetUid
8457                                 + " permission to " + perm.uri);
8458                         persistChanged |= perm.revokeModes(
8459                                 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, false);
8460                         if (perm.modeFlags == 0) {
8461                             it.remove();
8462                         }
8463                     }
8464                 }
8465                 if (perms.isEmpty()) {
8466                     mGrantedUriPermissions.remove(callingUid);
8467                 }
8468                 if (persistChanged) {
8469                     schedulePersistUriGrants();
8470                 }
8471             }
8472             return;
8473         }
8474
8475         boolean persistChanged = false;
8476
8477         // Go through all of the permissions and remove any that match.
8478         int N = mGrantedUriPermissions.size();
8479         for (int i = 0; i < N; i++) {
8480             final int targetUid = mGrantedUriPermissions.keyAt(i);
8481             final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i);
8482
8483             for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) {
8484                 final UriPermission perm = it.next();
8485                 if (perm.uri.sourceUserId == grantUri.sourceUserId
8486                         && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) {
8487                     if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8488                                 "Revoking " + perm.targetUid + " permission to " + perm.uri);
8489                     persistChanged |= perm.revokeModes(
8490                             modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true);
8491                     if (perm.modeFlags == 0) {
8492                         it.remove();
8493                     }
8494                 }
8495             }
8496
8497             if (perms.isEmpty()) {
8498                 mGrantedUriPermissions.remove(targetUid);
8499                 N--;
8500                 i--;
8501             }
8502         }
8503
8504         if (persistChanged) {
8505             schedulePersistUriGrants();
8506         }
8507     }
8508
8509     /**
8510      * @param uri This uri must NOT contain an embedded userId.
8511      * @param userId The userId in which the uri is to be resolved.
8512      */
8513     @Override
8514     public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags,
8515             int userId) {
8516         enforceNotIsolatedCaller("revokeUriPermission");
8517         synchronized(this) {
8518             final ProcessRecord r = getRecordForAppLocked(caller);
8519             if (r == null) {
8520                 throw new SecurityException("Unable to find app for caller "
8521                         + caller
8522                         + " when revoking permission to uri " + uri);
8523             }
8524             if (uri == null) {
8525                 Slog.w(TAG, "revokeUriPermission: null uri");
8526                 return;
8527             }
8528
8529             if (!Intent.isAccessUriMode(modeFlags)) {
8530                 return;
8531             }
8532
8533             final String authority = uri.getAuthority();
8534             final ProviderInfo pi = getProviderInfoLocked(authority, userId,
8535                     MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE);
8536             if (pi == null) {
8537                 Slog.w(TAG, "No content provider found for permission revoke: "
8538                         + uri.toSafeString());
8539                 return;
8540             }
8541
8542             revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags);
8543         }
8544     }
8545
8546     /**
8547      * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the
8548      * given package.
8549      *
8550      * @param packageName Package name to match, or {@code null} to apply to all
8551      *            packages.
8552      * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply
8553      *            to all users.
8554      * @param persistable If persistable grants should be removed.
8555      */
8556     private void removeUriPermissionsForPackageLocked(
8557             String packageName, int userHandle, boolean persistable) {
8558         if (userHandle == UserHandle.USER_ALL && packageName == null) {
8559             throw new IllegalArgumentException("Must narrow by either package or user");
8560         }
8561
8562         boolean persistChanged = false;
8563
8564         int N = mGrantedUriPermissions.size();
8565         for (int i = 0; i < N; i++) {
8566             final int targetUid = mGrantedUriPermissions.keyAt(i);
8567             final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i);
8568
8569             // Only inspect grants matching user
8570             if (userHandle == UserHandle.USER_ALL
8571                     || userHandle == UserHandle.getUserId(targetUid)) {
8572                 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) {
8573                     final UriPermission perm = it.next();
8574
8575                     // Only inspect grants matching package
8576                     if (packageName == null || perm.sourcePkg.equals(packageName)
8577                             || perm.targetPkg.equals(packageName)) {
8578                         // Hacky solution as part of fixing a security bug; ignore
8579                         // grants associated with DownloadManager so we don't have
8580                         // to immediately launch it to regrant the permissions
8581                         if (Downloads.Impl.AUTHORITY.equals(perm.uri.uri.getAuthority())
8582                                 && !persistable) continue;
8583
8584                         persistChanged |= perm.revokeModes(persistable
8585                                 ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true);
8586
8587                         // Only remove when no modes remain; any persisted grants
8588                         // will keep this alive.
8589                         if (perm.modeFlags == 0) {
8590                             it.remove();
8591                         }
8592                     }
8593                 }
8594
8595                 if (perms.isEmpty()) {
8596                     mGrantedUriPermissions.remove(targetUid);
8597                     N--;
8598                     i--;
8599                 }
8600             }
8601         }
8602
8603         if (persistChanged) {
8604             schedulePersistUriGrants();
8605         }
8606     }
8607
8608     @Override
8609     public IBinder newUriPermissionOwner(String name) {
8610         enforceNotIsolatedCaller("newUriPermissionOwner");
8611         synchronized(this) {
8612             UriPermissionOwner owner = new UriPermissionOwner(this, name);
8613             return owner.getExternalTokenLocked();
8614         }
8615     }
8616
8617     @Override
8618     public IBinder getUriPermissionOwnerForActivity(IBinder activityToken) {
8619         enforceNotIsolatedCaller("getUriPermissionOwnerForActivity");
8620         synchronized(this) {
8621             ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
8622             if (r == null) {
8623                 throw new IllegalArgumentException("Activity does not exist; token="
8624                         + activityToken);
8625             }
8626             return r.getUriPermissionsLocked().getExternalTokenLocked();
8627         }
8628     }
8629     /**
8630      * @param uri This uri must NOT contain an embedded userId.
8631      * @param sourceUserId The userId in which the uri is to be resolved.
8632      * @param targetUserId The userId of the app that receives the grant.
8633      */
8634     @Override
8635     public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri,
8636             final int modeFlags, int sourceUserId, int targetUserId) {
8637         targetUserId = mUserController.handleIncomingUser(Binder.getCallingPid(),
8638                 Binder.getCallingUid(), targetUserId, false, ALLOW_FULL_ONLY,
8639                 "grantUriPermissionFromOwner", null);
8640         synchronized(this) {
8641             UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token);
8642             if (owner == null) {
8643                 throw new IllegalArgumentException("Unknown owner: " + token);
8644             }
8645             if (fromUid != Binder.getCallingUid()) {
8646                 if (Binder.getCallingUid() != Process.myUid()) {
8647                     // Only system code can grant URI permissions on behalf
8648                     // of other users.
8649                     throw new SecurityException("nice try");
8650                 }
8651             }
8652             if (targetPkg == null) {
8653                 throw new IllegalArgumentException("null target");
8654             }
8655             if (uri == null) {
8656                 throw new IllegalArgumentException("null uri");
8657             }
8658
8659             grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false),
8660                     modeFlags, owner, targetUserId);
8661         }
8662     }
8663
8664     /**
8665      * @param uri This uri must NOT contain an embedded userId.
8666      * @param userId The userId in which the uri is to be resolved.
8667      */
8668     @Override
8669     public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) {
8670         synchronized(this) {
8671             UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token);
8672             if (owner == null) {
8673                 throw new IllegalArgumentException("Unknown owner: " + token);
8674             }
8675
8676             if (uri == null) {
8677                 owner.removeUriPermissionsLocked(mode);
8678             } else {
8679                 final boolean prefix = (mode & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0;
8680                 owner.removeUriPermissionLocked(new GrantUri(userId, uri, prefix), mode);
8681             }
8682         }
8683     }
8684
8685     private void schedulePersistUriGrants() {
8686         if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) {
8687             mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG),
8688                     10 * DateUtils.SECOND_IN_MILLIS);
8689         }
8690     }
8691
8692     private void writeGrantedUriPermissions() {
8693         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "writeGrantedUriPermissions()");
8694
8695         // Snapshot permissions so we can persist without lock
8696         ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList();
8697         synchronized (this) {
8698             final int size = mGrantedUriPermissions.size();
8699             for (int i = 0; i < size; i++) {
8700                 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i);
8701                 for (UriPermission perm : perms.values()) {
8702                     if (perm.persistedModeFlags != 0) {
8703                         persist.add(perm.snapshot());
8704                     }
8705                 }
8706             }
8707         }
8708
8709         FileOutputStream fos = null;
8710         try {
8711             fos = mGrantFile.startWrite();
8712
8713             XmlSerializer out = new FastXmlSerializer();
8714             out.setOutput(fos, StandardCharsets.UTF_8.name());
8715             out.startDocument(null, true);
8716             out.startTag(null, TAG_URI_GRANTS);
8717             for (UriPermission.Snapshot perm : persist) {
8718                 out.startTag(null, TAG_URI_GRANT);
8719                 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId);
8720                 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId);
8721                 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg);
8722                 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg);
8723                 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri));
8724                 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix);
8725                 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags);
8726                 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime);
8727                 out.endTag(null, TAG_URI_GRANT);
8728             }
8729             out.endTag(null, TAG_URI_GRANTS);
8730             out.endDocument();
8731
8732             mGrantFile.finishWrite(fos);
8733         } catch (IOException e) {
8734             if (fos != null) {
8735                 mGrantFile.failWrite(fos);
8736             }
8737         }
8738     }
8739
8740     private void readGrantedUriPermissionsLocked() {
8741         if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "readGrantedUriPermissions()");
8742
8743         final long now = System.currentTimeMillis();
8744
8745         FileInputStream fis = null;
8746         try {
8747             fis = mGrantFile.openRead();
8748             final XmlPullParser in = Xml.newPullParser();
8749             in.setInput(fis, StandardCharsets.UTF_8.name());
8750
8751             int type;
8752             while ((type = in.next()) != END_DOCUMENT) {
8753                 final String tag = in.getName();
8754                 if (type == START_TAG) {
8755                     if (TAG_URI_GRANT.equals(tag)) {
8756                         final int sourceUserId;
8757                         final int targetUserId;
8758                         final int userHandle = readIntAttribute(in,
8759                                 ATTR_USER_HANDLE, UserHandle.USER_NULL);
8760                         if (userHandle != UserHandle.USER_NULL) {
8761                             // For backwards compatibility.
8762                             sourceUserId = userHandle;
8763                             targetUserId = userHandle;
8764                         } else {
8765                             sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID);
8766                             targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID);
8767                         }
8768                         final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG);
8769                         final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG);
8770                         final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI));
8771                         final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX);
8772                         final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS);
8773                         final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now);
8774
8775                         // Sanity check that provider still belongs to source package
8776                         // Both direct boot aware and unaware packages are fine as we
8777                         // will do filtering at query time to avoid multiple parsing.
8778                         final ProviderInfo pi = getProviderInfoLocked(
8779                                 uri.getAuthority(), sourceUserId, MATCH_DIRECT_BOOT_AWARE
8780                                         | MATCH_DIRECT_BOOT_UNAWARE);
8781                         if (pi != null && sourcePkg.equals(pi.packageName)) {
8782                             int targetUid = -1;
8783                             try {
8784                                 targetUid = AppGlobals.getPackageManager().getPackageUid(
8785                                         targetPkg, MATCH_UNINSTALLED_PACKAGES, targetUserId);
8786                             } catch (RemoteException e) {
8787                             }
8788                             if (targetUid != -1) {
8789                                 final UriPermission perm = findOrCreateUriPermissionLocked(
8790                                         sourcePkg, targetPkg, targetUid,
8791                                         new GrantUri(sourceUserId, uri, prefix));
8792                                 perm.initPersistedModes(modeFlags, createdTime);
8793                             }
8794                         } else {
8795                             Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg
8796                                     + " but instead found " + pi);
8797                         }
8798                     }
8799                 }
8800             }
8801         } catch (FileNotFoundException e) {
8802             // Missing grants is okay
8803         } catch (IOException e) {
8804             Slog.wtf(TAG, "Failed reading Uri grants", e);
8805         } catch (XmlPullParserException e) {
8806             Slog.wtf(TAG, "Failed reading Uri grants", e);
8807         } finally {
8808             IoUtils.closeQuietly(fis);
8809         }
8810     }
8811
8812     /**
8813      * @param uri This uri must NOT contain an embedded userId.
8814      * @param userId The userId in which the uri is to be resolved.
8815      */
8816     @Override
8817     public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) {
8818         enforceNotIsolatedCaller("takePersistableUriPermission");
8819
8820         Preconditions.checkFlagsArgument(modeFlags,
8821                 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
8822
8823         synchronized (this) {
8824             final int callingUid = Binder.getCallingUid();
8825             boolean persistChanged = false;
8826             GrantUri grantUri = new GrantUri(userId, uri, false);
8827
8828             UriPermission exactPerm = findUriPermissionLocked(callingUid,
8829                     new GrantUri(userId, uri, false));
8830             UriPermission prefixPerm = findUriPermissionLocked(callingUid,
8831                     new GrantUri(userId, uri, true));
8832
8833             final boolean exactValid = (exactPerm != null)
8834                     && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags);
8835             final boolean prefixValid = (prefixPerm != null)
8836                     && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags);
8837
8838             if (!(exactValid || prefixValid)) {
8839                 throw new SecurityException("No persistable permission grants found for UID "
8840                         + callingUid + " and Uri " + grantUri.toSafeString());
8841             }
8842
8843             if (exactValid) {
8844                 persistChanged |= exactPerm.takePersistableModes(modeFlags);
8845             }
8846             if (prefixValid) {
8847                 persistChanged |= prefixPerm.takePersistableModes(modeFlags);
8848             }
8849
8850             persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid);
8851
8852             if (persistChanged) {
8853                 schedulePersistUriGrants();
8854             }
8855         }
8856     }
8857
8858     /**
8859      * @param uri This uri must NOT contain an embedded userId.
8860      * @param userId The userId in which the uri is to be resolved.
8861      */
8862     @Override
8863     public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) {
8864         enforceNotIsolatedCaller("releasePersistableUriPermission");
8865
8866         Preconditions.checkFlagsArgument(modeFlags,
8867                 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
8868
8869         synchronized (this) {
8870             final int callingUid = Binder.getCallingUid();
8871             boolean persistChanged = false;
8872
8873             UriPermission exactPerm = findUriPermissionLocked(callingUid,
8874                     new GrantUri(userId, uri, false));
8875             UriPermission prefixPerm = findUriPermissionLocked(callingUid,
8876                     new GrantUri(userId, uri, true));
8877             if (exactPerm == null && prefixPerm == null) {
8878                 throw new SecurityException("No permission grants found for UID " + callingUid
8879                         + " and Uri " + uri.toSafeString());
8880             }
8881
8882             if (exactPerm != null) {
8883                 persistChanged |= exactPerm.releasePersistableModes(modeFlags);
8884                 removeUriPermissionIfNeededLocked(exactPerm);
8885             }
8886             if (prefixPerm != null) {
8887                 persistChanged |= prefixPerm.releasePersistableModes(modeFlags);
8888                 removeUriPermissionIfNeededLocked(prefixPerm);
8889             }
8890
8891             if (persistChanged) {
8892                 schedulePersistUriGrants();
8893             }
8894         }
8895     }
8896
8897     /**
8898      * Prune any older {@link UriPermission} for the given UID until outstanding
8899      * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}.
8900      *
8901      * @return if any mutations occured that require persisting.
8902      */
8903     private boolean maybePrunePersistedUriGrantsLocked(int uid) {
8904         final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid);
8905         if (perms == null) return false;
8906         if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false;
8907
8908         final ArrayList<UriPermission> persisted = Lists.newArrayList();
8909         for (UriPermission perm : perms.values()) {
8910             if (perm.persistedModeFlags != 0) {
8911                 persisted.add(perm);
8912             }
8913         }
8914
8915         final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS;
8916         if (trimCount <= 0) return false;
8917
8918         Collections.sort(persisted, new UriPermission.PersistedTimeComparator());
8919         for (int i = 0; i < trimCount; i++) {
8920             final UriPermission perm = persisted.get(i);
8921
8922             if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION,
8923                     "Trimming grant created at " + perm.persistedCreateTime);
8924
8925             perm.releasePersistableModes(~0);
8926             removeUriPermissionIfNeededLocked(perm);
8927         }
8928
8929         return true;
8930     }
8931
8932     @Override
8933     public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions(
8934             String packageName, boolean incoming) {
8935         enforceNotIsolatedCaller("getPersistedUriPermissions");
8936         Preconditions.checkNotNull(packageName, "packageName");
8937
8938         final int callingUid = Binder.getCallingUid();
8939         final int callingUserId = UserHandle.getUserId(callingUid);
8940         final IPackageManager pm = AppGlobals.getPackageManager();
8941         try {
8942             final int packageUid = pm.getPackageUid(packageName,
8943                     MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, callingUserId);
8944             if (packageUid != callingUid) {
8945                 throw new SecurityException(
8946                         "Package " + packageName + " does not belong to calling UID " + callingUid);
8947             }
8948         } catch (RemoteException e) {
8949             throw new SecurityException("Failed to verify package name ownership");
8950         }
8951
8952         final ArrayList<android.content.UriPermission> result = Lists.newArrayList();
8953         synchronized (this) {
8954             if (incoming) {
8955                 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(
8956                         callingUid);
8957                 if (perms == null) {
8958                     Slog.w(TAG, "No permission grants found for " + packageName);
8959                 } else {
8960                     for (UriPermission perm : perms.values()) {
8961                         if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) {
8962                             result.add(perm.buildPersistedPublicApiObject());
8963                         }
8964                     }
8965                 }
8966             } else {
8967                 final int size = mGrantedUriPermissions.size();
8968                 for (int i = 0; i < size; i++) {
8969                     final ArrayMap<GrantUri, UriPermission> perms =
8970                             mGrantedUriPermissions.valueAt(i);
8971                     for (UriPermission perm : perms.values()) {
8972                         if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) {
8973                             result.add(perm.buildPersistedPublicApiObject());
8974                         }
8975                     }
8976                 }
8977             }
8978         }
8979         return new ParceledListSlice<android.content.UriPermission>(result);
8980     }
8981
8982     @Override
8983     public ParceledListSlice<android.content.UriPermission> getGrantedUriPermissions(
8984             String packageName, int userId) {
8985         enforceCallingPermission(android.Manifest.permission.GET_APP_GRANTED_URI_PERMISSIONS,
8986                 "getGrantedUriPermissions");
8987
8988         final ArrayList<android.content.UriPermission> result = Lists.newArrayList();
8989         synchronized (this) {
8990             final int size = mGrantedUriPermissions.size();
8991             for (int i = 0; i < size; i++) {
8992                 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i);
8993                 for (UriPermission perm : perms.values()) {
8994                     if (packageName.equals(perm.targetPkg) && perm.targetUserId == userId
8995                             && perm.persistedModeFlags != 0) {
8996                         result.add(perm.buildPersistedPublicApiObject());
8997                     }
8998                 }
8999             }
9000         }
9001         return new ParceledListSlice<android.content.UriPermission>(result);
9002     }
9003
9004     @Override
9005     public void clearGrantedUriPermissions(String packageName, int userId) {
9006         enforceCallingPermission(android.Manifest.permission.CLEAR_APP_GRANTED_URI_PERMISSIONS,
9007                 "clearGrantedUriPermissions");
9008         removeUriPermissionsForPackageLocked(packageName, userId, true);
9009     }
9010
9011     @Override
9012     public void showWaitingForDebugger(IApplicationThread who, boolean waiting) {
9013         synchronized (this) {
9014             ProcessRecord app =
9015                 who != null ? getRecordForAppLocked(who) : null;
9016             if (app == null) return;
9017
9018             Message msg = Message.obtain();
9019             msg.what = WAIT_FOR_DEBUGGER_UI_MSG;
9020             msg.obj = app;
9021             msg.arg1 = waiting ? 1 : 0;
9022             mUiHandler.sendMessage(msg);
9023         }
9024     }
9025
9026     @Override
9027     public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) {
9028         final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ);
9029         final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ);
9030         outInfo.availMem = Process.getFreeMemory();
9031         outInfo.totalMem = Process.getTotalMemory();
9032         outInfo.threshold = homeAppMem;
9033         outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2));
9034         outInfo.hiddenAppThreshold = cachedAppMem;
9035         outInfo.secondaryServerThreshold = mProcessList.getMemLevel(
9036                 ProcessList.SERVICE_ADJ);
9037         outInfo.visibleAppThreshold = mProcessList.getMemLevel(
9038                 ProcessList.VISIBLE_APP_ADJ);
9039         outInfo.foregroundAppThreshold = mProcessList.getMemLevel(
9040                 ProcessList.FOREGROUND_APP_ADJ);
9041     }
9042
9043     // =========================================================
9044     // TASK MANAGEMENT
9045     // =========================================================
9046
9047     @Override
9048     public List<IAppTask> getAppTasks(String callingPackage) {
9049         int callingUid = Binder.getCallingUid();
9050         long ident = Binder.clearCallingIdentity();
9051
9052         synchronized(this) {
9053             ArrayList<IAppTask> list = new ArrayList<IAppTask>();
9054             try {
9055                 if (DEBUG_ALL) Slog.v(TAG, "getAppTasks");
9056
9057                 final int N = mRecentTasks.size();
9058                 for (int i = 0; i < N; i++) {
9059                     TaskRecord tr = mRecentTasks.get(i);
9060                     // Skip tasks that do not match the caller.  We don't need to verify
9061                     // callingPackage, because we are also limiting to callingUid and know
9062                     // that will limit to the correct security sandbox.
9063                     if (tr.effectiveUid != callingUid) {
9064                         continue;
9065                     }
9066                     Intent intent = tr.getBaseIntent();
9067                     if (intent == null ||
9068                             !callingPackage.equals(intent.getComponent().getPackageName())) {
9069                         continue;
9070                     }
9071                     ActivityManager.RecentTaskInfo taskInfo =
9072                             createRecentTaskInfoFromTaskRecord(tr);
9073                     AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid);
9074                     list.add(taskImpl);
9075                 }
9076             } finally {
9077                 Binder.restoreCallingIdentity(ident);
9078             }
9079             return list;
9080         }
9081     }
9082
9083     @Override
9084     public List<RunningTaskInfo> getTasks(int maxNum, int flags) {
9085         final int callingUid = Binder.getCallingUid();
9086         ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>();
9087
9088         synchronized(this) {
9089             if (DEBUG_ALL) Slog.v(
9090                 TAG, "getTasks: max=" + maxNum + ", flags=" + flags);
9091
9092             final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(),
9093                     callingUid);
9094
9095             // TODO: Improve with MRU list from all ActivityStacks.
9096             mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed);
9097         }
9098
9099         return list;
9100     }
9101
9102     /**
9103      * Creates a new RecentTaskInfo from a TaskRecord.
9104      */
9105     private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) {
9106         // Update the task description to reflect any changes in the task stack
9107         tr.updateTaskDescription();
9108
9109         // Compose the recent task info
9110         ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo();
9111         rti.id = tr.getTopActivity() == null ? INVALID_TASK_ID : tr.taskId;
9112         rti.persistentId = tr.taskId;
9113         rti.baseIntent = new Intent(tr.getBaseIntent());
9114         rti.origActivity = tr.origActivity;
9115         rti.realActivity = tr.realActivity;
9116         rti.description = tr.lastDescription;
9117         rti.stackId = tr.stack != null ? tr.stack.mStackId : -1;
9118         rti.userId = tr.userId;
9119         rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription);
9120         rti.firstActiveTime = tr.firstActiveTime;
9121         rti.lastActiveTime = tr.lastActiveTime;
9122         rti.affiliatedTaskId = tr.mAffiliatedTaskId;
9123         rti.affiliatedTaskColor = tr.mAffiliatedTaskColor;
9124         rti.numActivities = 0;
9125         if (tr.mBounds != null) {
9126             rti.bounds = new Rect(tr.mBounds);
9127         }
9128         rti.isDockable = tr.canGoInDockedStack();
9129         rti.resizeMode = tr.mResizeMode;
9130
9131         ActivityRecord base = null;
9132         ActivityRecord top = null;
9133         ActivityRecord tmp;
9134
9135         for (int i = tr.mActivities.size() - 1; i >= 0; --i) {
9136             tmp = tr.mActivities.get(i);
9137             if (tmp.finishing) {
9138                 continue;
9139             }
9140             base = tmp;
9141             if (top == null || (top.state == ActivityState.INITIALIZING)) {
9142                 top = base;
9143             }
9144             rti.numActivities++;
9145         }
9146
9147         rti.baseActivity = (base != null) ? base.intent.getComponent() : null;
9148         rti.topActivity = (top != null) ? top.intent.getComponent() : null;
9149
9150         return rti;
9151     }
9152
9153     private boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) {
9154         boolean allowed = checkPermission(android.Manifest.permission.REAL_GET_TASKS,
9155                 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED;
9156         if (!allowed) {
9157             if (checkPermission(android.Manifest.permission.GET_TASKS,
9158                     callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) {
9159                 // Temporary compatibility: some existing apps on the system image may
9160                 // still be requesting the old permission and not switched to the new
9161                 // one; if so, we'll still allow them full access.  This means we need
9162                 // to see if they are holding the old permission and are a system app.
9163                 try {
9164                     if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) {
9165                         allowed = true;
9166                         if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid
9167                                 + " is using old GET_TASKS but privileged; allowing");
9168                     }
9169                 } catch (RemoteException e) {
9170                 }
9171             }
9172         }
9173         if (!allowed) {
9174             if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid
9175                     + " does not hold REAL_GET_TASKS; limiting output");
9176         }
9177         return allowed;
9178     }
9179
9180     @Override
9181     public ParceledListSlice<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags,
9182             int userId) {
9183         final int callingUid = Binder.getCallingUid();
9184         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId,
9185                 false, ALLOW_FULL_ONLY, "getRecentTasks", null);
9186
9187         final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0;
9188         final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0;
9189         synchronized (this) {
9190             final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(),
9191                     callingUid);
9192             final boolean detailed = checkCallingPermission(
9193                     android.Manifest.permission.GET_DETAILED_TASKS)
9194                     == PackageManager.PERMISSION_GRANTED;
9195
9196             if (!isUserRunning(userId, ActivityManager.FLAG_AND_UNLOCKED)) {
9197                 Slog.i(TAG, "user " + userId + " is still locked. Cannot load recents");
9198                 return ParceledListSlice.emptyList();
9199             }
9200             mRecentTasks.loadUserRecentsLocked(userId);
9201
9202             final int recentsCount = mRecentTasks.size();
9203             ArrayList<ActivityManager.RecentTaskInfo> res =
9204                     new ArrayList<>(maxNum < recentsCount ? maxNum : recentsCount);
9205
9206             final Set<Integer> includedUsers;
9207             if (includeProfiles) {
9208                 includedUsers = mUserController.getProfileIds(userId);
9209             } else {
9210                 includedUsers = new HashSet<>();
9211             }
9212             includedUsers.add(Integer.valueOf(userId));
9213
9214             for (int i = 0; i < recentsCount && maxNum > 0; i++) {
9215                 TaskRecord tr = mRecentTasks.get(i);
9216                 // Only add calling user or related users recent tasks
9217                 if (!includedUsers.contains(Integer.valueOf(tr.userId))) {
9218                     if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, not user: " + tr);
9219                     continue;
9220                 }
9221
9222                 if (tr.realActivitySuspended) {
9223                     if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, activity suspended: " + tr);
9224                     continue;
9225                 }
9226
9227                 // Return the entry if desired by the caller.  We always return
9228                 // the first entry, because callers always expect this to be the
9229                 // foreground app.  We may filter others if the caller has
9230                 // not supplied RECENT_WITH_EXCLUDED and there is some reason
9231                 // we should exclude the entry.
9232
9233                 if (i == 0
9234                         || withExcluded
9235                         || (tr.intent == null)
9236                         || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS)
9237                                 == 0)) {
9238                     if (!allowed) {
9239                         // If the caller doesn't have the GET_TASKS permission, then only
9240                         // allow them to see a small subset of tasks -- their own and home.
9241                         if (!tr.isHomeTask() && tr.effectiveUid != callingUid) {
9242                             if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, not allowed: " + tr);
9243                             continue;
9244                         }
9245                     }
9246                     if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) {
9247                         if (tr.stack != null && tr.stack.isHomeStack()) {
9248                             if (DEBUG_RECENTS) Slog.d(TAG_RECENTS,
9249                                     "Skipping, home stack task: " + tr);
9250                             continue;
9251                         }
9252                     }
9253                     if ((flags & ActivityManager.RECENT_INGORE_DOCKED_STACK_TOP_TASK) != 0) {
9254                         final ActivityStack stack = tr.stack;
9255                         if (stack != null && stack.isDockedStack() && stack.topTask() == tr) {
9256                             if (DEBUG_RECENTS) Slog.d(TAG_RECENTS,
9257                                     "Skipping, top task in docked stack: " + tr);
9258                             continue;
9259                         }
9260                     }
9261                     if ((flags & ActivityManager.RECENT_INGORE_PINNED_STACK_TASKS) != 0) {
9262                         if (tr.stack != null && tr.stack.isPinnedStack()) {
9263                             if (DEBUG_RECENTS) Slog.d(TAG_RECENTS,
9264                                     "Skipping, pinned stack task: " + tr);
9265                             continue;
9266                         }
9267                     }
9268                     if (tr.autoRemoveRecents && tr.getTopActivity() == null) {
9269                         // Don't include auto remove tasks that are finished or finishing.
9270                         if (DEBUG_RECENTS) Slog.d(TAG_RECENTS,
9271                                 "Skipping, auto-remove without activity: " + tr);
9272                         continue;
9273                     }
9274                     if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0
9275                             && !tr.isAvailable) {
9276                         if (DEBUG_RECENTS) Slog.d(TAG_RECENTS,
9277                                 "Skipping, unavail real act: " + tr);
9278                         continue;
9279                     }
9280
9281                     if (!tr.mUserSetupComplete) {
9282                         // Don't include task launched while user is not done setting-up.
9283                         if (DEBUG_RECENTS) Slog.d(TAG_RECENTS,
9284                                 "Skipping, user setup not complete: " + tr);
9285                         continue;
9286                     }
9287
9288                     ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr);
9289                     if (!detailed) {
9290                         rti.baseIntent.replaceExtras((Bundle)null);
9291                     }
9292
9293                     res.add(rti);
9294                     maxNum--;
9295                 }
9296             }
9297             return new ParceledListSlice<>(res);
9298         }
9299     }
9300
9301     @Override
9302     public ActivityManager.TaskThumbnail getTaskThumbnail(int id) {
9303         synchronized (this) {
9304             enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER,
9305                     "getTaskThumbnail()");
9306             final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(
9307                     id, !RESTORE_FROM_RECENTS, INVALID_STACK_ID);
9308             if (tr != null) {
9309                 return tr.getTaskThumbnailLocked();
9310             }
9311         }
9312         return null;
9313     }
9314
9315     @Override
9316     public int addAppTask(IBinder activityToken, Intent intent,
9317             ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException {
9318         final int callingUid = Binder.getCallingUid();
9319         final long callingIdent = Binder.clearCallingIdentity();
9320
9321         try {
9322             synchronized (this) {
9323                 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken);
9324                 if (r == null) {
9325                     throw new IllegalArgumentException("Activity does not exist; token="
9326                             + activityToken);
9327                 }
9328                 ComponentName comp = intent.getComponent();
9329                 if (comp == null) {
9330                     throw new IllegalArgumentException("Intent " + intent
9331                             + " must specify explicit component");
9332                 }
9333                 if (thumbnail.getWidth() != mThumbnailWidth
9334                         || thumbnail.getHeight() != mThumbnailHeight) {
9335                     throw new IllegalArgumentException("Bad thumbnail size: got "
9336                             + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require "
9337                             + mThumbnailWidth + "x" + mThumbnailHeight);
9338                 }
9339                 if (intent.getSelector() != null) {
9340                     intent.setSelector(null);
9341                 }
9342                 if (intent.getSourceBounds() != null) {
9343                     intent.setSourceBounds(null);
9344                 }
9345                 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) {
9346                     if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) {
9347                         // The caller has added this as an auto-remove task...  that makes no
9348                         // sense, so turn off auto-remove.
9349                         intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS);
9350                     }
9351                 }
9352                 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) {
9353                     mLastAddedTaskActivity = null;
9354                 }
9355                 ActivityInfo ainfo = mLastAddedTaskActivity;
9356                 if (ainfo == null) {
9357                     ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo(
9358                             comp, 0, UserHandle.getUserId(callingUid));
9359                     if (ainfo.applicationInfo.uid != callingUid) {
9360                         throw new SecurityException(
9361                                 "Can't add task for another application: target uid="
9362                                 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid);
9363                     }
9364                 }
9365
9366                 // Use the full screen as the context for the task thumbnail
9367                 final Point displaySize = new Point();
9368                 final TaskThumbnailInfo thumbnailInfo = new TaskThumbnailInfo();
9369                 r.task.stack.getDisplaySize(displaySize);
9370                 thumbnailInfo.taskWidth = displaySize.x;
9371                 thumbnailInfo.taskHeight = displaySize.y;
9372                 thumbnailInfo.screenOrientation = mConfiguration.orientation;
9373
9374                 TaskRecord task = new TaskRecord(this,
9375                         mStackSupervisor.getNextTaskIdForUserLocked(r.userId),
9376                         ainfo, intent, description, thumbnailInfo);
9377
9378                 int trimIdx = mRecentTasks.trimForTaskLocked(task, false);
9379                 if (trimIdx >= 0) {
9380                     // If this would have caused a trim, then we'll abort because that
9381                     // means it would be added at the end of the list but then just removed.
9382                     return INVALID_TASK_ID;
9383                 }
9384
9385                 final int N = mRecentTasks.size();
9386                 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) {
9387                     final TaskRecord tr = mRecentTasks.remove(N - 1);
9388                     tr.removedFromRecents();
9389                 }
9390
9391                 task.inRecents = true;
9392                 mRecentTasks.add(task);
9393                 r.task.stack.addTask(task, false, "addAppTask");
9394
9395                 task.setLastThumbnailLocked(thumbnail);
9396                 task.freeLastThumbnail();
9397
9398                 return task.taskId;
9399             }
9400         } finally {
9401             Binder.restoreCallingIdentity(callingIdent);
9402         }
9403     }
9404
9405     @Override
9406     public Point getAppTaskThumbnailSize() {
9407         synchronized (this) {
9408             return new Point(mThumbnailWidth,  mThumbnailHeight);
9409         }
9410     }
9411
9412     @Override
9413     public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) {
9414         synchronized (this) {
9415             ActivityRecord r = ActivityRecord.isInStackLocked(token);
9416             if (r != null) {
9417                 r.setTaskDescription(td);
9418                 r.task.updateTaskDescription();
9419             }
9420         }
9421     }
9422
9423     @Override
9424     public void setTaskResizeable(int taskId, int resizeableMode) {
9425         synchronized (this) {
9426             final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(
9427                     taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID);
9428             if (task == null) {
9429                 Slog.w(TAG, "setTaskResizeable: taskId=" + taskId + " not found");
9430                 return;
9431             }
9432             if (task.mResizeMode != resizeableMode) {
9433                 task.mResizeMode = resizeableMode;
9434                 mWindowManager.setTaskResizeable(taskId, resizeableMode);
9435                 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
9436                 mStackSupervisor.resumeFocusedStackTopActivityLocked();
9437             }
9438         }
9439     }
9440
9441     @Override
9442     public void resizeTask(int taskId, Rect bounds, int resizeMode) {
9443         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeTask()");
9444         long ident = Binder.clearCallingIdentity();
9445         try {
9446             synchronized (this) {
9447                 TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
9448                 if (task == null) {
9449                     Slog.w(TAG, "resizeTask: taskId=" + taskId + " not found");
9450                     return;
9451                 }
9452                 int stackId = task.stack.mStackId;
9453                 // We allow the task to scroll instead of resizing if this is a non-resizeable task
9454                 // in crop windows resize mode or if the task size is affected by the docked stack
9455                 // changing size. No need to update configuration.
9456                 if (bounds != null && task.inCropWindowsResizeMode()
9457                         && mStackSupervisor.isStackDockedInEffect(stackId)) {
9458                     mWindowManager.scrollTask(task.taskId, bounds);
9459                     return;
9460                 }
9461
9462                 // Place the task in the right stack if it isn't there already based on
9463                 // the requested bounds.
9464                 // The stack transition logic is:
9465                 // - a null bounds on a freeform task moves that task to fullscreen
9466                 // - a non-null bounds on a non-freeform (fullscreen OR docked) task moves
9467                 //   that task to freeform
9468                 // - otherwise the task is not moved
9469                 if (!StackId.isTaskResizeAllowed(stackId)) {
9470                     throw new IllegalArgumentException("resizeTask not allowed on task=" + task);
9471                 }
9472                 if (bounds == null && stackId == FREEFORM_WORKSPACE_STACK_ID) {
9473                     stackId = FULLSCREEN_WORKSPACE_STACK_ID;
9474                 } else if (bounds != null && stackId != FREEFORM_WORKSPACE_STACK_ID ) {
9475                     stackId = FREEFORM_WORKSPACE_STACK_ID;
9476                 }
9477                 boolean preserveWindow = (resizeMode & RESIZE_MODE_PRESERVE_WINDOW) != 0;
9478                 if (stackId != task.stack.mStackId) {
9479                     mStackSupervisor.moveTaskToStackUncheckedLocked(
9480                             task, stackId, ON_TOP, !FORCE_FOCUS, "resizeTask");
9481                     preserveWindow = false;
9482                 }
9483
9484                 mStackSupervisor.resizeTaskLocked(task, bounds, resizeMode, preserveWindow,
9485                         false /* deferResume */);
9486             }
9487         } finally {
9488             Binder.restoreCallingIdentity(ident);
9489         }
9490     }
9491
9492     @Override
9493     public Rect getTaskBounds(int taskId) {
9494         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getTaskBounds()");
9495         long ident = Binder.clearCallingIdentity();
9496         Rect rect = new Rect();
9497         try {
9498             synchronized (this) {
9499                 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(
9500                         taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID);
9501                 if (task == null) {
9502                     Slog.w(TAG, "getTaskBounds: taskId=" + taskId + " not found");
9503                     return rect;
9504                 }
9505                 if (task.stack != null) {
9506                     // Return the bounds from window manager since it will be adjusted for various
9507                     // things like the presense of a docked stack for tasks that aren't resizeable.
9508                     mWindowManager.getTaskBounds(task.taskId, rect);
9509                 } else {
9510                     // Task isn't in window manager yet since it isn't associated with a stack.
9511                     // Return the persist value from activity manager
9512                     if (task.mBounds != null) {
9513                         rect.set(task.mBounds);
9514                     } else if (task.mLastNonFullscreenBounds != null) {
9515                         rect.set(task.mLastNonFullscreenBounds);
9516                     }
9517                 }
9518             }
9519         } finally {
9520             Binder.restoreCallingIdentity(ident);
9521         }
9522         return rect;
9523     }
9524
9525     @Override
9526     public Bitmap getTaskDescriptionIcon(String filePath, int userId) {
9527         if (userId != UserHandle.getCallingUserId()) {
9528             enforceCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL,
9529                     "getTaskDescriptionIcon");
9530         }
9531         final File passedIconFile = new File(filePath);
9532         final File legitIconFile = new File(TaskPersister.getUserImagesDir(userId),
9533                 passedIconFile.getName());
9534         if (!legitIconFile.getPath().equals(filePath)
9535                 || !filePath.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) {
9536             throw new IllegalArgumentException("Bad file path: " + filePath
9537                     + " passed for userId " + userId);
9538         }
9539         return mRecentTasks.getTaskDescriptionIcon(filePath);
9540     }
9541
9542     @Override
9543     public void startInPlaceAnimationOnFrontMostApplication(ActivityOptions opts)
9544             throws RemoteException {
9545         if (opts.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE ||
9546                 opts.getCustomInPlaceResId() == 0) {
9547             throw new IllegalArgumentException("Expected in-place ActivityOption " +
9548                     "with valid animation");
9549         }
9550         mWindowManager.prepareAppTransition(TRANSIT_TASK_IN_PLACE, false);
9551         mWindowManager.overridePendingAppTransitionInPlace(opts.getPackageName(),
9552                 opts.getCustomInPlaceResId());
9553         mWindowManager.executeAppTransition();
9554     }
9555
9556     private void cleanUpRemovedTaskLocked(TaskRecord tr, boolean killProcess,
9557             boolean removeFromRecents) {
9558         if (removeFromRecents) {
9559             mRecentTasks.remove(tr);
9560             tr.removedFromRecents();
9561         }
9562         ComponentName component = tr.getBaseIntent().getComponent();
9563         if (component == null) {
9564             Slog.w(TAG, "No component for base intent of task: " + tr);
9565             return;
9566         }
9567
9568         // Find any running services associated with this app and stop if needed.
9569         mServices.cleanUpRemovedTaskLocked(tr, component, new Intent(tr.getBaseIntent()));
9570
9571         if (!killProcess) {
9572             return;
9573         }
9574
9575         // Determine if the process(es) for this task should be killed.
9576         final String pkg = component.getPackageName();
9577         ArrayList<ProcessRecord> procsToKill = new ArrayList<>();
9578         ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap();
9579         for (int i = 0; i < pmap.size(); i++) {
9580
9581             SparseArray<ProcessRecord> uids = pmap.valueAt(i);
9582             for (int j = 0; j < uids.size(); j++) {
9583                 ProcessRecord proc = uids.valueAt(j);
9584                 if (proc.userId != tr.userId) {
9585                     // Don't kill process for a different user.
9586                     continue;
9587                 }
9588                 if (proc == mHomeProcess) {
9589                     // Don't kill the home process along with tasks from the same package.
9590                     continue;
9591                 }
9592                 if (!proc.pkgList.containsKey(pkg)) {
9593                     // Don't kill process that is not associated with this task.
9594                     continue;
9595                 }
9596
9597                 for (int k = 0; k < proc.activities.size(); k++) {
9598                     TaskRecord otherTask = proc.activities.get(k).task;
9599                     if (tr.taskId != otherTask.taskId && otherTask.inRecents) {
9600                         // Don't kill process(es) that has an activity in a different task that is
9601                         // also in recents.
9602                         return;
9603                     }
9604                 }
9605
9606                 if (proc.foregroundServices) {
9607                     // Don't kill process(es) with foreground service.
9608                     return;
9609                 }
9610
9611                 // Add process to kill list.
9612                 procsToKill.add(proc);
9613             }
9614         }
9615
9616         // Kill the running processes.
9617         for (int i = 0; i < procsToKill.size(); i++) {
9618             ProcessRecord pr = procsToKill.get(i);
9619             if (pr.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND
9620                     && pr.curReceiver == null) {
9621                 pr.kill("remove task", true);
9622             } else {
9623                 // We delay killing processes that are not in the background or running a receiver.
9624                 pr.waitingToKill = "remove task";
9625             }
9626         }
9627     }
9628
9629     private void removeTasksByPackageNameLocked(String packageName, int userId) {
9630         // Remove all tasks with activities in the specified package from the list of recent tasks
9631         for (int i = mRecentTasks.size() - 1; i >= 0; i--) {
9632             TaskRecord tr = mRecentTasks.get(i);
9633             if (tr.userId != userId) continue;
9634
9635             ComponentName cn = tr.intent.getComponent();
9636             if (cn != null && cn.getPackageName().equals(packageName)) {
9637                 // If the package name matches, remove the task.
9638                 removeTaskByIdLocked(tr.taskId, true, REMOVE_FROM_RECENTS);
9639             }
9640         }
9641     }
9642
9643     private void cleanupDisabledPackageTasksLocked(String packageName, Set<String> filterByClasses,
9644             int userId) {
9645
9646         for (int i = mRecentTasks.size() - 1; i >= 0; i--) {
9647             TaskRecord tr = mRecentTasks.get(i);
9648             if (userId != UserHandle.USER_ALL && tr.userId != userId) {
9649                 continue;
9650             }
9651
9652             ComponentName cn = tr.intent.getComponent();
9653             final boolean sameComponent = cn != null && cn.getPackageName().equals(packageName)
9654                     && (filterByClasses == null || filterByClasses.contains(cn.getClassName()));
9655             if (sameComponent) {
9656                 removeTaskByIdLocked(tr.taskId, false, REMOVE_FROM_RECENTS);
9657             }
9658         }
9659     }
9660
9661     /**
9662      * Removes the task with the specified task id.
9663      *
9664      * @param taskId Identifier of the task to be removed.
9665      * @param killProcess Kill any process associated with the task if possible.
9666      * @param removeFromRecents Whether to also remove the task from recents.
9667      * @return Returns true if the given task was found and removed.
9668      */
9669     private boolean removeTaskByIdLocked(int taskId, boolean killProcess,
9670             boolean removeFromRecents) {
9671         final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(
9672                 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID);
9673         if (tr != null) {
9674             tr.removeTaskActivitiesLocked();
9675             cleanUpRemovedTaskLocked(tr, killProcess, removeFromRecents);
9676             if (tr.isPersistable) {
9677                 notifyTaskPersisterLocked(null, true);
9678             }
9679             return true;
9680         }
9681         Slog.w(TAG, "Request to remove task ignored for non-existent task " + taskId);
9682         return false;
9683     }
9684
9685     @Override
9686     public void removeStack(int stackId) {
9687         enforceCallingPermission(Manifest.permission.MANAGE_ACTIVITY_STACKS, "removeStack()");
9688         if (stackId == HOME_STACK_ID) {
9689             throw new IllegalArgumentException("Removing home stack is not allowed.");
9690         }
9691
9692         synchronized (this) {
9693             final long ident = Binder.clearCallingIdentity();
9694             try {
9695                 final ActivityStack stack = mStackSupervisor.getStack(stackId);
9696                 if (stack == null) {
9697                     return;
9698                 }
9699                 final ArrayList<TaskRecord> tasks = stack.getAllTasks();
9700                 for (int i = tasks.size() - 1; i >= 0; i--) {
9701                     removeTaskByIdLocked(
9702                             tasks.get(i).taskId, true /* killProcess */, REMOVE_FROM_RECENTS);
9703                 }
9704             } finally {
9705                 Binder.restoreCallingIdentity(ident);
9706             }
9707         }
9708     }
9709
9710     @Override
9711     public boolean removeTask(int taskId) {
9712         enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, "removeTask()");
9713         synchronized (this) {
9714             final long ident = Binder.clearCallingIdentity();
9715             try {
9716                 return removeTaskByIdLocked(taskId, true, REMOVE_FROM_RECENTS);
9717             } finally {
9718                 Binder.restoreCallingIdentity(ident);
9719             }
9720         }
9721     }
9722
9723     /**
9724      * TODO: Add mController hook
9725      */
9726     @Override
9727     public void moveTaskToFront(int taskId, int flags, Bundle bOptions) {
9728         enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, "moveTaskToFront()");
9729
9730         if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToFront: moving taskId=" + taskId);
9731         synchronized(this) {
9732             moveTaskToFrontLocked(taskId, flags, bOptions);
9733         }
9734     }
9735
9736     void moveTaskToFrontLocked(int taskId, int flags, Bundle bOptions) {
9737         ActivityOptions options = ActivityOptions.fromBundle(bOptions);
9738
9739         if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(),
9740                 Binder.getCallingUid(), -1, -1, "Task to front")) {
9741             ActivityOptions.abort(options);
9742             return;
9743         }
9744         final long origId = Binder.clearCallingIdentity();
9745         try {
9746             final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
9747             if (task == null) {
9748                 Slog.d(TAG, "Could not find task for id: "+ taskId);
9749                 return;
9750             }
9751             if (mStackSupervisor.isLockTaskModeViolation(task)) {
9752                 mStackSupervisor.showLockTaskToast();
9753                 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode");
9754                 return;
9755             }
9756             final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked();
9757             if (prev != null && prev.isRecentsActivity()) {
9758                 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE);
9759             }
9760             mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options, "moveTaskToFront",
9761                     false /* forceNonResizable */);
9762         } finally {
9763             Binder.restoreCallingIdentity(origId);
9764         }
9765         ActivityOptions.abort(options);
9766     }
9767
9768     /**
9769      * Moves an activity, and all of the other activities within the same task, to the bottom
9770      * of the history stack.  The activity's order within the task is unchanged.
9771      *
9772      * @param token A reference to the activity we wish to move
9773      * @param nonRoot If false then this only works if the activity is the root
9774      *                of a task; if true it will work for any activity in a task.
9775      * @return Returns true if the move completed, false if not.
9776      */
9777     @Override
9778     public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) {
9779         enforceNotIsolatedCaller("moveActivityTaskToBack");
9780         synchronized(this) {
9781             final long origId = Binder.clearCallingIdentity();
9782             try {
9783                 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot);
9784                 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
9785                 if (task != null) {
9786                     if (mStackSupervisor.isLockedTask(task)) {
9787                         mStackSupervisor.showLockTaskToast();
9788                         return false;
9789                     }
9790                     return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId);
9791                 }
9792             } finally {
9793                 Binder.restoreCallingIdentity(origId);
9794             }
9795         }
9796         return false;
9797     }
9798
9799     @Override
9800     public void moveTaskBackwards(int task) {
9801         enforceCallingPermission(android.Manifest.permission.REORDER_TASKS,
9802                 "moveTaskBackwards()");
9803
9804         synchronized(this) {
9805             if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(),
9806                     Binder.getCallingUid(), -1, -1, "Task backwards")) {
9807                 return;
9808             }
9809             final long origId = Binder.clearCallingIdentity();
9810             moveTaskBackwardsLocked(task);
9811             Binder.restoreCallingIdentity(origId);
9812         }
9813     }
9814
9815     private final void moveTaskBackwardsLocked(int task) {
9816         Slog.e(TAG, "moveTaskBackwards not yet implemented!");
9817     }
9818
9819     @Override
9820     public IActivityContainer createVirtualActivityContainer(IBinder parentActivityToken,
9821             IActivityContainerCallback callback) throws RemoteException {
9822         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createActivityContainer()");
9823         synchronized (this) {
9824             if (parentActivityToken == null) {
9825                 throw new IllegalArgumentException("parent token must not be null");
9826             }
9827             ActivityRecord r = ActivityRecord.forTokenLocked(parentActivityToken);
9828             if (r == null) {
9829                 return null;
9830             }
9831             if (callback == null) {
9832                 throw new IllegalArgumentException("callback must not be null");
9833             }
9834             return mStackSupervisor.createVirtualActivityContainer(r, callback);
9835         }
9836     }
9837
9838     @Override
9839     public void deleteActivityContainer(IActivityContainer container) throws RemoteException {
9840         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "deleteActivityContainer()");
9841         synchronized (this) {
9842             mStackSupervisor.deleteActivityContainer(container);
9843         }
9844     }
9845
9846     @Override
9847     public IActivityContainer createStackOnDisplay(int displayId) throws RemoteException {
9848         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createStackOnDisplay()");
9849         synchronized (this) {
9850             final int stackId = mStackSupervisor.getNextStackId();
9851             final ActivityStack stack =
9852                     mStackSupervisor.createStackOnDisplay(stackId, displayId, true /*onTop*/);
9853             if (stack == null) {
9854                 return null;
9855             }
9856             return stack.mActivityContainer;
9857         }
9858     }
9859
9860     @Override
9861     public int getActivityDisplayId(IBinder activityToken) throws RemoteException {
9862         synchronized (this) {
9863             ActivityStack stack = ActivityRecord.getStackLocked(activityToken);
9864             if (stack != null && stack.mActivityContainer.isAttachedLocked()) {
9865                 return stack.mActivityContainer.getDisplayId();
9866             }
9867             return Display.DEFAULT_DISPLAY;
9868         }
9869     }
9870
9871     @Override
9872     public int getActivityStackId(IBinder token) throws RemoteException {
9873         synchronized (this) {
9874             ActivityStack stack = ActivityRecord.getStackLocked(token);
9875             if (stack == null) {
9876                 return INVALID_STACK_ID;
9877             }
9878             return stack.mStackId;
9879         }
9880     }
9881
9882     @Override
9883     public void exitFreeformMode(IBinder token) throws RemoteException {
9884         synchronized (this) {
9885             long ident = Binder.clearCallingIdentity();
9886             try {
9887                 final ActivityRecord r = ActivityRecord.forTokenLocked(token);
9888                 if (r == null) {
9889                     throw new IllegalArgumentException(
9890                             "exitFreeformMode: No activity record matching token=" + token);
9891                 }
9892                 final ActivityStack stack = r.getStackLocked(token);
9893                 if (stack == null || stack.mStackId != FREEFORM_WORKSPACE_STACK_ID) {
9894                     throw new IllegalStateException(
9895                             "exitFreeformMode: You can only go fullscreen from freeform.");
9896                 }
9897                 if (DEBUG_STACK) Slog.d(TAG_STACK, "exitFreeformMode: " + r);
9898                 mStackSupervisor.moveTaskToStackLocked(r.task.taskId, FULLSCREEN_WORKSPACE_STACK_ID,
9899                         ON_TOP, !FORCE_FOCUS, "exitFreeformMode", ANIMATE);
9900             } finally {
9901                 Binder.restoreCallingIdentity(ident);
9902             }
9903         }
9904     }
9905
9906     @Override
9907     public void moveTaskToStack(int taskId, int stackId, boolean toTop) {
9908         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToStack()");
9909         if (stackId == HOME_STACK_ID) {
9910             throw new IllegalArgumentException(
9911                     "moveTaskToStack: Attempt to move task " + taskId + " to home stack");
9912         }
9913         synchronized (this) {
9914             long ident = Binder.clearCallingIdentity();
9915             try {
9916                 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToStack: moving task=" + taskId
9917                         + " to stackId=" + stackId + " toTop=" + toTop);
9918                 if (stackId == DOCKED_STACK_ID) {
9919                     mWindowManager.setDockedStackCreateState(DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT,
9920                             null /* initialBounds */);
9921                 }
9922                 boolean result = mStackSupervisor.moveTaskToStackLocked(taskId, stackId, toTop,
9923                         !FORCE_FOCUS, "moveTaskToStack", ANIMATE);
9924                 if (result && stackId == DOCKED_STACK_ID) {
9925                     // If task moved to docked stack - show recents if needed.
9926                     mStackSupervisor.moveHomeStackTaskToTop(RECENTS_ACTIVITY_TYPE,
9927                             "moveTaskToDockedStack");
9928                 }
9929             } finally {
9930                 Binder.restoreCallingIdentity(ident);
9931             }
9932         }
9933     }
9934
9935     @Override
9936     public void swapDockedAndFullscreenStack() throws RemoteException {
9937         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "swapDockedAndFullscreenStack()");
9938         synchronized (this) {
9939             long ident = Binder.clearCallingIdentity();
9940             try {
9941                 final ActivityStack fullscreenStack = mStackSupervisor.getStack(
9942                         FULLSCREEN_WORKSPACE_STACK_ID);
9943                 final TaskRecord topTask = fullscreenStack != null ? fullscreenStack.topTask()
9944                         : null;
9945                 final ActivityStack dockedStack = mStackSupervisor.getStack(DOCKED_STACK_ID);
9946                 final ArrayList<TaskRecord> tasks = dockedStack != null ? dockedStack.getAllTasks()
9947                         : null;
9948                 if (topTask == null || tasks == null || tasks.size() == 0) {
9949                     Slog.w(TAG,
9950                             "Unable to swap tasks, either docked or fullscreen stack is empty.");
9951                     return;
9952                 }
9953
9954                 // TODO: App transition
9955                 mWindowManager.prepareAppTransition(TRANSIT_ACTIVITY_RELAUNCH, false);
9956
9957                 // Defer the resume so resume/pausing while moving stacks is dangerous.
9958                 mStackSupervisor.moveTaskToStackLocked(topTask.taskId, DOCKED_STACK_ID,
9959                         false /* toTop */, !FORCE_FOCUS, "swapDockedAndFullscreenStack",
9960                         ANIMATE, true /* deferResume */);
9961                 final int size = tasks.size();
9962                 for (int i = 0; i < size; i++) {
9963                     final int id = tasks.get(i).taskId;
9964                     if (id == topTask.taskId) {
9965                         continue;
9966                     }
9967                     mStackSupervisor.moveTaskToStackLocked(id,
9968                             FULLSCREEN_WORKSPACE_STACK_ID, true /* toTop */, !FORCE_FOCUS,
9969                             "swapDockedAndFullscreenStack", ANIMATE, true /* deferResume */);
9970                 }
9971
9972                 // Because we deferred the resume, to avoid conflicts with stack switches while
9973                 // resuming, we need to do it after all the tasks are moved.
9974                 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
9975                 mStackSupervisor.resumeFocusedStackTopActivityLocked();
9976
9977                 mWindowManager.executeAppTransition();
9978             } finally {
9979                 Binder.restoreCallingIdentity(ident);
9980             }
9981         }
9982     }
9983
9984     /**
9985      * Moves the input task to the docked stack.
9986      *
9987      * @param taskId Id of task to move.
9988      * @param createMode The mode the docked stack should be created in if it doesn't exist
9989      *                   already. See
9990      *                   {@link android.app.ActivityManager#DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT}
9991      *                   and
9992      *                   {@link android.app.ActivityManager#DOCKED_STACK_CREATE_MODE_BOTTOM_OR_RIGHT}
9993      * @param toTop If the task and stack should be moved to the top.
9994      * @param animate Whether we should play an animation for the moving the task
9995      * @param initialBounds If the docked stack gets created, it will use these bounds for the
9996      *                      docked stack. Pass {@code null} to use default bounds.
9997      */
9998     @Override
9999     public boolean moveTaskToDockedStack(int taskId, int createMode, boolean toTop, boolean animate,
10000             Rect initialBounds, boolean moveHomeStackFront) {
10001         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToDockedStack()");
10002         synchronized (this) {
10003             long ident = Binder.clearCallingIdentity();
10004             try {
10005                 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToDockedStack: moving task=" + taskId
10006                         + " to createMode=" + createMode + " toTop=" + toTop);
10007                 mWindowManager.setDockedStackCreateState(createMode, initialBounds);
10008                 final boolean moved = mStackSupervisor.moveTaskToStackLocked(
10009                         taskId, DOCKED_STACK_ID, toTop, !FORCE_FOCUS, "moveTaskToDockedStack",
10010                         animate, DEFER_RESUME);
10011                 if (moved) {
10012                     if (moveHomeStackFront) {
10013                         mStackSupervisor.moveHomeStackToFront("moveTaskToDockedStack");
10014                     }
10015                     mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
10016                 }
10017                 return moved;
10018             } finally {
10019                 Binder.restoreCallingIdentity(ident);
10020             }
10021         }
10022     }
10023
10024     /**
10025      * Moves the top activity in the input stackId to the pinned stack.
10026      *
10027      * @param stackId Id of stack to move the top activity to pinned stack.
10028      * @param bounds Bounds to use for pinned stack.
10029      *
10030      * @return True if the top activity of the input stack was successfully moved to the pinned
10031      *          stack.
10032      */
10033     @Override
10034     public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) {
10035         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTopActivityToPinnedStack()");
10036         synchronized (this) {
10037             if (!mSupportsPictureInPicture) {
10038                 throw new IllegalStateException("moveTopActivityToPinnedStack:"
10039                         + "Device doesn't support picture-in-pciture mode");
10040             }
10041
10042             long ident = Binder.clearCallingIdentity();
10043             try {
10044                 return mStackSupervisor.moveTopStackActivityToPinnedStackLocked(stackId, bounds);
10045             } finally {
10046                 Binder.restoreCallingIdentity(ident);
10047             }
10048         }
10049     }
10050
10051     @Override
10052     public void resizeStack(int stackId, Rect bounds, boolean allowResizeInDockedMode,
10053             boolean preserveWindows, boolean animate, int animationDuration) {
10054         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()");
10055         long ident = Binder.clearCallingIdentity();
10056         try {
10057             synchronized (this) {
10058                 if (animate) {
10059                     if (stackId == PINNED_STACK_ID) {
10060                         mWindowManager.animateResizePinnedStack(bounds, animationDuration);
10061                     } else {
10062                         throw new IllegalArgumentException("Stack: " + stackId
10063                                 + " doesn't support animated resize.");
10064                     }
10065                 } else {
10066                     mStackSupervisor.resizeStackLocked(stackId, bounds, null /* tempTaskBounds */,
10067                             null /* tempTaskInsetBounds */, preserveWindows,
10068                             allowResizeInDockedMode, !DEFER_RESUME);
10069                 }
10070             }
10071         } finally {
10072             Binder.restoreCallingIdentity(ident);
10073         }
10074     }
10075
10076     @Override
10077     public void resizeDockedStack(Rect dockedBounds, Rect tempDockedTaskBounds,
10078             Rect tempDockedTaskInsetBounds,
10079             Rect tempOtherTaskBounds, Rect tempOtherTaskInsetBounds) {
10080         enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS,
10081                 "resizeDockedStack()");
10082         long ident = Binder.clearCallingIdentity();
10083         try {
10084             synchronized (this) {
10085                 mStackSupervisor.resizeDockedStackLocked(dockedBounds, tempDockedTaskBounds,
10086                         tempDockedTaskInsetBounds, tempOtherTaskBounds, tempOtherTaskInsetBounds,
10087                         PRESERVE_WINDOWS);
10088             }
10089         } finally {
10090             Binder.restoreCallingIdentity(ident);
10091         }
10092     }
10093
10094     @Override
10095     public void resizePinnedStack(Rect pinnedBounds, Rect tempPinnedTaskBounds) {
10096         enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS,
10097                 "resizePinnedStack()");
10098         final long ident = Binder.clearCallingIdentity();
10099         try {
10100             synchronized (this) {
10101                 mStackSupervisor.resizePinnedStackLocked(pinnedBounds, tempPinnedTaskBounds);
10102             }
10103         } finally {
10104             Binder.restoreCallingIdentity(ident);
10105         }
10106     }
10107
10108     @Override
10109     public void positionTaskInStack(int taskId, int stackId, int position) {
10110         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "positionTaskInStack()");
10111         if (stackId == HOME_STACK_ID) {
10112             throw new IllegalArgumentException(
10113                     "positionTaskInStack: Attempt to change the position of task "
10114                     + taskId + " in/to home stack");
10115         }
10116         synchronized (this) {
10117             long ident = Binder.clearCallingIdentity();
10118             try {
10119                 if (DEBUG_STACK) Slog.d(TAG_STACK,
10120                         "positionTaskInStack: positioning task=" + taskId
10121                         + " in stackId=" + stackId + " at position=" + position);
10122                 mStackSupervisor.positionTaskInStackLocked(taskId, stackId, position);
10123             } finally {
10124                 Binder.restoreCallingIdentity(ident);
10125             }
10126         }
10127     }
10128
10129     @Override
10130     public List<StackInfo> getAllStackInfos() {
10131         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getAllStackInfos()");
10132         long ident = Binder.clearCallingIdentity();
10133         try {
10134             synchronized (this) {
10135                 return mStackSupervisor.getAllStackInfosLocked();
10136             }
10137         } finally {
10138             Binder.restoreCallingIdentity(ident);
10139         }
10140     }
10141
10142     @Override
10143     public StackInfo getStackInfo(int stackId) {
10144         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()");
10145         long ident = Binder.clearCallingIdentity();
10146         try {
10147             synchronized (this) {
10148                 return mStackSupervisor.getStackInfoLocked(stackId);
10149             }
10150         } finally {
10151             Binder.restoreCallingIdentity(ident);
10152         }
10153     }
10154
10155     @Override
10156     public boolean isInHomeStack(int taskId) {
10157         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()");
10158         long ident = Binder.clearCallingIdentity();
10159         try {
10160             synchronized (this) {
10161                 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(
10162                         taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID);
10163                 return tr != null && tr.stack != null && tr.stack.isHomeStack();
10164             }
10165         } finally {
10166             Binder.restoreCallingIdentity(ident);
10167         }
10168     }
10169
10170     @Override
10171     public int getTaskForActivity(IBinder token, boolean onlyRoot) {
10172         synchronized(this) {
10173             return ActivityRecord.getTaskForActivityLocked(token, onlyRoot);
10174         }
10175     }
10176
10177     @Override
10178     public void updateDeviceOwner(String packageName) {
10179         final int callingUid = Binder.getCallingUid();
10180         if (callingUid != 0 && callingUid != Process.SYSTEM_UID) {
10181             throw new SecurityException("updateDeviceOwner called from non-system process");
10182         }
10183         synchronized (this) {
10184             mDeviceOwnerName = packageName;
10185         }
10186     }
10187
10188     @Override
10189     public void updateLockTaskPackages(int userId, String[] packages) {
10190         final int callingUid = Binder.getCallingUid();
10191         if (callingUid != 0 && callingUid != Process.SYSTEM_UID) {
10192             enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES,
10193                     "updateLockTaskPackages()");
10194         }
10195         synchronized (this) {
10196             if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Whitelisting " + userId + ":" +
10197                     Arrays.toString(packages));
10198             mLockTaskPackages.put(userId, packages);
10199             mStackSupervisor.onLockTaskPackagesUpdatedLocked();
10200         }
10201     }
10202
10203
10204     void startLockTaskModeLocked(TaskRecord task) {
10205         if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "startLockTaskModeLocked: " + task);
10206         if (task.mLockTaskAuth == LOCK_TASK_AUTH_DONT_LOCK) {
10207             return;
10208         }
10209
10210         // isSystemInitiated is used to distinguish between locked and pinned mode, as pinned mode
10211         // is initiated by system after the pinning request was shown and locked mode is initiated
10212         // by an authorized app directly
10213         final int callingUid = Binder.getCallingUid();
10214         boolean isSystemInitiated = callingUid == Process.SYSTEM_UID;
10215         long ident = Binder.clearCallingIdentity();
10216         try {
10217             if (!isSystemInitiated) {
10218                 task.mLockTaskUid = callingUid;
10219                 if (task.mLockTaskAuth == LOCK_TASK_AUTH_PINNABLE) {
10220                     // startLockTask() called by app and task mode is lockTaskModeDefault.
10221                     if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Mode default, asking user");
10222                     StatusBarManagerInternal statusBarManager =
10223                             LocalServices.getService(StatusBarManagerInternal.class);
10224                     if (statusBarManager != null) {
10225                         statusBarManager.showScreenPinningRequest(task.taskId);
10226                     }
10227                     return;
10228                 }
10229
10230                 final ActivityStack stack = mStackSupervisor.getFocusedStack();
10231                 if (stack == null || task != stack.topTask()) {
10232                     throw new IllegalArgumentException("Invalid task, not in foreground");
10233                 }
10234             }
10235             if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, isSystemInitiated ? "Locking pinned" :
10236                     "Locking fully");
10237             mStackSupervisor.setLockTaskModeLocked(task, isSystemInitiated ?
10238                     ActivityManager.LOCK_TASK_MODE_PINNED :
10239                     ActivityManager.LOCK_TASK_MODE_LOCKED,
10240                     "startLockTask", true);
10241         } finally {
10242             Binder.restoreCallingIdentity(ident);
10243         }
10244     }
10245
10246     @Override
10247     public void startLockTaskMode(int taskId) {
10248         synchronized (this) {
10249             final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId);
10250             if (task != null) {
10251                 startLockTaskModeLocked(task);
10252             }
10253         }
10254     }
10255
10256     @Override
10257     public void startLockTaskMode(IBinder token) {
10258         synchronized (this) {
10259             final ActivityRecord r = ActivityRecord.forTokenLocked(token);
10260             if (r == null) {
10261                 return;
10262             }
10263             final TaskRecord task = r.task;
10264             if (task != null) {
10265                 startLockTaskModeLocked(task);
10266             }
10267         }
10268     }
10269
10270     @Override
10271     public void startSystemLockTaskMode(int taskId) throws RemoteException {
10272         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startSystemLockTaskMode");
10273         // This makes inner call to look as if it was initiated by system.
10274         long ident = Binder.clearCallingIdentity();
10275         try {
10276             synchronized (this) {
10277                 startLockTaskMode(taskId);
10278             }
10279         } finally {
10280             Binder.restoreCallingIdentity(ident);
10281         }
10282     }
10283
10284     @Override
10285     public void stopLockTaskMode() {
10286         final TaskRecord lockTask = mStackSupervisor.getLockedTaskLocked();
10287         if (lockTask == null) {
10288             // Our work here is done.
10289             return;
10290         }
10291
10292         final int callingUid = Binder.getCallingUid();
10293         final int lockTaskUid = lockTask.mLockTaskUid;
10294         final int lockTaskModeState = mStackSupervisor.getLockTaskModeState();
10295         if (lockTaskModeState == ActivityManager.LOCK_TASK_MODE_NONE) {
10296             // Done.
10297             return;
10298         } else {
10299             // Ensure the same caller for startLockTaskMode and stopLockTaskMode.
10300             // It is possible lockTaskMode was started by the system process because
10301             // android:lockTaskMode is set to a locking value in the application manifest
10302             // instead of the app calling startLockTaskMode. In this case
10303             // {@link TaskRecord.mLockTaskUid} will be 0, so we compare the callingUid to the
10304             // {@link TaskRecord.effectiveUid} instead. Also caller with
10305             // {@link MANAGE_ACTIVITY_STACKS} can stop any lock task.
10306             if (checkCallingPermission(MANAGE_ACTIVITY_STACKS) != PERMISSION_GRANTED
10307                     && callingUid != lockTaskUid
10308                     && (lockTaskUid != 0 || callingUid != lockTask.effectiveUid)) {
10309                 throw new SecurityException("Invalid uid, expected " + lockTaskUid
10310                         + " callingUid=" + callingUid + " effectiveUid=" + lockTask.effectiveUid);
10311             }
10312         }
10313         long ident = Binder.clearCallingIdentity();
10314         try {
10315             Log.d(TAG, "stopLockTaskMode");
10316             // Stop lock task
10317             synchronized (this) {
10318                 mStackSupervisor.setLockTaskModeLocked(null, ActivityManager.LOCK_TASK_MODE_NONE,
10319                         "stopLockTask", true);
10320             }
10321             TelecomManager tm = (TelecomManager) mContext.getSystemService(Context.TELECOM_SERVICE);
10322             if (tm != null) {
10323                 tm.showInCallScreen(false);
10324             }
10325         } finally {
10326             Binder.restoreCallingIdentity(ident);
10327         }
10328     }
10329
10330     /**
10331      * This API should be called by SystemUI only when user perform certain action to dismiss
10332      * lock task mode. We should only dismiss pinned lock task mode in this case.
10333      */
10334     @Override
10335     public void stopSystemLockTaskMode() throws RemoteException {
10336         if (mStackSupervisor.getLockTaskModeState() == ActivityManager.LOCK_TASK_MODE_PINNED) {
10337             stopLockTaskMode();
10338         } else {
10339             mStackSupervisor.showLockTaskToast();
10340         }
10341     }
10342
10343     @Override
10344     public boolean isInLockTaskMode() {
10345         return getLockTaskModeState() != ActivityManager.LOCK_TASK_MODE_NONE;
10346     }
10347
10348     @Override
10349     public int getLockTaskModeState() {
10350         synchronized (this) {
10351             return mStackSupervisor.getLockTaskModeState();
10352         }
10353     }
10354
10355     @Override
10356     public void showLockTaskEscapeMessage(IBinder token) {
10357         synchronized (this) {
10358             final ActivityRecord r = ActivityRecord.forTokenLocked(token);
10359             if (r == null) {
10360                 return;
10361             }
10362             mStackSupervisor.showLockTaskEscapeMessageLocked(r.task);
10363         }
10364     }
10365
10366     // =========================================================
10367     // CONTENT PROVIDERS
10368     // =========================================================
10369
10370     private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) {
10371         List<ProviderInfo> providers = null;
10372         try {
10373             providers = AppGlobals.getPackageManager()
10374                     .queryContentProviders(app.processName, app.uid,
10375                             STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS
10376                                     | MATCH_DEBUG_TRIAGED_MISSING)
10377                     .getList();
10378         } catch (RemoteException ex) {
10379         }
10380         if (DEBUG_MU) Slog.v(TAG_MU,
10381                 "generateApplicationProvidersLocked, app.info.uid = " + app.uid);
10382         int userId = app.userId;
10383         if (providers != null) {
10384             int N = providers.size();
10385             app.pubProviders.ensureCapacity(N + app.pubProviders.size());
10386             for (int i=0; i<N; i++) {
10387                 // TODO: keep logic in sync with installEncryptionUnawareProviders
10388                 ProviderInfo cpi =
10389                     (ProviderInfo)providers.get(i);
10390                 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo,
10391                         cpi.name, cpi.flags);
10392                 if (singleton && UserHandle.getUserId(app.uid) != UserHandle.USER_SYSTEM) {
10393                     // This is a singleton provider, but a user besides the
10394                     // default user is asking to initialize a process it runs
10395                     // in...  well, no, it doesn't actually run in this process,
10396                     // it runs in the process of the default user.  Get rid of it.
10397                     providers.remove(i);
10398                     N--;
10399                     i--;
10400                     continue;
10401                 }
10402
10403                 ComponentName comp = new ComponentName(cpi.packageName, cpi.name);
10404                 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId);
10405                 if (cpr == null) {
10406                     cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton);
10407                     mProviderMap.putProviderByClass(comp, cpr);
10408                 }
10409                 if (DEBUG_MU) Slog.v(TAG_MU,
10410                         "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid);
10411                 app.pubProviders.put(cpi.name, cpr);
10412                 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) {
10413                     // Don't add this if it is a platform component that is marked
10414                     // to run in multiple processes, because this is actually
10415                     // part of the framework so doesn't make sense to track as a
10416                     // separate apk in the process.
10417                     app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode,
10418                             mProcessStats);
10419                 }
10420                 notifyPackageUse(cpi.applicationInfo.packageName,
10421                                  PackageManager.NOTIFY_PACKAGE_USE_CONTENT_PROVIDER);
10422             }
10423         }
10424         return providers;
10425     }
10426
10427     /**
10428      * Check if the calling UID has a possible chance at accessing the provider
10429      * at the given authority and user.
10430      */
10431     public String checkContentProviderAccess(String authority, int userId) {
10432         if (userId == UserHandle.USER_ALL) {
10433             mContext.enforceCallingOrSelfPermission(
10434                     Manifest.permission.INTERACT_ACROSS_USERS_FULL, TAG);
10435             userId = UserHandle.getCallingUserId();
10436         }
10437
10438         ProviderInfo cpi = null;
10439         try {
10440             cpi = AppGlobals.getPackageManager().resolveContentProvider(authority,
10441                     STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS
10442                             | PackageManager.MATCH_DIRECT_BOOT_AWARE
10443                             | PackageManager.MATCH_DIRECT_BOOT_UNAWARE,
10444                     userId);
10445         } catch (RemoteException ignored) {
10446         }
10447         if (cpi == null) {
10448             // TODO: make this an outright failure in a future platform release;
10449             // until then anonymous content notifications are unprotected
10450             //return "Failed to find provider " + authority + " for user " + userId;
10451             return null;
10452         }
10453
10454         ProcessRecord r = null;
10455         synchronized (mPidsSelfLocked) {
10456             r = mPidsSelfLocked.get(Binder.getCallingPid());
10457         }
10458         if (r == null) {
10459             return "Failed to find PID " + Binder.getCallingPid();
10460         }
10461
10462         synchronized (this) {
10463             return checkContentProviderPermissionLocked(cpi, r, userId, true);
10464         }
10465     }
10466
10467     /**
10468      * Check if {@link ProcessRecord} has a possible chance at accessing the
10469      * given {@link ProviderInfo}. Final permission checking is always done
10470      * in {@link ContentProvider}.
10471      */
10472     private final String checkContentProviderPermissionLocked(
10473             ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) {
10474         final int callingPid = (r != null) ? r.pid : Binder.getCallingPid();
10475         final int callingUid = (r != null) ? r.uid : Binder.getCallingUid();
10476         boolean checkedGrants = false;
10477         if (checkUser) {
10478             // Looking for cross-user grants before enforcing the typical cross-users permissions
10479             int tmpTargetUserId = mUserController.unsafeConvertIncomingUserLocked(userId);
10480             if (tmpTargetUserId != UserHandle.getUserId(callingUid)) {
10481                 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) {
10482                     return null;
10483                 }
10484                 checkedGrants = true;
10485             }
10486             userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false,
10487                     ALLOW_NON_FULL, "checkContentProviderPermissionLocked " + cpi.authority, null);
10488             if (userId != tmpTargetUserId) {
10489                 // When we actually went to determine the final targer user ID, this ended
10490                 // up different than our initial check for the authority.  This is because
10491                 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to
10492                 // SELF.  So we need to re-check the grants again.
10493                 checkedGrants = false;
10494             }
10495         }
10496         if (checkComponentPermission(cpi.readPermission, callingPid, callingUid,
10497                 cpi.applicationInfo.uid, cpi.exported)
10498                 == PackageManager.PERMISSION_GRANTED) {
10499             return null;
10500         }
10501         if (checkComponentPermission(cpi.writePermission, callingPid, callingUid,
10502                 cpi.applicationInfo.uid, cpi.exported)
10503                 == PackageManager.PERMISSION_GRANTED) {
10504             return null;
10505         }
10506
10507         PathPermission[] pps = cpi.pathPermissions;
10508         if (pps != null) {
10509             int i = pps.length;
10510             while (i > 0) {
10511                 i--;
10512                 PathPermission pp = pps[i];
10513                 String pprperm = pp.getReadPermission();
10514                 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid,
10515                         cpi.applicationInfo.uid, cpi.exported)
10516                         == PackageManager.PERMISSION_GRANTED) {
10517                     return null;
10518                 }
10519                 String ppwperm = pp.getWritePermission();
10520                 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid,
10521                         cpi.applicationInfo.uid, cpi.exported)
10522                         == PackageManager.PERMISSION_GRANTED) {
10523                     return null;
10524                 }
10525             }
10526         }
10527         if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) {
10528             return null;
10529         }
10530
10531         String msg;
10532         if (!cpi.exported) {
10533             msg = "Permission Denial: opening provider " + cpi.name
10534                     + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid
10535                     + ", uid=" + callingUid + ") that is not exported from uid "
10536                     + cpi.applicationInfo.uid;
10537         } else {
10538             msg = "Permission Denial: opening provider " + cpi.name
10539                     + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid
10540                     + ", uid=" + callingUid + ") requires "
10541                     + cpi.readPermission + " or " + cpi.writePermission;
10542         }
10543         Slog.w(TAG, msg);
10544         return msg;
10545     }
10546
10547     /**
10548      * Returns if the ContentProvider has granted a uri to callingUid
10549      */
10550     boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) {
10551         final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid);
10552         if (perms != null) {
10553             for (int i=perms.size()-1; i>=0; i--) {
10554                 GrantUri grantUri = perms.keyAt(i);
10555                 if (grantUri.sourceUserId == userId || !checkUser) {
10556                     if (matchesProvider(grantUri.uri, cpi)) {
10557                         return true;
10558                     }
10559                 }
10560             }
10561         }
10562         return false;
10563     }
10564
10565     /**
10566      * Returns true if the uri authority is one of the authorities specified in the provider.
10567      */
10568     boolean matchesProvider(Uri uri, ProviderInfo cpi) {
10569         String uriAuth = uri.getAuthority();
10570         String cpiAuth = cpi.authority;
10571         if (cpiAuth.indexOf(';') == -1) {
10572             return cpiAuth.equals(uriAuth);
10573         }
10574         String[] cpiAuths = cpiAuth.split(";");
10575         int length = cpiAuths.length;
10576         for (int i = 0; i < length; i++) {
10577             if (cpiAuths[i].equals(uriAuth)) return true;
10578         }
10579         return false;
10580     }
10581
10582     ContentProviderConnection incProviderCountLocked(ProcessRecord r,
10583             final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) {
10584         if (r != null) {
10585             for (int i=0; i<r.conProviders.size(); i++) {
10586                 ContentProviderConnection conn = r.conProviders.get(i);
10587                 if (conn.provider == cpr) {
10588                     if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER,
10589                             "Adding provider requested by "
10590                             + r.processName + " from process "
10591                             + cpr.info.processName + ": " + cpr.name.flattenToShortString()
10592                             + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount);
10593                     if (stable) {
10594                         conn.stableCount++;
10595                         conn.numStableIncs++;
10596                     } else {
10597                         conn.unstableCount++;
10598                         conn.numUnstableIncs++;
10599                     }
10600                     return conn;
10601                 }
10602             }
10603             ContentProviderConnection conn = new ContentProviderConnection(cpr, r);
10604             if (stable) {
10605                 conn.stableCount = 1;
10606                 conn.numStableIncs = 1;
10607             } else {
10608                 conn.unstableCount = 1;
10609                 conn.numUnstableIncs = 1;
10610             }
10611             cpr.connections.add(conn);
10612             r.conProviders.add(conn);
10613             startAssociationLocked(r.uid, r.processName, r.curProcState,
10614                     cpr.uid, cpr.name, cpr.info.processName);
10615             return conn;
10616         }
10617         cpr.addExternalProcessHandleLocked(externalProcessToken);
10618         return null;
10619     }
10620
10621     boolean decProviderCountLocked(ContentProviderConnection conn,
10622             ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) {
10623         if (conn != null) {
10624             cpr = conn.provider;
10625             if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER,
10626                     "Removing provider requested by "
10627                     + conn.client.processName + " from process "
10628                     + cpr.info.processName + ": " + cpr.name.flattenToShortString()
10629                     + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount);
10630             if (stable) {
10631                 conn.stableCount--;
10632             } else {
10633                 conn.unstableCount--;
10634             }
10635             if (conn.stableCount == 0 && conn.unstableCount == 0) {
10636                 cpr.connections.remove(conn);
10637                 conn.client.conProviders.remove(conn);
10638                 if (conn.client.setProcState < ActivityManager.PROCESS_STATE_LAST_ACTIVITY) {
10639                     // The client is more important than last activity -- note the time this
10640                     // is happening, so we keep the old provider process around a bit as last
10641                     // activity to avoid thrashing it.
10642                     if (cpr.proc != null) {
10643                         cpr.proc.lastProviderTime = SystemClock.uptimeMillis();
10644                     }
10645                 }
10646                 stopAssociationLocked(conn.client.uid, conn.client.processName, cpr.uid, cpr.name);
10647                 return true;
10648             }
10649             return false;
10650         }
10651         cpr.removeExternalProcessHandleLocked(externalProcessToken);
10652         return false;
10653     }
10654
10655     private void checkTime(long startTime, String where) {
10656         long now = SystemClock.uptimeMillis();
10657         if ((now-startTime) > 50) {
10658             // If we are taking more than 50ms, log about it.
10659             Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where);
10660         }
10661     }
10662
10663     private static final int[] PROCESS_STATE_STATS_FORMAT = new int[] {
10664             PROC_SPACE_TERM,
10665             PROC_SPACE_TERM|PROC_PARENS,
10666             PROC_SPACE_TERM|PROC_CHAR|PROC_OUT_LONG,        // 3: process state
10667     };
10668
10669     private final long[] mProcessStateStatsLongs = new long[1];
10670
10671     boolean isProcessAliveLocked(ProcessRecord proc) {
10672         if (proc.procStatFile == null) {
10673             proc.procStatFile = "/proc/" + proc.pid + "/stat";
10674         }
10675         mProcessStateStatsLongs[0] = 0;
10676         if (!Process.readProcFile(proc.procStatFile, PROCESS_STATE_STATS_FORMAT, null,
10677                 mProcessStateStatsLongs, null)) {
10678             if (DEBUG_OOM_ADJ) Slog.d(TAG, "UNABLE TO RETRIEVE STATE FOR " + proc.procStatFile);
10679             return false;
10680         }
10681         final long state = mProcessStateStatsLongs[0];
10682         if (DEBUG_OOM_ADJ) Slog.d(TAG, "RETRIEVED STATE FOR " + proc.procStatFile + ": "
10683                 + (char)state);
10684         return state != 'Z' && state != 'X' && state != 'x' && state != 'K';
10685     }
10686
10687     private ContentProviderHolder getContentProviderImpl(IApplicationThread caller,
10688             String name, IBinder token, boolean stable, int userId) {
10689         ContentProviderRecord cpr;
10690         ContentProviderConnection conn = null;
10691         ProviderInfo cpi = null;
10692
10693         synchronized(this) {
10694             long startTime = SystemClock.uptimeMillis();
10695
10696             ProcessRecord r = null;
10697             if (caller != null) {
10698                 r = getRecordForAppLocked(caller);
10699                 if (r == null) {
10700                     throw new SecurityException(
10701                             "Unable to find app for caller " + caller
10702                           + " (pid=" + Binder.getCallingPid()
10703                           + ") when getting content provider " + name);
10704                 }
10705             }
10706
10707             boolean checkCrossUser = true;
10708
10709             checkTime(startTime, "getContentProviderImpl: getProviderByName");
10710
10711             // First check if this content provider has been published...
10712             cpr = mProviderMap.getProviderByName(name, userId);
10713             // If that didn't work, check if it exists for user 0 and then
10714             // verify that it's a singleton provider before using it.
10715             if (cpr == null && userId != UserHandle.USER_SYSTEM) {
10716                 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_SYSTEM);
10717                 if (cpr != null) {
10718                     cpi = cpr.info;
10719                     if (isSingleton(cpi.processName, cpi.applicationInfo,
10720                             cpi.name, cpi.flags)
10721                             && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) {
10722                         userId = UserHandle.USER_SYSTEM;
10723                         checkCrossUser = false;
10724                     } else {
10725                         cpr = null;
10726                         cpi = null;
10727                     }
10728                 }
10729             }
10730
10731             boolean providerRunning = cpr != null && cpr.proc != null && !cpr.proc.killed;
10732             if (providerRunning) {
10733                 cpi = cpr.info;
10734                 String msg;
10735                 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission");
10736                 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser))
10737                         != null) {
10738                     throw new SecurityException(msg);
10739                 }
10740                 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission");
10741
10742                 if (r != null && cpr.canRunHere(r)) {
10743                     // This provider has been published or is in the process
10744                     // of being published...  but it is also allowed to run
10745                     // in the caller's process, so don't make a connection
10746                     // and just let the caller instantiate its own instance.
10747                     ContentProviderHolder holder = cpr.newHolder(null);
10748                     // don't give caller the provider object, it needs
10749                     // to make its own.
10750                     holder.provider = null;
10751                     return holder;
10752                 }
10753
10754                 final long origId = Binder.clearCallingIdentity();
10755
10756                 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked");
10757
10758                 // In this case the provider instance already exists, so we can
10759                 // return it right away.
10760                 conn = incProviderCountLocked(r, cpr, token, stable);
10761                 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) {
10762                     if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) {
10763                         // If this is a perceptible app accessing the provider,
10764                         // make sure to count it as being accessed and thus
10765                         // back up on the LRU list.  This is good because
10766                         // content providers are often expensive to start.
10767                         checkTime(startTime, "getContentProviderImpl: before updateLruProcess");
10768                         updateLruProcessLocked(cpr.proc, false, null);
10769                         checkTime(startTime, "getContentProviderImpl: after updateLruProcess");
10770                     }
10771                 }
10772
10773                 checkTime(startTime, "getContentProviderImpl: before updateOomAdj");
10774                 final int verifiedAdj = cpr.proc.verifiedAdj;
10775                 boolean success = updateOomAdjLocked(cpr.proc);
10776                 // XXX things have changed so updateOomAdjLocked doesn't actually tell us
10777                 // if the process has been successfully adjusted.  So to reduce races with
10778                 // it, we will check whether the process still exists.  Note that this doesn't
10779                 // completely get rid of races with LMK killing the process, but should make
10780                 // them much smaller.
10781                 if (success && verifiedAdj != cpr.proc.setAdj && !isProcessAliveLocked(cpr.proc)) {
10782                     success = false;
10783                 }
10784                 maybeUpdateProviderUsageStatsLocked(r, cpr.info.packageName, name);
10785                 checkTime(startTime, "getContentProviderImpl: after updateOomAdj");
10786                 if (DEBUG_PROVIDER) Slog.i(TAG_PROVIDER, "Adjust success: " + success);
10787                 // NOTE: there is still a race here where a signal could be
10788                 // pending on the process even though we managed to update its
10789                 // adj level.  Not sure what to do about this, but at least
10790                 // the race is now smaller.
10791                 if (!success) {
10792                     // Uh oh...  it looks like the provider's process
10793                     // has been killed on us.  We need to wait for a new
10794                     // process to be started, and make sure its death
10795                     // doesn't kill our process.
10796                     Slog.i(TAG, "Existing provider " + cpr.name.flattenToShortString()
10797                             + " is crashing; detaching " + r);
10798                     boolean lastRef = decProviderCountLocked(conn, cpr, token, stable);
10799                     checkTime(startTime, "getContentProviderImpl: before appDied");
10800                     appDiedLocked(cpr.proc);
10801                     checkTime(startTime, "getContentProviderImpl: after appDied");
10802                     if (!lastRef) {
10803                         // This wasn't the last ref our process had on
10804                         // the provider...  we have now been killed, bail.
10805                         return null;
10806                     }
10807                     providerRunning = false;
10808                     conn = null;
10809                 } else {
10810                     cpr.proc.verifiedAdj = cpr.proc.setAdj;
10811                 }
10812
10813                 Binder.restoreCallingIdentity(origId);
10814             }
10815
10816             if (!providerRunning) {
10817                 try {
10818                     checkTime(startTime, "getContentProviderImpl: before resolveContentProvider");
10819                     cpi = AppGlobals.getPackageManager().
10820                         resolveContentProvider(name,
10821                             STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId);
10822                     checkTime(startTime, "getContentProviderImpl: after resolveContentProvider");
10823                 } catch (RemoteException ex) {
10824                 }
10825                 if (cpi == null) {
10826                     return null;
10827                 }
10828                 // If the provider is a singleton AND
10829                 // (it's a call within the same user || the provider is a
10830                 // privileged app)
10831                 // Then allow connecting to the singleton provider
10832                 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo,
10833                         cpi.name, cpi.flags)
10834                         && isValidSingletonCall(r.uid, cpi.applicationInfo.uid);
10835                 if (singleton) {
10836                     userId = UserHandle.USER_SYSTEM;
10837                 }
10838                 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId);
10839                 checkTime(startTime, "getContentProviderImpl: got app info for user");
10840
10841                 String msg;
10842                 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission");
10843                 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton))
10844                         != null) {
10845                     throw new SecurityException(msg);
10846                 }
10847                 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission");
10848
10849                 if (!mProcessesReady
10850                         && !cpi.processName.equals("system")) {
10851                     // If this content provider does not run in the system
10852                     // process, and the system is not yet ready to run other
10853                     // processes, then fail fast instead of hanging.
10854                     throw new IllegalArgumentException(
10855                             "Attempt to launch content provider before system ready");
10856                 }
10857
10858                 // Make sure that the user who owns this provider is running.  If not,
10859                 // we don't want to allow it to run.
10860                 if (!mUserController.isUserRunningLocked(userId, 0)) {
10861                     Slog.w(TAG, "Unable to launch app "
10862                             + cpi.applicationInfo.packageName + "/"
10863                             + cpi.applicationInfo.uid + " for provider "
10864                             + name + ": user " + userId + " is stopped");
10865                     return null;
10866                 }
10867
10868                 ComponentName comp = new ComponentName(cpi.packageName, cpi.name);
10869                 checkTime(startTime, "getContentProviderImpl: before getProviderByClass");
10870                 cpr = mProviderMap.getProviderByClass(comp, userId);
10871                 checkTime(startTime, "getContentProviderImpl: after getProviderByClass");
10872                 final boolean firstClass = cpr == null;
10873                 if (firstClass) {
10874                     final long ident = Binder.clearCallingIdentity();
10875
10876                     // If permissions need a review before any of the app components can run,
10877                     // we return no provider and launch a review activity if the calling app
10878                     // is in the foreground.
10879                     if (mPermissionReviewRequired || Build.PERMISSIONS_REVIEW_REQUIRED) {
10880                         if (!requestTargetProviderPermissionsReviewIfNeededLocked(cpi, r, userId)) {
10881                             return null;
10882                         }
10883                     }
10884
10885                     try {
10886                         checkTime(startTime, "getContentProviderImpl: before getApplicationInfo");
10887                         ApplicationInfo ai =
10888                             AppGlobals.getPackageManager().
10889                                 getApplicationInfo(
10890                                         cpi.applicationInfo.packageName,
10891                                         STOCK_PM_FLAGS, userId);
10892                         checkTime(startTime, "getContentProviderImpl: after getApplicationInfo");
10893                         if (ai == null) {
10894                             Slog.w(TAG, "No package info for content provider "
10895                                     + cpi.name);
10896                             return null;
10897                         }
10898                         ai = getAppInfoForUser(ai, userId);
10899                         cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton);
10900                     } catch (RemoteException ex) {
10901                         // pm is in same process, this will never happen.
10902                     } finally {
10903                         Binder.restoreCallingIdentity(ident);
10904                     }
10905                 }
10906
10907                 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord");
10908
10909                 if (r != null && cpr.canRunHere(r)) {
10910                     // If this is a multiprocess provider, then just return its
10911                     // info and allow the caller to instantiate it.  Only do
10912                     // this if the provider is the same user as the caller's
10913                     // process, or can run as root (so can be in any process).
10914                     return cpr.newHolder(null);
10915                 }
10916
10917                 if (DEBUG_PROVIDER) Slog.w(TAG_PROVIDER, "LAUNCHING REMOTE PROVIDER (myuid "
10918                             + (r != null ? r.uid : null) + " pruid " + cpr.appInfo.uid + "): "
10919                             + cpr.info.name + " callers=" + Debug.getCallers(6));
10920
10921                 // This is single process, and our app is now connecting to it.
10922                 // See if we are already in the process of launching this
10923                 // provider.
10924                 final int N = mLaunchingProviders.size();
10925                 int i;
10926                 for (i = 0; i < N; i++) {
10927                     if (mLaunchingProviders.get(i) == cpr) {
10928                         break;
10929                     }
10930                 }
10931
10932                 // If the provider is not already being launched, then get it
10933                 // started.
10934                 if (i >= N) {
10935                     final long origId = Binder.clearCallingIdentity();
10936
10937                     try {
10938                         // Content provider is now in use, its package can't be stopped.
10939                         try {
10940                             checkTime(startTime, "getContentProviderImpl: before set stopped state");
10941                             AppGlobals.getPackageManager().setPackageStoppedState(
10942                                     cpr.appInfo.packageName, false, userId);
10943                             checkTime(startTime, "getContentProviderImpl: after set stopped state");
10944                         } catch (RemoteException e) {
10945                         } catch (IllegalArgumentException e) {
10946                             Slog.w(TAG, "Failed trying to unstop package "
10947                                     + cpr.appInfo.packageName + ": " + e);
10948                         }
10949
10950                         // Use existing process if already started
10951                         checkTime(startTime, "getContentProviderImpl: looking for process record");
10952                         ProcessRecord proc = getProcessRecordLocked(
10953                                 cpi.processName, cpr.appInfo.uid, false);
10954                         if (proc != null && proc.thread != null && !proc.killed) {
10955                             if (DEBUG_PROVIDER) Slog.d(TAG_PROVIDER,
10956                                     "Installing in existing process " + proc);
10957                             if (!proc.pubProviders.containsKey(cpi.name)) {
10958                                 checkTime(startTime, "getContentProviderImpl: scheduling install");
10959                                 proc.pubProviders.put(cpi.name, cpr);
10960                                 try {
10961                                     proc.thread.scheduleInstallProvider(cpi);
10962                                 } catch (RemoteException e) {
10963                                 }
10964                             }
10965                         } else {
10966                             checkTime(startTime, "getContentProviderImpl: before start process");
10967                             proc = startProcessLocked(cpi.processName,
10968                                     cpr.appInfo, false, 0, "content provider",
10969                                     new ComponentName(cpi.applicationInfo.packageName,
10970                                             cpi.name), false, false, false);
10971                             checkTime(startTime, "getContentProviderImpl: after start process");
10972                             if (proc == null) {
10973                                 Slog.w(TAG, "Unable to launch app "
10974                                         + cpi.applicationInfo.packageName + "/"
10975                                         + cpi.applicationInfo.uid + " for provider "
10976                                         + name + ": process is bad");
10977                                 return null;
10978                             }
10979                         }
10980                         cpr.launchingApp = proc;
10981                         mLaunchingProviders.add(cpr);
10982                     } finally {
10983                         Binder.restoreCallingIdentity(origId);
10984                     }
10985                 }
10986
10987                 checkTime(startTime, "getContentProviderImpl: updating data structures");
10988
10989                 // Make sure the provider is published (the same provider class
10990                 // may be published under multiple names).
10991                 if (firstClass) {
10992                     mProviderMap.putProviderByClass(comp, cpr);
10993                 }
10994
10995                 mProviderMap.putProviderByName(name, cpr);
10996                 conn = incProviderCountLocked(r, cpr, token, stable);
10997                 if (conn != null) {
10998                     conn.waiting = true;
10999                 }
11000             }
11001             checkTime(startTime, "getContentProviderImpl: done!");
11002         }
11003
11004         // Wait for the provider to be published...
11005         synchronized (cpr) {
11006             while (cpr.provider == null) {
11007                 if (cpr.launchingApp == null) {
11008                     Slog.w(TAG, "Unable to launch app "
11009                             + cpi.applicationInfo.packageName + "/"
11010                             + cpi.applicationInfo.uid + " for provider "
11011                             + name + ": launching app became null");
11012                     EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS,
11013                             UserHandle.getUserId(cpi.applicationInfo.uid),
11014                             cpi.applicationInfo.packageName,
11015                             cpi.applicationInfo.uid, name);
11016                     return null;
11017                 }
11018                 try {
11019                     if (DEBUG_MU) Slog.v(TAG_MU,
11020                             "Waiting to start provider " + cpr
11021                             + " launchingApp=" + cpr.launchingApp);
11022                     if (conn != null) {
11023                         conn.waiting = true;
11024                     }
11025                     cpr.wait();
11026                 } catch (InterruptedException ex) {
11027                 } finally {
11028                     if (conn != null) {
11029                         conn.waiting = false;
11030                     }
11031                 }
11032             }
11033         }
11034         return cpr != null ? cpr.newHolder(conn) : null;
11035     }
11036
11037     private boolean requestTargetProviderPermissionsReviewIfNeededLocked(ProviderInfo cpi,
11038             ProcessRecord r, final int userId) {
11039         if (getPackageManagerInternalLocked().isPermissionsReviewRequired(
11040                 cpi.packageName, userId)) {
11041
11042             final boolean callerForeground = r == null || r.setSchedGroup
11043                     != ProcessList.SCHED_GROUP_BACKGROUND;
11044
11045             // Show a permission review UI only for starting from a foreground app
11046             if (!callerForeground) {
11047                 Slog.w(TAG, "u" + userId + " Instantiating a provider in package"
11048                         + cpi.packageName + " requires a permissions review");
11049                 return false;
11050             }
11051
11052             final Intent intent = new Intent(Intent.ACTION_REVIEW_PERMISSIONS);
11053             intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK
11054                     | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
11055             intent.putExtra(Intent.EXTRA_PACKAGE_NAME, cpi.packageName);
11056
11057             if (DEBUG_PERMISSIONS_REVIEW) {
11058                 Slog.i(TAG, "u" + userId + " Launching permission review "
11059                         + "for package " + cpi.packageName);
11060             }
11061
11062             final UserHandle userHandle = new UserHandle(userId);
11063             mHandler.post(new Runnable() {
11064                 @Override
11065                 public void run() {
11066                     mContext.startActivityAsUser(intent, userHandle);
11067                 }
11068             });
11069
11070             return false;
11071         }
11072
11073         return true;
11074     }
11075
11076     PackageManagerInternal getPackageManagerInternalLocked() {
11077         if (mPackageManagerInt == null) {
11078             mPackageManagerInt = LocalServices.getService(PackageManagerInternal.class);
11079         }
11080         return mPackageManagerInt;
11081     }
11082
11083     @Override
11084     public final ContentProviderHolder getContentProvider(
11085             IApplicationThread caller, String name, int userId, boolean stable) {
11086         enforceNotIsolatedCaller("getContentProvider");
11087         if (caller == null) {
11088             String msg = "null IApplicationThread when getting content provider "
11089                     + name;
11090             Slog.w(TAG, msg);
11091             throw new SecurityException(msg);
11092         }
11093         // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal
11094         // with cross-user grant.
11095         return getContentProviderImpl(caller, name, null, stable, userId);
11096     }
11097
11098     public ContentProviderHolder getContentProviderExternal(
11099             String name, int userId, IBinder token) {
11100         enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY,
11101             "Do not have permission in call getContentProviderExternal()");
11102         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
11103                 userId, false, ALLOW_FULL_ONLY, "getContentProvider", null);
11104         return getContentProviderExternalUnchecked(name, token, userId);
11105     }
11106
11107     private ContentProviderHolder getContentProviderExternalUnchecked(String name,
11108             IBinder token, int userId) {
11109         return getContentProviderImpl(null, name, token, true, userId);
11110     }
11111
11112     /**
11113      * Drop a content provider from a ProcessRecord's bookkeeping
11114      */
11115     public void removeContentProvider(IBinder connection, boolean stable) {
11116         enforceNotIsolatedCaller("removeContentProvider");
11117         long ident = Binder.clearCallingIdentity();
11118         try {
11119             synchronized (this) {
11120                 ContentProviderConnection conn;
11121                 try {
11122                     conn = (ContentProviderConnection)connection;
11123                 } catch (ClassCastException e) {
11124                     String msg ="removeContentProvider: " + connection
11125                             + " not a ContentProviderConnection";
11126                     Slog.w(TAG, msg);
11127                     throw new IllegalArgumentException(msg);
11128                 }
11129                 if (conn == null) {
11130                     throw new NullPointerException("connection is null");
11131                 }
11132                 if (decProviderCountLocked(conn, null, null, stable)) {
11133                     updateOomAdjLocked();
11134                 }
11135             }
11136         } finally {
11137             Binder.restoreCallingIdentity(ident);
11138         }
11139     }
11140
11141     public void removeContentProviderExternal(String name, IBinder token) {
11142         enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY,
11143             "Do not have permission in call removeContentProviderExternal()");
11144         int userId = UserHandle.getCallingUserId();
11145         long ident = Binder.clearCallingIdentity();
11146         try {
11147             removeContentProviderExternalUnchecked(name, token, userId);
11148         } finally {
11149             Binder.restoreCallingIdentity(ident);
11150         }
11151     }
11152
11153     private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) {
11154         synchronized (this) {
11155             ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId);
11156             if(cpr == null) {
11157                 //remove from mProvidersByClass
11158                 if(DEBUG_ALL) Slog.v(TAG, name+" content provider not found in providers list");
11159                 return;
11160             }
11161
11162             //update content provider record entry info
11163             ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name);
11164             ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId);
11165             if (localCpr.hasExternalProcessHandles()) {
11166                 if (localCpr.removeExternalProcessHandleLocked(token)) {
11167                     updateOomAdjLocked();
11168                 } else {
11169                     Slog.e(TAG, "Attmpt to remove content provider " + localCpr
11170                             + " with no external reference for token: "
11171                             + token + ".");
11172                 }
11173             } else {
11174                 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr
11175                         + " with no external references.");
11176             }
11177         }
11178     }
11179
11180     public final void publishContentProviders(IApplicationThread caller,
11181             List<ContentProviderHolder> providers) {
11182         if (providers == null) {
11183             return;
11184         }
11185
11186         enforceNotIsolatedCaller("publishContentProviders");
11187         synchronized (this) {
11188             final ProcessRecord r = getRecordForAppLocked(caller);
11189             if (DEBUG_MU) Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid);
11190             if (r == null) {
11191                 throw new SecurityException(
11192                         "Unable to find app for caller " + caller
11193                       + " (pid=" + Binder.getCallingPid()
11194                       + ") when publishing content providers");
11195             }
11196
11197             final long origId = Binder.clearCallingIdentity();
11198
11199             final int N = providers.size();
11200             for (int i = 0; i < N; i++) {
11201                 ContentProviderHolder src = providers.get(i);
11202                 if (src == null || src.info == null || src.provider == null) {
11203                     continue;
11204                 }
11205                 ContentProviderRecord dst = r.pubProviders.get(src.info.name);
11206                 if (DEBUG_MU) Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid);
11207                 if (dst != null) {
11208                     ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name);
11209                     mProviderMap.putProviderByClass(comp, dst);
11210                     String names[] = dst.info.authority.split(";");
11211                     for (int j = 0; j < names.length; j++) {
11212                         mProviderMap.putProviderByName(names[j], dst);
11213                     }
11214
11215                     int launchingCount = mLaunchingProviders.size();
11216                     int j;
11217                     boolean wasInLaunchingProviders = false;
11218                     for (j = 0; j < launchingCount; j++) {
11219                         if (mLaunchingProviders.get(j) == dst) {
11220                             mLaunchingProviders.remove(j);
11221                             wasInLaunchingProviders = true;
11222                             j--;
11223                             launchingCount--;
11224                         }
11225                     }
11226                     if (wasInLaunchingProviders) {
11227                         mHandler.removeMessages(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG, r);
11228                     }
11229                     synchronized (dst) {
11230                         dst.provider = src.provider;
11231                         dst.proc = r;
11232                         dst.notifyAll();
11233                     }
11234                     updateOomAdjLocked(r);
11235                     maybeUpdateProviderUsageStatsLocked(r, src.info.packageName,
11236                             src.info.authority);
11237                 }
11238             }
11239
11240             Binder.restoreCallingIdentity(origId);
11241         }
11242     }
11243
11244     public boolean refContentProvider(IBinder connection, int stable, int unstable) {
11245         ContentProviderConnection conn;
11246         try {
11247             conn = (ContentProviderConnection)connection;
11248         } catch (ClassCastException e) {
11249             String msg ="refContentProvider: " + connection
11250                     + " not a ContentProviderConnection";
11251             Slog.w(TAG, msg);
11252             throw new IllegalArgumentException(msg);
11253         }
11254         if (conn == null) {
11255             throw new NullPointerException("connection is null");
11256         }
11257
11258         synchronized (this) {
11259             if (stable > 0) {
11260                 conn.numStableIncs += stable;
11261             }
11262             stable = conn.stableCount + stable;
11263             if (stable < 0) {
11264                 throw new IllegalStateException("stableCount < 0: " + stable);
11265             }
11266
11267             if (unstable > 0) {
11268                 conn.numUnstableIncs += unstable;
11269             }
11270             unstable = conn.unstableCount + unstable;
11271             if (unstable < 0) {
11272                 throw new IllegalStateException("unstableCount < 0: " + unstable);
11273             }
11274
11275             if ((stable+unstable) <= 0) {
11276                 throw new IllegalStateException("ref counts can't go to zero here: stable="
11277                         + stable + " unstable=" + unstable);
11278             }
11279             conn.stableCount = stable;
11280             conn.unstableCount = unstable;
11281             return !conn.dead;
11282         }
11283     }
11284
11285     public void unstableProviderDied(IBinder connection) {
11286         ContentProviderConnection conn;
11287         try {
11288             conn = (ContentProviderConnection)connection;
11289         } catch (ClassCastException e) {
11290             String msg ="refContentProvider: " + connection
11291                     + " not a ContentProviderConnection";
11292             Slog.w(TAG, msg);
11293             throw new IllegalArgumentException(msg);
11294         }
11295         if (conn == null) {
11296             throw new NullPointerException("connection is null");
11297         }
11298
11299         // Safely retrieve the content provider associated with the connection.
11300         IContentProvider provider;
11301         synchronized (this) {
11302             provider = conn.provider.provider;
11303         }
11304
11305         if (provider == null) {
11306             // Um, yeah, we're way ahead of you.
11307             return;
11308         }
11309
11310         // Make sure the caller is being honest with us.
11311         if (provider.asBinder().pingBinder()) {
11312             // Er, no, still looks good to us.
11313             synchronized (this) {
11314                 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid()
11315                         + " says " + conn + " died, but we don't agree");
11316                 return;
11317             }
11318         }
11319
11320         // Well look at that!  It's dead!
11321         synchronized (this) {
11322             if (conn.provider.provider != provider) {
11323                 // But something changed...  good enough.
11324                 return;
11325             }
11326
11327             ProcessRecord proc = conn.provider.proc;
11328             if (proc == null || proc.thread == null) {
11329                 // Seems like the process is already cleaned up.
11330                 return;
11331             }
11332
11333             // As far as we're concerned, this is just like receiving a
11334             // death notification...  just a bit prematurely.
11335             Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid
11336                     + ") early provider death");
11337             final long ident = Binder.clearCallingIdentity();
11338             try {
11339                 appDiedLocked(proc);
11340             } finally {
11341                 Binder.restoreCallingIdentity(ident);
11342             }
11343         }
11344     }
11345
11346     @Override
11347     public void appNotRespondingViaProvider(IBinder connection) {
11348         enforceCallingPermission(
11349                 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()");
11350
11351         final ContentProviderConnection conn = (ContentProviderConnection) connection;
11352         if (conn == null) {
11353             Slog.w(TAG, "ContentProviderConnection is null");
11354             return;
11355         }
11356
11357         final ProcessRecord host = conn.provider.proc;
11358         if (host == null) {
11359             Slog.w(TAG, "Failed to find hosting ProcessRecord");
11360             return;
11361         }
11362
11363         mHandler.post(new Runnable() {
11364             @Override
11365             public void run() {
11366                 mAppErrors.appNotResponding(host, null, null, false,
11367                         "ContentProvider not responding");
11368             }
11369         });
11370     }
11371
11372     public final void installSystemProviders() {
11373         List<ProviderInfo> providers;
11374         synchronized (this) {
11375             ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID);
11376             providers = generateApplicationProvidersLocked(app);
11377             if (providers != null) {
11378                 for (int i=providers.size()-1; i>=0; i--) {
11379                     ProviderInfo pi = (ProviderInfo)providers.get(i);
11380                     if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) {
11381                         Slog.w(TAG, "Not installing system proc provider " + pi.name
11382                                 + ": not system .apk");
11383                         providers.remove(i);
11384                     }
11385                 }
11386             }
11387         }
11388         if (providers != null) {
11389             mSystemThread.installSystemProviders(providers);
11390         }
11391
11392         mCoreSettingsObserver = new CoreSettingsObserver(this);
11393         mFontScaleSettingObserver = new FontScaleSettingObserver();
11394
11395         //mUsageStatsService.monitorPackages();
11396     }
11397
11398     private void startPersistentApps(int matchFlags) {
11399         if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) return;
11400
11401         synchronized (this) {
11402             try {
11403                 final List<ApplicationInfo> apps = AppGlobals.getPackageManager()
11404                         .getPersistentApplications(STOCK_PM_FLAGS | matchFlags).getList();
11405                 for (ApplicationInfo app : apps) {
11406                     if (!"android".equals(app.packageName)) {
11407                         addAppLocked(app, false, null /* ABI override */);
11408                     }
11409                 }
11410             } catch (RemoteException ex) {
11411             }
11412         }
11413     }
11414
11415     /**
11416      * When a user is unlocked, we need to install encryption-unaware providers
11417      * belonging to any running apps.
11418      */
11419     private void installEncryptionUnawareProviders(int userId) {
11420         // We're only interested in providers that are encryption unaware, and
11421         // we don't care about uninstalled apps, since there's no way they're
11422         // running at this point.
11423         final int matchFlags = GET_PROVIDERS | MATCH_DIRECT_BOOT_UNAWARE;
11424
11425         synchronized (this) {
11426             final int NP = mProcessNames.getMap().size();
11427             for (int ip = 0; ip < NP; ip++) {
11428                 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
11429                 final int NA = apps.size();
11430                 for (int ia = 0; ia < NA; ia++) {
11431                     final ProcessRecord app = apps.valueAt(ia);
11432                     if (app.userId != userId || app.thread == null || app.unlocked) continue;
11433
11434                     final int NG = app.pkgList.size();
11435                     for (int ig = 0; ig < NG; ig++) {
11436                         try {
11437                             final String pkgName = app.pkgList.keyAt(ig);
11438                             final PackageInfo pkgInfo = AppGlobals.getPackageManager()
11439                                     .getPackageInfo(pkgName, matchFlags, userId);
11440                             if (pkgInfo != null && !ArrayUtils.isEmpty(pkgInfo.providers)) {
11441                                 for (ProviderInfo pi : pkgInfo.providers) {
11442                                     // TODO: keep in sync with generateApplicationProvidersLocked
11443                                     final boolean processMatch = Objects.equals(pi.processName,
11444                                             app.processName) || pi.multiprocess;
11445                                     final boolean userMatch = isSingleton(pi.processName,
11446                                             pi.applicationInfo, pi.name, pi.flags)
11447                                                     ? (app.userId == UserHandle.USER_SYSTEM) : true;
11448                                     if (processMatch && userMatch) {
11449                                         Log.v(TAG, "Installing " + pi);
11450                                         app.thread.scheduleInstallProvider(pi);
11451                                     } else {
11452                                         Log.v(TAG, "Skipping " + pi);
11453                                     }
11454                                 }
11455                             }
11456                         } catch (RemoteException ignored) {
11457                         }
11458                     }
11459                 }
11460             }
11461         }
11462     }
11463
11464     /**
11465      * Allows apps to retrieve the MIME type of a URI.
11466      * If an app is in the same user as the ContentProvider, or if it is allowed to interact across
11467      * users, then it does not need permission to access the ContentProvider.
11468      * Either, it needs cross-user uri grants.
11469      *
11470      * CTS tests for this functionality can be run with "runtest cts-appsecurity".
11471      *
11472      * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/
11473      *     src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java
11474      */
11475     public String getProviderMimeType(Uri uri, int userId) {
11476         enforceNotIsolatedCaller("getProviderMimeType");
11477         final String name = uri.getAuthority();
11478         int callingUid = Binder.getCallingUid();
11479         int callingPid = Binder.getCallingPid();
11480         long ident = 0;
11481         boolean clearedIdentity = false;
11482         synchronized (this) {
11483             userId = mUserController.unsafeConvertIncomingUserLocked(userId);
11484         }
11485         if (canClearIdentity(callingPid, callingUid, userId)) {
11486             clearedIdentity = true;
11487             ident = Binder.clearCallingIdentity();
11488         }
11489         ContentProviderHolder holder = null;
11490         try {
11491             holder = getContentProviderExternalUnchecked(name, null, userId);
11492             if (holder != null) {
11493                 return holder.provider.getType(uri);
11494             }
11495         } catch (RemoteException e) {
11496             Log.w(TAG, "Content provider dead retrieving " + uri, e);
11497             return null;
11498         } catch (Exception e) {
11499             Log.w(TAG, "Exception while determining type of " + uri, e);
11500             return null;
11501         } finally {
11502             // We need to clear the identity to call removeContentProviderExternalUnchecked
11503             if (!clearedIdentity) {
11504                 ident = Binder.clearCallingIdentity();
11505             }
11506             try {
11507                 if (holder != null) {
11508                     removeContentProviderExternalUnchecked(name, null, userId);
11509                 }
11510             } finally {
11511                 Binder.restoreCallingIdentity(ident);
11512             }
11513         }
11514
11515         return null;
11516     }
11517
11518     private boolean canClearIdentity(int callingPid, int callingUid, int userId) {
11519         if (UserHandle.getUserId(callingUid) == userId) {
11520             return true;
11521         }
11522         if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid,
11523                 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED
11524                 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid,
11525                 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) {
11526                 return true;
11527         }
11528         return false;
11529     }
11530
11531     // =========================================================
11532     // GLOBAL MANAGEMENT
11533     // =========================================================
11534
11535     final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess,
11536             boolean isolated, int isolatedUid) {
11537         String proc = customProcess != null ? customProcess : info.processName;
11538         BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
11539         final int userId = UserHandle.getUserId(info.uid);
11540         int uid = info.uid;
11541         if (isolated) {
11542             if (isolatedUid == 0) {
11543                 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1;
11544                 while (true) {
11545                     if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID
11546                             || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) {
11547                         mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID;
11548                     }
11549                     uid = UserHandle.getUid(userId, mNextIsolatedProcessUid);
11550                     mNextIsolatedProcessUid++;
11551                     if (mIsolatedProcesses.indexOfKey(uid) < 0) {
11552                         // No process for this uid, use it.
11553                         break;
11554                     }
11555                     stepsLeft--;
11556                     if (stepsLeft <= 0) {
11557                         return null;
11558                     }
11559                 }
11560             } else {
11561                 // Special case for startIsolatedProcess (internal only), where
11562                 // the uid of the isolated process is specified by the caller.
11563                 uid = isolatedUid;
11564             }
11565
11566             // Register the isolated UID with this application so BatteryStats knows to
11567             // attribute resource usage to the application.
11568             //
11569             // NOTE: This is done here before addProcessNameLocked, which will tell BatteryStats
11570             // about the process state of the isolated UID *before* it is registered with the
11571             // owning application.
11572             mBatteryStatsService.addIsolatedUid(uid, info.uid);
11573         }
11574         final ProcessRecord r = new ProcessRecord(stats, info, proc, uid);
11575         if (!mBooted && !mBooting
11576                 && userId == UserHandle.USER_SYSTEM
11577                 && (info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) {
11578             r.persistent = true;
11579         }
11580         addProcessNameLocked(r);
11581         return r;
11582     }
11583
11584     final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated,
11585             String abiOverride) {
11586         ProcessRecord app;
11587         if (!isolated) {
11588             app = getProcessRecordLocked(info.processName, info.uid, true);
11589         } else {
11590             app = null;
11591         }
11592
11593         if (app == null) {
11594             app = newProcessRecordLocked(info, null, isolated, 0);
11595             updateLruProcessLocked(app, false, null);
11596             updateOomAdjLocked();
11597         }
11598
11599         // This package really, really can not be stopped.
11600         try {
11601             AppGlobals.getPackageManager().setPackageStoppedState(
11602                     info.packageName, false, UserHandle.getUserId(app.uid));
11603         } catch (RemoteException e) {
11604         } catch (IllegalArgumentException e) {
11605             Slog.w(TAG, "Failed trying to unstop package "
11606                     + info.packageName + ": " + e);
11607         }
11608
11609         if ((info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) {
11610             app.persistent = true;
11611             app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ;
11612         }
11613         if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) {
11614             mPersistentStartingProcesses.add(app);
11615             startProcessLocked(app, "added application", app.processName, abiOverride,
11616                     null /* entryPoint */, null /* entryPointArgs */);
11617         }
11618
11619         return app;
11620     }
11621
11622     public void unhandledBack() {
11623         enforceCallingPermission(android.Manifest.permission.FORCE_BACK,
11624                 "unhandledBack()");
11625
11626         synchronized(this) {
11627             final long origId = Binder.clearCallingIdentity();
11628             try {
11629                 getFocusedStack().unhandledBackLocked();
11630             } finally {
11631                 Binder.restoreCallingIdentity(origId);
11632             }
11633         }
11634     }
11635
11636     public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException {
11637         enforceNotIsolatedCaller("openContentUri");
11638         final int userId = UserHandle.getCallingUserId();
11639         String name = uri.getAuthority();
11640         ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId);
11641         ParcelFileDescriptor pfd = null;
11642         if (cph != null) {
11643             // We record the binder invoker's uid in thread-local storage before
11644             // going to the content provider to open the file.  Later, in the code
11645             // that handles all permissions checks, we look for this uid and use
11646             // that rather than the Activity Manager's own uid.  The effect is that
11647             // we do the check against the caller's permissions even though it looks
11648             // to the content provider like the Activity Manager itself is making
11649             // the request.
11650             Binder token = new Binder();
11651             sCallerIdentity.set(new Identity(
11652                     token, Binder.getCallingPid(), Binder.getCallingUid()));
11653             try {
11654                 pfd = cph.provider.openFile(null, uri, "r", null, token);
11655             } catch (FileNotFoundException e) {
11656                 // do nothing; pfd will be returned null
11657             } finally {
11658                 // Ensure that whatever happens, we clean up the identity state
11659                 sCallerIdentity.remove();
11660                 // Ensure we're done with the provider.
11661                 removeContentProviderExternalUnchecked(name, null, userId);
11662             }
11663         } else {
11664             Slog.d(TAG, "Failed to get provider for authority '" + name + "'");
11665         }
11666         return pfd;
11667     }
11668
11669     // Actually is sleeping or shutting down or whatever else in the future
11670     // is an inactive state.
11671     boolean isSleepingOrShuttingDownLocked() {
11672         return isSleepingLocked() || mShuttingDown;
11673     }
11674
11675     boolean isShuttingDownLocked() {
11676         return mShuttingDown;
11677     }
11678
11679     boolean isSleepingLocked() {
11680         return mSleeping;
11681     }
11682
11683     void onWakefulnessChanged(int wakefulness) {
11684         synchronized(this) {
11685             mWakefulness = wakefulness;
11686             updateSleepIfNeededLocked();
11687         }
11688     }
11689
11690     void finishRunningVoiceLocked() {
11691         if (mRunningVoice != null) {
11692             mRunningVoice = null;
11693             mVoiceWakeLock.release();
11694             updateSleepIfNeededLocked();
11695         }
11696     }
11697
11698     void startTimeTrackingFocusedActivityLocked() {
11699         if (!mSleeping && mCurAppTimeTracker != null && mFocusedActivity != null) {
11700             mCurAppTimeTracker.start(mFocusedActivity.packageName);
11701         }
11702     }
11703
11704     void updateSleepIfNeededLocked() {
11705         if (mSleeping && !shouldSleepLocked()) {
11706             mSleeping = false;
11707             startTimeTrackingFocusedActivityLocked();
11708             mTopProcessState = ActivityManager.PROCESS_STATE_TOP;
11709             mStackSupervisor.comeOutOfSleepIfNeededLocked();
11710             sendNotifyVrManagerOfSleepState(false);
11711             updateOomAdjLocked();
11712         } else if (!mSleeping && shouldSleepLocked()) {
11713             mSleeping = true;
11714             if (mCurAppTimeTracker != null) {
11715                 mCurAppTimeTracker.stop();
11716             }
11717             mTopProcessState = ActivityManager.PROCESS_STATE_TOP_SLEEPING;
11718             mStackSupervisor.goingToSleepLocked();
11719             sendNotifyVrManagerOfSleepState(true);
11720             updateOomAdjLocked();
11721
11722             // Initialize the wake times of all processes.
11723             checkExcessivePowerUsageLocked(false);
11724             mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG);
11725             Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG);
11726             mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY);
11727         }
11728     }
11729
11730     private boolean shouldSleepLocked() {
11731         // Resume applications while running a voice interactor.
11732         if (mRunningVoice != null) {
11733             return false;
11734         }
11735
11736         // TODO: Transform the lock screen state into a sleep token instead.
11737         switch (mWakefulness) {
11738             case PowerManagerInternal.WAKEFULNESS_AWAKE:
11739             case PowerManagerInternal.WAKEFULNESS_DREAMING:
11740             case PowerManagerInternal.WAKEFULNESS_DOZING:
11741                 // Pause applications whenever the lock screen is shown or any sleep
11742                 // tokens have been acquired.
11743                 return (mLockScreenShown != LOCK_SCREEN_HIDDEN || !mSleepTokens.isEmpty());
11744             case PowerManagerInternal.WAKEFULNESS_ASLEEP:
11745             default:
11746                 // If we're asleep then pause applications unconditionally.
11747                 return true;
11748         }
11749     }
11750
11751     /** Pokes the task persister. */
11752     void notifyTaskPersisterLocked(TaskRecord task, boolean flush) {
11753         mRecentTasks.notifyTaskPersisterLocked(task, flush);
11754     }
11755
11756     /** Notifies all listeners when the task stack has changed. */
11757     void notifyTaskStackChangedLocked() {
11758         mHandler.sendEmptyMessage(LOG_STACK_STATE);
11759         mHandler.removeMessages(NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG);
11760         Message nmsg = mHandler.obtainMessage(NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG);
11761         mHandler.sendMessageDelayed(nmsg, NOTIFY_TASK_STACK_CHANGE_LISTENERS_DELAY);
11762     }
11763
11764     /** Notifies all listeners when an Activity is pinned. */
11765     void notifyActivityPinnedLocked() {
11766         mHandler.removeMessages(NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG);
11767         mHandler.obtainMessage(NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG).sendToTarget();
11768     }
11769
11770     /**
11771      * Notifies all listeners when an attempt was made to start an an activity that is already
11772      * running in the pinned stack and the activity was not actually started, but the task is
11773      * either brought to the front or a new Intent is delivered to it.
11774      */
11775     void notifyPinnedActivityRestartAttemptLocked() {
11776         mHandler.removeMessages(NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG);
11777         mHandler.obtainMessage(NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG).sendToTarget();
11778     }
11779
11780     /** Notifies all listeners when the pinned stack animation ends. */
11781     @Override
11782     public void notifyPinnedStackAnimationEnded() {
11783         synchronized (this) {
11784             mHandler.removeMessages(NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG);
11785             mHandler.obtainMessage(
11786                     NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG).sendToTarget();
11787         }
11788     }
11789
11790     @Override
11791     public void notifyCleartextNetwork(int uid, byte[] firstPacket) {
11792         mHandler.obtainMessage(NOTIFY_CLEARTEXT_NETWORK_MSG, uid, 0, firstPacket).sendToTarget();
11793     }
11794
11795     @Override
11796     public boolean shutdown(int timeout) {
11797         if (checkCallingPermission(android.Manifest.permission.SHUTDOWN)
11798                 != PackageManager.PERMISSION_GRANTED) {
11799             throw new SecurityException("Requires permission "
11800                     + android.Manifest.permission.SHUTDOWN);
11801         }
11802
11803         boolean timedout = false;
11804
11805         synchronized(this) {
11806             mShuttingDown = true;
11807             updateEventDispatchingLocked();
11808             timedout = mStackSupervisor.shutdownLocked(timeout);
11809         }
11810
11811         mAppOpsService.shutdown();
11812         if (mUsageStatsService != null) {
11813             mUsageStatsService.prepareShutdown();
11814         }
11815         mBatteryStatsService.shutdown();
11816         synchronized (this) {
11817             mProcessStats.shutdownLocked();
11818             notifyTaskPersisterLocked(null, true);
11819         }
11820
11821         return timedout;
11822     }
11823
11824     public final void activitySlept(IBinder token) {
11825         if (DEBUG_ALL) Slog.v(TAG, "Activity slept: token=" + token);
11826
11827         final long origId = Binder.clearCallingIdentity();
11828
11829         synchronized (this) {
11830             final ActivityRecord r = ActivityRecord.isInStackLocked(token);
11831             if (r != null) {
11832                 mStackSupervisor.activitySleptLocked(r);
11833             }
11834         }
11835
11836         Binder.restoreCallingIdentity(origId);
11837     }
11838
11839     private String lockScreenShownToString() {
11840         switch (mLockScreenShown) {
11841             case LOCK_SCREEN_HIDDEN: return "LOCK_SCREEN_HIDDEN";
11842             case LOCK_SCREEN_LEAVING: return "LOCK_SCREEN_LEAVING";
11843             case LOCK_SCREEN_SHOWN: return "LOCK_SCREEN_SHOWN";
11844             default: return "Unknown=" + mLockScreenShown;
11845         }
11846     }
11847
11848     void logLockScreen(String msg) {
11849         if (DEBUG_LOCKSCREEN) Slog.d(TAG_LOCKSCREEN, Debug.getCallers(2) + ":" + msg
11850                 + " mLockScreenShown=" + lockScreenShownToString() + " mWakefulness="
11851                 + PowerManagerInternal.wakefulnessToString(mWakefulness)
11852                 + " mSleeping=" + mSleeping);
11853     }
11854
11855     void startRunningVoiceLocked(IVoiceInteractionSession session, int targetUid) {
11856         Slog.d(TAG, "<<<  startRunningVoiceLocked()");
11857         mVoiceWakeLock.setWorkSource(new WorkSource(targetUid));
11858         if (mRunningVoice == null || mRunningVoice.asBinder() != session.asBinder()) {
11859             boolean wasRunningVoice = mRunningVoice != null;
11860             mRunningVoice = session;
11861             if (!wasRunningVoice) {
11862                 mVoiceWakeLock.acquire();
11863                 updateSleepIfNeededLocked();
11864             }
11865         }
11866     }
11867
11868     private void updateEventDispatchingLocked() {
11869         mWindowManager.setEventDispatching(mBooted && !mShuttingDown);
11870     }
11871
11872     public void setLockScreenShown(boolean showing, boolean occluded) {
11873         if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER)
11874                 != PackageManager.PERMISSION_GRANTED) {
11875             throw new SecurityException("Requires permission "
11876                     + android.Manifest.permission.DEVICE_POWER);
11877         }
11878
11879         synchronized(this) {
11880             long ident = Binder.clearCallingIdentity();
11881             try {
11882                 if (DEBUG_LOCKSCREEN) logLockScreen(" showing=" + showing + " occluded=" + occluded);
11883                 mLockScreenShown = (showing && !occluded) ? LOCK_SCREEN_SHOWN : LOCK_SCREEN_HIDDEN;
11884                 if (showing && occluded) {
11885                     // The lock screen is currently showing, but is occluded by a window that can
11886                     // show on top of the lock screen. In this can we want to dismiss the docked
11887                     // stack since it will be complicated/risky to try to put the activity on top
11888                     // of the lock screen in the right fullscreen configuration.
11889                     mStackSupervisor.moveTasksToFullscreenStackLocked(DOCKED_STACK_ID,
11890                             mStackSupervisor.mFocusedStack.getStackId() == DOCKED_STACK_ID);
11891                 }
11892
11893                 updateSleepIfNeededLocked();
11894             } finally {
11895                 Binder.restoreCallingIdentity(ident);
11896             }
11897         }
11898     }
11899
11900     @Override
11901     public void notifyLockedProfile(@UserIdInt int userId) {
11902         try {
11903             if (!AppGlobals.getPackageManager().isUidPrivileged(Binder.getCallingUid())) {
11904                 throw new SecurityException("Only privileged app can call notifyLockedProfile");
11905             }
11906         } catch (RemoteException ex) {
11907             throw new SecurityException("Fail to check is caller a privileged app", ex);
11908         }
11909
11910         synchronized (this) {
11911             if (mStackSupervisor.isUserLockedProfile(userId)) {
11912                 final long ident = Binder.clearCallingIdentity();
11913                 try {
11914                     final int currentUserId = mUserController.getCurrentUserIdLocked();
11915
11916                     // Drop locked freeform tasks out into the fullscreen stack.
11917                     // TODO: Redact the tasks in place. It's much better to keep them on the screen
11918                     //       where they were before, but in an obscured state.
11919                     mStackSupervisor.moveProfileTasksFromFreeformToFullscreenStackLocked(userId);
11920
11921                     if (mUserController.isLockScreenDisabled(currentUserId)) {
11922                         // If there is no device lock, we will show the profile's credential page.
11923                         mActivityStarter.showConfirmDeviceCredential(userId);
11924                     } else {
11925                         // Showing launcher to avoid user entering credential twice.
11926                         startHomeActivityLocked(currentUserId, "notifyLockedProfile");
11927                     }
11928                 } finally {
11929                     Binder.restoreCallingIdentity(ident);
11930                 }
11931             }
11932         }
11933     }
11934
11935     @Override
11936     public void startConfirmDeviceCredentialIntent(Intent intent) {
11937         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startConfirmDeviceCredentialIntent");
11938         synchronized (this) {
11939             final long ident = Binder.clearCallingIdentity();
11940             try {
11941                 mActivityStarter.startConfirmCredentialIntent(intent);
11942             } finally {
11943                 Binder.restoreCallingIdentity(ident);
11944             }
11945         }
11946     }
11947
11948     @Override
11949     public void stopAppSwitches() {
11950         if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES)
11951                 != PackageManager.PERMISSION_GRANTED) {
11952             throw new SecurityException("viewquires permission "
11953                     + android.Manifest.permission.STOP_APP_SWITCHES);
11954         }
11955
11956         synchronized(this) {
11957             mAppSwitchesAllowedTime = SystemClock.uptimeMillis()
11958                     + APP_SWITCH_DELAY_TIME;
11959             mDidAppSwitch = false;
11960             mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG);
11961             Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG);
11962             mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME);
11963         }
11964     }
11965
11966     public void resumeAppSwitches() {
11967         if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES)
11968                 != PackageManager.PERMISSION_GRANTED) {
11969             throw new SecurityException("Requires permission "
11970                     + android.Manifest.permission.STOP_APP_SWITCHES);
11971         }
11972
11973         synchronized(this) {
11974             // Note that we don't execute any pending app switches... we will
11975             // let those wait until either the timeout, or the next start
11976             // activity request.
11977             mAppSwitchesAllowedTime = 0;
11978         }
11979     }
11980
11981     boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid,
11982             int callingPid, int callingUid, String name) {
11983         if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) {
11984             return true;
11985         }
11986
11987         int perm = checkComponentPermission(
11988                 android.Manifest.permission.STOP_APP_SWITCHES, sourcePid,
11989                 sourceUid, -1, true);
11990         if (perm == PackageManager.PERMISSION_GRANTED) {
11991             return true;
11992         }
11993
11994         // If the actual IPC caller is different from the logical source, then
11995         // also see if they are allowed to control app switches.
11996         if (callingUid != -1 && callingUid != sourceUid) {
11997             perm = checkComponentPermission(
11998                     android.Manifest.permission.STOP_APP_SWITCHES, callingPid,
11999                     callingUid, -1, true);
12000             if (perm == PackageManager.PERMISSION_GRANTED) {
12001                 return true;
12002             }
12003         }
12004
12005         Slog.w(TAG, name + " request from " + sourceUid + " stopped");
12006         return false;
12007     }
12008
12009     public void setDebugApp(String packageName, boolean waitForDebugger,
12010             boolean persistent) {
12011         enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP,
12012                 "setDebugApp()");
12013
12014         long ident = Binder.clearCallingIdentity();
12015         try {
12016             // Note that this is not really thread safe if there are multiple
12017             // callers into it at the same time, but that's not a situation we
12018             // care about.
12019             if (persistent) {
12020                 final ContentResolver resolver = mContext.getContentResolver();
12021                 Settings.Global.putString(
12022                     resolver, Settings.Global.DEBUG_APP,
12023                     packageName);
12024                 Settings.Global.putInt(
12025                     resolver, Settings.Global.WAIT_FOR_DEBUGGER,
12026                     waitForDebugger ? 1 : 0);
12027             }
12028
12029             synchronized (this) {
12030                 if (!persistent) {
12031                     mOrigDebugApp = mDebugApp;
12032                     mOrigWaitForDebugger = mWaitForDebugger;
12033                 }
12034                 mDebugApp = packageName;
12035                 mWaitForDebugger = waitForDebugger;
12036                 mDebugTransient = !persistent;
12037                 if (packageName != null) {
12038                     forceStopPackageLocked(packageName, -1, false, false, true, true,
12039                             false, UserHandle.USER_ALL, "set debug app");
12040                 }
12041             }
12042         } finally {
12043             Binder.restoreCallingIdentity(ident);
12044         }
12045     }
12046
12047     void setTrackAllocationApp(ApplicationInfo app, String processName) {
12048         synchronized (this) {
12049             boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
12050             if (!isDebuggable) {
12051                 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) {
12052                     throw new SecurityException("Process not debuggable: " + app.packageName);
12053                 }
12054             }
12055
12056             mTrackAllocationApp = processName;
12057         }
12058     }
12059
12060     void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) {
12061         synchronized (this) {
12062             boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
12063             if (!isDebuggable) {
12064                 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) {
12065                     throw new SecurityException("Process not debuggable: " + app.packageName);
12066                 }
12067             }
12068             mProfileApp = processName;
12069             mProfileFile = profilerInfo.profileFile;
12070             if (mProfileFd != null) {
12071                 try {
12072                     mProfileFd.close();
12073                 } catch (IOException e) {
12074                 }
12075                 mProfileFd = null;
12076             }
12077             mProfileFd = profilerInfo.profileFd;
12078             mSamplingInterval = profilerInfo.samplingInterval;
12079             mAutoStopProfiler = profilerInfo.autoStopProfiler;
12080             mProfileType = 0;
12081         }
12082     }
12083
12084     void setNativeDebuggingAppLocked(ApplicationInfo app, String processName) {
12085         boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
12086         if (!isDebuggable) {
12087             if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) {
12088                 throw new SecurityException("Process not debuggable: " + app.packageName);
12089             }
12090         }
12091         mNativeDebuggingApp = processName;
12092     }
12093
12094     @Override
12095     public void setAlwaysFinish(boolean enabled) {
12096         enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH,
12097                 "setAlwaysFinish()");
12098
12099         long ident = Binder.clearCallingIdentity();
12100         try {
12101             Settings.Global.putInt(
12102                     mContext.getContentResolver(),
12103                     Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0);
12104
12105             synchronized (this) {
12106                 mAlwaysFinishActivities = enabled;
12107             }
12108         } finally {
12109             Binder.restoreCallingIdentity(ident);
12110         }
12111     }
12112
12113     @Override
12114     public void setLenientBackgroundCheck(boolean enabled) {
12115         enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT,
12116                 "setLenientBackgroundCheck()");
12117
12118         long ident = Binder.clearCallingIdentity();
12119         try {
12120             Settings.Global.putInt(
12121                     mContext.getContentResolver(),
12122                     Settings.Global.LENIENT_BACKGROUND_CHECK, enabled ? 1 : 0);
12123
12124             synchronized (this) {
12125                 mLenientBackgroundCheck = enabled;
12126             }
12127         } finally {
12128             Binder.restoreCallingIdentity(ident);
12129         }
12130     }
12131
12132     @Override
12133     public void setActivityController(IActivityController controller, boolean imAMonkey) {
12134         enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER,
12135                 "setActivityController()");
12136         synchronized (this) {
12137             mController = controller;
12138             mControllerIsAMonkey = imAMonkey;
12139             Watchdog.getInstance().setActivityController(controller);
12140         }
12141     }
12142
12143     @Override
12144     public void setUserIsMonkey(boolean userIsMonkey) {
12145         synchronized (this) {
12146             synchronized (mPidsSelfLocked) {
12147                 final int callingPid = Binder.getCallingPid();
12148                 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid);
12149                 if (precessRecord == null) {
12150                     throw new SecurityException("Unknown process: " + callingPid);
12151                 }
12152                 if (precessRecord.instrumentationUiAutomationConnection  == null) {
12153                     throw new SecurityException("Only an instrumentation process "
12154                             + "with a UiAutomation can call setUserIsMonkey");
12155                 }
12156             }
12157             mUserIsMonkey = userIsMonkey;
12158         }
12159     }
12160
12161     @Override
12162     public boolean isUserAMonkey() {
12163         synchronized (this) {
12164             // If there is a controller also implies the user is a monkey.
12165             return (mUserIsMonkey || (mController != null && mControllerIsAMonkey));
12166         }
12167     }
12168
12169     public void requestBugReport(int bugreportType) {
12170         String service = null;
12171         switch (bugreportType) {
12172             case ActivityManager.BUGREPORT_OPTION_FULL:
12173                 service = "bugreport";
12174                 break;
12175             case ActivityManager.BUGREPORT_OPTION_INTERACTIVE:
12176                 service = "bugreportplus";
12177                 break;
12178             case ActivityManager.BUGREPORT_OPTION_REMOTE:
12179                 service = "bugreportremote";
12180                 break;
12181             case ActivityManager.BUGREPORT_OPTION_WEAR:
12182                 service = "bugreportwear";
12183                 break;
12184             case ActivityManager.BUGREPORT_OPTION_TELEPHONY:
12185                 service = "bugreportelefony";
12186                 break;
12187         }
12188         if (service == null) {
12189             throw new IllegalArgumentException("Provided bugreport type is not correct, value: "
12190                     + bugreportType);
12191         }
12192         enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport");
12193         SystemProperties.set("ctl.start", service);
12194     }
12195
12196     public static long getInputDispatchingTimeoutLocked(ActivityRecord r) {
12197         return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT;
12198     }
12199
12200     public static long getInputDispatchingTimeoutLocked(ProcessRecord r) {
12201         if (r != null && (r.instrumentationClass != null || r.usingWrapper)) {
12202             return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT;
12203         }
12204         return KEY_DISPATCHING_TIMEOUT;
12205     }
12206
12207     @Override
12208     public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) {
12209         if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS)
12210                 != PackageManager.PERMISSION_GRANTED) {
12211             throw new SecurityException("Requires permission "
12212                     + android.Manifest.permission.FILTER_EVENTS);
12213         }
12214         ProcessRecord proc;
12215         long timeout;
12216         synchronized (this) {
12217             synchronized (mPidsSelfLocked) {
12218                 proc = mPidsSelfLocked.get(pid);
12219             }
12220             timeout = getInputDispatchingTimeoutLocked(proc);
12221         }
12222
12223         if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) {
12224             return -1;
12225         }
12226
12227         return timeout;
12228     }
12229
12230     /**
12231      * Handle input dispatching timeouts.
12232      * Returns whether input dispatching should be aborted or not.
12233      */
12234     public boolean inputDispatchingTimedOut(final ProcessRecord proc,
12235             final ActivityRecord activity, final ActivityRecord parent,
12236             final boolean aboveSystem, String reason) {
12237         if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS)
12238                 != PackageManager.PERMISSION_GRANTED) {
12239             throw new SecurityException("Requires permission "
12240                     + android.Manifest.permission.FILTER_EVENTS);
12241         }
12242
12243         final String annotation;
12244         if (reason == null) {
12245             annotation = "Input dispatching timed out";
12246         } else {
12247             annotation = "Input dispatching timed out (" + reason + ")";
12248         }
12249
12250         if (proc != null) {
12251             synchronized (this) {
12252                 if (proc.debugging) {
12253                     return false;
12254                 }
12255
12256                 if (mDidDexOpt) {
12257                     // Give more time since we were dexopting.
12258                     mDidDexOpt = false;
12259                     return false;
12260                 }
12261
12262                 if (proc.instrumentationClass != null) {
12263                     Bundle info = new Bundle();
12264                     info.putString("shortMsg", "keyDispatchingTimedOut");
12265                     info.putString("longMsg", annotation);
12266                     finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info);
12267                     return true;
12268                 }
12269             }
12270             mHandler.post(new Runnable() {
12271                 @Override
12272                 public void run() {
12273                     mAppErrors.appNotResponding(proc, activity, parent, aboveSystem, annotation);
12274                 }
12275             });
12276         }
12277
12278         return true;
12279     }
12280
12281     @Override
12282     public Bundle getAssistContextExtras(int requestType) {
12283         PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, null,
12284                 null, null, true /* focused */, true /* newSessionId */,
12285                 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_TIMEOUT);
12286         if (pae == null) {
12287             return null;
12288         }
12289         synchronized (pae) {
12290             while (!pae.haveResult) {
12291                 try {
12292                     pae.wait();
12293                 } catch (InterruptedException e) {
12294                 }
12295             }
12296         }
12297         synchronized (this) {
12298             buildAssistBundleLocked(pae, pae.result);
12299             mPendingAssistExtras.remove(pae);
12300             mUiHandler.removeCallbacks(pae);
12301         }
12302         return pae.extras;
12303     }
12304
12305     @Override
12306     public boolean isAssistDataAllowedOnCurrentActivity() {
12307         int userId;
12308         synchronized (this) {
12309             userId = mUserController.getCurrentUserIdLocked();
12310             ActivityRecord activity = getFocusedStack().topActivity();
12311             if (activity == null) {
12312                 return false;
12313             }
12314             userId = activity.userId;
12315         }
12316         DevicePolicyManager dpm = (DevicePolicyManager) mContext.getSystemService(
12317                 Context.DEVICE_POLICY_SERVICE);
12318         return (dpm == null) || (!dpm.getScreenCaptureDisabled(null, userId));
12319     }
12320
12321     @Override
12322     public boolean showAssistFromActivity(IBinder token, Bundle args) {
12323         long ident = Binder.clearCallingIdentity();
12324         try {
12325             synchronized (this) {
12326                 ActivityRecord caller = ActivityRecord.forTokenLocked(token);
12327                 ActivityRecord top = getFocusedStack().topActivity();
12328                 if (top != caller) {
12329                     Slog.w(TAG, "showAssistFromActivity failed: caller " + caller
12330                             + " is not current top " + top);
12331                     return false;
12332                 }
12333                 if (!top.nowVisible) {
12334                     Slog.w(TAG, "showAssistFromActivity failed: caller " + caller
12335                             + " is not visible");
12336                     return false;
12337                 }
12338             }
12339             AssistUtils utils = new AssistUtils(mContext);
12340             return utils.showSessionForActiveService(args,
12341                     VoiceInteractionSession.SHOW_SOURCE_APPLICATION, null, token);
12342         } finally {
12343             Binder.restoreCallingIdentity(ident);
12344         }
12345     }
12346
12347     @Override
12348     public boolean requestAssistContextExtras(int requestType, IResultReceiver receiver,
12349             Bundle receiverExtras,
12350             IBinder activityToken, boolean focused, boolean newSessionId) {
12351         return enqueueAssistContext(requestType, null, null, receiver, receiverExtras,
12352                 activityToken, focused, newSessionId,
12353                 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_LONG_TIMEOUT)
12354                 != null;
12355     }
12356
12357     private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint,
12358             IResultReceiver receiver, Bundle receiverExtras, IBinder activityToken,
12359             boolean focused, boolean newSessionId, int userHandle, Bundle args, long timeout) {
12360         enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO,
12361                 "enqueueAssistContext()");
12362         synchronized (this) {
12363             ActivityRecord activity = getFocusedStack().topActivity();
12364             if (activity == null) {
12365                 Slog.w(TAG, "getAssistContextExtras failed: no top activity");
12366                 return null;
12367             }
12368             if (activity.app == null || activity.app.thread == null) {
12369                 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity);
12370                 return null;
12371             }
12372             if (focused) {
12373                 if (activityToken != null) {
12374                     ActivityRecord caller = ActivityRecord.forTokenLocked(activityToken);
12375                     if (activity != caller) {
12376                         Slog.w(TAG, "enqueueAssistContext failed: caller " + caller
12377                                 + " is not current top " + activity);
12378                         return null;
12379                     }
12380                 }
12381             } else {
12382                 activity = ActivityRecord.forTokenLocked(activityToken);
12383                 if (activity == null) {
12384                     Slog.w(TAG, "enqueueAssistContext failed: activity for token=" + activityToken
12385                             + " couldn't be found");
12386                     return null;
12387                 }
12388             }
12389
12390             PendingAssistExtras pae;
12391             Bundle extras = new Bundle();
12392             if (args != null) {
12393                 extras.putAll(args);
12394             }
12395             extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName);
12396             extras.putInt(Intent.EXTRA_ASSIST_UID, activity.app.uid);
12397             pae = new PendingAssistExtras(activity, extras, intent, hint, receiver, receiverExtras,
12398                     userHandle);
12399             // Increment the sessionId if necessary
12400             if (newSessionId) {
12401                 mViSessionId++;
12402             }
12403             try {
12404                 activity.app.thread.requestAssistContextExtras(activity.appToken, pae,
12405                         requestType, mViSessionId);
12406                 mPendingAssistExtras.add(pae);
12407                 mUiHandler.postDelayed(pae, timeout);
12408             } catch (RemoteException e) {
12409                 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity);
12410                 return null;
12411             }
12412             return pae;
12413         }
12414     }
12415
12416     void pendingAssistExtrasTimedOut(PendingAssistExtras pae) {
12417         IResultReceiver receiver;
12418         synchronized (this) {
12419             mPendingAssistExtras.remove(pae);
12420             receiver = pae.receiver;
12421         }
12422         if (receiver != null) {
12423             // Caller wants result sent back to them.
12424             Bundle sendBundle = new Bundle();
12425             // At least return the receiver extras
12426             sendBundle.putBundle(VoiceInteractionSession.KEY_RECEIVER_EXTRAS,
12427                     pae.receiverExtras);
12428             try {
12429                 pae.receiver.send(0, sendBundle);
12430             } catch (RemoteException e) {
12431             }
12432         }
12433     }
12434
12435     private void buildAssistBundleLocked(PendingAssistExtras pae, Bundle result) {
12436         if (result != null) {
12437             pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, result);
12438         }
12439         if (pae.hint != null) {
12440             pae.extras.putBoolean(pae.hint, true);
12441         }
12442     }
12443
12444     public void reportAssistContextExtras(IBinder token, Bundle extras, AssistStructure structure,
12445             AssistContent content, Uri referrer) {
12446         PendingAssistExtras pae = (PendingAssistExtras)token;
12447         synchronized (pae) {
12448             pae.result = extras;
12449             pae.structure = structure;
12450             pae.content = content;
12451             if (referrer != null) {
12452                 pae.extras.putParcelable(Intent.EXTRA_REFERRER, referrer);
12453             }
12454             pae.haveResult = true;
12455             pae.notifyAll();
12456             if (pae.intent == null && pae.receiver == null) {
12457                 // Caller is just waiting for the result.
12458                 return;
12459             }
12460         }
12461
12462         // We are now ready to launch the assist activity.
12463         IResultReceiver sendReceiver = null;
12464         Bundle sendBundle = null;
12465         synchronized (this) {
12466             buildAssistBundleLocked(pae, extras);
12467             boolean exists = mPendingAssistExtras.remove(pae);
12468             mUiHandler.removeCallbacks(pae);
12469             if (!exists) {
12470                 // Timed out.
12471                 return;
12472             }
12473             if ((sendReceiver=pae.receiver) != null) {
12474                 // Caller wants result sent back to them.
12475                 sendBundle = new Bundle();
12476                 sendBundle.putBundle(VoiceInteractionSession.KEY_DATA, pae.extras);
12477                 sendBundle.putParcelable(VoiceInteractionSession.KEY_STRUCTURE, pae.structure);
12478                 sendBundle.putParcelable(VoiceInteractionSession.KEY_CONTENT, pae.content);
12479                 sendBundle.putBundle(VoiceInteractionSession.KEY_RECEIVER_EXTRAS,
12480                         pae.receiverExtras);
12481             }
12482         }
12483         if (sendReceiver != null) {
12484             try {
12485                 sendReceiver.send(0, sendBundle);
12486             } catch (RemoteException e) {
12487             }
12488             return;
12489         }
12490
12491         long ident = Binder.clearCallingIdentity();
12492         try {
12493             pae.intent.replaceExtras(pae.extras);
12494             pae.intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
12495                     | Intent.FLAG_ACTIVITY_SINGLE_TOP
12496                     | Intent.FLAG_ACTIVITY_CLEAR_TOP);
12497             closeSystemDialogs("assist");
12498             try {
12499                 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle));
12500             } catch (ActivityNotFoundException e) {
12501                 Slog.w(TAG, "No activity to handle assist action.", e);
12502             }
12503         } finally {
12504             Binder.restoreCallingIdentity(ident);
12505         }
12506     }
12507
12508     public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle,
12509             Bundle args) {
12510         return enqueueAssistContext(requestType, intent, hint, null, null, null,
12511                 true /* focused */, true /* newSessionId */,
12512                 userHandle, args, PENDING_ASSIST_EXTRAS_TIMEOUT) != null;
12513     }
12514
12515     public void registerProcessObserver(IProcessObserver observer) {
12516         enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER,
12517                 "registerProcessObserver()");
12518         synchronized (this) {
12519             mProcessObservers.register(observer);
12520         }
12521     }
12522
12523     @Override
12524     public void unregisterProcessObserver(IProcessObserver observer) {
12525         synchronized (this) {
12526             mProcessObservers.unregister(observer);
12527         }
12528     }
12529
12530     @Override
12531     public void registerUidObserver(IUidObserver observer, int which) {
12532         enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER,
12533                 "registerUidObserver()");
12534         synchronized (this) {
12535             mUidObservers.register(observer, which);
12536         }
12537     }
12538
12539     @Override
12540     public void unregisterUidObserver(IUidObserver observer) {
12541         synchronized (this) {
12542             mUidObservers.unregister(observer);
12543         }
12544     }
12545
12546     @Override
12547     public boolean convertFromTranslucent(IBinder token) {
12548         final long origId = Binder.clearCallingIdentity();
12549         try {
12550             synchronized (this) {
12551                 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
12552                 if (r == null) {
12553                     return false;
12554                 }
12555                 final boolean translucentChanged = r.changeWindowTranslucency(true);
12556                 if (translucentChanged) {
12557                     r.task.stack.releaseBackgroundResources(r);
12558                     mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
12559                 }
12560                 mWindowManager.setAppFullscreen(token, true);
12561                 return translucentChanged;
12562             }
12563         } finally {
12564             Binder.restoreCallingIdentity(origId);
12565         }
12566     }
12567
12568     @Override
12569     public boolean convertToTranslucent(IBinder token, ActivityOptions options) {
12570         final long origId = Binder.clearCallingIdentity();
12571         try {
12572             synchronized (this) {
12573                 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
12574                 if (r == null) {
12575                     return false;
12576                 }
12577                 int index = r.task.mActivities.lastIndexOf(r);
12578                 if (index > 0) {
12579                     ActivityRecord under = r.task.mActivities.get(index - 1);
12580                     under.returningOptions = options;
12581                 }
12582                 final boolean translucentChanged = r.changeWindowTranslucency(false);
12583                 if (translucentChanged) {
12584                     r.task.stack.convertActivityToTranslucent(r);
12585                 }
12586                 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
12587                 mWindowManager.setAppFullscreen(token, false);
12588                 return translucentChanged;
12589             }
12590         } finally {
12591             Binder.restoreCallingIdentity(origId);
12592         }
12593     }
12594
12595     @Override
12596     public boolean requestVisibleBehind(IBinder token, boolean visible) {
12597         final long origId = Binder.clearCallingIdentity();
12598         try {
12599             synchronized (this) {
12600                 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
12601                 if (r != null) {
12602                     return mStackSupervisor.requestVisibleBehindLocked(r, visible);
12603                 }
12604             }
12605             return false;
12606         } finally {
12607             Binder.restoreCallingIdentity(origId);
12608         }
12609     }
12610
12611     @Override
12612     public boolean isBackgroundVisibleBehind(IBinder token) {
12613         final long origId = Binder.clearCallingIdentity();
12614         try {
12615             synchronized (this) {
12616                 final ActivityStack stack = ActivityRecord.getStackLocked(token);
12617                 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity();
12618                 if (DEBUG_VISIBLE_BEHIND) Slog.d(TAG_VISIBLE_BEHIND,
12619                         "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible);
12620                 return visible;
12621             }
12622         } finally {
12623             Binder.restoreCallingIdentity(origId);
12624         }
12625     }
12626
12627     @Override
12628     public ActivityOptions getActivityOptions(IBinder token) {
12629         final long origId = Binder.clearCallingIdentity();
12630         try {
12631             synchronized (this) {
12632                 final ActivityRecord r = ActivityRecord.isInStackLocked(token);
12633                 if (r != null) {
12634                     final ActivityOptions activityOptions = r.pendingOptions;
12635                     r.pendingOptions = null;
12636                     return activityOptions;
12637                 }
12638                 return null;
12639             }
12640         } finally {
12641             Binder.restoreCallingIdentity(origId);
12642         }
12643     }
12644
12645     @Override
12646     public void setImmersive(IBinder token, boolean immersive) {
12647         synchronized(this) {
12648             final ActivityRecord r = ActivityRecord.isInStackLocked(token);
12649             if (r == null) {
12650                 throw new IllegalArgumentException();
12651             }
12652             r.immersive = immersive;
12653
12654             // update associated state if we're frontmost
12655             if (r == mFocusedActivity) {
12656                 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, "Frontmost changed immersion: "+ r);
12657                 applyUpdateLockStateLocked(r);
12658             }
12659         }
12660     }
12661
12662     @Override
12663     public boolean isImmersive(IBinder token) {
12664         synchronized (this) {
12665             ActivityRecord r = ActivityRecord.isInStackLocked(token);
12666             if (r == null) {
12667                 throw new IllegalArgumentException();
12668             }
12669             return r.immersive;
12670         }
12671     }
12672
12673     public void setVrThread(int tid) {
12674         if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) {
12675             throw new UnsupportedOperationException("VR mode not supported on this device!");
12676         }
12677
12678         synchronized (this) {
12679             ProcessRecord proc;
12680             synchronized (mPidsSelfLocked) {
12681                 final int pid = Binder.getCallingPid();
12682                 proc = mPidsSelfLocked.get(pid);
12683
12684                 if (proc != null && mInVrMode && tid >= 0) {
12685                     // ensure the tid belongs to the process
12686                     if (!Process.isThreadInProcess(pid, tid)) {
12687                         throw new IllegalArgumentException("VR thread does not belong to process");
12688                     }
12689
12690                     // reset existing VR thread to CFS if this thread still exists and belongs to
12691                     // the calling process
12692                     if (proc.vrThreadTid != 0
12693                             && Process.isThreadInProcess(pid, proc.vrThreadTid)) {
12694                         try {
12695                             Process.setThreadScheduler(proc.vrThreadTid, Process.SCHED_OTHER, 0);
12696                         } catch (IllegalArgumentException e) {
12697                             // Ignore this.  Only occurs in race condition where previous VR thread
12698                             // was destroyed during this method call.
12699                         }
12700                     }
12701
12702                     proc.vrThreadTid = tid;
12703
12704                     // promote to FIFO now if the tid is non-zero
12705                     try {
12706                         if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP &&
12707                             proc.vrThreadTid > 0) {
12708                             Process.setThreadScheduler(proc.vrThreadTid,
12709                                 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1);
12710                         }
12711                     } catch (IllegalArgumentException e) {
12712                         Slog.e(TAG, "Failed to set scheduling policy, thread does"
12713                                + " not exist:\n" + e);
12714                     }
12715                 }
12716             }
12717         }
12718     }
12719
12720     @Override
12721     public void setRenderThread(int tid) {
12722         synchronized (this) {
12723             ProcessRecord proc;
12724             synchronized (mPidsSelfLocked) {
12725                 int pid = Binder.getCallingPid();
12726                 proc = mPidsSelfLocked.get(pid);
12727                 if (proc != null && proc.renderThreadTid == 0 && tid > 0) {
12728                     // ensure the tid belongs to the process
12729                     if (!Process.isThreadInProcess(pid, tid)) {
12730                         throw new IllegalArgumentException(
12731                             "Render thread does not belong to process");
12732                     }
12733                     proc.renderThreadTid = tid;
12734                     if (DEBUG_OOM_ADJ) {
12735                         Slog.d("UI_FIFO", "Set RenderThread tid " + tid + " for pid " + pid);
12736                     }
12737                     // promote to FIFO now
12738                     if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) {
12739                         if (DEBUG_OOM_ADJ) Slog.d("UI_FIFO", "Promoting " + tid + "out of band");
12740                         if (mUseFifoUiScheduling) {
12741                             Process.setThreadScheduler(proc.renderThreadTid,
12742                                 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1);
12743                         } else {
12744                             Process.setThreadPriority(proc.renderThreadTid, -10);
12745                         }
12746                     }
12747                 } else {
12748                     if (DEBUG_OOM_ADJ) {
12749                         Slog.d("UI_FIFO", "Didn't set thread from setRenderThread? " +
12750                                "PID: " + pid + ", TID: " + tid + " FIFO: " +
12751                                mUseFifoUiScheduling);
12752                     }
12753                 }
12754             }
12755         }
12756     }
12757
12758     @Override
12759     public int setVrMode(IBinder token, boolean enabled, ComponentName packageName) {
12760         if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) {
12761             throw new UnsupportedOperationException("VR mode not supported on this device!");
12762         }
12763
12764         final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class);
12765
12766         ActivityRecord r;
12767         synchronized (this) {
12768             r = ActivityRecord.isInStackLocked(token);
12769         }
12770
12771         if (r == null) {
12772             throw new IllegalArgumentException();
12773         }
12774
12775         int err;
12776         if ((err = vrService.hasVrPackage(packageName, r.userId)) !=
12777                 VrManagerInternal.NO_ERROR) {
12778             return err;
12779         }
12780
12781         synchronized(this) {
12782             r.requestedVrComponent = (enabled) ? packageName : null;
12783
12784             // Update associated state if this activity is currently focused
12785             if (r == mFocusedActivity) {
12786                 applyUpdateVrModeLocked(r);
12787             }
12788             return 0;
12789         }
12790     }
12791
12792     @Override
12793     public boolean isVrModePackageEnabled(ComponentName packageName) {
12794         if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) {
12795             throw new UnsupportedOperationException("VR mode not supported on this device!");
12796         }
12797
12798         final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class);
12799
12800         return vrService.hasVrPackage(packageName, UserHandle.getCallingUserId()) ==
12801                 VrManagerInternal.NO_ERROR;
12802     }
12803
12804     public boolean isTopActivityImmersive() {
12805         enforceNotIsolatedCaller("startActivity");
12806         synchronized (this) {
12807             ActivityRecord r = getFocusedStack().topRunningActivityLocked();
12808             return (r != null) ? r.immersive : false;
12809         }
12810     }
12811
12812     @Override
12813     public boolean isTopOfTask(IBinder token) {
12814         synchronized (this) {
12815             ActivityRecord r = ActivityRecord.isInStackLocked(token);
12816             if (r == null) {
12817                 throw new IllegalArgumentException();
12818             }
12819             return r.task.getTopActivity() == r;
12820         }
12821     }
12822
12823     @Override
12824     public void setHasTopUi(boolean hasTopUi) throws RemoteException {
12825         if (checkCallingPermission(permission.INTERNAL_SYSTEM_WINDOW) != PERMISSION_GRANTED) {
12826             String msg = "Permission Denial: setHasTopUi() from pid="
12827                     + Binder.getCallingPid()
12828                     + ", uid=" + Binder.getCallingUid()
12829                     + " requires " + permission.INTERNAL_SYSTEM_WINDOW;
12830             Slog.w(TAG, msg);
12831             throw new SecurityException(msg);
12832         }
12833         final int pid = Binder.getCallingPid();
12834         final long origId = Binder.clearCallingIdentity();
12835         try {
12836             synchronized (this) {
12837                 boolean changed = false;
12838                 ProcessRecord pr;
12839                 synchronized (mPidsSelfLocked) {
12840                     pr = mPidsSelfLocked.get(pid);
12841                     if (pr == null) {
12842                         Slog.w(TAG, "setHasTopUi called on unknown pid: " + pid);
12843                         return;
12844                     }
12845                     if (pr.hasTopUi != hasTopUi) {
12846                         Slog.i(TAG, "Setting hasTopUi=" + hasTopUi + " for pid=" + pid);
12847                         pr.hasTopUi = hasTopUi;
12848                         changed = true;
12849                     }
12850                 }
12851                 if (changed) {
12852                     updateOomAdjLocked(pr);
12853                 }
12854             }
12855         } finally {
12856             Binder.restoreCallingIdentity(origId);
12857         }
12858     }
12859
12860     public final void enterSafeMode() {
12861         synchronized(this) {
12862             // It only makes sense to do this before the system is ready
12863             // and started launching other packages.
12864             if (!mSystemReady) {
12865                 try {
12866                     AppGlobals.getPackageManager().enterSafeMode();
12867                 } catch (RemoteException e) {
12868                 }
12869             }
12870
12871             mSafeMode = true;
12872         }
12873     }
12874
12875     public final void showSafeModeOverlay() {
12876         View v = LayoutInflater.from(mContext).inflate(
12877                 com.android.internal.R.layout.safe_mode, null);
12878         WindowManager.LayoutParams lp = new WindowManager.LayoutParams();
12879         lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY;
12880         lp.width = WindowManager.LayoutParams.WRAP_CONTENT;
12881         lp.height = WindowManager.LayoutParams.WRAP_CONTENT;
12882         lp.gravity = Gravity.BOTTOM | Gravity.START;
12883         lp.format = v.getBackground().getOpacity();
12884         lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
12885                 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE;
12886         lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS;
12887         ((WindowManager)mContext.getSystemService(
12888                 Context.WINDOW_SERVICE)).addView(v, lp);
12889     }
12890
12891     public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg, String tag) {
12892         if (sender != null && !(sender instanceof PendingIntentRecord)) {
12893             return;
12894         }
12895         final PendingIntentRecord rec = (PendingIntentRecord)sender;
12896         final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
12897         synchronized (stats) {
12898             if (mBatteryStatsService.isOnBattery()) {
12899                 mBatteryStatsService.enforceCallingPermission();
12900                 int MY_UID = Binder.getCallingUid();
12901                 final int uid;
12902                 if (sender == null) {
12903                     uid = sourceUid;
12904                 } else {
12905                     uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid;
12906                 }
12907                 BatteryStatsImpl.Uid.Pkg pkg =
12908                     stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid,
12909                             sourcePkg != null ? sourcePkg : rec.key.packageName);
12910                 pkg.noteWakeupAlarmLocked(tag);
12911             }
12912         }
12913     }
12914
12915     public void noteAlarmStart(IIntentSender sender, int sourceUid, String tag) {
12916         if (sender != null && !(sender instanceof PendingIntentRecord)) {
12917             return;
12918         }
12919         final PendingIntentRecord rec = (PendingIntentRecord)sender;
12920         final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
12921         synchronized (stats) {
12922             mBatteryStatsService.enforceCallingPermission();
12923             int MY_UID = Binder.getCallingUid();
12924             final int uid;
12925             if (sender == null) {
12926                 uid = sourceUid;
12927             } else {
12928                 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid;
12929             }
12930             mBatteryStatsService.noteAlarmStart(tag, sourceUid >= 0 ? sourceUid : uid);
12931         }
12932     }
12933
12934     public void noteAlarmFinish(IIntentSender sender, int sourceUid, String tag) {
12935         if (sender != null && !(sender instanceof PendingIntentRecord)) {
12936             return;
12937         }
12938         final PendingIntentRecord rec = (PendingIntentRecord)sender;
12939         final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
12940         synchronized (stats) {
12941             mBatteryStatsService.enforceCallingPermission();
12942             int MY_UID = Binder.getCallingUid();
12943             final int uid;
12944             if (sender == null) {
12945                 uid = sourceUid;
12946             } else {
12947                 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid;
12948             }
12949             mBatteryStatsService.noteAlarmFinish(tag, sourceUid >= 0 ? sourceUid : uid);
12950         }
12951     }
12952
12953     public boolean killPids(int[] pids, String pReason, boolean secure) {
12954         if (Binder.getCallingUid() != Process.SYSTEM_UID) {
12955             throw new SecurityException("killPids only available to the system");
12956         }
12957         String reason = (pReason == null) ? "Unknown" : pReason;
12958         // XXX Note: don't acquire main activity lock here, because the window
12959         // manager calls in with its locks held.
12960
12961         boolean killed = false;
12962         synchronized (mPidsSelfLocked) {
12963             int worstType = 0;
12964             for (int i=0; i<pids.length; i++) {
12965                 ProcessRecord proc = mPidsSelfLocked.get(pids[i]);
12966                 if (proc != null) {
12967                     int type = proc.setAdj;
12968                     if (type > worstType) {
12969                         worstType = type;
12970                     }
12971                 }
12972             }
12973
12974             // If the worst oom_adj is somewhere in the cached proc LRU range,
12975             // then constrain it so we will kill all cached procs.
12976             if (worstType < ProcessList.CACHED_APP_MAX_ADJ
12977                     && worstType > ProcessList.CACHED_APP_MIN_ADJ) {
12978                 worstType = ProcessList.CACHED_APP_MIN_ADJ;
12979             }
12980
12981             // If this is not a secure call, don't let it kill processes that
12982             // are important.
12983             if (!secure && worstType < ProcessList.SERVICE_ADJ) {
12984                 worstType = ProcessList.SERVICE_ADJ;
12985             }
12986
12987             Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType);
12988             for (int i=0; i<pids.length; i++) {
12989                 ProcessRecord proc = mPidsSelfLocked.get(pids[i]);
12990                 if (proc == null) {
12991                     continue;
12992                 }
12993                 int adj = proc.setAdj;
12994                 if (adj >= worstType && !proc.killedByAm) {
12995                     proc.kill(reason, true);
12996                     killed = true;
12997                 }
12998             }
12999         }
13000         return killed;
13001     }
13002
13003     @Override
13004     public void killUid(int appId, int userId, String reason) {
13005         enforceCallingPermission(Manifest.permission.KILL_UID, "killUid");
13006         synchronized (this) {
13007             final long identity = Binder.clearCallingIdentity();
13008             try {
13009                 killPackageProcessesLocked(null, appId, userId,
13010                         ProcessList.PERSISTENT_PROC_ADJ, false, true, true, true,
13011                         reason != null ? reason : "kill uid");
13012             } finally {
13013                 Binder.restoreCallingIdentity(identity);
13014             }
13015         }
13016     }
13017
13018     @Override
13019     public boolean killProcessesBelowForeground(String reason) {
13020         if (Binder.getCallingUid() != Process.SYSTEM_UID) {
13021             throw new SecurityException("killProcessesBelowForeground() only available to system");
13022         }
13023
13024         return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason);
13025     }
13026
13027     private boolean killProcessesBelowAdj(int belowAdj, String reason) {
13028         if (Binder.getCallingUid() != Process.SYSTEM_UID) {
13029             throw new SecurityException("killProcessesBelowAdj() only available to system");
13030         }
13031
13032         boolean killed = false;
13033         synchronized (mPidsSelfLocked) {
13034             final int size = mPidsSelfLocked.size();
13035             for (int i = 0; i < size; i++) {
13036                 final int pid = mPidsSelfLocked.keyAt(i);
13037                 final ProcessRecord proc = mPidsSelfLocked.valueAt(i);
13038                 if (proc == null) continue;
13039
13040                 final int adj = proc.setAdj;
13041                 if (adj > belowAdj && !proc.killedByAm) {
13042                     proc.kill(reason, true);
13043                     killed = true;
13044                 }
13045             }
13046         }
13047         return killed;
13048     }
13049
13050     @Override
13051     public void hang(final IBinder who, boolean allowRestart) {
13052         if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
13053                 != PackageManager.PERMISSION_GRANTED) {
13054             throw new SecurityException("Requires permission "
13055                     + android.Manifest.permission.SET_ACTIVITY_WATCHER);
13056         }
13057
13058         final IBinder.DeathRecipient death = new DeathRecipient() {
13059             @Override
13060             public void binderDied() {
13061                 synchronized (this) {
13062                     notifyAll();
13063                 }
13064             }
13065         };
13066
13067         try {
13068             who.linkToDeath(death, 0);
13069         } catch (RemoteException e) {
13070             Slog.w(TAG, "hang: given caller IBinder is already dead.");
13071             return;
13072         }
13073
13074         synchronized (this) {
13075             Watchdog.getInstance().setAllowRestart(allowRestart);
13076             Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid());
13077             synchronized (death) {
13078                 while (who.isBinderAlive()) {
13079                     try {
13080                         death.wait();
13081                     } catch (InterruptedException e) {
13082                     }
13083                 }
13084             }
13085             Watchdog.getInstance().setAllowRestart(true);
13086         }
13087     }
13088
13089     @Override
13090     public void restart() {
13091         if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
13092                 != PackageManager.PERMISSION_GRANTED) {
13093             throw new SecurityException("Requires permission "
13094                     + android.Manifest.permission.SET_ACTIVITY_WATCHER);
13095         }
13096
13097         Log.i(TAG, "Sending shutdown broadcast...");
13098
13099         BroadcastReceiver br = new BroadcastReceiver() {
13100             @Override public void onReceive(Context context, Intent intent) {
13101                 // Now the broadcast is done, finish up the low-level shutdown.
13102                 Log.i(TAG, "Shutting down activity manager...");
13103                 shutdown(10000);
13104                 Log.i(TAG, "Shutdown complete, restarting!");
13105                 Process.killProcess(Process.myPid());
13106                 System.exit(10);
13107             }
13108         };
13109
13110         // First send the high-level shut down broadcast.
13111         Intent intent = new Intent(Intent.ACTION_SHUTDOWN);
13112         intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
13113         intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true);
13114         /* For now we are not doing a clean shutdown, because things seem to get unhappy.
13115         mContext.sendOrderedBroadcastAsUser(intent,
13116                 UserHandle.ALL, null, br, mHandler, 0, null, null);
13117         */
13118         br.onReceive(mContext, intent);
13119     }
13120
13121     private long getLowRamTimeSinceIdle(long now) {
13122         return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0);
13123     }
13124
13125     @Override
13126     public void performIdleMaintenance() {
13127         if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
13128                 != PackageManager.PERMISSION_GRANTED) {
13129             throw new SecurityException("Requires permission "
13130                     + android.Manifest.permission.SET_ACTIVITY_WATCHER);
13131         }
13132
13133         synchronized (this) {
13134             final long now = SystemClock.uptimeMillis();
13135             final long timeSinceLastIdle = now - mLastIdleTime;
13136             final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now);
13137             mLastIdleTime = now;
13138             mLowRamTimeSinceLastIdle = 0;
13139             if (mLowRamStartTime != 0) {
13140                 mLowRamStartTime = now;
13141             }
13142
13143             StringBuilder sb = new StringBuilder(128);
13144             sb.append("Idle maintenance over ");
13145             TimeUtils.formatDuration(timeSinceLastIdle, sb);
13146             sb.append(" low RAM for ");
13147             TimeUtils.formatDuration(lowRamSinceLastIdle, sb);
13148             Slog.i(TAG, sb.toString());
13149
13150             // If at least 1/3 of our time since the last idle period has been spent
13151             // with RAM low, then we want to kill processes.
13152             boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3);
13153
13154             for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
13155                 ProcessRecord proc = mLruProcesses.get(i);
13156                 if (proc.notCachedSinceIdle) {
13157                     if (proc.setProcState != ActivityManager.PROCESS_STATE_TOP_SLEEPING
13158                             && proc.setProcState >= ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE
13159                             && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) {
13160                         if (doKilling && proc.initialIdlePss != 0
13161                                 && proc.lastPss > ((proc.initialIdlePss*3)/2)) {
13162                             sb = new StringBuilder(128);
13163                             sb.append("Kill");
13164                             sb.append(proc.processName);
13165                             sb.append(" in idle maint: pss=");
13166                             sb.append(proc.lastPss);
13167                             sb.append(", swapPss=");
13168                             sb.append(proc.lastSwapPss);
13169                             sb.append(", initialPss=");
13170                             sb.append(proc.initialIdlePss);
13171                             sb.append(", period=");
13172                             TimeUtils.formatDuration(timeSinceLastIdle, sb);
13173                             sb.append(", lowRamPeriod=");
13174                             TimeUtils.formatDuration(lowRamSinceLastIdle, sb);
13175                             Slog.wtfQuiet(TAG, sb.toString());
13176                             proc.kill("idle maint (pss " + proc.lastPss
13177                                     + " from " + proc.initialIdlePss + ")", true);
13178                         }
13179                     }
13180                 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME
13181                         && proc.setProcState > ActivityManager.PROCESS_STATE_NONEXISTENT) {
13182                     proc.notCachedSinceIdle = true;
13183                     proc.initialIdlePss = 0;
13184                     proc.nextPssTime = ProcessList.computeNextPssTime(proc.setProcState, true,
13185                             mTestPssMode, isSleepingLocked(), now);
13186                 }
13187             }
13188
13189             mHandler.removeMessages(REQUEST_ALL_PSS_MSG);
13190             mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000);
13191         }
13192     }
13193
13194     @Override
13195     public void sendIdleJobTrigger() {
13196         if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
13197                 != PackageManager.PERMISSION_GRANTED) {
13198             throw new SecurityException("Requires permission "
13199                     + android.Manifest.permission.SET_ACTIVITY_WATCHER);
13200         }
13201
13202         final long ident = Binder.clearCallingIdentity();
13203         try {
13204             Intent intent = new Intent(ACTION_TRIGGER_IDLE)
13205                     .setPackage("android")
13206                     .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
13207             broadcastIntent(null, intent, null, null, 0, null, null, null,
13208                     android.app.AppOpsManager.OP_NONE, null, true, false, UserHandle.USER_ALL);
13209         } finally {
13210             Binder.restoreCallingIdentity(ident);
13211         }
13212     }
13213
13214     private void retrieveSettings() {
13215         final ContentResolver resolver = mContext.getContentResolver();
13216         final boolean freeformWindowManagement =
13217                 mContext.getPackageManager().hasSystemFeature(FEATURE_FREEFORM_WINDOW_MANAGEMENT)
13218                         || Settings.Global.getInt(
13219                                 resolver, DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT, 0) != 0;
13220         final boolean supportsPictureInPicture =
13221                 mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE);
13222
13223         final boolean supportsMultiWindow = ActivityManager.supportsMultiWindow();
13224         final String debugApp = Settings.Global.getString(resolver, DEBUG_APP);
13225         final boolean waitForDebugger = Settings.Global.getInt(resolver, WAIT_FOR_DEBUGGER, 0) != 0;
13226         final boolean alwaysFinishActivities =
13227                 Settings.Global.getInt(resolver, ALWAYS_FINISH_ACTIVITIES, 0) != 0;
13228         final boolean lenientBackgroundCheck =
13229                 Settings.Global.getInt(resolver, LENIENT_BACKGROUND_CHECK, 0) != 0;
13230         final boolean forceRtl = Settings.Global.getInt(resolver, DEVELOPMENT_FORCE_RTL, 0) != 0;
13231         final boolean forceResizable = Settings.Global.getInt(
13232                 resolver, DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES, 0) != 0;
13233         final boolean supportsLeanbackOnly =
13234                 mContext.getPackageManager().hasSystemFeature(FEATURE_LEANBACK_ONLY);
13235
13236         // Transfer any global setting for forcing RTL layout, into a System Property
13237         SystemProperties.set(DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0");
13238
13239         final Configuration configuration = new Configuration();
13240         Settings.System.getConfiguration(resolver, configuration);
13241         if (forceRtl) {
13242             // This will take care of setting the correct layout direction flags
13243             configuration.setLayoutDirection(configuration.locale);
13244         }
13245
13246         synchronized (this) {
13247             mDebugApp = mOrigDebugApp = debugApp;
13248             mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger;
13249             mAlwaysFinishActivities = alwaysFinishActivities;
13250             mLenientBackgroundCheck = lenientBackgroundCheck;
13251             mSupportsLeanbackOnly = supportsLeanbackOnly;
13252             mForceResizableActivities = forceResizable;
13253             mWindowManager.setForceResizableTasks(mForceResizableActivities);
13254             if (supportsMultiWindow || forceResizable) {
13255                 mSupportsMultiWindow = true;
13256                 mSupportsFreeformWindowManagement = freeformWindowManagement || forceResizable;
13257                 mSupportsPictureInPicture = supportsPictureInPicture || forceResizable;
13258             } else {
13259                 mSupportsMultiWindow = false;
13260                 mSupportsFreeformWindowManagement = false;
13261                 mSupportsPictureInPicture = false;
13262             }
13263             // This happens before any activities are started, so we can
13264             // change mConfiguration in-place.
13265             updateConfigurationLocked(configuration, null, true);
13266             if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION,
13267                     "Initial config: " + mConfiguration);
13268
13269             // Load resources only after the current configuration has been set.
13270             final Resources res = mContext.getResources();
13271             mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents);
13272             mThumbnailWidth = res.getDimensionPixelSize(
13273                     com.android.internal.R.dimen.thumbnail_width);
13274             mThumbnailHeight = res.getDimensionPixelSize(
13275                     com.android.internal.R.dimen.thumbnail_height);
13276             mDefaultPinnedStackBounds = Rect.unflattenFromString(res.getString(
13277                     com.android.internal.R.string.config_defaultPictureInPictureBounds));
13278             mAppErrors.loadAppsNotReportingCrashesFromConfigLocked(res.getString(
13279                     com.android.internal.R.string.config_appsNotReportingCrashes));
13280             if ((mConfiguration.uiMode & UI_MODE_TYPE_TELEVISION) == UI_MODE_TYPE_TELEVISION) {
13281                 mFullscreenThumbnailScale = (float) res
13282                     .getInteger(com.android.internal.R.integer.thumbnail_width_tv) /
13283                     (float) mConfiguration.screenWidthDp;
13284             } else {
13285                 mFullscreenThumbnailScale = res.getFraction(
13286                     com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1);
13287             }
13288         }
13289     }
13290
13291     public boolean testIsSystemReady() {
13292         // no need to synchronize(this) just to read & return the value
13293         return mSystemReady;
13294     }
13295
13296     public void systemReady(final Runnable goingCallback) {
13297         synchronized(this) {
13298             if (mSystemReady) {
13299                 // If we're done calling all the receivers, run the next "boot phase" passed in
13300                 // by the SystemServer
13301                 if (goingCallback != null) {
13302                     goingCallback.run();
13303                 }
13304                 return;
13305             }
13306
13307             mLocalDeviceIdleController
13308                     = LocalServices.getService(DeviceIdleController.LocalService.class);
13309
13310             // Make sure we have the current profile info, since it is needed for security checks.
13311             mUserController.onSystemReady();
13312             mRecentTasks.onSystemReadyLocked();
13313             mAppOpsService.systemReady();
13314             mSystemReady = true;
13315         }
13316
13317         ArrayList<ProcessRecord> procsToKill = null;
13318         synchronized(mPidsSelfLocked) {
13319             for (int i=mPidsSelfLocked.size()-1; i>=0; i--) {
13320                 ProcessRecord proc = mPidsSelfLocked.valueAt(i);
13321                 if (!isAllowedWhileBooting(proc.info)){
13322                     if (procsToKill == null) {
13323                         procsToKill = new ArrayList<ProcessRecord>();
13324                     }
13325                     procsToKill.add(proc);
13326                 }
13327             }
13328         }
13329
13330         synchronized(this) {
13331             if (procsToKill != null) {
13332                 for (int i=procsToKill.size()-1; i>=0; i--) {
13333                     ProcessRecord proc = procsToKill.get(i);
13334                     Slog.i(TAG, "Removing system update proc: " + proc);
13335                     removeProcessLocked(proc, true, false, "system update done");
13336                 }
13337             }
13338
13339             // Now that we have cleaned up any update processes, we
13340             // are ready to start launching real processes and know that
13341             // we won't trample on them any more.
13342             mProcessesReady = true;
13343         }
13344
13345         Slog.i(TAG, "System now ready");
13346         EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY,
13347             SystemClock.uptimeMillis());
13348
13349         synchronized(this) {
13350             // Make sure we have no pre-ready processes sitting around.
13351
13352             if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) {
13353                 ResolveInfo ri = mContext.getPackageManager()
13354                         .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST),
13355                                 STOCK_PM_FLAGS);
13356                 CharSequence errorMsg = null;
13357                 if (ri != null) {
13358                     ActivityInfo ai = ri.activityInfo;
13359                     ApplicationInfo app = ai.applicationInfo;
13360                     if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) {
13361                         mTopAction = Intent.ACTION_FACTORY_TEST;
13362                         mTopData = null;
13363                         mTopComponent = new ComponentName(app.packageName,
13364                                 ai.name);
13365                     } else {
13366                         errorMsg = mContext.getResources().getText(
13367                                 com.android.internal.R.string.factorytest_not_system);
13368                     }
13369                 } else {
13370                     errorMsg = mContext.getResources().getText(
13371                             com.android.internal.R.string.factorytest_no_action);
13372                 }
13373                 if (errorMsg != null) {
13374                     mTopAction = null;
13375                     mTopData = null;
13376                     mTopComponent = null;
13377                     Message msg = Message.obtain();
13378                     msg.what = SHOW_FACTORY_ERROR_UI_MSG;
13379                     msg.getData().putCharSequence("msg", errorMsg);
13380                     mUiHandler.sendMessage(msg);
13381                 }
13382             }
13383         }
13384
13385         retrieveSettings();
13386         final int currentUserId;
13387         synchronized (this) {
13388             currentUserId = mUserController.getCurrentUserIdLocked();
13389             readGrantedUriPermissionsLocked();
13390         }
13391
13392         if (goingCallback != null) goingCallback.run();
13393
13394         mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START,
13395                 Integer.toString(currentUserId), currentUserId);
13396         mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START,
13397                 Integer.toString(currentUserId), currentUserId);
13398         mSystemServiceManager.startUser(currentUserId);
13399
13400         synchronized (this) {
13401             // Only start up encryption-aware persistent apps; once user is
13402             // unlocked we'll come back around and start unaware apps
13403             startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_AWARE);
13404
13405             // Start up initial activity.
13406             mBooting = true;
13407             // Enable home activity for system user, so that the system can always boot
13408             if (UserManager.isSplitSystemUser()) {
13409                 ComponentName cName = new ComponentName(mContext, SystemUserHomeActivity.class);
13410                 try {
13411                     AppGlobals.getPackageManager().setComponentEnabledSetting(cName,
13412                             PackageManager.COMPONENT_ENABLED_STATE_ENABLED, 0,
13413                             UserHandle.USER_SYSTEM);
13414                 } catch (RemoteException e) {
13415                     throw e.rethrowAsRuntimeException();
13416                 }
13417             }
13418             startHomeActivityLocked(currentUserId, "systemReady");
13419
13420             try {
13421                 if (AppGlobals.getPackageManager().hasSystemUidErrors()) {
13422                     Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your"
13423                             + " data partition or your device will be unstable.");
13424                     mUiHandler.obtainMessage(SHOW_UID_ERROR_UI_MSG).sendToTarget();
13425                 }
13426             } catch (RemoteException e) {
13427             }
13428
13429             if (!Build.isBuildConsistent()) {
13430                 Slog.e(TAG, "Build fingerprint is not consistent, warning user");
13431                 mUiHandler.obtainMessage(SHOW_FINGERPRINT_ERROR_UI_MSG).sendToTarget();
13432             }
13433
13434             long ident = Binder.clearCallingIdentity();
13435             try {
13436                 Intent intent = new Intent(Intent.ACTION_USER_STARTED);
13437                 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY
13438                         | Intent.FLAG_RECEIVER_FOREGROUND);
13439                 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId);
13440                 broadcastIntentLocked(null, null, intent,
13441                         null, null, 0, null, null, null, AppOpsManager.OP_NONE,
13442                         null, false, false, MY_PID, Process.SYSTEM_UID,
13443                         currentUserId);
13444                 intent = new Intent(Intent.ACTION_USER_STARTING);
13445                 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
13446                 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId);
13447                 broadcastIntentLocked(null, null, intent,
13448                         null, new IIntentReceiver.Stub() {
13449                             @Override
13450                             public void performReceive(Intent intent, int resultCode, String data,
13451                                     Bundle extras, boolean ordered, boolean sticky, int sendingUser)
13452                                     throws RemoteException {
13453                             }
13454                         }, 0, null, null,
13455                         new String[] {INTERACT_ACROSS_USERS}, AppOpsManager.OP_NONE,
13456                         null, true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL);
13457             } catch (Throwable t) {
13458                 Slog.wtf(TAG, "Failed sending first user broadcasts", t);
13459             } finally {
13460                 Binder.restoreCallingIdentity(ident);
13461             }
13462             mStackSupervisor.resumeFocusedStackTopActivityLocked();
13463             mUserController.sendUserSwitchBroadcastsLocked(-1, currentUserId);
13464         }
13465     }
13466
13467     void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) {
13468         synchronized (this) {
13469             mAppErrors.killAppAtUserRequestLocked(app, fromDialog);
13470         }
13471     }
13472
13473     void skipCurrentReceiverLocked(ProcessRecord app) {
13474         for (BroadcastQueue queue : mBroadcastQueues) {
13475             queue.skipCurrentReceiverLocked(app);
13476         }
13477     }
13478
13479     /**
13480      * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes.
13481      * The application process will exit immediately after this call returns.
13482      * @param app object of the crashing app, null for the system server
13483      * @param crashInfo describing the exception
13484      */
13485     public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) {
13486         ProcessRecord r = findAppProcess(app, "Crash");
13487         final String processName = app == null ? "system_server"
13488                 : (r == null ? "unknown" : r.processName);
13489
13490         handleApplicationCrashInner("crash", r, processName, crashInfo);
13491     }
13492
13493     /* Native crash reporting uses this inner version because it needs to be somewhat
13494      * decoupled from the AM-managed cleanup lifecycle
13495      */
13496     void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName,
13497             ApplicationErrorReport.CrashInfo crashInfo) {
13498         EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(),
13499                 UserHandle.getUserId(Binder.getCallingUid()), processName,
13500                 r == null ? -1 : r.info.flags,
13501                 crashInfo.exceptionClassName,
13502                 crashInfo.exceptionMessage,
13503                 crashInfo.throwFileName,
13504                 crashInfo.throwLineNumber);
13505
13506         addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo);
13507
13508         mAppErrors.crashApplication(r, crashInfo);
13509     }
13510
13511     public void handleApplicationStrictModeViolation(
13512             IBinder app,
13513             int violationMask,
13514             StrictMode.ViolationInfo info) {
13515         ProcessRecord r = findAppProcess(app, "StrictMode");
13516         if (r == null) {
13517             return;
13518         }
13519
13520         if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) {
13521             Integer stackFingerprint = info.hashCode();
13522             boolean logIt = true;
13523             synchronized (mAlreadyLoggedViolatedStacks) {
13524                 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) {
13525                     logIt = false;
13526                     // TODO: sub-sample into EventLog for these, with
13527                     // the info.durationMillis?  Then we'd get
13528                     // the relative pain numbers, without logging all
13529                     // the stack traces repeatedly.  We'd want to do
13530                     // likewise in the client code, which also does
13531                     // dup suppression, before the Binder call.
13532                 } else {
13533                     if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) {
13534                         mAlreadyLoggedViolatedStacks.clear();
13535                     }
13536                     mAlreadyLoggedViolatedStacks.add(stackFingerprint);
13537                 }
13538             }
13539             if (logIt) {
13540                 logStrictModeViolationToDropBox(r, info);
13541             }
13542         }
13543
13544         if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) {
13545             AppErrorResult result = new AppErrorResult();
13546             synchronized (this) {
13547                 final long origId = Binder.clearCallingIdentity();
13548
13549                 Message msg = Message.obtain();
13550                 msg.what = SHOW_STRICT_MODE_VIOLATION_UI_MSG;
13551                 HashMap<String, Object> data = new HashMap<String, Object>();
13552                 data.put("result", result);
13553                 data.put("app", r);
13554                 data.put("violationMask", violationMask);
13555                 data.put("info", info);
13556                 msg.obj = data;
13557                 mUiHandler.sendMessage(msg);
13558
13559                 Binder.restoreCallingIdentity(origId);
13560             }
13561             int res = result.get();
13562             Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res);
13563         }
13564     }
13565
13566     // Depending on the policy in effect, there could be a bunch of
13567     // these in quick succession so we try to batch these together to
13568     // minimize disk writes, number of dropbox entries, and maximize
13569     // compression, by having more fewer, larger records.
13570     private void logStrictModeViolationToDropBox(
13571             ProcessRecord process,
13572             StrictMode.ViolationInfo info) {
13573         if (info == null) {
13574             return;
13575         }
13576         final boolean isSystemApp = process == null ||
13577                 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM |
13578                                        ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0;
13579         final String processName = process == null ? "unknown" : process.processName;
13580         final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode";
13581         final DropBoxManager dbox = (DropBoxManager)
13582                 mContext.getSystemService(Context.DROPBOX_SERVICE);
13583
13584         // Exit early if the dropbox isn't configured to accept this report type.
13585         if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return;
13586
13587         boolean bufferWasEmpty;
13588         boolean needsFlush;
13589         final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024);
13590         synchronized (sb) {
13591             bufferWasEmpty = sb.length() == 0;
13592             appendDropBoxProcessHeaders(process, processName, sb);
13593             sb.append("Build: ").append(Build.FINGERPRINT).append("\n");
13594             sb.append("System-App: ").append(isSystemApp).append("\n");
13595             sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n");
13596             if (info.violationNumThisLoop != 0) {
13597                 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n");
13598             }
13599             if (info.numAnimationsRunning != 0) {
13600                 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n");
13601             }
13602             if (info.broadcastIntentAction != null) {
13603                 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n");
13604             }
13605             if (info.durationMillis != -1) {
13606                 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n");
13607             }
13608             if (info.numInstances != -1) {
13609                 sb.append("Instance-Count: ").append(info.numInstances).append("\n");
13610             }
13611             if (info.tags != null) {
13612                 for (String tag : info.tags) {
13613                     sb.append("Span-Tag: ").append(tag).append("\n");
13614                 }
13615             }
13616             sb.append("\n");
13617             if (info.crashInfo != null && info.crashInfo.stackTrace != null) {
13618                 sb.append(info.crashInfo.stackTrace);
13619                 sb.append("\n");
13620             }
13621             if (info.message != null) {
13622                 sb.append(info.message);
13623                 sb.append("\n");
13624             }
13625
13626             // Only buffer up to ~64k.  Various logging bits truncate
13627             // things at 128k.
13628             needsFlush = (sb.length() > 64 * 1024);
13629         }
13630
13631         // Flush immediately if the buffer's grown too large, or this
13632         // is a non-system app.  Non-system apps are isolated with a
13633         // different tag & policy and not batched.
13634         //
13635         // Batching is useful during internal testing with
13636         // StrictMode settings turned up high.  Without batching,
13637         // thousands of separate files could be created on boot.
13638         if (!isSystemApp || needsFlush) {
13639             new Thread("Error dump: " + dropboxTag) {
13640                 @Override
13641                 public void run() {
13642                     String report;
13643                     synchronized (sb) {
13644                         report = sb.toString();
13645                         sb.delete(0, sb.length());
13646                         sb.trimToSize();
13647                     }
13648                     if (report.length() != 0) {
13649                         dbox.addText(dropboxTag, report);
13650                     }
13651                 }
13652             }.start();
13653             return;
13654         }
13655
13656         // System app batching:
13657         if (!bufferWasEmpty) {
13658             // An existing dropbox-writing thread is outstanding, so
13659             // we don't need to start it up.  The existing thread will
13660             // catch the buffer appends we just did.
13661             return;
13662         }
13663
13664         // Worker thread to both batch writes and to avoid blocking the caller on I/O.
13665         // (After this point, we shouldn't access AMS internal data structures.)
13666         new Thread("Error dump: " + dropboxTag) {
13667             @Override
13668             public void run() {
13669                 // 5 second sleep to let stacks arrive and be batched together
13670                 try {
13671                     Thread.sleep(5000);  // 5 seconds
13672                 } catch (InterruptedException e) {}
13673
13674                 String errorReport;
13675                 synchronized (mStrictModeBuffer) {
13676                     errorReport = mStrictModeBuffer.toString();
13677                     if (errorReport.length() == 0) {
13678                         return;
13679                     }
13680                     mStrictModeBuffer.delete(0, mStrictModeBuffer.length());
13681                     mStrictModeBuffer.trimToSize();
13682                 }
13683                 dbox.addText(dropboxTag, errorReport);
13684             }
13685         }.start();
13686     }
13687
13688     /**
13689      * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors.
13690      * @param app object of the crashing app, null for the system server
13691      * @param tag reported by the caller
13692      * @param system whether this wtf is coming from the system
13693      * @param crashInfo describing the context of the error
13694      * @return true if the process should exit immediately (WTF is fatal)
13695      */
13696     public boolean handleApplicationWtf(final IBinder app, final String tag, boolean system,
13697             final ApplicationErrorReport.CrashInfo crashInfo) {
13698         final int callingUid = Binder.getCallingUid();
13699         final int callingPid = Binder.getCallingPid();
13700
13701         if (system) {
13702             // If this is coming from the system, we could very well have low-level
13703             // system locks held, so we want to do this all asynchronously.  And we
13704             // never want this to become fatal, so there is that too.
13705             mHandler.post(new Runnable() {
13706                 @Override public void run() {
13707                     handleApplicationWtfInner(callingUid, callingPid, app, tag, crashInfo);
13708                 }
13709             });
13710             return false;
13711         }
13712
13713         final ProcessRecord r = handleApplicationWtfInner(callingUid, callingPid, app, tag,
13714                 crashInfo);
13715
13716         if (r != null && r.pid != Process.myPid() &&
13717                 Settings.Global.getInt(mContext.getContentResolver(),
13718                         Settings.Global.WTF_IS_FATAL, 0) != 0) {
13719             mAppErrors.crashApplication(r, crashInfo);
13720             return true;
13721         } else {
13722             return false;
13723         }
13724     }
13725
13726     ProcessRecord handleApplicationWtfInner(int callingUid, int callingPid, IBinder app, String tag,
13727             final ApplicationErrorReport.CrashInfo crashInfo) {
13728         final ProcessRecord r = findAppProcess(app, "WTF");
13729         final String processName = app == null ? "system_server"
13730                 : (r == null ? "unknown" : r.processName);
13731
13732         EventLog.writeEvent(EventLogTags.AM_WTF, UserHandle.getUserId(callingUid), callingPid,
13733                 processName, r == null ? -1 : r.info.flags, tag, crashInfo.exceptionMessage);
13734
13735         addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo);
13736
13737         return r;
13738     }
13739
13740     /**
13741      * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit})
13742      * @return the corresponding {@link ProcessRecord} object, or null if none could be found
13743      */
13744     private ProcessRecord findAppProcess(IBinder app, String reason) {
13745         if (app == null) {
13746             return null;
13747         }
13748
13749         synchronized (this) {
13750             final int NP = mProcessNames.getMap().size();
13751             for (int ip=0; ip<NP; ip++) {
13752                 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
13753                 final int NA = apps.size();
13754                 for (int ia=0; ia<NA; ia++) {
13755                     ProcessRecord p = apps.valueAt(ia);
13756                     if (p.thread != null && p.thread.asBinder() == app) {
13757                         return p;
13758                     }
13759                 }
13760             }
13761
13762             Slog.w(TAG, "Can't find mystery application for " + reason
13763                     + " from pid=" + Binder.getCallingPid()
13764                     + " uid=" + Binder.getCallingUid() + ": " + app);
13765             return null;
13766         }
13767     }
13768
13769     /**
13770      * Utility function for addErrorToDropBox and handleStrictModeViolation's logging
13771      * to append various headers to the dropbox log text.
13772      */
13773     private void appendDropBoxProcessHeaders(ProcessRecord process, String processName,
13774             StringBuilder sb) {
13775         // Watchdog thread ends up invoking this function (with
13776         // a null ProcessRecord) to add the stack file to dropbox.
13777         // Do not acquire a lock on this (am) in such cases, as it
13778         // could cause a potential deadlock, if and when watchdog
13779         // is invoked due to unavailability of lock on am and it
13780         // would prevent watchdog from killing system_server.
13781         if (process == null) {
13782             sb.append("Process: ").append(processName).append("\n");
13783             return;
13784         }
13785         // Note: ProcessRecord 'process' is guarded by the service
13786         // instance.  (notably process.pkgList, which could otherwise change
13787         // concurrently during execution of this method)
13788         synchronized (this) {
13789             sb.append("Process: ").append(processName).append("\n");
13790             int flags = process.info.flags;
13791             IPackageManager pm = AppGlobals.getPackageManager();
13792             sb.append("Flags: 0x").append(Integer.toHexString(flags)).append("\n");
13793             for (int ip=0; ip<process.pkgList.size(); ip++) {
13794                 String pkg = process.pkgList.keyAt(ip);
13795                 sb.append("Package: ").append(pkg);
13796                 try {
13797                     PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId());
13798                     if (pi != null) {
13799                         sb.append(" v").append(pi.versionCode);
13800                         if (pi.versionName != null) {
13801                             sb.append(" (").append(pi.versionName).append(")");
13802                         }
13803                     }
13804                 } catch (RemoteException e) {
13805                     Slog.e(TAG, "Error getting package info: " + pkg, e);
13806                 }
13807                 sb.append("\n");
13808             }
13809         }
13810     }
13811
13812     private static String processClass(ProcessRecord process) {
13813         if (process == null || process.pid == MY_PID) {
13814             return "system_server";
13815         } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) {
13816             return "system_app";
13817         } else {
13818             return "data_app";
13819         }
13820     }
13821
13822     private volatile long mWtfClusterStart;
13823     private volatile int mWtfClusterCount;
13824
13825     /**
13826      * Write a description of an error (crash, WTF, ANR) to the drop box.
13827      * @param eventType to include in the drop box tag ("crash", "wtf", etc.)
13828      * @param process which caused the error, null means the system server
13829      * @param activity which triggered the error, null if unknown
13830      * @param parent activity related to the error, null if unknown
13831      * @param subject line related to the error, null if absent
13832      * @param report in long form describing the error, null if absent
13833      * @param dataFile text file to include in the report, null if none
13834      * @param crashInfo giving an application stack trace, null if absent
13835      */
13836     public void addErrorToDropBox(String eventType,
13837             ProcessRecord process, String processName, ActivityRecord activity,
13838             ActivityRecord parent, String subject,
13839             final String report, final File dataFile,
13840             final ApplicationErrorReport.CrashInfo crashInfo) {
13841         // NOTE -- this must never acquire the ActivityManagerService lock,
13842         // otherwise the watchdog may be prevented from resetting the system.
13843
13844         final String dropboxTag = processClass(process) + "_" + eventType;
13845         final DropBoxManager dbox = (DropBoxManager)
13846                 mContext.getSystemService(Context.DROPBOX_SERVICE);
13847
13848         // Exit early if the dropbox isn't configured to accept this report type.
13849         if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return;
13850
13851         // Rate-limit how often we're willing to do the heavy lifting below to
13852         // collect and record logs; currently 5 logs per 10 second period.
13853         final long now = SystemClock.elapsedRealtime();
13854         if (now - mWtfClusterStart > 10 * DateUtils.SECOND_IN_MILLIS) {
13855             mWtfClusterStart = now;
13856             mWtfClusterCount = 1;
13857         } else {
13858             if (mWtfClusterCount++ >= 5) return;
13859         }
13860
13861         final StringBuilder sb = new StringBuilder(1024);
13862         appendDropBoxProcessHeaders(process, processName, sb);
13863         if (process != null) {
13864             sb.append("Foreground: ")
13865                     .append(process.isInterestingToUserLocked() ? "Yes" : "No")
13866                     .append("\n");
13867         }
13868         if (activity != null) {
13869             sb.append("Activity: ").append(activity.shortComponentName).append("\n");
13870         }
13871         if (parent != null && parent.app != null && parent.app.pid != process.pid) {
13872             sb.append("Parent-Process: ").append(parent.app.processName).append("\n");
13873         }
13874         if (parent != null && parent != activity) {
13875             sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n");
13876         }
13877         if (subject != null) {
13878             sb.append("Subject: ").append(subject).append("\n");
13879         }
13880         sb.append("Build: ").append(Build.FINGERPRINT).append("\n");
13881         if (Debug.isDebuggerConnected()) {
13882             sb.append("Debugger: Connected\n");
13883         }
13884         sb.append("\n");
13885
13886         // Do the rest in a worker thread to avoid blocking the caller on I/O
13887         // (After this point, we shouldn't access AMS internal data structures.)
13888         Thread worker = new Thread("Error dump: " + dropboxTag) {
13889             @Override
13890             public void run() {
13891                 if (report != null) {
13892                     sb.append(report);
13893                 }
13894
13895                 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag;
13896                 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0);
13897                 int maxDataFileSize = DROPBOX_MAX_SIZE - sb.length()
13898                         - lines * RESERVED_BYTES_PER_LOGCAT_LINE;
13899
13900                 if (dataFile != null && maxDataFileSize > 0) {
13901                     try {
13902                         sb.append(FileUtils.readTextFile(dataFile, maxDataFileSize,
13903                                     "\n\n[[TRUNCATED]]"));
13904                     } catch (IOException e) {
13905                         Slog.e(TAG, "Error reading " + dataFile, e);
13906                     }
13907                 }
13908                 if (crashInfo != null && crashInfo.stackTrace != null) {
13909                     sb.append(crashInfo.stackTrace);
13910                 }
13911
13912                 if (lines > 0) {
13913                     sb.append("\n");
13914
13915                     // Merge several logcat streams, and take the last N lines
13916                     InputStreamReader input = null;
13917                     try {
13918                         java.lang.Process logcat = new ProcessBuilder(
13919                                 "/system/bin/timeout", "-k", "15s", "10s",
13920                                 "/system/bin/logcat", "-v", "threadtime", "-b", "events", "-b", "system",
13921                                 "-b", "main", "-b", "crash", "-t", String.valueOf(lines))
13922                                         .redirectErrorStream(true).start();
13923
13924                         try { logcat.getOutputStream().close(); } catch (IOException e) {}
13925                         try { logcat.getErrorStream().close(); } catch (IOException e) {}
13926                         input = new InputStreamReader(logcat.getInputStream());
13927
13928                         int num;
13929                         char[] buf = new char[8192];
13930                         while ((num = input.read(buf)) > 0) sb.append(buf, 0, num);
13931                     } catch (IOException e) {
13932                         Slog.e(TAG, "Error running logcat", e);
13933                     } finally {
13934                         if (input != null) try { input.close(); } catch (IOException e) {}
13935                     }
13936                 }
13937
13938                 dbox.addText(dropboxTag, sb.toString());
13939             }
13940         };
13941
13942         if (process == null) {
13943             // If process is null, we are being called from some internal code
13944             // and may be about to die -- run this synchronously.
13945             worker.run();
13946         } else {
13947             worker.start();
13948         }
13949     }
13950
13951     @Override
13952     public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() {
13953         enforceNotIsolatedCaller("getProcessesInErrorState");
13954         // assume our apps are happy - lazy create the list
13955         List<ActivityManager.ProcessErrorStateInfo> errList = null;
13956
13957         final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL,
13958                 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED;
13959         int userId = UserHandle.getUserId(Binder.getCallingUid());
13960
13961         synchronized (this) {
13962
13963             // iterate across all processes
13964             for (int i=mLruProcesses.size()-1; i>=0; i--) {
13965                 ProcessRecord app = mLruProcesses.get(i);
13966                 if (!allUsers && app.userId != userId) {
13967                     continue;
13968                 }
13969                 if ((app.thread != null) && (app.crashing || app.notResponding)) {
13970                     // This one's in trouble, so we'll generate a report for it
13971                     // crashes are higher priority (in case there's a crash *and* an anr)
13972                     ActivityManager.ProcessErrorStateInfo report = null;
13973                     if (app.crashing) {
13974                         report = app.crashingReport;
13975                     } else if (app.notResponding) {
13976                         report = app.notRespondingReport;
13977                     }
13978
13979                     if (report != null) {
13980                         if (errList == null) {
13981                             errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1);
13982                         }
13983                         errList.add(report);
13984                     } else {
13985                         Slog.w(TAG, "Missing app error report, app = " + app.processName +
13986                                 " crashing = " + app.crashing +
13987                                 " notResponding = " + app.notResponding);
13988                     }
13989                 }
13990             }
13991         }
13992
13993         return errList;
13994     }
13995
13996     static int procStateToImportance(int procState, int memAdj,
13997             ActivityManager.RunningAppProcessInfo currApp) {
13998         int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState);
13999         if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) {
14000             currApp.lru = memAdj;
14001         } else {
14002             currApp.lru = 0;
14003         }
14004         return imp;
14005     }
14006
14007     private void fillInProcMemInfo(ProcessRecord app,
14008             ActivityManager.RunningAppProcessInfo outInfo) {
14009         outInfo.pid = app.pid;
14010         outInfo.uid = app.info.uid;
14011         if (mHeavyWeightProcess == app) {
14012             outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE;
14013         }
14014         if (app.persistent) {
14015             outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT;
14016         }
14017         if (app.activities.size() > 0) {
14018             outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES;
14019         }
14020         outInfo.lastTrimLevel = app.trimMemoryLevel;
14021         int adj = app.curAdj;
14022         int procState = app.curProcState;
14023         outInfo.importance = procStateToImportance(procState, adj, outInfo);
14024         outInfo.importanceReasonCode = app.adjTypeCode;
14025         outInfo.processState = app.curProcState;
14026     }
14027
14028     @Override
14029     public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() {
14030         enforceNotIsolatedCaller("getRunningAppProcesses");
14031
14032         final int callingUid = Binder.getCallingUid();
14033
14034         // Lazy instantiation of list
14035         List<ActivityManager.RunningAppProcessInfo> runList = null;
14036         final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL,
14037                 callingUid) == PackageManager.PERMISSION_GRANTED;
14038         final int userId = UserHandle.getUserId(callingUid);
14039         final boolean allUids = isGetTasksAllowed(
14040                 "getRunningAppProcesses", Binder.getCallingPid(), callingUid);
14041
14042         synchronized (this) {
14043             // Iterate across all processes
14044             for (int i = mLruProcesses.size() - 1; i >= 0; i--) {
14045                 ProcessRecord app = mLruProcesses.get(i);
14046                 if ((!allUsers && app.userId != userId)
14047                         || (!allUids && app.uid != callingUid)) {
14048                     continue;
14049                 }
14050                 if ((app.thread != null) && (!app.crashing && !app.notResponding)) {
14051                     // Generate process state info for running application
14052                     ActivityManager.RunningAppProcessInfo currApp =
14053                         new ActivityManager.RunningAppProcessInfo(app.processName,
14054                                 app.pid, app.getPackageList());
14055                     fillInProcMemInfo(app, currApp);
14056                     if (app.adjSource instanceof ProcessRecord) {
14057                         currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid;
14058                         currApp.importanceReasonImportance =
14059                                 ActivityManager.RunningAppProcessInfo.procStateToImportance(
14060                                         app.adjSourceProcState);
14061                     } else if (app.adjSource instanceof ActivityRecord) {
14062                         ActivityRecord r = (ActivityRecord)app.adjSource;
14063                         if (r.app != null) currApp.importanceReasonPid = r.app.pid;
14064                     }
14065                     if (app.adjTarget instanceof ComponentName) {
14066                         currApp.importanceReasonComponent = (ComponentName)app.adjTarget;
14067                     }
14068                     //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance
14069                     //        + " lru=" + currApp.lru);
14070                     if (runList == null) {
14071                         runList = new ArrayList<>();
14072                     }
14073                     runList.add(currApp);
14074                 }
14075             }
14076         }
14077         return runList;
14078     }
14079
14080     @Override
14081     public List<ApplicationInfo> getRunningExternalApplications() {
14082         enforceNotIsolatedCaller("getRunningExternalApplications");
14083         List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses();
14084         List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>();
14085         if (runningApps != null && runningApps.size() > 0) {
14086             Set<String> extList = new HashSet<String>();
14087             for (ActivityManager.RunningAppProcessInfo app : runningApps) {
14088                 if (app.pkgList != null) {
14089                     for (String pkg : app.pkgList) {
14090                         extList.add(pkg);
14091                     }
14092                 }
14093             }
14094             IPackageManager pm = AppGlobals.getPackageManager();
14095             for (String pkg : extList) {
14096                 try {
14097                     ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId());
14098                     if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) {
14099                         retList.add(info);
14100                     }
14101                 } catch (RemoteException e) {
14102                 }
14103             }
14104         }
14105         return retList;
14106     }
14107
14108     @Override
14109     public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) {
14110         enforceNotIsolatedCaller("getMyMemoryState");
14111         synchronized (this) {
14112             ProcessRecord proc;
14113             synchronized (mPidsSelfLocked) {
14114                 proc = mPidsSelfLocked.get(Binder.getCallingPid());
14115             }
14116             fillInProcMemInfo(proc, outInfo);
14117         }
14118     }
14119
14120     @Override
14121     public int getMemoryTrimLevel() {
14122         enforceNotIsolatedCaller("getMyMemoryState");
14123         synchronized (this) {
14124             return mLastMemoryLevel;
14125         }
14126     }
14127
14128     @Override
14129     public void onShellCommand(FileDescriptor in, FileDescriptor out,
14130             FileDescriptor err, String[] args, ResultReceiver resultReceiver) {
14131         (new ActivityManagerShellCommand(this, false)).exec(
14132                 this, in, out, err, args, resultReceiver);
14133     }
14134
14135     @Override
14136     protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
14137         if (checkCallingPermission(android.Manifest.permission.DUMP)
14138                 != PackageManager.PERMISSION_GRANTED) {
14139             pw.println("Permission Denial: can't dump ActivityManager from from pid="
14140                     + Binder.getCallingPid()
14141                     + ", uid=" + Binder.getCallingUid()
14142                     + " without permission "
14143                     + android.Manifest.permission.DUMP);
14144             return;
14145         }
14146
14147         boolean dumpAll = false;
14148         boolean dumpClient = false;
14149         boolean dumpCheckin = false;
14150         boolean dumpCheckinFormat = false;
14151         String dumpPackage = null;
14152
14153         int opti = 0;
14154         while (opti < args.length) {
14155             String opt = args[opti];
14156             if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') {
14157                 break;
14158             }
14159             opti++;
14160             if ("-a".equals(opt)) {
14161                 dumpAll = true;
14162             } else if ("-c".equals(opt)) {
14163                 dumpClient = true;
14164             } else if ("-p".equals(opt)) {
14165                 if (opti < args.length) {
14166                     dumpPackage = args[opti];
14167                     opti++;
14168                 } else {
14169                     pw.println("Error: -p option requires package argument");
14170                     return;
14171                 }
14172                 dumpClient = true;
14173             } else if ("--checkin".equals(opt)) {
14174                 dumpCheckin = dumpCheckinFormat = true;
14175             } else if ("-C".equals(opt)) {
14176                 dumpCheckinFormat = true;
14177             } else if ("-h".equals(opt)) {
14178                 ActivityManagerShellCommand.dumpHelp(pw, true);
14179                 return;
14180             } else {
14181                 pw.println("Unknown argument: " + opt + "; use -h for help");
14182             }
14183         }
14184
14185         long origId = Binder.clearCallingIdentity();
14186         boolean more = false;
14187         // Is the caller requesting to dump a particular piece of data?
14188         if (opti < args.length) {
14189             String cmd = args[opti];
14190             opti++;
14191             if ("activities".equals(cmd) || "a".equals(cmd)) {
14192                 synchronized (this) {
14193                     dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, dumpPackage);
14194                 }
14195             } else if ("recents".equals(cmd) || "r".equals(cmd)) {
14196                 synchronized (this) {
14197                     dumpRecentsLocked(fd, pw, args, opti, true, dumpPackage);
14198                 }
14199             } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) {
14200                 String[] newArgs;
14201                 String name;
14202                 if (opti >= args.length) {
14203                     name = null;
14204                     newArgs = EMPTY_STRING_ARRAY;
14205                 } else {
14206                     dumpPackage = args[opti];
14207                     opti++;
14208                     newArgs = new String[args.length - opti];
14209                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0,
14210                             args.length - opti);
14211                 }
14212                 synchronized (this) {
14213                     dumpBroadcastsLocked(fd, pw, args, opti, true, dumpPackage);
14214                 }
14215             } else if ("broadcast-stats".equals(cmd)) {
14216                 String[] newArgs;
14217                 String name;
14218                 if (opti >= args.length) {
14219                     name = null;
14220                     newArgs = EMPTY_STRING_ARRAY;
14221                 } else {
14222                     dumpPackage = args[opti];
14223                     opti++;
14224                     newArgs = new String[args.length - opti];
14225                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0,
14226                             args.length - opti);
14227                 }
14228                 synchronized (this) {
14229                     if (dumpCheckinFormat) {
14230                         dumpBroadcastStatsCheckinLocked(fd, pw, args, opti, dumpCheckin,
14231                                 dumpPackage);
14232                     } else {
14233                         dumpBroadcastStatsLocked(fd, pw, args, opti, true, dumpPackage);
14234                     }
14235                 }
14236             } else if ("intents".equals(cmd) || "i".equals(cmd)) {
14237                 String[] newArgs;
14238                 String name;
14239                 if (opti >= args.length) {
14240                     name = null;
14241                     newArgs = EMPTY_STRING_ARRAY;
14242                 } else {
14243                     dumpPackage = args[opti];
14244                     opti++;
14245                     newArgs = new String[args.length - opti];
14246                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0,
14247                             args.length - opti);
14248                 }
14249                 synchronized (this) {
14250                     dumpPendingIntentsLocked(fd, pw, args, opti, true, dumpPackage);
14251                 }
14252             } else if ("processes".equals(cmd) || "p".equals(cmd)) {
14253                 String[] newArgs;
14254                 String name;
14255                 if (opti >= args.length) {
14256                     name = null;
14257                     newArgs = EMPTY_STRING_ARRAY;
14258                 } else {
14259                     dumpPackage = args[opti];
14260                     opti++;
14261                     newArgs = new String[args.length - opti];
14262                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0,
14263                             args.length - opti);
14264                 }
14265                 synchronized (this) {
14266                     dumpProcessesLocked(fd, pw, args, opti, true, dumpPackage);
14267                 }
14268             } else if ("oom".equals(cmd) || "o".equals(cmd)) {
14269                 synchronized (this) {
14270                     dumpOomLocked(fd, pw, args, opti, true);
14271                 }
14272             } else if ("permissions".equals(cmd) || "perm".equals(cmd)) {
14273                 synchronized (this) {
14274                     dumpPermissionsLocked(fd, pw, args, opti, true, null);
14275                 }
14276             } else if ("provider".equals(cmd)) {
14277                 String[] newArgs;
14278                 String name;
14279                 if (opti >= args.length) {
14280                     name = null;
14281                     newArgs = EMPTY_STRING_ARRAY;
14282                 } else {
14283                     name = args[opti];
14284                     opti++;
14285                     newArgs = new String[args.length - opti];
14286                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti);
14287                 }
14288                 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) {
14289                     pw.println("No providers match: " + name);
14290                     pw.println("Use -h for help.");
14291                 }
14292             } else if ("providers".equals(cmd) || "prov".equals(cmd)) {
14293                 synchronized (this) {
14294                     dumpProvidersLocked(fd, pw, args, opti, true, null);
14295                 }
14296             } else if ("service".equals(cmd)) {
14297                 String[] newArgs;
14298                 String name;
14299                 if (opti >= args.length) {
14300                     name = null;
14301                     newArgs = EMPTY_STRING_ARRAY;
14302                 } else {
14303                     name = args[opti];
14304                     opti++;
14305                     newArgs = new String[args.length - opti];
14306                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0,
14307                             args.length - opti);
14308                 }
14309                 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) {
14310                     pw.println("No services match: " + name);
14311                     pw.println("Use -h for help.");
14312                 }
14313             } else if ("package".equals(cmd)) {
14314                 String[] newArgs;
14315                 if (opti >= args.length) {
14316                     pw.println("package: no package name specified");
14317                     pw.println("Use -h for help.");
14318                 } else {
14319                     dumpPackage = args[opti];
14320                     opti++;
14321                     newArgs = new String[args.length - opti];
14322                     if (args.length > 2) System.arraycopy(args, opti, newArgs, 0,
14323                             args.length - opti);
14324                     args = newArgs;
14325                     opti = 0;
14326                     more = true;
14327                 }
14328             } else if ("associations".equals(cmd) || "as".equals(cmd)) {
14329                 synchronized (this) {
14330                     dumpAssociationsLocked(fd, pw, args, opti, true, dumpClient, dumpPackage);
14331                 }
14332             } else if ("services".equals(cmd) || "s".equals(cmd)) {
14333                 if (dumpClient) {
14334                     ActiveServices.ServiceDumper dumper;
14335                     synchronized (this) {
14336                         dumper = mServices.newServiceDumperLocked(fd, pw, args, opti, true,
14337                                 dumpPackage);
14338                     }
14339                     dumper.dumpWithClient();
14340                 } else {
14341                     synchronized (this) {
14342                         mServices.newServiceDumperLocked(fd, pw, args, opti, true,
14343                                 dumpPackage).dumpLocked();
14344                     }
14345                 }
14346             } else if ("locks".equals(cmd)) {
14347                 LockGuard.dump(fd, pw, args);
14348             } else {
14349                 // Dumping a single activity?
14350                 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) {
14351                     ActivityManagerShellCommand shell = new ActivityManagerShellCommand(this, true);
14352                     int res = shell.exec(this, null, fd, null, args, new ResultReceiver(null));
14353                     if (res < 0) {
14354                         pw.println("Bad activity command, or no activities match: " + cmd);
14355                         pw.println("Use -h for help.");
14356                     }
14357                 }
14358             }
14359             if (!more) {
14360                 Binder.restoreCallingIdentity(origId);
14361                 return;
14362             }
14363         }
14364
14365         // No piece of data specified, dump everything.
14366         if (dumpCheckinFormat) {
14367             dumpBroadcastStatsCheckinLocked(fd, pw, args, opti, dumpCheckin, dumpPackage);
14368         } else if (dumpClient) {
14369             ActiveServices.ServiceDumper sdumper;
14370             synchronized (this) {
14371                 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14372                 pw.println();
14373                 if (dumpAll) {
14374                     pw.println("-------------------------------------------------------------------------------");
14375                 }
14376                 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14377                 pw.println();
14378                 if (dumpAll) {
14379                     pw.println("-------------------------------------------------------------------------------");
14380                 }
14381                 if (dumpAll || dumpPackage != null) {
14382                     dumpBroadcastStatsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14383                     pw.println();
14384                     if (dumpAll) {
14385                         pw.println("-------------------------------------------------------------------------------");
14386                     }
14387                 }
14388                 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14389                 pw.println();
14390                 if (dumpAll) {
14391                     pw.println("-------------------------------------------------------------------------------");
14392                 }
14393                 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14394                 pw.println();
14395                 if (dumpAll) {
14396                     pw.println("-------------------------------------------------------------------------------");
14397                 }
14398                 sdumper = mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll,
14399                         dumpPackage);
14400             }
14401             sdumper.dumpWithClient();
14402             pw.println();
14403             synchronized (this) {
14404                 if (dumpAll) {
14405                     pw.println("-------------------------------------------------------------------------------");
14406                 }
14407                 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14408                 pw.println();
14409                 if (dumpAll) {
14410                     pw.println("-------------------------------------------------------------------------------");
14411                 }
14412                 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage);
14413                 if (mAssociations.size() > 0) {
14414                     pw.println();
14415                     if (dumpAll) {
14416                         pw.println("-------------------------------------------------------------------------------");
14417                     }
14418                     dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage);
14419                 }
14420                 pw.println();
14421                 if (dumpAll) {
14422                     pw.println("-------------------------------------------------------------------------------");
14423                 }
14424                 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14425             }
14426
14427         } else {
14428             synchronized (this) {
14429                 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14430                 pw.println();
14431                 if (dumpAll) {
14432                     pw.println("-------------------------------------------------------------------------------");
14433                 }
14434                 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14435                 pw.println();
14436                 if (dumpAll) {
14437                     pw.println("-------------------------------------------------------------------------------");
14438                 }
14439                 if (dumpAll || dumpPackage != null) {
14440                     dumpBroadcastStatsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14441                     pw.println();
14442                     if (dumpAll) {
14443                         pw.println("-------------------------------------------------------------------------------");
14444                     }
14445                 }
14446                 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14447                 pw.println();
14448                 if (dumpAll) {
14449                     pw.println("-------------------------------------------------------------------------------");
14450                 }
14451                 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14452                 pw.println();
14453                 if (dumpAll) {
14454                     pw.println("-------------------------------------------------------------------------------");
14455                 }
14456                 mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, dumpPackage)
14457                         .dumpLocked();
14458                 pw.println();
14459                 if (dumpAll) {
14460                     pw.println("-------------------------------------------------------------------------------");
14461                 }
14462                 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14463                 pw.println();
14464                 if (dumpAll) {
14465                     pw.println("-------------------------------------------------------------------------------");
14466                 }
14467                 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage);
14468                 if (mAssociations.size() > 0) {
14469                     pw.println();
14470                     if (dumpAll) {
14471                         pw.println("-------------------------------------------------------------------------------");
14472                     }
14473                     dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage);
14474                 }
14475                 pw.println();
14476                 if (dumpAll) {
14477                     pw.println("-------------------------------------------------------------------------------");
14478                 }
14479                 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage);
14480             }
14481         }
14482         Binder.restoreCallingIdentity(origId);
14483     }
14484
14485     void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args,
14486             int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) {
14487         pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)");
14488
14489         boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient,
14490                 dumpPackage);
14491         boolean needSep = printedAnything;
14492
14493         boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity,
14494                 dumpPackage, needSep, "  mFocusedActivity: ");
14495         if (printed) {
14496             printedAnything = true;
14497             needSep = false;
14498         }
14499
14500         if (dumpPackage == null) {
14501             if (needSep) {
14502                 pw.println();
14503             }
14504             needSep = true;
14505             printedAnything = true;
14506             mStackSupervisor.dump(pw, "  ");
14507         }
14508
14509         if (!printedAnything) {
14510             pw.println("  (nothing)");
14511         }
14512     }
14513
14514     void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args,
14515             int opti, boolean dumpAll, String dumpPackage) {
14516         pw.println("ACTIVITY MANAGER RECENT TASKS (dumpsys activity recents)");
14517
14518         boolean printedAnything = false;
14519
14520         if (mRecentTasks != null && mRecentTasks.size() > 0) {
14521             boolean printedHeader = false;
14522
14523             final int N = mRecentTasks.size();
14524             for (int i=0; i<N; i++) {
14525                 TaskRecord tr = mRecentTasks.get(i);
14526                 if (dumpPackage != null) {
14527                     if (tr.realActivity == null ||
14528                             !dumpPackage.equals(tr.realActivity)) {
14529                         continue;
14530                     }
14531                 }
14532                 if (!printedHeader) {
14533                     pw.println("  Recent tasks:");
14534                     printedHeader = true;
14535                     printedAnything = true;
14536                 }
14537                 pw.print("  * Recent #"); pw.print(i); pw.print(": ");
14538                         pw.println(tr);
14539                 if (dumpAll) {
14540                     mRecentTasks.get(i).dump(pw, "    ");
14541                 }
14542             }
14543         }
14544
14545         if (!printedAnything) {
14546             pw.println("  (nothing)");
14547         }
14548     }
14549
14550     void dumpAssociationsLocked(FileDescriptor fd, PrintWriter pw, String[] args,
14551             int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) {
14552         pw.println("ACTIVITY MANAGER ASSOCIATIONS (dumpsys activity associations)");
14553
14554         int dumpUid = 0;
14555         if (dumpPackage != null) {
14556             IPackageManager pm = AppGlobals.getPackageManager();
14557             try {
14558                 dumpUid = pm.getPackageUid(dumpPackage, MATCH_UNINSTALLED_PACKAGES, 0);
14559             } catch (RemoteException e) {
14560             }
14561         }
14562
14563         boolean printedAnything = false;
14564
14565         final long now = SystemClock.uptimeMillis();
14566
14567         for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) {
14568             ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents
14569                     = mAssociations.valueAt(i1);
14570             for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) {
14571                 SparseArray<ArrayMap<String, Association>> sourceUids
14572                         = targetComponents.valueAt(i2);
14573                 for (int i3=0, N3=sourceUids.size(); i3<N3; i3++) {
14574                     ArrayMap<String, Association> sourceProcesses = sourceUids.valueAt(i3);
14575                     for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) {
14576                         Association ass = sourceProcesses.valueAt(i4);
14577                         if (dumpPackage != null) {
14578                             if (!ass.mTargetComponent.getPackageName().equals(dumpPackage)
14579                                     && UserHandle.getAppId(ass.mSourceUid) != dumpUid) {
14580                                 continue;
14581                             }
14582                         }
14583                         printedAnything = true;
14584                         pw.print("  ");
14585                         pw.print(ass.mTargetProcess);
14586                         pw.print("/");
14587                         UserHandle.formatUid(pw, ass.mTargetUid);
14588                         pw.print(" <- ");
14589                         pw.print(ass.mSourceProcess);
14590                         pw.print("/");
14591                         UserHandle.formatUid(pw, ass.mSourceUid);
14592                         pw.println();
14593                         pw.print("    via ");
14594                         pw.print(ass.mTargetComponent.flattenToShortString());
14595                         pw.println();
14596                         pw.print("    ");
14597                         long dur = ass.mTime;
14598                         if (ass.mNesting > 0) {
14599                             dur += now - ass.mStartTime;
14600                         }
14601                         TimeUtils.formatDuration(dur, pw);
14602                         pw.print(" (");
14603                         pw.print(ass.mCount);
14604                         pw.print(" times)");
14605                         pw.print("  ");
14606                         for (int i=0; i<ass.mStateTimes.length; i++) {
14607                             long amt = ass.mStateTimes[i];
14608                             if (ass.mLastState-ActivityManager.MIN_PROCESS_STATE == i) {
14609                                 amt += now - ass.mLastStateUptime;
14610                             }
14611                             if (amt != 0) {
14612                                 pw.print(" ");
14613                                 pw.print(ProcessList.makeProcStateString(
14614                                             i + ActivityManager.MIN_PROCESS_STATE));
14615                                 pw.print("=");
14616                                 TimeUtils.formatDuration(amt, pw);
14617                                 if (ass.mLastState-ActivityManager.MIN_PROCESS_STATE == i) {
14618                                     pw.print("*");
14619                                 }
14620                             }
14621                         }
14622                         pw.println();
14623                         if (ass.mNesting > 0) {
14624                             pw.print("    Currently active: ");
14625                             TimeUtils.formatDuration(now - ass.mStartTime, pw);
14626                             pw.println();
14627                         }
14628                     }
14629                 }
14630             }
14631
14632         }
14633
14634         if (!printedAnything) {
14635             pw.println("  (nothing)");
14636         }
14637     }
14638
14639     boolean dumpUids(PrintWriter pw, String dumpPackage, SparseArray<UidRecord> uids,
14640             String header, boolean needSep) {
14641         boolean printed = false;
14642         int whichAppId = -1;
14643         if (dumpPackage != null) {
14644             try {
14645                 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo(
14646                         dumpPackage, 0);
14647                 whichAppId = UserHandle.getAppId(info.uid);
14648             } catch (NameNotFoundException e) {
14649                 e.printStackTrace();
14650             }
14651         }
14652         for (int i=0; i<uids.size(); i++) {
14653             UidRecord uidRec = uids.valueAt(i);
14654             if (dumpPackage != null && UserHandle.getAppId(uidRec.uid) != whichAppId) {
14655                 continue;
14656             }
14657             if (!printed) {
14658                 printed = true;
14659                 if (needSep) {
14660                     pw.println();
14661                 }
14662                 pw.print("  ");
14663                 pw.println(header);
14664                 needSep = true;
14665             }
14666             pw.print("    UID "); UserHandle.formatUid(pw, uidRec.uid);
14667             pw.print(": "); pw.println(uidRec);
14668         }
14669         return printed;
14670     }
14671
14672     void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args,
14673             int opti, boolean dumpAll, String dumpPackage) {
14674         boolean needSep = false;
14675         boolean printedAnything = false;
14676         int numPers = 0;
14677
14678         pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)");
14679
14680         if (dumpAll) {
14681             final int NP = mProcessNames.getMap().size();
14682             for (int ip=0; ip<NP; ip++) {
14683                 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip);
14684                 final int NA = procs.size();
14685                 for (int ia=0; ia<NA; ia++) {
14686                     ProcessRecord r = procs.valueAt(ia);
14687                     if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) {
14688                         continue;
14689                     }
14690                     if (!needSep) {
14691                         pw.println("  All known processes:");
14692                         needSep = true;
14693                         printedAnything = true;
14694                     }
14695                     pw.print(r.persistent ? "  *PERS*" : "  *APP*");
14696                         pw.print(" UID "); pw.print(procs.keyAt(ia));
14697                         pw.print(" "); pw.println(r);
14698                     r.dump(pw, "    ");
14699                     if (r.persistent) {
14700                         numPers++;
14701                     }
14702                 }
14703             }
14704         }
14705
14706         if (mIsolatedProcesses.size() > 0) {
14707             boolean printed = false;
14708             for (int i=0; i<mIsolatedProcesses.size(); i++) {
14709                 ProcessRecord r = mIsolatedProcesses.valueAt(i);
14710                 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) {
14711                     continue;
14712                 }
14713                 if (!printed) {
14714                     if (needSep) {
14715                         pw.println();
14716                     }
14717                     pw.println("  Isolated process list (sorted by uid):");
14718                     printedAnything = true;
14719                     printed = true;
14720                     needSep = true;
14721                 }
14722                 pw.println(String.format("%sIsolated #%2d: %s",
14723                         "    ", i, r.toString()));
14724             }
14725         }
14726
14727         if (mActiveUids.size() > 0) {
14728             if (dumpUids(pw, dumpPackage, mActiveUids, "UID states:", needSep)) {
14729                 printedAnything = needSep = true;
14730             }
14731         }
14732         if (mValidateUids.size() > 0) {
14733             if (dumpUids(pw, dumpPackage, mValidateUids, "UID validation:", needSep)) {
14734                 printedAnything = needSep = true;
14735             }
14736         }
14737
14738         if (mLruProcesses.size() > 0) {
14739             if (needSep) {
14740                 pw.println();
14741             }
14742             pw.print("  Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size());
14743                     pw.print(" total, non-act at ");
14744                     pw.print(mLruProcesses.size()-mLruProcessActivityStart);
14745                     pw.print(", non-svc at ");
14746                     pw.print(mLruProcesses.size()-mLruProcessServiceStart);
14747                     pw.println("):");
14748             dumpProcessOomList(pw, this, mLruProcesses, "    ", "Proc", "PERS", false, dumpPackage);
14749             needSep = true;
14750             printedAnything = true;
14751         }
14752
14753         if (dumpAll || dumpPackage != null) {
14754             synchronized (mPidsSelfLocked) {
14755                 boolean printed = false;
14756                 for (int i=0; i<mPidsSelfLocked.size(); i++) {
14757                     ProcessRecord r = mPidsSelfLocked.valueAt(i);
14758                     if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) {
14759                         continue;
14760                     }
14761                     if (!printed) {
14762                         if (needSep) pw.println();
14763                         needSep = true;
14764                         pw.println("  PID mappings:");
14765                         printed = true;
14766                         printedAnything = true;
14767                     }
14768                     pw.print("    PID #"); pw.print(mPidsSelfLocked.keyAt(i));
14769                         pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i));
14770                 }
14771             }
14772         }
14773
14774         if (mForegroundProcesses.size() > 0) {
14775             synchronized (mPidsSelfLocked) {
14776                 boolean printed = false;
14777                 for (int i=0; i<mForegroundProcesses.size(); i++) {
14778                     ProcessRecord r = mPidsSelfLocked.get(
14779                             mForegroundProcesses.valueAt(i).pid);
14780                     if (dumpPackage != null && (r == null
14781                             || !r.pkgList.containsKey(dumpPackage))) {
14782                         continue;
14783                     }
14784                     if (!printed) {
14785                         if (needSep) pw.println();
14786                         needSep = true;
14787                         pw.println("  Foreground Processes:");
14788                         printed = true;
14789                         printedAnything = true;
14790                     }
14791                     pw.print("    PID #"); pw.print(mForegroundProcesses.keyAt(i));
14792                             pw.print(": "); pw.println(mForegroundProcesses.valueAt(i));
14793                 }
14794             }
14795         }
14796
14797         if (mPersistentStartingProcesses.size() > 0) {
14798             if (needSep) pw.println();
14799             needSep = true;
14800             printedAnything = true;
14801             pw.println("  Persisent processes that are starting:");
14802             dumpProcessList(pw, this, mPersistentStartingProcesses, "    ",
14803                     "Starting Norm", "Restarting PERS", dumpPackage);
14804         }
14805
14806         if (mRemovedProcesses.size() > 0) {
14807             if (needSep) pw.println();
14808             needSep = true;
14809             printedAnything = true;
14810             pw.println("  Processes that are being removed:");
14811             dumpProcessList(pw, this, mRemovedProcesses, "    ",
14812                     "Removed Norm", "Removed PERS", dumpPackage);
14813         }
14814
14815         if (mProcessesOnHold.size() > 0) {
14816             if (needSep) pw.println();
14817             needSep = true;
14818             printedAnything = true;
14819             pw.println("  Processes that are on old until the system is ready:");
14820             dumpProcessList(pw, this, mProcessesOnHold, "    ",
14821                     "OnHold Norm", "OnHold PERS", dumpPackage);
14822         }
14823
14824         needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage);
14825
14826         needSep = mAppErrors.dumpLocked(fd, pw, needSep, dumpPackage);
14827         if (needSep) {
14828             printedAnything = true;
14829         }
14830
14831         if (dumpPackage == null) {
14832             pw.println();
14833             needSep = false;
14834             mUserController.dump(pw, dumpAll);
14835         }
14836         if (mHomeProcess != null && (dumpPackage == null
14837                 || mHomeProcess.pkgList.containsKey(dumpPackage))) {
14838             if (needSep) {
14839                 pw.println();
14840                 needSep = false;
14841             }
14842             pw.println("  mHomeProcess: " + mHomeProcess);
14843         }
14844         if (mPreviousProcess != null && (dumpPackage == null
14845                 || mPreviousProcess.pkgList.containsKey(dumpPackage))) {
14846             if (needSep) {
14847                 pw.println();
14848                 needSep = false;
14849             }
14850             pw.println("  mPreviousProcess: " + mPreviousProcess);
14851         }
14852         if (dumpAll) {
14853             StringBuilder sb = new StringBuilder(128);
14854             sb.append("  mPreviousProcessVisibleTime: ");
14855             TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb);
14856             pw.println(sb);
14857         }
14858         if (mHeavyWeightProcess != null && (dumpPackage == null
14859                 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) {
14860             if (needSep) {
14861                 pw.println();
14862                 needSep = false;
14863             }
14864             pw.println("  mHeavyWeightProcess: " + mHeavyWeightProcess);
14865         }
14866         if (dumpPackage == null) {
14867             pw.println("  mConfiguration: " + mConfiguration);
14868         }
14869         if (dumpAll) {
14870             pw.println("  mConfigWillChange: " + getFocusedStack().mConfigWillChange);
14871             if (mCompatModePackages.getPackages().size() > 0) {
14872                 boolean printed = false;
14873                 for (Map.Entry<String, Integer> entry
14874                         : mCompatModePackages.getPackages().entrySet()) {
14875                     String pkg = entry.getKey();
14876                     int mode = entry.getValue();
14877                     if (dumpPackage != null && !dumpPackage.equals(pkg)) {
14878                         continue;
14879                     }
14880                     if (!printed) {
14881                         pw.println("  mScreenCompatPackages:");
14882                         printed = true;
14883                     }
14884                     pw.print("    "); pw.print(pkg); pw.print(": ");
14885                             pw.print(mode); pw.println();
14886                 }
14887             }
14888         }
14889         if (dumpPackage == null) {
14890             pw.println("  mWakefulness="
14891                     + PowerManagerInternal.wakefulnessToString(mWakefulness));
14892             pw.println("  mSleepTokens=" + mSleepTokens);
14893             pw.println("  mSleeping=" + mSleeping + " mLockScreenShown="
14894                     + lockScreenShownToString());
14895             pw.println("  mShuttingDown=" + mShuttingDown + " mTestPssMode=" + mTestPssMode);
14896             if (mRunningVoice != null) {
14897                 pw.println("  mRunningVoice=" + mRunningVoice);
14898                 pw.println("  mVoiceWakeLock" + mVoiceWakeLock);
14899             }
14900         }
14901         if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient
14902                 || mOrigWaitForDebugger) {
14903             if (dumpPackage == null || dumpPackage.equals(mDebugApp)
14904                     || dumpPackage.equals(mOrigDebugApp)) {
14905                 if (needSep) {
14906                     pw.println();
14907                     needSep = false;
14908                 }
14909                 pw.println("  mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp
14910                         + " mDebugTransient=" + mDebugTransient
14911                         + " mOrigWaitForDebugger=" + mOrigWaitForDebugger);
14912             }
14913         }
14914         if (mCurAppTimeTracker != null) {
14915             mCurAppTimeTracker.dumpWithHeader(pw, "  ", true);
14916         }
14917         if (mMemWatchProcesses.getMap().size() > 0) {
14918             pw.println("  Mem watch processes:");
14919             final ArrayMap<String, SparseArray<Pair<Long, String>>> procs
14920                     = mMemWatchProcesses.getMap();
14921             for (int i=0; i<procs.size(); i++) {
14922                 final String proc = procs.keyAt(i);
14923                 final SparseArray<Pair<Long, String>> uids = procs.valueAt(i);
14924                 for (int j=0; j<uids.size(); j++) {
14925                     if (needSep) {
14926                         pw.println();
14927                         needSep = false;
14928                     }
14929                     StringBuilder sb = new StringBuilder();
14930                     sb.append("    ").append(proc).append('/');
14931                     UserHandle.formatUid(sb, uids.keyAt(j));
14932                     Pair<Long, String> val = uids.valueAt(j);
14933                     sb.append(": "); DebugUtils.sizeValueToString(val.first, sb);
14934                     if (val.second != null) {
14935                         sb.append(", report to ").append(val.second);
14936                     }
14937                     pw.println(sb.toString());
14938                 }
14939             }
14940             pw.print("  mMemWatchDumpProcName="); pw.println(mMemWatchDumpProcName);
14941             pw.print("  mMemWatchDumpFile="); pw.println(mMemWatchDumpFile);
14942             pw.print("  mMemWatchDumpPid="); pw.print(mMemWatchDumpPid);
14943                     pw.print(" mMemWatchDumpUid="); pw.println(mMemWatchDumpUid);
14944         }
14945         if (mTrackAllocationApp != null) {
14946             if (dumpPackage == null || dumpPackage.equals(mTrackAllocationApp)) {
14947                 if (needSep) {
14948                     pw.println();
14949                     needSep = false;
14950                 }
14951                 pw.println("  mTrackAllocationApp=" + mTrackAllocationApp);
14952             }
14953         }
14954         if (mProfileApp != null || mProfileProc != null || mProfileFile != null
14955                 || mProfileFd != null) {
14956             if (dumpPackage == null || dumpPackage.equals(mProfileApp)) {
14957                 if (needSep) {
14958                     pw.println();
14959                     needSep = false;
14960                 }
14961                 pw.println("  mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc);
14962                 pw.println("  mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd);
14963                 pw.println("  mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler="
14964                         + mAutoStopProfiler);
14965                 pw.println("  mProfileType=" + mProfileType);
14966             }
14967         }
14968         if (mNativeDebuggingApp != null) {
14969             if (dumpPackage == null || dumpPackage.equals(mNativeDebuggingApp)) {
14970                 if (needSep) {
14971                     pw.println();
14972                     needSep = false;
14973                 }
14974                 pw.println("  mNativeDebuggingApp=" + mNativeDebuggingApp);
14975             }
14976         }
14977         if (dumpPackage == null) {
14978             if (mAlwaysFinishActivities || mLenientBackgroundCheck) {
14979                 pw.println("  mAlwaysFinishActivities=" + mAlwaysFinishActivities
14980                         + " mLenientBackgroundCheck=" + mLenientBackgroundCheck);
14981             }
14982             if (mController != null) {
14983                 pw.println("  mController=" + mController
14984                         + " mControllerIsAMonkey=" + mControllerIsAMonkey);
14985             }
14986             if (dumpAll) {
14987                 pw.println("  Total persistent processes: " + numPers);
14988                 pw.println("  mProcessesReady=" + mProcessesReady
14989                         + " mSystemReady=" + mSystemReady
14990                         + " mBooted=" + mBooted
14991                         + " mFactoryTest=" + mFactoryTest);
14992                 pw.println("  mBooting=" + mBooting
14993                         + " mCallFinishBooting=" + mCallFinishBooting
14994                         + " mBootAnimationComplete=" + mBootAnimationComplete);
14995                 pw.print("  mLastPowerCheckRealtime=");
14996                         TimeUtils.formatDuration(mLastPowerCheckRealtime, pw);
14997                         pw.println("");
14998                 pw.print("  mLastPowerCheckUptime=");
14999                         TimeUtils.formatDuration(mLastPowerCheckUptime, pw);
15000                         pw.println("");
15001                 pw.println("  mGoingToSleep=" + mStackSupervisor.mGoingToSleep);
15002                 pw.println("  mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity);
15003                 pw.println("  mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq);
15004                 pw.println("  mNumNonCachedProcs=" + mNumNonCachedProcs
15005                         + " (" + mLruProcesses.size() + " total)"
15006                         + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs
15007                         + " mNumServiceProcs=" + mNumServiceProcs
15008                         + " mNewNumServiceProcs=" + mNewNumServiceProcs);
15009                 pw.println("  mAllowLowerMemLevel=" + mAllowLowerMemLevel
15010                         + " mLastMemoryLevel=" + mLastMemoryLevel
15011                         + " mLastNumProcesses=" + mLastNumProcesses);
15012                 long now = SystemClock.uptimeMillis();
15013                 pw.print("  mLastIdleTime=");
15014                         TimeUtils.formatDuration(now, mLastIdleTime, pw);
15015                         pw.print(" mLowRamSinceLastIdle=");
15016                         TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw);
15017                         pw.println();
15018             }
15019         }
15020
15021         if (!printedAnything) {
15022             pw.println("  (nothing)");
15023         }
15024     }
15025
15026     boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args,
15027             int opti, boolean needSep, boolean dumpAll, String dumpPackage) {
15028         if (mProcessesToGc.size() > 0) {
15029             boolean printed = false;
15030             long now = SystemClock.uptimeMillis();
15031             for (int i=0; i<mProcessesToGc.size(); i++) {
15032                 ProcessRecord proc = mProcessesToGc.get(i);
15033                 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) {
15034                     continue;
15035                 }
15036                 if (!printed) {
15037                     if (needSep) pw.println();
15038                     needSep = true;
15039                     pw.println("  Processes that are waiting to GC:");
15040                     printed = true;
15041                 }
15042                 pw.print("    Process "); pw.println(proc);
15043                 pw.print("      lowMem="); pw.print(proc.reportLowMemory);
15044                         pw.print(", last gced=");
15045                         pw.print(now-proc.lastRequestedGc);
15046                         pw.print(" ms ago, last lowMem=");
15047                         pw.print(now-proc.lastLowMemory);
15048                         pw.println(" ms ago");
15049
15050             }
15051         }
15052         return needSep;
15053     }
15054
15055     void printOomLevel(PrintWriter pw, String name, int adj) {
15056         pw.print("    ");
15057         if (adj >= 0) {
15058             pw.print(' ');
15059             if (adj < 10) pw.print(' ');
15060         } else {
15061             if (adj > -10) pw.print(' ');
15062         }
15063         pw.print(adj);
15064         pw.print(": ");
15065         pw.print(name);
15066         pw.print(" (");
15067         pw.print(stringifySize(mProcessList.getMemLevel(adj), 1024));
15068         pw.println(")");
15069     }
15070
15071     boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15072             int opti, boolean dumpAll) {
15073         boolean needSep = false;
15074
15075         if (mLruProcesses.size() > 0) {
15076             if (needSep) pw.println();
15077             needSep = true;
15078             pw.println("  OOM levels:");
15079             printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ);
15080             printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ);
15081             printOomLevel(pw, "PERSISTENT_SERVICE_ADJ", ProcessList.PERSISTENT_SERVICE_ADJ);
15082             printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ);
15083             printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ);
15084             printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ);
15085             printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ);
15086             printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ);
15087             printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ);
15088             printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ);
15089             printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ);
15090             printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ);
15091             printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ);
15092             printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ);
15093
15094             if (needSep) pw.println();
15095             pw.print("  Process OOM control ("); pw.print(mLruProcesses.size());
15096                     pw.print(" total, non-act at ");
15097                     pw.print(mLruProcesses.size()-mLruProcessActivityStart);
15098                     pw.print(", non-svc at ");
15099                     pw.print(mLruProcesses.size()-mLruProcessServiceStart);
15100                     pw.println("):");
15101             dumpProcessOomList(pw, this, mLruProcesses, "    ", "Proc", "PERS", true, null);
15102             needSep = true;
15103         }
15104
15105         dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null);
15106
15107         pw.println();
15108         pw.println("  mHomeProcess: " + mHomeProcess);
15109         pw.println("  mPreviousProcess: " + mPreviousProcess);
15110         if (mHeavyWeightProcess != null) {
15111             pw.println("  mHeavyWeightProcess: " + mHeavyWeightProcess);
15112         }
15113
15114         return true;
15115     }
15116
15117     /**
15118      * There are three ways to call this:
15119      *  - no provider specified: dump all the providers
15120      *  - a flattened component name that matched an existing provider was specified as the
15121      *    first arg: dump that one provider
15122      *  - the first arg isn't the flattened component name of an existing provider:
15123      *    dump all providers whose component contains the first arg as a substring
15124      */
15125     protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args,
15126             int opti, boolean dumpAll) {
15127         return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll);
15128     }
15129
15130     static class ItemMatcher {
15131         ArrayList<ComponentName> components;
15132         ArrayList<String> strings;
15133         ArrayList<Integer> objects;
15134         boolean all;
15135
15136         ItemMatcher() {
15137             all = true;
15138         }
15139
15140         void build(String name) {
15141             ComponentName componentName = ComponentName.unflattenFromString(name);
15142             if (componentName != null) {
15143                 if (components == null) {
15144                     components = new ArrayList<ComponentName>();
15145                 }
15146                 components.add(componentName);
15147                 all = false;
15148             } else {
15149                 int objectId = 0;
15150                 // Not a '/' separated full component name; maybe an object ID?
15151                 try {
15152                     objectId = Integer.parseInt(name, 16);
15153                     if (objects == null) {
15154                         objects = new ArrayList<Integer>();
15155                     }
15156                     objects.add(objectId);
15157                     all = false;
15158                 } catch (RuntimeException e) {
15159                     // Not an integer; just do string match.
15160                     if (strings == null) {
15161                         strings = new ArrayList<String>();
15162                     }
15163                     strings.add(name);
15164                     all = false;
15165                 }
15166             }
15167         }
15168
15169         int build(String[] args, int opti) {
15170             for (; opti<args.length; opti++) {
15171                 String name = args[opti];
15172                 if ("--".equals(name)) {
15173                     return opti+1;
15174                 }
15175                 build(name);
15176             }
15177             return opti;
15178         }
15179
15180         boolean match(Object object, ComponentName comp) {
15181             if (all) {
15182                 return true;
15183             }
15184             if (components != null) {
15185                 for (int i=0; i<components.size(); i++) {
15186                     if (components.get(i).equals(comp)) {
15187                         return true;
15188                     }
15189                 }
15190             }
15191             if (objects != null) {
15192                 for (int i=0; i<objects.size(); i++) {
15193                     if (System.identityHashCode(object) == objects.get(i)) {
15194                         return true;
15195                     }
15196                 }
15197             }
15198             if (strings != null) {
15199                 String flat = comp.flattenToString();
15200                 for (int i=0; i<strings.size(); i++) {
15201                     if (flat.contains(strings.get(i))) {
15202                         return true;
15203                     }
15204                 }
15205             }
15206             return false;
15207         }
15208     }
15209
15210     /**
15211      * There are three things that cmd can be:
15212      *  - a flattened component name that matches an existing activity
15213      *  - the cmd arg isn't the flattened component name of an existing activity:
15214      *    dump all activity whose component contains the cmd as a substring
15215      *  - A hex number of the ActivityRecord object instance.
15216      */
15217     protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args,
15218             int opti, boolean dumpAll) {
15219         ArrayList<ActivityRecord> activities;
15220
15221         synchronized (this) {
15222             activities = mStackSupervisor.getDumpActivitiesLocked(name);
15223         }
15224
15225         if (activities.size() <= 0) {
15226             return false;
15227         }
15228
15229         String[] newArgs = new String[args.length - opti];
15230         System.arraycopy(args, opti, newArgs, 0, args.length - opti);
15231
15232         TaskRecord lastTask = null;
15233         boolean needSep = false;
15234         for (int i=activities.size()-1; i>=0; i--) {
15235             ActivityRecord r = activities.get(i);
15236             if (needSep) {
15237                 pw.println();
15238             }
15239             needSep = true;
15240             synchronized (this) {
15241                 if (lastTask != r.task) {
15242                     lastTask = r.task;
15243                     pw.print("TASK "); pw.print(lastTask.affinity);
15244                             pw.print(" id="); pw.println(lastTask.taskId);
15245                     if (dumpAll) {
15246                         lastTask.dump(pw, "  ");
15247                     }
15248                 }
15249             }
15250             dumpActivity("  ", fd, pw, activities.get(i), newArgs, dumpAll);
15251         }
15252         return true;
15253     }
15254
15255     /**
15256      * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if
15257      * there is a thread associated with the activity.
15258      */
15259     private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw,
15260             final ActivityRecord r, String[] args, boolean dumpAll) {
15261         String innerPrefix = prefix + "  ";
15262         synchronized (this) {
15263             pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName);
15264                     pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r)));
15265                     pw.print(" pid=");
15266                     if (r.app != null) pw.println(r.app.pid);
15267                     else pw.println("(not running)");
15268             if (dumpAll) {
15269                 r.dump(pw, innerPrefix);
15270             }
15271         }
15272         if (r.app != null && r.app.thread != null) {
15273             // flush anything that is already in the PrintWriter since the thread is going
15274             // to write to the file descriptor directly
15275             pw.flush();
15276             try {
15277                 TransferPipe tp = new TransferPipe();
15278                 try {
15279                     r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(),
15280                             r.appToken, innerPrefix, args);
15281                     tp.go(fd);
15282                 } finally {
15283                     tp.kill();
15284                 }
15285             } catch (IOException e) {
15286                 pw.println(innerPrefix + "Failure while dumping the activity: " + e);
15287             } catch (RemoteException e) {
15288                 pw.println(innerPrefix + "Got a RemoteException while dumping the activity");
15289             }
15290         }
15291     }
15292
15293     void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15294             int opti, boolean dumpAll, String dumpPackage) {
15295         boolean needSep = false;
15296         boolean onlyHistory = false;
15297         boolean printedAnything = false;
15298
15299         if ("history".equals(dumpPackage)) {
15300             if (opti < args.length && "-s".equals(args[opti])) {
15301                 dumpAll = false;
15302             }
15303             onlyHistory = true;
15304             dumpPackage = null;
15305         }
15306
15307         pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)");
15308         if (!onlyHistory && dumpAll) {
15309             if (mRegisteredReceivers.size() > 0) {
15310                 boolean printed = false;
15311                 Iterator it = mRegisteredReceivers.values().iterator();
15312                 while (it.hasNext()) {
15313                     ReceiverList r = (ReceiverList)it.next();
15314                     if (dumpPackage != null && (r.app == null ||
15315                             !dumpPackage.equals(r.app.info.packageName))) {
15316                         continue;
15317                     }
15318                     if (!printed) {
15319                         pw.println("  Registered Receivers:");
15320                         needSep = true;
15321                         printed = true;
15322                         printedAnything = true;
15323                     }
15324                     pw.print("  * "); pw.println(r);
15325                     r.dump(pw, "    ");
15326                 }
15327             }
15328
15329             if (mReceiverResolver.dump(pw, needSep ?
15330                     "\n  Receiver Resolver Table:" : "  Receiver Resolver Table:",
15331                     "    ", dumpPackage, false, false)) {
15332                 needSep = true;
15333                 printedAnything = true;
15334             }
15335         }
15336
15337         for (BroadcastQueue q : mBroadcastQueues) {
15338             needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep);
15339             printedAnything |= needSep;
15340         }
15341
15342         needSep = true;
15343
15344         if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) {
15345             for (int user=0; user<mStickyBroadcasts.size(); user++) {
15346                 if (needSep) {
15347                     pw.println();
15348                 }
15349                 needSep = true;
15350                 printedAnything = true;
15351                 pw.print("  Sticky broadcasts for user ");
15352                         pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":");
15353                 StringBuilder sb = new StringBuilder(128);
15354                 for (Map.Entry<String, ArrayList<Intent>> ent
15355                         : mStickyBroadcasts.valueAt(user).entrySet()) {
15356                     pw.print("  * Sticky action "); pw.print(ent.getKey());
15357                     if (dumpAll) {
15358                         pw.println(":");
15359                         ArrayList<Intent> intents = ent.getValue();
15360                         final int N = intents.size();
15361                         for (int i=0; i<N; i++) {
15362                             sb.setLength(0);
15363                             sb.append("    Intent: ");
15364                             intents.get(i).toShortString(sb, false, true, false, false);
15365                             pw.println(sb.toString());
15366                             Bundle bundle = intents.get(i).getExtras();
15367                             if (bundle != null) {
15368                                 pw.print("      ");
15369                                 pw.println(bundle.toString());
15370                             }
15371                         }
15372                     } else {
15373                         pw.println("");
15374                     }
15375                 }
15376             }
15377         }
15378
15379         if (!onlyHistory && dumpAll) {
15380             pw.println();
15381             for (BroadcastQueue queue : mBroadcastQueues) {
15382                 pw.println("  mBroadcastsScheduled [" + queue.mQueueName + "]="
15383                         + queue.mBroadcastsScheduled);
15384             }
15385             pw.println("  mHandler:");
15386             mHandler.dump(new PrintWriterPrinter(pw), "    ");
15387             needSep = true;
15388             printedAnything = true;
15389         }
15390
15391         if (!printedAnything) {
15392             pw.println("  (nothing)");
15393         }
15394     }
15395
15396     void dumpBroadcastStatsLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15397             int opti, boolean dumpAll, String dumpPackage) {
15398         if (mCurBroadcastStats == null) {
15399             return;
15400         }
15401
15402         pw.println("ACTIVITY MANAGER BROADCAST STATS STATE (dumpsys activity broadcast-stats)");
15403         final long now = SystemClock.elapsedRealtime();
15404         if (mLastBroadcastStats != null) {
15405             pw.print("  Last stats (from ");
15406             TimeUtils.formatDuration(mLastBroadcastStats.mStartRealtime, now, pw);
15407             pw.print(" to ");
15408             TimeUtils.formatDuration(mLastBroadcastStats.mEndRealtime, now, pw);
15409             pw.print(", ");
15410             TimeUtils.formatDuration(mLastBroadcastStats.mEndUptime
15411                     - mLastBroadcastStats.mStartUptime, pw);
15412             pw.println(" uptime):");
15413             if (!mLastBroadcastStats.dumpStats(pw, "    ", dumpPackage)) {
15414                 pw.println("    (nothing)");
15415             }
15416             pw.println();
15417         }
15418         pw.print("  Current stats (from ");
15419         TimeUtils.formatDuration(mCurBroadcastStats.mStartRealtime, now, pw);
15420         pw.print(" to now, ");
15421         TimeUtils.formatDuration(SystemClock.uptimeMillis()
15422                 - mCurBroadcastStats.mStartUptime, pw);
15423         pw.println(" uptime):");
15424         if (!mCurBroadcastStats.dumpStats(pw, "    ", dumpPackage)) {
15425             pw.println("    (nothing)");
15426         }
15427     }
15428
15429     void dumpBroadcastStatsCheckinLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15430             int opti, boolean fullCheckin, String dumpPackage) {
15431         if (mCurBroadcastStats == null) {
15432             return;
15433         }
15434
15435         if (mLastBroadcastStats != null) {
15436             mLastBroadcastStats.dumpCheckinStats(pw, dumpPackage);
15437             if (fullCheckin) {
15438                 mLastBroadcastStats = null;
15439                 return;
15440             }
15441         }
15442         mCurBroadcastStats.dumpCheckinStats(pw, dumpPackage);
15443         if (fullCheckin) {
15444             mCurBroadcastStats = null;
15445         }
15446     }
15447
15448     void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15449             int opti, boolean dumpAll, String dumpPackage) {
15450         boolean needSep;
15451         boolean printedAnything = false;
15452
15453         ItemMatcher matcher = new ItemMatcher();
15454         matcher.build(args, opti);
15455
15456         pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)");
15457
15458         needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage);
15459         printedAnything |= needSep;
15460
15461         if (mLaunchingProviders.size() > 0) {
15462             boolean printed = false;
15463             for (int i=mLaunchingProviders.size()-1; i>=0; i--) {
15464                 ContentProviderRecord r = mLaunchingProviders.get(i);
15465                 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) {
15466                     continue;
15467                 }
15468                 if (!printed) {
15469                     if (needSep) pw.println();
15470                     needSep = true;
15471                     pw.println("  Launching content providers:");
15472                     printed = true;
15473                     printedAnything = true;
15474                 }
15475                 pw.print("  Launching #"); pw.print(i); pw.print(": ");
15476                         pw.println(r);
15477             }
15478         }
15479
15480         if (!printedAnything) {
15481             pw.println("  (nothing)");
15482         }
15483     }
15484
15485     void dumpPermissionsLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15486             int opti, boolean dumpAll, String dumpPackage) {
15487         boolean needSep = false;
15488         boolean printedAnything = false;
15489
15490         pw.println("ACTIVITY MANAGER URI PERMISSIONS (dumpsys activity permissions)");
15491
15492         if (mGrantedUriPermissions.size() > 0) {
15493             boolean printed = false;
15494             int dumpUid = -2;
15495             if (dumpPackage != null) {
15496                 try {
15497                     dumpUid = mContext.getPackageManager().getPackageUidAsUser(dumpPackage,
15498                             MATCH_UNINSTALLED_PACKAGES, 0);
15499                 } catch (NameNotFoundException e) {
15500                     dumpUid = -1;
15501                 }
15502             }
15503             for (int i=0; i<mGrantedUriPermissions.size(); i++) {
15504                 int uid = mGrantedUriPermissions.keyAt(i);
15505                 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) {
15506                     continue;
15507                 }
15508                 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i);
15509                 if (!printed) {
15510                     if (needSep) pw.println();
15511                     needSep = true;
15512                     pw.println("  Granted Uri Permissions:");
15513                     printed = true;
15514                     printedAnything = true;
15515                 }
15516                 pw.print("  * UID "); pw.print(uid); pw.println(" holds:");
15517                 for (UriPermission perm : perms.values()) {
15518                     pw.print("    "); pw.println(perm);
15519                     if (dumpAll) {
15520                         perm.dump(pw, "      ");
15521                     }
15522                 }
15523             }
15524         }
15525
15526         if (!printedAnything) {
15527             pw.println("  (nothing)");
15528         }
15529     }
15530
15531     void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args,
15532             int opti, boolean dumpAll, String dumpPackage) {
15533         boolean printed = false;
15534
15535         pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)");
15536
15537         if (mIntentSenderRecords.size() > 0) {
15538             Iterator<WeakReference<PendingIntentRecord>> it
15539                     = mIntentSenderRecords.values().iterator();
15540             while (it.hasNext()) {
15541                 WeakReference<PendingIntentRecord> ref = it.next();
15542                 PendingIntentRecord rec = ref != null ? ref.get(): null;
15543                 if (dumpPackage != null && (rec == null
15544                         || !dumpPackage.equals(rec.key.packageName))) {
15545                     continue;
15546                 }
15547                 printed = true;
15548                 if (rec != null) {
15549                     pw.print("  * "); pw.println(rec);
15550                     if (dumpAll) {
15551                         rec.dump(pw, "    ");
15552                     }
15553                 } else {
15554                     pw.print("  * "); pw.println(ref);
15555                 }
15556             }
15557         }
15558
15559         if (!printed) {
15560             pw.println("  (nothing)");
15561         }
15562     }
15563
15564     private static final int dumpProcessList(PrintWriter pw,
15565             ActivityManagerService service, List list,
15566             String prefix, String normalLabel, String persistentLabel,
15567             String dumpPackage) {
15568         int numPers = 0;
15569         final int N = list.size()-1;
15570         for (int i=N; i>=0; i--) {
15571             ProcessRecord r = (ProcessRecord)list.get(i);
15572             if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) {
15573                 continue;
15574             }
15575             pw.println(String.format("%s%s #%2d: %s",
15576                     prefix, (r.persistent ? persistentLabel : normalLabel),
15577                     i, r.toString()));
15578             if (r.persistent) {
15579                 numPers++;
15580             }
15581         }
15582         return numPers;
15583     }
15584
15585     private static final boolean dumpProcessOomList(PrintWriter pw,
15586             ActivityManagerService service, List<ProcessRecord> origList,
15587             String prefix, String normalLabel, String persistentLabel,
15588             boolean inclDetails, String dumpPackage) {
15589
15590         ArrayList<Pair<ProcessRecord, Integer>> list
15591                 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size());
15592         for (int i=0; i<origList.size(); i++) {
15593             ProcessRecord r = origList.get(i);
15594             if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) {
15595                 continue;
15596             }
15597             list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i));
15598         }
15599
15600         if (list.size() <= 0) {
15601             return false;
15602         }
15603
15604         Comparator<Pair<ProcessRecord, Integer>> comparator
15605                 = new Comparator<Pair<ProcessRecord, Integer>>() {
15606             @Override
15607             public int compare(Pair<ProcessRecord, Integer> object1,
15608                     Pair<ProcessRecord, Integer> object2) {
15609                 if (object1.first.setAdj != object2.first.setAdj) {
15610                     return object1.first.setAdj > object2.first.setAdj ? -1 : 1;
15611                 }
15612                 if (object1.first.setProcState != object2.first.setProcState) {
15613                     return object1.first.setProcState > object2.first.setProcState ? -1 : 1;
15614                 }
15615                 if (object1.second.intValue() != object2.second.intValue()) {
15616                     return object1.second.intValue() > object2.second.intValue() ? -1 : 1;
15617                 }
15618                 return 0;
15619             }
15620         };
15621
15622         Collections.sort(list, comparator);
15623
15624         final long curRealtime = SystemClock.elapsedRealtime();
15625         final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime;
15626         final long curUptime = SystemClock.uptimeMillis();
15627         final long uptimeSince = curUptime - service.mLastPowerCheckUptime;
15628
15629         for (int i=list.size()-1; i>=0; i--) {
15630             ProcessRecord r = list.get(i).first;
15631             String oomAdj = ProcessList.makeOomAdjString(r.setAdj);
15632             char schedGroup;
15633             switch (r.setSchedGroup) {
15634                 case ProcessList.SCHED_GROUP_BACKGROUND:
15635                     schedGroup = 'B';
15636                     break;
15637                 case ProcessList.SCHED_GROUP_DEFAULT:
15638                     schedGroup = 'F';
15639                     break;
15640                 case ProcessList.SCHED_GROUP_TOP_APP:
15641                     schedGroup = 'T';
15642                     break;
15643                 default:
15644                     schedGroup = '?';
15645                     break;
15646             }
15647             char foreground;
15648             if (r.foregroundActivities) {
15649                 foreground = 'A';
15650             } else if (r.foregroundServices) {
15651                 foreground = 'S';
15652             } else {
15653                 foreground = ' ';
15654             }
15655             String procState = ProcessList.makeProcStateString(r.curProcState);
15656             pw.print(prefix);
15657             pw.print(r.persistent ? persistentLabel : normalLabel);
15658             pw.print(" #");
15659             int num = (origList.size()-1)-list.get(i).second;
15660             if (num < 10) pw.print(' ');
15661             pw.print(num);
15662             pw.print(": ");
15663             pw.print(oomAdj);
15664             pw.print(' ');
15665             pw.print(schedGroup);
15666             pw.print('/');
15667             pw.print(foreground);
15668             pw.print('/');
15669             pw.print(procState);
15670             pw.print(" trm:");
15671             if (r.trimMemoryLevel < 10) pw.print(' ');
15672             pw.print(r.trimMemoryLevel);
15673             pw.print(' ');
15674             pw.print(r.toShortString());
15675             pw.print(" (");
15676             pw.print(r.adjType);
15677             pw.println(')');
15678             if (r.adjSource != null || r.adjTarget != null) {
15679                 pw.print(prefix);
15680                 pw.print("    ");
15681                 if (r.adjTarget instanceof ComponentName) {
15682                     pw.print(((ComponentName)r.adjTarget).flattenToShortString());
15683                 } else if (r.adjTarget != null) {
15684                     pw.print(r.adjTarget.toString());
15685                 } else {
15686                     pw.print("{null}");
15687                 }
15688                 pw.print("<=");
15689                 if (r.adjSource instanceof ProcessRecord) {
15690                     pw.print("Proc{");
15691                     pw.print(((ProcessRecord)r.adjSource).toShortString());
15692                     pw.println("}");
15693                 } else if (r.adjSource != null) {
15694                     pw.println(r.adjSource.toString());
15695                 } else {
15696                     pw.println("{null}");
15697                 }
15698             }
15699             if (inclDetails) {
15700                 pw.print(prefix);
15701                 pw.print("    ");
15702                 pw.print("oom: max="); pw.print(r.maxAdj);
15703                 pw.print(" curRaw="); pw.print(r.curRawAdj);
15704                 pw.print(" setRaw="); pw.print(r.setRawAdj);
15705                 pw.print(" cur="); pw.print(r.curAdj);
15706                 pw.print(" set="); pw.println(r.setAdj);
15707                 pw.print(prefix);
15708                 pw.print("    ");
15709                 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState));
15710                 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState));
15711                 pw.print(" lastPss="); DebugUtils.printSizeValue(pw, r.lastPss*1024);
15712                 pw.print(" lastSwapPss="); DebugUtils.printSizeValue(pw, r.lastSwapPss*1024);
15713                 pw.print(" lastCachedPss="); DebugUtils.printSizeValue(pw, r.lastCachedPss*1024);
15714                 pw.println();
15715                 pw.print(prefix);
15716                 pw.print("    ");
15717                 pw.print("cached="); pw.print(r.cached);
15718                 pw.print(" empty="); pw.print(r.empty);
15719                 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient);
15720
15721                 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) {
15722                     if (r.lastWakeTime != 0) {
15723                         long wtime;
15724                         BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics();
15725                         synchronized (stats) {
15726                             wtime = stats.getProcessWakeTime(r.info.uid,
15727                                     r.pid, curRealtime);
15728                         }
15729                         long timeUsed = wtime - r.lastWakeTime;
15730                         pw.print(prefix);
15731                         pw.print("    ");
15732                         pw.print("keep awake over ");
15733                         TimeUtils.formatDuration(realtimeSince, pw);
15734                         pw.print(" used ");
15735                         TimeUtils.formatDuration(timeUsed, pw);
15736                         pw.print(" (");
15737                         pw.print((timeUsed*100)/realtimeSince);
15738                         pw.println("%)");
15739                     }
15740                     if (r.lastCpuTime != 0) {
15741                         long timeUsed = r.curCpuTime - r.lastCpuTime;
15742                         pw.print(prefix);
15743                         pw.print("    ");
15744                         pw.print("run cpu over ");
15745                         TimeUtils.formatDuration(uptimeSince, pw);
15746                         pw.print(" used ");
15747                         TimeUtils.formatDuration(timeUsed, pw);
15748                         pw.print(" (");
15749                         pw.print((timeUsed*100)/uptimeSince);
15750                         pw.println("%)");
15751                     }
15752                 }
15753             }
15754         }
15755         return true;
15756     }
15757
15758     ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, boolean allPkgs,
15759             String[] args) {
15760         ArrayList<ProcessRecord> procs;
15761         synchronized (this) {
15762             if (args != null && args.length > start
15763                     && args[start].charAt(0) != '-') {
15764                 procs = new ArrayList<ProcessRecord>();
15765                 int pid = -1;
15766                 try {
15767                     pid = Integer.parseInt(args[start]);
15768                 } catch (NumberFormatException e) {
15769                 }
15770                 for (int i=mLruProcesses.size()-1; i>=0; i--) {
15771                     ProcessRecord proc = mLruProcesses.get(i);
15772                     if (proc.pid == pid) {
15773                         procs.add(proc);
15774                     } else if (allPkgs && proc.pkgList != null
15775                             && proc.pkgList.containsKey(args[start])) {
15776                         procs.add(proc);
15777                     } else if (proc.processName.equals(args[start])) {
15778                         procs.add(proc);
15779                     }
15780                 }
15781                 if (procs.size() <= 0) {
15782                     return null;
15783                 }
15784             } else {
15785                 procs = new ArrayList<ProcessRecord>(mLruProcesses);
15786             }
15787         }
15788         return procs;
15789     }
15790
15791     final void dumpGraphicsHardwareUsage(FileDescriptor fd,
15792             PrintWriter pw, String[] args) {
15793         ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args);
15794         if (procs == null) {
15795             pw.println("No process found for: " + args[0]);
15796             return;
15797         }
15798
15799         long uptime = SystemClock.uptimeMillis();
15800         long realtime = SystemClock.elapsedRealtime();
15801         pw.println("Applications Graphics Acceleration Info:");
15802         pw.println("Uptime: " + uptime + " Realtime: " + realtime);
15803
15804         for (int i = procs.size() - 1 ; i >= 0 ; i--) {
15805             ProcessRecord r = procs.get(i);
15806             if (r.thread != null) {
15807                 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **");
15808                 pw.flush();
15809                 try {
15810                     TransferPipe tp = new TransferPipe();
15811                     try {
15812                         r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args);
15813                         tp.go(fd);
15814                     } finally {
15815                         tp.kill();
15816                     }
15817                 } catch (IOException e) {
15818                     pw.println("Failure while dumping the app: " + r);
15819                     pw.flush();
15820                 } catch (RemoteException e) {
15821                     pw.println("Got a RemoteException while dumping the app " + r);
15822                     pw.flush();
15823                 }
15824             }
15825         }
15826     }
15827
15828     final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) {
15829         ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args);
15830         if (procs == null) {
15831             pw.println("No process found for: " + args[0]);
15832             return;
15833         }
15834
15835         pw.println("Applications Database Info:");
15836
15837         for (int i = procs.size() - 1 ; i >= 0 ; i--) {
15838             ProcessRecord r = procs.get(i);
15839             if (r.thread != null) {
15840                 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **");
15841                 pw.flush();
15842                 try {
15843                     TransferPipe tp = new TransferPipe();
15844                     try {
15845                         r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args);
15846                         tp.go(fd);
15847                     } finally {
15848                         tp.kill();
15849                     }
15850                 } catch (IOException e) {
15851                     pw.println("Failure while dumping the app: " + r);
15852                     pw.flush();
15853                 } catch (RemoteException e) {
15854                     pw.println("Got a RemoteException while dumping the app " + r);
15855                     pw.flush();
15856                 }
15857             }
15858         }
15859     }
15860
15861     final static class MemItem {
15862         final boolean isProc;
15863         final String label;
15864         final String shortLabel;
15865         final long pss;
15866         final long swapPss;
15867         final int id;
15868         final boolean hasActivities;
15869         ArrayList<MemItem> subitems;
15870
15871         public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id,
15872                 boolean _hasActivities) {
15873             isProc = true;
15874             label = _label;
15875             shortLabel = _shortLabel;
15876             pss = _pss;
15877             swapPss = _swapPss;
15878             id = _id;
15879             hasActivities = _hasActivities;
15880         }
15881
15882         public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id) {
15883             isProc = false;
15884             label = _label;
15885             shortLabel = _shortLabel;
15886             pss = _pss;
15887             swapPss = _swapPss;
15888             id = _id;
15889             hasActivities = false;
15890         }
15891     }
15892
15893     static final void dumpMemItems(PrintWriter pw, String prefix, String tag,
15894             ArrayList<MemItem> items, boolean sort, boolean isCompact, boolean dumpSwapPss) {
15895         if (sort && !isCompact) {
15896             Collections.sort(items, new Comparator<MemItem>() {
15897                 @Override
15898                 public int compare(MemItem lhs, MemItem rhs) {
15899                     if (lhs.pss < rhs.pss) {
15900                         return 1;
15901                     } else if (lhs.pss > rhs.pss) {
15902                         return -1;
15903                     }
15904                     return 0;
15905                 }
15906             });
15907         }
15908
15909         for (int i=0; i<items.size(); i++) {
15910             MemItem mi = items.get(i);
15911             if (!isCompact) {
15912                 if (dumpSwapPss) {
15913                     pw.printf("%s%s: %-60s (%s in swap)\n", prefix, stringifyKBSize(mi.pss),
15914                             mi.label, stringifyKBSize(mi.swapPss));
15915                 } else {
15916                     pw.printf("%s%s: %s\n", prefix, stringifyKBSize(mi.pss), mi.label);
15917                 }
15918             } else if (mi.isProc) {
15919                 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel);
15920                 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); pw.print(",");
15921                 pw.print(dumpSwapPss ? mi.swapPss : "N/A");
15922                 pw.println(mi.hasActivities ? ",a" : ",e");
15923             } else {
15924                 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(",");
15925                 pw.print(mi.pss); pw.print(","); pw.println(dumpSwapPss ? mi.swapPss : "N/A");
15926             }
15927             if (mi.subitems != null) {
15928                 dumpMemItems(pw, prefix + "    ", mi.shortLabel, mi.subitems,
15929                         true, isCompact, dumpSwapPss);
15930             }
15931         }
15932     }
15933
15934     // These are in KB.
15935     static final long[] DUMP_MEM_BUCKETS = new long[] {
15936         5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024,
15937         120*1024, 160*1024, 200*1024,
15938         250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024,
15939         1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024
15940     };
15941
15942     static final void appendMemBucket(StringBuilder out, long memKB, String label,
15943             boolean stackLike) {
15944         int start = label.lastIndexOf('.');
15945         if (start >= 0) start++;
15946         else start = 0;
15947         int end = label.length();
15948         for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) {
15949             if (DUMP_MEM_BUCKETS[i] >= memKB) {
15950                 long bucket = DUMP_MEM_BUCKETS[i]/1024;
15951                 out.append(bucket);
15952                 out.append(stackLike ? "MB." : "MB ");
15953                 out.append(label, start, end);
15954                 return;
15955             }
15956         }
15957         out.append(memKB/1024);
15958         out.append(stackLike ? "MB." : "MB ");
15959         out.append(label, start, end);
15960     }
15961
15962     static final int[] DUMP_MEM_OOM_ADJ = new int[] {
15963             ProcessList.NATIVE_ADJ,
15964             ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ,
15965             ProcessList.PERSISTENT_SERVICE_ADJ, ProcessList.FOREGROUND_APP_ADJ,
15966             ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ,
15967             ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ,
15968             ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ,
15969             ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MIN_ADJ
15970     };
15971     static final String[] DUMP_MEM_OOM_LABEL = new String[] {
15972             "Native",
15973             "System", "Persistent", "Persistent Service", "Foreground",
15974             "Visible", "Perceptible",
15975             "Heavy Weight", "Backup",
15976             "A Services", "Home",
15977             "Previous", "B Services", "Cached"
15978     };
15979     static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] {
15980             "native",
15981             "sys", "pers", "persvc", "fore",
15982             "vis", "percept",
15983             "heavy", "backup",
15984             "servicea", "home",
15985             "prev", "serviceb", "cached"
15986     };
15987
15988     private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime,
15989             long realtime, boolean isCheckinRequest, boolean isCompact) {
15990         if (isCompact) {
15991             pw.print("version,"); pw.println(MEMINFO_COMPACT_VERSION);
15992         }
15993         if (isCheckinRequest || isCompact) {
15994             // short checkin version
15995             pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime);
15996         } else {
15997             pw.println("Applications Memory Usage (in Kilobytes):");
15998             pw.println("Uptime: " + uptime + " Realtime: " + realtime);
15999         }
16000     }
16001
16002     private static final int KSM_SHARED = 0;
16003     private static final int KSM_SHARING = 1;
16004     private static final int KSM_UNSHARED = 2;
16005     private static final int KSM_VOLATILE = 3;
16006
16007     private final long[] getKsmInfo() {
16008         long[] longOut = new long[4];
16009         final int[] SINGLE_LONG_FORMAT = new int[] {
16010             Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG
16011         };
16012         long[] longTmp = new long[1];
16013         Process.readProcFile("/sys/kernel/mm/ksm/pages_shared",
16014                 SINGLE_LONG_FORMAT, null, longTmp, null);
16015         longOut[KSM_SHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024;
16016         longTmp[0] = 0;
16017         Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing",
16018                 SINGLE_LONG_FORMAT, null, longTmp, null);
16019         longOut[KSM_SHARING] = longTmp[0] * ProcessList.PAGE_SIZE / 1024;
16020         longTmp[0] = 0;
16021         Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared",
16022                 SINGLE_LONG_FORMAT, null, longTmp, null);
16023         longOut[KSM_UNSHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024;
16024         longTmp[0] = 0;
16025         Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile",
16026                 SINGLE_LONG_FORMAT, null, longTmp, null);
16027         longOut[KSM_VOLATILE] = longTmp[0] * ProcessList.PAGE_SIZE / 1024;
16028         return longOut;
16029     }
16030
16031     private static String stringifySize(long size, int order) {
16032         Locale locale = Locale.US;
16033         switch (order) {
16034             case 1:
16035                 return String.format(locale, "%,13d", size);
16036             case 1024:
16037                 return String.format(locale, "%,9dK", size / 1024);
16038             case 1024 * 1024:
16039                 return String.format(locale, "%,5dM", size / 1024 / 1024);
16040             case 1024 * 1024 * 1024:
16041                 return String.format(locale, "%,1dG", size / 1024 / 1024 / 1024);
16042             default:
16043                 throw new IllegalArgumentException("Invalid size order");
16044         }
16045     }
16046
16047     private static String stringifyKBSize(long size) {
16048         return stringifySize(size * 1024, 1024);
16049     }
16050
16051     // Update this version number in case you change the 'compact' format
16052     private static final int MEMINFO_COMPACT_VERSION = 1;
16053
16054     final void dumpApplicationMemoryUsage(FileDescriptor fd,
16055             PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) {
16056         boolean dumpDetails = false;
16057         boolean dumpFullDetails = false;
16058         boolean dumpDalvik = false;
16059         boolean dumpSummaryOnly = false;
16060         boolean dumpUnreachable = false;
16061         boolean oomOnly = false;
16062         boolean isCompact = false;
16063         boolean localOnly = false;
16064         boolean packages = false;
16065         boolean isCheckinRequest = false;
16066         boolean dumpSwapPss = false;
16067
16068         int opti = 0;
16069         while (opti < args.length) {
16070             String opt = args[opti];
16071             if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') {
16072                 break;
16073             }
16074             opti++;
16075             if ("-a".equals(opt)) {
16076                 dumpDetails = true;
16077                 dumpFullDetails = true;
16078                 dumpDalvik = true;
16079                 dumpSwapPss = true;
16080             } else if ("-d".equals(opt)) {
16081                 dumpDalvik = true;
16082             } else if ("-c".equals(opt)) {
16083                 isCompact = true;
16084             } else if ("-s".equals(opt)) {
16085                 dumpDetails = true;
16086                 dumpSummaryOnly = true;
16087             } else if ("-S".equals(opt)) {
16088                 dumpSwapPss = true;
16089             } else if ("--unreachable".equals(opt)) {
16090                 dumpUnreachable = true;
16091             } else if ("--oom".equals(opt)) {
16092                 oomOnly = true;
16093             } else if ("--local".equals(opt)) {
16094                 localOnly = true;
16095             } else if ("--package".equals(opt)) {
16096                 packages = true;
16097             } else if ("--checkin".equals(opt)) {
16098                 isCheckinRequest = true;
16099
16100             } else if ("-h".equals(opt)) {
16101                 pw.println("meminfo dump options: [-a] [-d] [-c] [-s] [--oom] [process]");
16102                 pw.println("  -a: include all available information for each process.");
16103                 pw.println("  -d: include dalvik details.");
16104                 pw.println("  -c: dump in a compact machine-parseable representation.");
16105                 pw.println("  -s: dump only summary of application memory usage.");
16106                 pw.println("  -S: dump also SwapPss.");
16107                 pw.println("  --oom: only show processes organized by oom adj.");
16108                 pw.println("  --local: only collect details locally, don't call process.");
16109                 pw.println("  --package: interpret process arg as package, dumping all");
16110                 pw.println("             processes that have loaded that package.");
16111                 pw.println("  --checkin: dump data for a checkin");
16112                 pw.println("If [process] is specified it can be the name or ");
16113                 pw.println("pid of a specific process to dump.");
16114                 return;
16115             } else {
16116                 pw.println("Unknown argument: " + opt + "; use -h for help");
16117             }
16118         }
16119
16120         long uptime = SystemClock.uptimeMillis();
16121         long realtime = SystemClock.elapsedRealtime();
16122         final long[] tmpLong = new long[1];
16123
16124         ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, packages, args);
16125         if (procs == null) {
16126             // No Java processes.  Maybe they want to print a native process.
16127             if (args != null && args.length > opti
16128                     && args[opti].charAt(0) != '-') {
16129                 ArrayList<ProcessCpuTracker.Stats> nativeProcs
16130                         = new ArrayList<ProcessCpuTracker.Stats>();
16131                 updateCpuStatsNow();
16132                 int findPid = -1;
16133                 try {
16134                     findPid = Integer.parseInt(args[opti]);
16135                 } catch (NumberFormatException e) {
16136                 }
16137                 synchronized (mProcessCpuTracker) {
16138                     final int N = mProcessCpuTracker.countStats();
16139                     for (int i=0; i<N; i++) {
16140                         ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i);
16141                         if (st.pid == findPid || (st.baseName != null
16142                                 && st.baseName.equals(args[opti]))) {
16143                             nativeProcs.add(st);
16144                         }
16145                     }
16146                 }
16147                 if (nativeProcs.size() > 0) {
16148                     dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest,
16149                             isCompact);
16150                     Debug.MemoryInfo mi = null;
16151                     for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) {
16152                         final ProcessCpuTracker.Stats r = nativeProcs.get(i);
16153                         final int pid = r.pid;
16154                         if (!isCheckinRequest && dumpDetails) {
16155                             pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **");
16156                         }
16157                         if (mi == null) {
16158                             mi = new Debug.MemoryInfo();
16159                         }
16160                         if (dumpDetails || (!brief && !oomOnly)) {
16161                             Debug.getMemoryInfo(pid, mi);
16162                         } else {
16163                             mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null);
16164                             mi.dalvikPrivateDirty = (int)tmpLong[0];
16165                         }
16166                         ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails,
16167                                 dumpDalvik, dumpSummaryOnly, pid, r.baseName, 0, 0, 0, 0, 0, 0);
16168                         if (isCheckinRequest) {
16169                             pw.println();
16170                         }
16171                     }
16172                     return;
16173                 }
16174             }
16175             pw.println("No process found for: " + args[opti]);
16176             return;
16177         }
16178
16179         if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest || packages)) {
16180             dumpDetails = true;
16181         }
16182
16183         dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact);
16184
16185         String[] innerArgs = new String[args.length-opti];
16186         System.arraycopy(args, opti, innerArgs, 0, args.length-opti);
16187
16188         ArrayList<MemItem> procMems = new ArrayList<MemItem>();
16189         final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>();
16190         long nativePss = 0;
16191         long nativeSwapPss = 0;
16192         long dalvikPss = 0;
16193         long dalvikSwapPss = 0;
16194         long[] dalvikSubitemPss = dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] :
16195                 EmptyArray.LONG;
16196         long[] dalvikSubitemSwapPss = dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] :
16197                 EmptyArray.LONG;
16198         long otherPss = 0;
16199         long otherSwapPss = 0;
16200         long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS];
16201         long[] miscSwapPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS];
16202
16203         long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length];
16204         long oomSwapPss[] = new long[DUMP_MEM_OOM_LABEL.length];
16205         ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[])
16206                 new ArrayList[DUMP_MEM_OOM_LABEL.length];
16207
16208         long totalPss = 0;
16209         long totalSwapPss = 0;
16210         long cachedPss = 0;
16211         long cachedSwapPss = 0;
16212         boolean hasSwapPss = false;
16213
16214         Debug.MemoryInfo mi = null;
16215         for (int i = procs.size() - 1 ; i >= 0 ; i--) {
16216             final ProcessRecord r = procs.get(i);
16217             final IApplicationThread thread;
16218             final int pid;
16219             final int oomAdj;
16220             final boolean hasActivities;
16221             synchronized (this) {
16222                 thread = r.thread;
16223                 pid = r.pid;
16224                 oomAdj = r.getSetAdjWithServices();
16225                 hasActivities = r.activities.size() > 0;
16226             }
16227             if (thread != null) {
16228                 if (!isCheckinRequest && dumpDetails) {
16229                     pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **");
16230                 }
16231                 if (mi == null) {
16232                     mi = new Debug.MemoryInfo();
16233                 }
16234                 if (dumpDetails || (!brief && !oomOnly)) {
16235                     Debug.getMemoryInfo(pid, mi);
16236                     hasSwapPss = mi.hasSwappedOutPss;
16237                 } else {
16238                     mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null);
16239                     mi.dalvikPrivateDirty = (int)tmpLong[0];
16240                 }
16241                 if (dumpDetails) {
16242                     if (localOnly) {
16243                         ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails,
16244                                 dumpDalvik, dumpSummaryOnly, pid, r.processName, 0, 0, 0, 0, 0, 0);
16245                         if (isCheckinRequest) {
16246                             pw.println();
16247                         }
16248                     } else {
16249                         try {
16250                             pw.flush();
16251                             thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails,
16252                                     dumpDalvik, dumpSummaryOnly, dumpUnreachable, innerArgs);
16253                         } catch (RemoteException e) {
16254                             if (!isCheckinRequest) {
16255                                 pw.println("Got RemoteException!");
16256                                 pw.flush();
16257                             }
16258                         }
16259                     }
16260                 }
16261
16262                 final long myTotalPss = mi.getTotalPss();
16263                 final long myTotalUss = mi.getTotalUss();
16264                 final long myTotalSwapPss = mi.getTotalSwappedOutPss();
16265
16266                 synchronized (this) {
16267                     if (r.thread != null && oomAdj == r.getSetAdjWithServices()) {
16268                         // Record this for posterity if the process has been stable.
16269                         r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList);
16270                     }
16271                 }
16272
16273                 if (!isCheckinRequest && mi != null) {
16274                     totalPss += myTotalPss;
16275                     totalSwapPss += myTotalSwapPss;
16276                     MemItem pssItem = new MemItem(r.processName + " (pid " + pid +
16277                             (hasActivities ? " / activities)" : ")"), r.processName, myTotalPss,
16278                             myTotalSwapPss, pid, hasActivities);
16279                     procMems.add(pssItem);
16280                     procMemsMap.put(pid, pssItem);
16281
16282                     nativePss += mi.nativePss;
16283                     nativeSwapPss += mi.nativeSwappedOutPss;
16284                     dalvikPss += mi.dalvikPss;
16285                     dalvikSwapPss += mi.dalvikSwappedOutPss;
16286                     for (int j=0; j<dalvikSubitemPss.length; j++) {
16287                         dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j);
16288                         dalvikSubitemSwapPss[j] +=
16289                                 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j);
16290                     }
16291                     otherPss += mi.otherPss;
16292                     otherSwapPss += mi.otherSwappedOutPss;
16293                     for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) {
16294                         long mem = mi.getOtherPss(j);
16295                         miscPss[j] += mem;
16296                         otherPss -= mem;
16297                         mem = mi.getOtherSwappedOutPss(j);
16298                         miscSwapPss[j] += mem;
16299                         otherSwapPss -= mem;
16300                     }
16301
16302                     if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) {
16303                         cachedPss += myTotalPss;
16304                         cachedSwapPss += myTotalSwapPss;
16305                     }
16306
16307                     for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) {
16308                         if (oomIndex == (oomPss.length - 1)
16309                                 || (oomAdj >= DUMP_MEM_OOM_ADJ[oomIndex]
16310                                         && oomAdj < DUMP_MEM_OOM_ADJ[oomIndex + 1])) {
16311                             oomPss[oomIndex] += myTotalPss;
16312                             oomSwapPss[oomIndex] += myTotalSwapPss;
16313                             if (oomProcs[oomIndex] == null) {
16314                                 oomProcs[oomIndex] = new ArrayList<MemItem>();
16315                             }
16316                             oomProcs[oomIndex].add(pssItem);
16317                             break;
16318                         }
16319                     }
16320                 }
16321             }
16322         }
16323
16324         long nativeProcTotalPss = 0;
16325
16326         if (!isCheckinRequest && procs.size() > 1 && !packages) {
16327             // If we are showing aggregations, also look for native processes to
16328             // include so that our aggregations are more accurate.
16329             updateCpuStatsNow();
16330             mi = null;
16331             synchronized (mProcessCpuTracker) {
16332                 final int N = mProcessCpuTracker.countStats();
16333                 for (int i=0; i<N; i++) {
16334                     ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i);
16335                     if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) {
16336                         if (mi == null) {
16337                             mi = new Debug.MemoryInfo();
16338                         }
16339                         if (!brief && !oomOnly) {
16340                             Debug.getMemoryInfo(st.pid, mi);
16341                         } else {
16342                             mi.nativePss = (int)Debug.getPss(st.pid, tmpLong, null);
16343                             mi.nativePrivateDirty = (int)tmpLong[0];
16344                         }
16345
16346                         final long myTotalPss = mi.getTotalPss();
16347                         final long myTotalSwapPss = mi.getTotalSwappedOutPss();
16348                         totalPss += myTotalPss;
16349                         nativeProcTotalPss += myTotalPss;
16350
16351                         MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")",
16352                                 st.name, myTotalPss, mi.getSummaryTotalSwapPss(), st.pid, false);
16353                         procMems.add(pssItem);
16354
16355                         nativePss += mi.nativePss;
16356                         nativeSwapPss += mi.nativeSwappedOutPss;
16357                         dalvikPss += mi.dalvikPss;
16358                         dalvikSwapPss += mi.dalvikSwappedOutPss;
16359                         for (int j=0; j<dalvikSubitemPss.length; j++) {
16360                             dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j);
16361                             dalvikSubitemSwapPss[j] +=
16362                                     mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j);
16363                         }
16364                         otherPss += mi.otherPss;
16365                         otherSwapPss += mi.otherSwappedOutPss;
16366                         for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) {
16367                             long mem = mi.getOtherPss(j);
16368                             miscPss[j] += mem;
16369                             otherPss -= mem;
16370                             mem = mi.getOtherSwappedOutPss(j);
16371                             miscSwapPss[j] += mem;
16372                             otherSwapPss -= mem;
16373                         }
16374                         oomPss[0] += myTotalPss;
16375                         oomSwapPss[0] += myTotalSwapPss;
16376                         if (oomProcs[0] == null) {
16377                             oomProcs[0] = new ArrayList<MemItem>();
16378                         }
16379                         oomProcs[0].add(pssItem);
16380                     }
16381                 }
16382             }
16383
16384             ArrayList<MemItem> catMems = new ArrayList<MemItem>();
16385
16386             catMems.add(new MemItem("Native", "Native", nativePss, nativeSwapPss, -1));
16387             final MemItem dalvikItem =
16388                     new MemItem("Dalvik", "Dalvik", dalvikPss, dalvikSwapPss, -2);
16389             if (dalvikSubitemPss.length > 0) {
16390                 dalvikItem.subitems = new ArrayList<MemItem>();
16391                 for (int j=0; j<dalvikSubitemPss.length; j++) {
16392                     final String name = Debug.MemoryInfo.getOtherLabel(
16393                             Debug.MemoryInfo.NUM_OTHER_STATS + j);
16394                     dalvikItem.subitems.add(new MemItem(name, name, dalvikSubitemPss[j],
16395                                     dalvikSubitemSwapPss[j], j));
16396                 }
16397             }
16398             catMems.add(dalvikItem);
16399             catMems.add(new MemItem("Unknown", "Unknown", otherPss, otherSwapPss, -3));
16400             for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) {
16401                 String label = Debug.MemoryInfo.getOtherLabel(j);
16402                 catMems.add(new MemItem(label, label, miscPss[j], miscSwapPss[j], j));
16403             }
16404
16405             ArrayList<MemItem> oomMems = new ArrayList<MemItem>();
16406             for (int j=0; j<oomPss.length; j++) {
16407                 if (oomPss[j] != 0) {
16408                     String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j]
16409                             : DUMP_MEM_OOM_LABEL[j];
16410                     MemItem item = new MemItem(label, label, oomPss[j], oomSwapPss[j],
16411                             DUMP_MEM_OOM_ADJ[j]);
16412                     item.subitems = oomProcs[j];
16413                     oomMems.add(item);
16414                 }
16415             }
16416
16417             dumpSwapPss = dumpSwapPss && hasSwapPss && totalSwapPss != 0;
16418             if (!brief && !oomOnly && !isCompact) {
16419                 pw.println();
16420                 pw.println("Total PSS by process:");
16421                 dumpMemItems(pw, "  ", "proc", procMems, true, isCompact, dumpSwapPss);
16422                 pw.println();
16423             }
16424             if (!isCompact) {
16425                 pw.println("Total PSS by OOM adjustment:");
16426             }
16427             dumpMemItems(pw, "  ", "oom", oomMems, false, isCompact, dumpSwapPss);
16428             if (!brief && !oomOnly) {
16429                 PrintWriter out = categoryPw != null ? categoryPw : pw;
16430                 if (!isCompact) {
16431                     out.println();
16432                     out.println("Total PSS by category:");
16433                 }
16434                 dumpMemItems(out, "  ", "cat", catMems, true, isCompact, dumpSwapPss);
16435             }
16436             if (!isCompact) {
16437                 pw.println();
16438             }
16439             MemInfoReader memInfo = new MemInfoReader();
16440             memInfo.readMemInfo();
16441             if (nativeProcTotalPss > 0) {
16442                 synchronized (this) {
16443                     final long cachedKb = memInfo.getCachedSizeKb();
16444                     final long freeKb = memInfo.getFreeSizeKb();
16445                     final long zramKb = memInfo.getZramTotalSizeKb();
16446                     final long kernelKb = memInfo.getKernelUsedSizeKb();
16447                     EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024,
16448                             kernelKb*1024, nativeProcTotalPss*1024);
16449                     mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb,
16450                             nativeProcTotalPss);
16451                 }
16452             }
16453             if (!brief) {
16454                 if (!isCompact) {
16455                     pw.print("Total RAM: "); pw.print(stringifyKBSize(memInfo.getTotalSizeKb()));
16456                     pw.print(" (status ");
16457                     switch (mLastMemoryLevel) {
16458                         case ProcessStats.ADJ_MEM_FACTOR_NORMAL:
16459                             pw.println("normal)");
16460                             break;
16461                         case ProcessStats.ADJ_MEM_FACTOR_MODERATE:
16462                             pw.println("moderate)");
16463                             break;
16464                         case ProcessStats.ADJ_MEM_FACTOR_LOW:
16465                             pw.println("low)");
16466                             break;
16467                         case ProcessStats.ADJ_MEM_FACTOR_CRITICAL:
16468                             pw.println("critical)");
16469                             break;
16470                         default:
16471                             pw.print(mLastMemoryLevel);
16472                             pw.println(")");
16473                             break;
16474                     }
16475                     pw.print(" Free RAM: ");
16476                     pw.print(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb()
16477                             + memInfo.getFreeSizeKb()));
16478                     pw.print(" (");
16479                     pw.print(stringifyKBSize(cachedPss));
16480                     pw.print(" cached pss + ");
16481                     pw.print(stringifyKBSize(memInfo.getCachedSizeKb()));
16482                     pw.print(" cached kernel + ");
16483                     pw.print(stringifyKBSize(memInfo.getFreeSizeKb()));
16484                     pw.println(" free)");
16485                 } else {
16486                     pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(",");
16487                     pw.print(cachedPss + memInfo.getCachedSizeKb()
16488                             + memInfo.getFreeSizeKb()); pw.print(",");
16489                     pw.println(totalPss - cachedPss);
16490                 }
16491             }
16492             long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss)
16493                     - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb()
16494                     - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb();
16495             if (!isCompact) {
16496                 pw.print(" Used RAM: "); pw.print(stringifyKBSize(totalPss - cachedPss
16497                         + memInfo.getKernelUsedSizeKb())); pw.print(" (");
16498                 pw.print(stringifyKBSize(totalPss - cachedPss)); pw.print(" used pss + ");
16499                 pw.print(stringifyKBSize(memInfo.getKernelUsedSizeKb())); pw.print(" kernel)\n");
16500                 pw.print(" Lost RAM: "); pw.println(stringifyKBSize(lostRAM));
16501             } else {
16502                 pw.print("lostram,"); pw.println(lostRAM);
16503             }
16504             if (!brief) {
16505                 if (memInfo.getZramTotalSizeKb() != 0) {
16506                     if (!isCompact) {
16507                         pw.print("     ZRAM: ");
16508                         pw.print(stringifyKBSize(memInfo.getZramTotalSizeKb()));
16509                                 pw.print(" physical used for ");
16510                                 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb()
16511                                         - memInfo.getSwapFreeSizeKb()));
16512                                 pw.print(" in swap (");
16513                                 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb()));
16514                                 pw.println(" total swap)");
16515                     } else {
16516                         pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(",");
16517                                 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(",");
16518                                 pw.println(memInfo.getSwapFreeSizeKb());
16519                     }
16520                 }
16521                 final long[] ksm = getKsmInfo();
16522                 if (!isCompact) {
16523                     if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0
16524                             || ksm[KSM_VOLATILE] != 0) {
16525                         pw.print("      KSM: "); pw.print(stringifyKBSize(ksm[KSM_SHARING]));
16526                                 pw.print(" saved from shared ");
16527                                 pw.print(stringifyKBSize(ksm[KSM_SHARED]));
16528                         pw.print("           "); pw.print(stringifyKBSize(ksm[KSM_UNSHARED]));
16529                                 pw.print(" unshared; ");
16530                                 pw.print(stringifyKBSize(
16531                                              ksm[KSM_VOLATILE])); pw.println(" volatile");
16532                     }
16533                     pw.print("   Tuning: ");
16534                     pw.print(ActivityManager.staticGetMemoryClass());
16535                     pw.print(" (large ");
16536                     pw.print(ActivityManager.staticGetLargeMemoryClass());
16537                     pw.print("), oom ");
16538                     pw.print(stringifySize(
16539                                 mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ), 1024));
16540                     pw.print(", restore limit ");
16541                     pw.print(stringifyKBSize(mProcessList.getCachedRestoreThresholdKb()));
16542                     if (ActivityManager.isLowRamDeviceStatic()) {
16543                         pw.print(" (low-ram)");
16544                     }
16545                     if (ActivityManager.isHighEndGfx()) {
16546                         pw.print(" (high-end-gfx)");
16547                     }
16548                     pw.println();
16549                 } else {
16550                     pw.print("ksm,"); pw.print(ksm[KSM_SHARING]); pw.print(",");
16551                     pw.print(ksm[KSM_SHARED]); pw.print(","); pw.print(ksm[KSM_UNSHARED]);
16552                     pw.print(","); pw.println(ksm[KSM_VOLATILE]);
16553                     pw.print("tuning,");
16554                     pw.print(ActivityManager.staticGetMemoryClass());
16555                     pw.print(',');
16556                     pw.print(ActivityManager.staticGetLargeMemoryClass());
16557                     pw.print(',');
16558                     pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024);
16559                     if (ActivityManager.isLowRamDeviceStatic()) {
16560                         pw.print(",low-ram");
16561                     }
16562                     if (ActivityManager.isHighEndGfx()) {
16563                         pw.print(",high-end-gfx");
16564                     }
16565                     pw.println();
16566                 }
16567             }
16568         }
16569     }
16570
16571     private void appendBasicMemEntry(StringBuilder sb, int oomAdj, int procState, long pss,
16572             long memtrack, String name) {
16573         sb.append("  ");
16574         sb.append(ProcessList.makeOomAdjString(oomAdj));
16575         sb.append(' ');
16576         sb.append(ProcessList.makeProcStateString(procState));
16577         sb.append(' ');
16578         ProcessList.appendRamKb(sb, pss);
16579         sb.append(": ");
16580         sb.append(name);
16581         if (memtrack > 0) {
16582             sb.append(" (");
16583             sb.append(stringifyKBSize(memtrack));
16584             sb.append(" memtrack)");
16585         }
16586     }
16587
16588     private void appendMemInfo(StringBuilder sb, ProcessMemInfo mi) {
16589         appendBasicMemEntry(sb, mi.oomAdj, mi.procState, mi.pss, mi.memtrack, mi.name);
16590         sb.append(" (pid ");
16591         sb.append(mi.pid);
16592         sb.append(") ");
16593         sb.append(mi.adjType);
16594         sb.append('\n');
16595         if (mi.adjReason != null) {
16596             sb.append("                      ");
16597             sb.append(mi.adjReason);
16598             sb.append('\n');
16599         }
16600     }
16601
16602     void reportMemUsage(ArrayList<ProcessMemInfo> memInfos) {
16603         final SparseArray<ProcessMemInfo> infoMap = new SparseArray<>(memInfos.size());
16604         for (int i=0, N=memInfos.size(); i<N; i++) {
16605             ProcessMemInfo mi = memInfos.get(i);
16606             infoMap.put(mi.pid, mi);
16607         }
16608         updateCpuStatsNow();
16609         long[] memtrackTmp = new long[1];
16610         final List<ProcessCpuTracker.Stats> stats;
16611         // Get a list of Stats that have vsize > 0
16612         synchronized (mProcessCpuTracker) {
16613             stats = mProcessCpuTracker.getStats((st) -> {
16614                 return st.vsize > 0;
16615             });
16616         }
16617         final int statsCount = stats.size();
16618         for (int i = 0; i < statsCount; i++) {
16619             ProcessCpuTracker.Stats st = stats.get(i);
16620             long pss = Debug.getPss(st.pid, null, memtrackTmp);
16621             if (pss > 0) {
16622                 if (infoMap.indexOfKey(st.pid) < 0) {
16623                     ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid,
16624                             ProcessList.NATIVE_ADJ, -1, "native", null);
16625                     mi.pss = pss;
16626                     mi.memtrack = memtrackTmp[0];
16627                     memInfos.add(mi);
16628                 }
16629             }
16630         }
16631
16632         long totalPss = 0;
16633         long totalMemtrack = 0;
16634         for (int i=0, N=memInfos.size(); i<N; i++) {
16635             ProcessMemInfo mi = memInfos.get(i);
16636             if (mi.pss == 0) {
16637                 mi.pss = Debug.getPss(mi.pid, null, memtrackTmp);
16638                 mi.memtrack = memtrackTmp[0];
16639             }
16640             totalPss += mi.pss;
16641             totalMemtrack += mi.memtrack;
16642         }
16643         Collections.sort(memInfos, new Comparator<ProcessMemInfo>() {
16644             @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) {
16645                 if (lhs.oomAdj != rhs.oomAdj) {
16646                     return lhs.oomAdj < rhs.oomAdj ? -1 : 1;
16647                 }
16648                 if (lhs.pss != rhs.pss) {
16649                     return lhs.pss < rhs.pss ? 1 : -1;
16650                 }
16651                 return 0;
16652             }
16653         });
16654
16655         StringBuilder tag = new StringBuilder(128);
16656         StringBuilder stack = new StringBuilder(128);
16657         tag.append("Low on memory -- ");
16658         appendMemBucket(tag, totalPss, "total", false);
16659         appendMemBucket(stack, totalPss, "total", true);
16660
16661         StringBuilder fullNativeBuilder = new StringBuilder(1024);
16662         StringBuilder shortNativeBuilder = new StringBuilder(1024);
16663         StringBuilder fullJavaBuilder = new StringBuilder(1024);
16664
16665         boolean firstLine = true;
16666         int lastOomAdj = Integer.MIN_VALUE;
16667         long extraNativeRam = 0;
16668         long extraNativeMemtrack = 0;
16669         long cachedPss = 0;
16670         for (int i=0, N=memInfos.size(); i<N; i++) {
16671             ProcessMemInfo mi = memInfos.get(i);
16672
16673             if (mi.oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) {
16674                 cachedPss += mi.pss;
16675             }
16676
16677             if (mi.oomAdj != ProcessList.NATIVE_ADJ
16678                     && (mi.oomAdj < ProcessList.SERVICE_ADJ
16679                             || mi.oomAdj == ProcessList.HOME_APP_ADJ
16680                             || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) {
16681                 if (lastOomAdj != mi.oomAdj) {
16682                     lastOomAdj = mi.oomAdj;
16683                     if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) {
16684                         tag.append(" / ");
16685                     }
16686                     if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) {
16687                         if (firstLine) {
16688                             stack.append(":");
16689                             firstLine = false;
16690                         }
16691                         stack.append("\n\t at ");
16692                     } else {
16693                         stack.append("$");
16694                     }
16695                 } else {
16696                     tag.append(" ");
16697                     stack.append("$");
16698                 }
16699                 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) {
16700                     appendMemBucket(tag, mi.pss, mi.name, false);
16701                 }
16702                 appendMemBucket(stack, mi.pss, mi.name, true);
16703                 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ
16704                         && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) {
16705                     stack.append("(");
16706                     for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) {
16707                         if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) {
16708                             stack.append(DUMP_MEM_OOM_LABEL[k]);
16709                             stack.append(":");
16710                             stack.append(DUMP_MEM_OOM_ADJ[k]);
16711                         }
16712                     }
16713                     stack.append(")");
16714                 }
16715             }
16716
16717             appendMemInfo(fullNativeBuilder, mi);
16718             if (mi.oomAdj == ProcessList.NATIVE_ADJ) {
16719                 // The short form only has native processes that are >= 512K.
16720                 if (mi.pss >= 512) {
16721                     appendMemInfo(shortNativeBuilder, mi);
16722                 } else {
16723                     extraNativeRam += mi.pss;
16724                     extraNativeMemtrack += mi.memtrack;
16725                 }
16726             } else {
16727                 // Short form has all other details, but if we have collected RAM
16728                 // from smaller native processes let's dump a summary of that.
16729                 if (extraNativeRam > 0) {
16730                     appendBasicMemEntry(shortNativeBuilder, ProcessList.NATIVE_ADJ,
16731                             -1, extraNativeRam, extraNativeMemtrack, "(Other native)");
16732                     shortNativeBuilder.append('\n');
16733                     extraNativeRam = 0;
16734                 }
16735                 appendMemInfo(fullJavaBuilder, mi);
16736             }
16737         }
16738
16739         fullJavaBuilder.append("           ");
16740         ProcessList.appendRamKb(fullJavaBuilder, totalPss);
16741         fullJavaBuilder.append(": TOTAL");
16742         if (totalMemtrack > 0) {
16743             fullJavaBuilder.append(" (");
16744             fullJavaBuilder.append(stringifyKBSize(totalMemtrack));
16745             fullJavaBuilder.append(" memtrack)");
16746         } else {
16747         }
16748         fullJavaBuilder.append("\n");
16749
16750         MemInfoReader memInfo = new MemInfoReader();
16751         memInfo.readMemInfo();
16752         final long[] infos = memInfo.getRawInfo();
16753
16754         StringBuilder memInfoBuilder = new StringBuilder(1024);
16755         Debug.getMemInfo(infos);
16756         memInfoBuilder.append("  MemInfo: ");
16757         memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SLAB])).append(" slab, ");
16758         memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SHMEM])).append(" shmem, ");
16759         memInfoBuilder.append(stringifyKBSize(
16760                                   infos[Debug.MEMINFO_VM_ALLOC_USED])).append(" vm alloc, ");
16761         memInfoBuilder.append(stringifyKBSize(
16762                                   infos[Debug.MEMINFO_PAGE_TABLES])).append(" page tables ");
16763         memInfoBuilder.append(stringifyKBSize(
16764                                   infos[Debug.MEMINFO_KERNEL_STACK])).append(" kernel stack\n");
16765         memInfoBuilder.append("           ");
16766         memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_BUFFERS])).append(" buffers, ");
16767         memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_CACHED])).append(" cached, ");
16768         memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_MAPPED])).append(" mapped, ");
16769         memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_FREE])).append(" free\n");
16770         if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) {
16771             memInfoBuilder.append("  ZRAM: ");
16772             memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_ZRAM_TOTAL]));
16773             memInfoBuilder.append(" RAM, ");
16774             memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_TOTAL]));
16775             memInfoBuilder.append(" swap total, ");
16776             memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_FREE]));
16777             memInfoBuilder.append(" swap free\n");
16778         }
16779         final long[] ksm = getKsmInfo();
16780         if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0
16781                 || ksm[KSM_VOLATILE] != 0) {
16782             memInfoBuilder.append("  KSM: ");
16783             memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARING]));
16784             memInfoBuilder.append(" saved from shared ");
16785             memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARED]));
16786             memInfoBuilder.append("\n       ");
16787             memInfoBuilder.append(stringifyKBSize(ksm[KSM_UNSHARED]));
16788             memInfoBuilder.append(" unshared; ");
16789             memInfoBuilder.append(stringifyKBSize(ksm[KSM_VOLATILE]));
16790             memInfoBuilder.append(" volatile\n");
16791         }
16792         memInfoBuilder.append("  Free RAM: ");
16793         memInfoBuilder.append(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb()
16794                 + memInfo.getFreeSizeKb()));
16795         memInfoBuilder.append("\n");
16796         memInfoBuilder.append("  Used RAM: ");
16797         memInfoBuilder.append(stringifyKBSize(
16798                                   totalPss - cachedPss + memInfo.getKernelUsedSizeKb()));
16799         memInfoBuilder.append("\n");
16800         memInfoBuilder.append("  Lost RAM: ");
16801         memInfoBuilder.append(stringifyKBSize(memInfo.getTotalSizeKb()
16802                 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb()
16803                 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb()));
16804         memInfoBuilder.append("\n");
16805         Slog.i(TAG, "Low on memory:");
16806         Slog.i(TAG, shortNativeBuilder.toString());
16807         Slog.i(TAG, fullJavaBuilder.toString());
16808         Slog.i(TAG, memInfoBuilder.toString());
16809
16810         StringBuilder dropBuilder = new StringBuilder(1024);
16811         /*
16812         StringWriter oomSw = new StringWriter();
16813         PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256);
16814         StringWriter catSw = new StringWriter();
16815         PrintWriter catPw = new FastPrintWriter(catSw, false, 256);
16816         String[] emptyArgs = new String[] { };
16817         dumpApplicationMemoryUsage(null, oomPw, "  ", emptyArgs, true, catPw);
16818         oomPw.flush();
16819         String oomString = oomSw.toString();
16820         */
16821         dropBuilder.append("Low on memory:");
16822         dropBuilder.append(stack);
16823         dropBuilder.append('\n');
16824         dropBuilder.append(fullNativeBuilder);
16825         dropBuilder.append(fullJavaBuilder);
16826         dropBuilder.append('\n');
16827         dropBuilder.append(memInfoBuilder);
16828         dropBuilder.append('\n');
16829         /*
16830         dropBuilder.append(oomString);
16831         dropBuilder.append('\n');
16832         */
16833         StringWriter catSw = new StringWriter();
16834         synchronized (ActivityManagerService.this) {
16835             PrintWriter catPw = new FastPrintWriter(catSw, false, 256);
16836             String[] emptyArgs = new String[] { };
16837             catPw.println();
16838             dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null);
16839             catPw.println();
16840             mServices.newServiceDumperLocked(null, catPw, emptyArgs, 0,
16841                     false, null).dumpLocked();
16842             catPw.println();
16843             dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null);
16844             catPw.flush();
16845         }
16846         dropBuilder.append(catSw.toString());
16847         addErrorToDropBox("lowmem", null, "system_server", null,
16848                 null, tag.toString(), dropBuilder.toString(), null, null);
16849         //Slog.i(TAG, "Sent to dropbox:");
16850         //Slog.i(TAG, dropBuilder.toString());
16851         synchronized (ActivityManagerService.this) {
16852             long now = SystemClock.uptimeMillis();
16853             if (mLastMemUsageReportTime < now) {
16854                 mLastMemUsageReportTime = now;
16855             }
16856         }
16857     }
16858
16859     /**
16860      * Searches array of arguments for the specified string
16861      * @param args array of argument strings
16862      * @param value value to search for
16863      * @return true if the value is contained in the array
16864      */
16865     private static boolean scanArgs(String[] args, String value) {
16866         if (args != null) {
16867             for (String arg : args) {
16868                 if (value.equals(arg)) {
16869                     return true;
16870                 }
16871             }
16872         }
16873         return false;
16874     }
16875
16876     private final boolean removeDyingProviderLocked(ProcessRecord proc,
16877             ContentProviderRecord cpr, boolean always) {
16878         final boolean inLaunching = mLaunchingProviders.contains(cpr);
16879
16880         if (!inLaunching || always) {
16881             synchronized (cpr) {
16882                 cpr.launchingApp = null;
16883                 cpr.notifyAll();
16884             }
16885             mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid));
16886             String names[] = cpr.info.authority.split(";");
16887             for (int j = 0; j < names.length; j++) {
16888                 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid));
16889             }
16890         }
16891
16892         for (int i = cpr.connections.size() - 1; i >= 0; i--) {
16893             ContentProviderConnection conn = cpr.connections.get(i);
16894             if (conn.waiting) {
16895                 // If this connection is waiting for the provider, then we don't
16896                 // need to mess with its process unless we are always removing
16897                 // or for some reason the provider is not currently launching.
16898                 if (inLaunching && !always) {
16899                     continue;
16900                 }
16901             }
16902             ProcessRecord capp = conn.client;
16903             conn.dead = true;
16904             if (conn.stableCount > 0) {
16905                 if (!capp.persistent && capp.thread != null
16906                         && capp.pid != 0
16907                         && capp.pid != MY_PID) {
16908                     capp.kill("depends on provider "
16909                             + cpr.name.flattenToShortString()
16910                             + " in dying proc " + (proc != null ? proc.processName : "??")
16911                             + " (adj " + (proc != null ? proc.setAdj : "??") + ")", true);
16912                 }
16913             } else if (capp.thread != null && conn.provider.provider != null) {
16914                 try {
16915                     capp.thread.unstableProviderDied(conn.provider.provider.asBinder());
16916                 } catch (RemoteException e) {
16917                 }
16918                 // In the protocol here, we don't expect the client to correctly
16919                 // clean up this connection, we'll just remove it.
16920                 cpr.connections.remove(i);
16921                 if (conn.client.conProviders.remove(conn)) {
16922                     stopAssociationLocked(capp.uid, capp.processName, cpr.uid, cpr.name);
16923                 }
16924             }
16925         }
16926
16927         if (inLaunching && always) {
16928             mLaunchingProviders.remove(cpr);
16929         }
16930         return inLaunching;
16931     }
16932
16933     /**
16934      * Main code for cleaning up a process when it has gone away.  This is
16935      * called both as a result of the process dying, or directly when stopping
16936      * a process when running in single process mode.
16937      *
16938      * @return Returns true if the given process has been restarted, so the
16939      * app that was passed in must remain on the process lists.
16940      */
16941     private final boolean cleanUpApplicationRecordLocked(ProcessRecord app,
16942             boolean restarting, boolean allowRestart, int index, boolean replacingPid) {
16943         Slog.d(TAG, "cleanUpApplicationRecord -- " + app.pid);
16944         if (index >= 0) {
16945             removeLruProcessLocked(app);
16946             ProcessList.remove(app.pid);
16947         }
16948
16949         mProcessesToGc.remove(app);
16950         mPendingPssProcesses.remove(app);
16951
16952         // Dismiss any open dialogs.
16953         if (app.crashDialog != null && !app.forceCrashReport) {
16954             app.crashDialog.dismiss();
16955             app.crashDialog = null;
16956         }
16957         if (app.anrDialog != null) {
16958             app.anrDialog.dismiss();
16959             app.anrDialog = null;
16960         }
16961         if (app.waitDialog != null) {
16962             app.waitDialog.dismiss();
16963             app.waitDialog = null;
16964         }
16965
16966         app.crashing = false;
16967         app.notResponding = false;
16968
16969         app.resetPackageList(mProcessStats);
16970         app.unlinkDeathRecipient();
16971         app.makeInactive(mProcessStats);
16972         app.waitingToKill = null;
16973         app.forcingToForeground = null;
16974         updateProcessForegroundLocked(app, false, false);
16975         app.foregroundActivities = false;
16976         app.hasShownUi = false;
16977         app.treatLikeActivity = false;
16978         app.hasAboveClient = false;
16979         app.hasClientActivities = false;
16980
16981         mServices.killServicesLocked(app, allowRestart);
16982
16983         boolean restart = false;
16984
16985         // Remove published content providers.
16986         for (int i = app.pubProviders.size() - 1; i >= 0; i--) {
16987             ContentProviderRecord cpr = app.pubProviders.valueAt(i);
16988             final boolean always = app.bad || !allowRestart;
16989             boolean inLaunching = removeDyingProviderLocked(app, cpr, always);
16990             if ((inLaunching || always) && cpr.hasConnectionOrHandle()) {
16991                 // We left the provider in the launching list, need to
16992                 // restart it.
16993                 restart = true;
16994             }
16995
16996             cpr.provider = null;
16997             cpr.proc = null;
16998         }
16999         app.pubProviders.clear();
17000
17001         // Take care of any launching providers waiting for this process.
17002         if (cleanupAppInLaunchingProvidersLocked(app, false)) {
17003             restart = true;
17004         }
17005
17006         // Unregister from connected content providers.
17007         if (!app.conProviders.isEmpty()) {
17008             for (int i = app.conProviders.size() - 1; i >= 0; i--) {
17009                 ContentProviderConnection conn = app.conProviders.get(i);
17010                 conn.provider.connections.remove(conn);
17011                 stopAssociationLocked(app.uid, app.processName, conn.provider.uid,
17012                         conn.provider.name);
17013             }
17014             app.conProviders.clear();
17015         }
17016
17017         // At this point there may be remaining entries in mLaunchingProviders
17018         // where we were the only one waiting, so they are no longer of use.
17019         // Look for these and clean up if found.
17020         // XXX Commented out for now.  Trying to figure out a way to reproduce
17021         // the actual situation to identify what is actually going on.
17022         if (false) {
17023             for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) {
17024                 ContentProviderRecord cpr = mLaunchingProviders.get(i);
17025                 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) {
17026                     synchronized (cpr) {
17027                         cpr.launchingApp = null;
17028                         cpr.notifyAll();
17029                     }
17030                 }
17031             }
17032         }
17033
17034         skipCurrentReceiverLocked(app);
17035
17036         // Unregister any receivers.
17037         for (int i = app.receivers.size() - 1; i >= 0; i--) {
17038             removeReceiverLocked(app.receivers.valueAt(i));
17039         }
17040         app.receivers.clear();
17041
17042         // If the app is undergoing backup, tell the backup manager about it
17043         if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) {
17044             if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG_CLEANUP, "App "
17045                     + mBackupTarget.appInfo + " died during backup");
17046             try {
17047                 IBackupManager bm = IBackupManager.Stub.asInterface(
17048                         ServiceManager.getService(Context.BACKUP_SERVICE));
17049                 bm.agentDisconnected(app.info.packageName);
17050             } catch (RemoteException e) {
17051                 // can't happen; backup manager is local
17052             }
17053         }
17054
17055         for (int i = mPendingProcessChanges.size() - 1; i >= 0; i--) {
17056             ProcessChangeItem item = mPendingProcessChanges.get(i);
17057             if (item.pid == app.pid) {
17058                 mPendingProcessChanges.remove(i);
17059                 mAvailProcessChanges.add(item);
17060             }
17061         }
17062         mUiHandler.obtainMessage(DISPATCH_PROCESS_DIED_UI_MSG, app.pid, app.info.uid,
17063                 null).sendToTarget();
17064
17065         // If the caller is restarting this app, then leave it in its
17066         // current lists and let the caller take care of it.
17067         if (restarting) {
17068             return false;
17069         }
17070
17071         if (!app.persistent || app.isolated) {
17072             if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_CLEANUP,
17073                     "Removing non-persistent process during cleanup: " + app);
17074             if (!replacingPid) {
17075                 removeProcessNameLocked(app.processName, app.uid, app);
17076             }
17077             if (mHeavyWeightProcess == app) {
17078                 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG,
17079                         mHeavyWeightProcess.userId, 0));
17080                 mHeavyWeightProcess = null;
17081             }
17082         } else if (!app.removed) {
17083             // This app is persistent, so we need to keep its record around.
17084             // If it is not already on the pending app list, add it there
17085             // and start a new process for it.
17086             if (mPersistentStartingProcesses.indexOf(app) < 0) {
17087                 mPersistentStartingProcesses.add(app);
17088                 restart = true;
17089             }
17090         }
17091         if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(
17092                 TAG_CLEANUP, "Clean-up removing on hold: " + app);
17093         mProcessesOnHold.remove(app);
17094
17095         if (app == mHomeProcess) {
17096             mHomeProcess = null;
17097         }
17098         if (app == mPreviousProcess) {
17099             mPreviousProcess = null;
17100         }
17101
17102         if (restart && !app.isolated) {
17103             // We have components that still need to be running in the
17104             // process, so re-launch it.
17105             if (index < 0) {
17106                 ProcessList.remove(app.pid);
17107             }
17108             addProcessNameLocked(app);
17109             startProcessLocked(app, "restart", app.processName);
17110             return true;
17111         } else if (app.pid > 0 && app.pid != MY_PID) {
17112             // Goodbye!
17113             boolean removed;
17114             synchronized (mPidsSelfLocked) {
17115                 mPidsSelfLocked.remove(app.pid);
17116                 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
17117             }
17118             mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid);
17119             if (app.isolated) {
17120                 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid);
17121             }
17122             app.setPid(0);
17123         }
17124         return false;
17125     }
17126
17127     boolean checkAppInLaunchingProvidersLocked(ProcessRecord app) {
17128         for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) {
17129             ContentProviderRecord cpr = mLaunchingProviders.get(i);
17130             if (cpr.launchingApp == app) {
17131                 return true;
17132             }
17133         }
17134         return false;
17135     }
17136
17137     boolean cleanupAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) {
17138         // Look through the content providers we are waiting to have launched,
17139         // and if any run in this process then either schedule a restart of
17140         // the process or kill the client waiting for it if this process has
17141         // gone bad.
17142         boolean restart = false;
17143         for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) {
17144             ContentProviderRecord cpr = mLaunchingProviders.get(i);
17145             if (cpr.launchingApp == app) {
17146                 if (!alwaysBad && !app.bad && cpr.hasConnectionOrHandle()) {
17147                     restart = true;
17148                 } else {
17149                     removeDyingProviderLocked(app, cpr, true);
17150                 }
17151             }
17152         }
17153         return restart;
17154     }
17155
17156     // =========================================================
17157     // SERVICES
17158     // =========================================================
17159
17160     @Override
17161     public List<ActivityManager.RunningServiceInfo> getServices(int maxNum,
17162             int flags) {
17163         enforceNotIsolatedCaller("getServices");
17164         synchronized (this) {
17165             return mServices.getRunningServiceInfoLocked(maxNum, flags);
17166         }
17167     }
17168
17169     @Override
17170     public PendingIntent getRunningServiceControlPanel(ComponentName name) {
17171         enforceNotIsolatedCaller("getRunningServiceControlPanel");
17172         synchronized (this) {
17173             return mServices.getRunningServiceControlPanelLocked(name);
17174         }
17175     }
17176
17177     @Override
17178     public ComponentName startService(IApplicationThread caller, Intent service,
17179             String resolvedType, String callingPackage, int userId)
17180             throws TransactionTooLargeException {
17181         enforceNotIsolatedCaller("startService");
17182         // Refuse possible leaked file descriptors
17183         if (service != null && service.hasFileDescriptors() == true) {
17184             throw new IllegalArgumentException("File descriptors passed in Intent");
17185         }
17186
17187         if (callingPackage == null) {
17188             throw new IllegalArgumentException("callingPackage cannot be null");
17189         }
17190
17191         if (DEBUG_SERVICE) Slog.v(TAG_SERVICE,
17192                 "startService: " + service + " type=" + resolvedType);
17193         synchronized(this) {
17194             final int callingPid = Binder.getCallingPid();
17195             final int callingUid = Binder.getCallingUid();
17196             final long origId = Binder.clearCallingIdentity();
17197             ComponentName res = mServices.startServiceLocked(caller, service,
17198                     resolvedType, callingPid, callingUid, callingPackage, userId);
17199             Binder.restoreCallingIdentity(origId);
17200             return res;
17201         }
17202     }
17203
17204     ComponentName startServiceInPackage(int uid, Intent service, String resolvedType,
17205             String callingPackage, int userId)
17206             throws TransactionTooLargeException {
17207         synchronized(this) {
17208             if (DEBUG_SERVICE) Slog.v(TAG_SERVICE,
17209                     "startServiceInPackage: " + service + " type=" + resolvedType);
17210             final long origId = Binder.clearCallingIdentity();
17211             ComponentName res = mServices.startServiceLocked(null, service,
17212                     resolvedType, -1, uid, callingPackage, userId);
17213             Binder.restoreCallingIdentity(origId);
17214             return res;
17215         }
17216     }
17217
17218     @Override
17219     public int stopService(IApplicationThread caller, Intent service,
17220             String resolvedType, int userId) {
17221         enforceNotIsolatedCaller("stopService");
17222         // Refuse possible leaked file descriptors
17223         if (service != null && service.hasFileDescriptors() == true) {
17224             throw new IllegalArgumentException("File descriptors passed in Intent");
17225         }
17226
17227         synchronized(this) {
17228             return mServices.stopServiceLocked(caller, service, resolvedType, userId);
17229         }
17230     }
17231
17232     @Override
17233     public IBinder peekService(Intent service, String resolvedType, String callingPackage) {
17234         enforceNotIsolatedCaller("peekService");
17235         // Refuse possible leaked file descriptors
17236         if (service != null && service.hasFileDescriptors() == true) {
17237             throw new IllegalArgumentException("File descriptors passed in Intent");
17238         }
17239
17240         if (callingPackage == null) {
17241             throw new IllegalArgumentException("callingPackage cannot be null");
17242         }
17243
17244         synchronized(this) {
17245             return mServices.peekServiceLocked(service, resolvedType, callingPackage);
17246         }
17247     }
17248
17249     @Override
17250     public boolean stopServiceToken(ComponentName className, IBinder token,
17251             int startId) {
17252         synchronized(this) {
17253             return mServices.stopServiceTokenLocked(className, token, startId);
17254         }
17255     }
17256
17257     @Override
17258     public void setServiceForeground(ComponentName className, IBinder token,
17259             int id, Notification notification, int flags) {
17260         synchronized(this) {
17261             mServices.setServiceForegroundLocked(className, token, id, notification, flags);
17262         }
17263     }
17264
17265     @Override
17266     public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll,
17267             boolean requireFull, String name, String callerPackage) {
17268         return mUserController.handleIncomingUser(callingPid, callingUid, userId, allowAll,
17269                 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage);
17270     }
17271
17272     boolean isSingleton(String componentProcessName, ApplicationInfo aInfo,
17273             String className, int flags) {
17274         boolean result = false;
17275         // For apps that don't have pre-defined UIDs, check for permission
17276         if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) {
17277             if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) {
17278                 if (ActivityManager.checkUidPermission(
17279                         INTERACT_ACROSS_USERS,
17280                         aInfo.uid) != PackageManager.PERMISSION_GRANTED) {
17281                     ComponentName comp = new ComponentName(aInfo.packageName, className);
17282                     String msg = "Permission Denial: Component " + comp.flattenToShortString()
17283                             + " requests FLAG_SINGLE_USER, but app does not hold "
17284                             + INTERACT_ACROSS_USERS;
17285                     Slog.w(TAG, msg);
17286                     throw new SecurityException(msg);
17287                 }
17288                 // Permission passed
17289                 result = true;
17290             }
17291         } else if ("system".equals(componentProcessName)) {
17292             result = true;
17293         } else if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) {
17294             // Phone app and persistent apps are allowed to export singleuser providers.
17295             result = UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID)
17296                     || (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0;
17297         }
17298         if (DEBUG_MU) Slog.v(TAG_MU,
17299                 "isSingleton(" + componentProcessName + ", " + aInfo + ", " + className + ", 0x"
17300                 + Integer.toHexString(flags) + ") = " + result);
17301         return result;
17302     }
17303
17304     /**
17305      * Checks to see if the caller is in the same app as the singleton
17306      * component, or the component is in a special app. It allows special apps
17307      * to export singleton components but prevents exporting singleton
17308      * components for regular apps.
17309      */
17310     boolean isValidSingletonCall(int callingUid, int componentUid) {
17311         int componentAppId = UserHandle.getAppId(componentUid);
17312         return UserHandle.isSameApp(callingUid, componentUid)
17313                 || componentAppId == Process.SYSTEM_UID
17314                 || componentAppId == Process.PHONE_UID
17315                 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid)
17316                         == PackageManager.PERMISSION_GRANTED;
17317     }
17318
17319     public int bindService(IApplicationThread caller, IBinder token, Intent service,
17320             String resolvedType, IServiceConnection connection, int flags, String callingPackage,
17321             int userId) throws TransactionTooLargeException {
17322         enforceNotIsolatedCaller("bindService");
17323
17324         // Refuse possible leaked file descriptors
17325         if (service != null && service.hasFileDescriptors() == true) {
17326             throw new IllegalArgumentException("File descriptors passed in Intent");
17327         }
17328
17329         if (callingPackage == null) {
17330             throw new IllegalArgumentException("callingPackage cannot be null");
17331         }
17332
17333         synchronized(this) {
17334             return mServices.bindServiceLocked(caller, token, service,
17335                     resolvedType, connection, flags, callingPackage, userId);
17336         }
17337     }
17338
17339     public boolean unbindService(IServiceConnection connection) {
17340         synchronized (this) {
17341             return mServices.unbindServiceLocked(connection);
17342         }
17343     }
17344
17345     public void publishService(IBinder token, Intent intent, IBinder service) {
17346         // Refuse possible leaked file descriptors
17347         if (intent != null && intent.hasFileDescriptors() == true) {
17348             throw new IllegalArgumentException("File descriptors passed in Intent");
17349         }
17350
17351         synchronized(this) {
17352             if (!(token instanceof ServiceRecord)) {
17353                 throw new IllegalArgumentException("Invalid service token");
17354             }
17355             mServices.publishServiceLocked((ServiceRecord)token, intent, service);
17356         }
17357     }
17358
17359     public void unbindFinished(IBinder token, Intent intent, boolean doRebind) {
17360         // Refuse possible leaked file descriptors
17361         if (intent != null && intent.hasFileDescriptors() == true) {
17362             throw new IllegalArgumentException("File descriptors passed in Intent");
17363         }
17364
17365         synchronized(this) {
17366             mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind);
17367         }
17368     }
17369
17370     public void serviceDoneExecuting(IBinder token, int type, int startId, int res) {
17371         synchronized(this) {
17372             if (!(token instanceof ServiceRecord)) {
17373                 Slog.e(TAG, "serviceDoneExecuting: Invalid service token=" + token);
17374                 throw new IllegalArgumentException("Invalid service token");
17375             }
17376             mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res);
17377         }
17378     }
17379
17380     // =========================================================
17381     // BACKUP AND RESTORE
17382     // =========================================================
17383
17384     // Cause the target app to be launched if necessary and its backup agent
17385     // instantiated.  The backup agent will invoke backupAgentCreated() on the
17386     // activity manager to announce its creation.
17387     public boolean bindBackupAgent(String packageName, int backupMode, int userId) {
17388         if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + packageName + " mode=" + backupMode);
17389         enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent");
17390
17391         IPackageManager pm = AppGlobals.getPackageManager();
17392         ApplicationInfo app = null;
17393         try {
17394             app = pm.getApplicationInfo(packageName, 0, userId);
17395         } catch (RemoteException e) {
17396             // can't happen; package manager is process-local
17397         }
17398         if (app == null) {
17399             Slog.w(TAG, "Unable to bind backup agent for " + packageName);
17400             return false;
17401         }
17402
17403         synchronized(this) {
17404             // !!! TODO: currently no check here that we're already bound
17405             BatteryStatsImpl.Uid.Pkg.Serv ss = null;
17406             BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
17407             synchronized (stats) {
17408                 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name);
17409             }
17410
17411             // Backup agent is now in use, its package can't be stopped.
17412             try {
17413                 AppGlobals.getPackageManager().setPackageStoppedState(
17414                         app.packageName, false, UserHandle.getUserId(app.uid));
17415             } catch (RemoteException e) {
17416             } catch (IllegalArgumentException e) {
17417                 Slog.w(TAG, "Failed trying to unstop package "
17418                         + app.packageName + ": " + e);
17419             }
17420
17421             BackupRecord r = new BackupRecord(ss, app, backupMode);
17422             ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL)
17423                     ? new ComponentName(app.packageName, app.backupAgentName)
17424                     : new ComponentName("android", "FullBackupAgent");
17425             // startProcessLocked() returns existing proc's record if it's already running
17426             ProcessRecord proc = startProcessLocked(app.processName, app,
17427                     false, 0, "backup", hostingName, false, false, false);
17428             if (proc == null) {
17429                 Slog.e(TAG, "Unable to start backup agent process " + r);
17430                 return false;
17431             }
17432
17433             // If the app is a regular app (uid >= 10000) and not the system server or phone
17434             // process, etc, then mark it as being in full backup so that certain calls to the
17435             // process can be blocked. This is not reset to false anywhere because we kill the
17436             // process after the full backup is done and the ProcessRecord will vaporize anyway.
17437             if (UserHandle.isApp(app.uid) && backupMode == IApplicationThread.BACKUP_MODE_FULL) {
17438                 proc.inFullBackup = true;
17439             }
17440             r.app = proc;
17441             mBackupTarget = r;
17442             mBackupAppName = app.packageName;
17443
17444             // Try not to kill the process during backup
17445             updateOomAdjLocked(proc);
17446
17447             // If the process is already attached, schedule the creation of the backup agent now.
17448             // If it is not yet live, this will be done when it attaches to the framework.
17449             if (proc.thread != null) {
17450                 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc already running: " + proc);
17451                 try {
17452                     proc.thread.scheduleCreateBackupAgent(app,
17453                             compatibilityInfoForPackageLocked(app), backupMode);
17454                 } catch (RemoteException e) {
17455                     // Will time out on the backup manager side
17456                 }
17457             } else {
17458                 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc not running, waiting for attach");
17459             }
17460             // Invariants: at this point, the target app process exists and the application
17461             // is either already running or in the process of coming up.  mBackupTarget and
17462             // mBackupAppName describe the app, so that when it binds back to the AM we
17463             // know that it's scheduled for a backup-agent operation.
17464         }
17465
17466         return true;
17467     }
17468
17469     @Override
17470     public void clearPendingBackup() {
17471         if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "clearPendingBackup");
17472         enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup");
17473
17474         synchronized (this) {
17475             mBackupTarget = null;
17476             mBackupAppName = null;
17477         }
17478     }
17479
17480     // A backup agent has just come up
17481     public void backupAgentCreated(String agentPackageName, IBinder agent) {
17482         if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "backupAgentCreated: " + agentPackageName
17483                 + " = " + agent);
17484
17485         synchronized(this) {
17486             if (!agentPackageName.equals(mBackupAppName)) {
17487                 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!");
17488                 return;
17489             }
17490         }
17491
17492         long oldIdent = Binder.clearCallingIdentity();
17493         try {
17494             IBackupManager bm = IBackupManager.Stub.asInterface(
17495                     ServiceManager.getService(Context.BACKUP_SERVICE));
17496             bm.agentConnected(agentPackageName, agent);
17497         } catch (RemoteException e) {
17498             // can't happen; the backup manager service is local
17499         } catch (Exception e) {
17500             Slog.w(TAG, "Exception trying to deliver BackupAgent binding: ");
17501             e.printStackTrace();
17502         } finally {
17503             Binder.restoreCallingIdentity(oldIdent);
17504         }
17505     }
17506
17507     // done with this agent
17508     public void unbindBackupAgent(ApplicationInfo appInfo) {
17509         if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "unbindBackupAgent: " + appInfo);
17510         if (appInfo == null) {
17511             Slog.w(TAG, "unbind backup agent for null app");
17512             return;
17513         }
17514
17515         synchronized(this) {
17516             try {
17517                 if (mBackupAppName == null) {
17518                     Slog.w(TAG, "Unbinding backup agent with no active backup");
17519                     return;
17520                 }
17521
17522                 if (!mBackupAppName.equals(appInfo.packageName)) {
17523                     Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target");
17524                     return;
17525                 }
17526
17527                 // Not backing this app up any more; reset its OOM adjustment
17528                 final ProcessRecord proc = mBackupTarget.app;
17529                 updateOomAdjLocked(proc);
17530
17531                 // If the app crashed during backup, 'thread' will be null here
17532                 if (proc.thread != null) {
17533                     try {
17534                         proc.thread.scheduleDestroyBackupAgent(appInfo,
17535                                 compatibilityInfoForPackageLocked(appInfo));
17536                     } catch (Exception e) {
17537                         Slog.e(TAG, "Exception when unbinding backup agent:");
17538                         e.printStackTrace();
17539                     }
17540                 }
17541             } finally {
17542                 mBackupTarget = null;
17543                 mBackupAppName = null;
17544             }
17545         }
17546     }
17547     // =========================================================
17548     // BROADCASTS
17549     // =========================================================
17550
17551     boolean isPendingBroadcastProcessLocked(int pid) {
17552         return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid)
17553                 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid);
17554     }
17555
17556     void skipPendingBroadcastLocked(int pid) {
17557             Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping");
17558             for (BroadcastQueue queue : mBroadcastQueues) {
17559                 queue.skipPendingBroadcastLocked(pid);
17560             }
17561     }
17562
17563     // The app just attached; send any pending broadcasts that it should receive
17564     boolean sendPendingBroadcastsLocked(ProcessRecord app) {
17565         boolean didSomething = false;
17566         for (BroadcastQueue queue : mBroadcastQueues) {
17567             didSomething |= queue.sendPendingBroadcastsLocked(app);
17568         }
17569         return didSomething;
17570     }
17571
17572     public Intent registerReceiver(IApplicationThread caller, String callerPackage,
17573             IIntentReceiver receiver, IntentFilter filter, String permission, int userId) {
17574         enforceNotIsolatedCaller("registerReceiver");
17575         ArrayList<Intent> stickyIntents = null;
17576         ProcessRecord callerApp = null;
17577         int callingUid;
17578         int callingPid;
17579         synchronized(this) {
17580             if (caller != null) {
17581                 callerApp = getRecordForAppLocked(caller);
17582                 if (callerApp == null) {
17583                     throw new SecurityException(
17584                             "Unable to find app for caller " + caller
17585                             + " (pid=" + Binder.getCallingPid()
17586                             + ") when registering receiver " + receiver);
17587                 }
17588                 if (callerApp.info.uid != Process.SYSTEM_UID &&
17589                         !callerApp.pkgList.containsKey(callerPackage) &&
17590                         !"android".equals(callerPackage)) {
17591                     throw new SecurityException("Given caller package " + callerPackage
17592                             + " is not running in process " + callerApp);
17593                 }
17594                 callingUid = callerApp.info.uid;
17595                 callingPid = callerApp.pid;
17596             } else {
17597                 callerPackage = null;
17598                 callingUid = Binder.getCallingUid();
17599                 callingPid = Binder.getCallingPid();
17600             }
17601
17602             userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true,
17603                     ALLOW_FULL_ONLY, "registerReceiver", callerPackage);
17604
17605             Iterator<String> actions = filter.actionsIterator();
17606             if (actions == null) {
17607                 ArrayList<String> noAction = new ArrayList<String>(1);
17608                 noAction.add(null);
17609                 actions = noAction.iterator();
17610             }
17611
17612             // Collect stickies of users
17613             int[] userIds = { UserHandle.USER_ALL, UserHandle.getUserId(callingUid) };
17614             while (actions.hasNext()) {
17615                 String action = actions.next();
17616                 for (int id : userIds) {
17617                     ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(id);
17618                     if (stickies != null) {
17619                         ArrayList<Intent> intents = stickies.get(action);
17620                         if (intents != null) {
17621                             if (stickyIntents == null) {
17622                                 stickyIntents = new ArrayList<Intent>();
17623                             }
17624                             stickyIntents.addAll(intents);
17625                         }
17626                     }
17627                 }
17628             }
17629         }
17630
17631         ArrayList<Intent> allSticky = null;
17632         if (stickyIntents != null) {
17633             final ContentResolver resolver = mContext.getContentResolver();
17634             // Look for any matching sticky broadcasts...
17635             for (int i = 0, N = stickyIntents.size(); i < N; i++) {
17636                 Intent intent = stickyIntents.get(i);
17637                 // If intent has scheme "content", it will need to acccess
17638                 // provider that needs to lock mProviderMap in ActivityThread
17639                 // and also it may need to wait application response, so we
17640                 // cannot lock ActivityManagerService here.
17641                 if (filter.match(resolver, intent, true, TAG) >= 0) {
17642                     if (allSticky == null) {
17643                         allSticky = new ArrayList<Intent>();
17644                     }
17645                     allSticky.add(intent);
17646                 }
17647             }
17648         }
17649
17650         // The first sticky in the list is returned directly back to the client.
17651         Intent sticky = allSticky != null ? allSticky.get(0) : null;
17652         if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Register receiver " + filter + ": " + sticky);
17653         if (receiver == null) {
17654             return sticky;
17655         }
17656
17657         synchronized (this) {
17658             if (callerApp != null && (callerApp.thread == null
17659                     || callerApp.thread.asBinder() != caller.asBinder())) {
17660                 // Original caller already died
17661                 return null;
17662             }
17663             ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder());
17664             if (rl == null) {
17665                 rl = new ReceiverList(this, callerApp, callingPid, callingUid,
17666                         userId, receiver);
17667                 if (rl.app != null) {
17668                     rl.app.receivers.add(rl);
17669                 } else {
17670                     try {
17671                         receiver.asBinder().linkToDeath(rl, 0);
17672                     } catch (RemoteException e) {
17673                         return sticky;
17674                     }
17675                     rl.linkedToDeath = true;
17676                 }
17677                 mRegisteredReceivers.put(receiver.asBinder(), rl);
17678             } else if (rl.uid != callingUid) {
17679                 throw new IllegalArgumentException(
17680                         "Receiver requested to register for uid " + callingUid
17681                         + " was previously registered for uid " + rl.uid);
17682             } else if (rl.pid != callingPid) {
17683                 throw new IllegalArgumentException(
17684                         "Receiver requested to register for pid " + callingPid
17685                         + " was previously registered for pid " + rl.pid);
17686             } else if (rl.userId != userId) {
17687                 throw new IllegalArgumentException(
17688                         "Receiver requested to register for user " + userId
17689                         + " was previously registered for user " + rl.userId);
17690             }
17691             BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage,
17692                     permission, callingUid, userId);
17693             rl.add(bf);
17694             if (!bf.debugCheck()) {
17695                 Slog.w(TAG, "==> For Dynamic broadcast");
17696             }
17697             mReceiverResolver.addFilter(bf);
17698
17699             // Enqueue broadcasts for all existing stickies that match
17700             // this filter.
17701             if (allSticky != null) {
17702                 ArrayList receivers = new ArrayList();
17703                 receivers.add(bf);
17704
17705                 final int stickyCount = allSticky.size();
17706                 for (int i = 0; i < stickyCount; i++) {
17707                     Intent intent = allSticky.get(i);
17708                     BroadcastQueue queue = broadcastQueueForIntent(intent);
17709                     BroadcastRecord r = new BroadcastRecord(queue, intent, null,
17710                             null, -1, -1, null, null, AppOpsManager.OP_NONE, null, receivers,
17711                             null, 0, null, null, false, true, true, -1);
17712                     queue.enqueueParallelBroadcastLocked(r);
17713                     queue.scheduleBroadcastsLocked();
17714                 }
17715             }
17716
17717             return sticky;
17718         }
17719     }
17720
17721     public void unregisterReceiver(IIntentReceiver receiver) {
17722         if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Unregister receiver: " + receiver);
17723
17724         final long origId = Binder.clearCallingIdentity();
17725         try {
17726             boolean doTrim = false;
17727
17728             synchronized(this) {
17729                 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder());
17730                 if (rl != null) {
17731                     final BroadcastRecord r = rl.curBroadcast;
17732                     if (r != null && r == r.queue.getMatchingOrderedReceiver(r)) {
17733                         final boolean doNext = r.queue.finishReceiverLocked(
17734                                 r, r.resultCode, r.resultData, r.resultExtras,
17735                                 r.resultAbort, false);
17736                         if (doNext) {
17737                             doTrim = true;
17738                             r.queue.processNextBroadcast(false);
17739                         }
17740                     }
17741
17742                     if (rl.app != null) {
17743                         rl.app.receivers.remove(rl);
17744                     }
17745                     removeReceiverLocked(rl);
17746                     if (rl.linkedToDeath) {
17747                         rl.linkedToDeath = false;
17748                         rl.receiver.asBinder().unlinkToDeath(rl, 0);
17749                     }
17750                 }
17751             }
17752
17753             // If we actually concluded any broadcasts, we might now be able
17754             // to trim the recipients' apps from our working set
17755             if (doTrim) {
17756                 trimApplications();
17757                 return;
17758             }
17759
17760         } finally {
17761             Binder.restoreCallingIdentity(origId);
17762         }
17763     }
17764
17765     void removeReceiverLocked(ReceiverList rl) {
17766         mRegisteredReceivers.remove(rl.receiver.asBinder());
17767         for (int i = rl.size() - 1; i >= 0; i--) {
17768             mReceiverResolver.removeFilter(rl.get(i));
17769         }
17770     }
17771
17772     private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) {
17773         for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
17774             ProcessRecord r = mLruProcesses.get(i);
17775             if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) {
17776                 try {
17777                     r.thread.dispatchPackageBroadcast(cmd, packages);
17778                 } catch (RemoteException ex) {
17779                 }
17780             }
17781         }
17782     }
17783
17784     private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType,
17785             int callingUid, int[] users) {
17786         // TODO: come back and remove this assumption to triage all broadcasts
17787         int pmFlags = STOCK_PM_FLAGS | MATCH_DEBUG_TRIAGED_MISSING;
17788
17789         List<ResolveInfo> receivers = null;
17790         try {
17791             HashSet<ComponentName> singleUserReceivers = null;
17792             boolean scannedFirstReceivers = false;
17793             for (int user : users) {
17794                 // Skip users that have Shell restrictions, with exception of always permitted
17795                 // Shell broadcasts
17796                 if (callingUid == Process.SHELL_UID
17797                         && mUserController.hasUserRestriction(
17798                                 UserManager.DISALLOW_DEBUGGING_FEATURES, user)
17799                         && !isPermittedShellBroadcast(intent)) {
17800                     continue;
17801                 }
17802                 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager()
17803                         .queryIntentReceivers(intent, resolvedType, pmFlags, user).getList();
17804                 if (user != UserHandle.USER_SYSTEM && newReceivers != null) {
17805                     // If this is not the system user, we need to check for
17806                     // any receivers that should be filtered out.
17807                     for (int i=0; i<newReceivers.size(); i++) {
17808                         ResolveInfo ri = newReceivers.get(i);
17809                         if ((ri.activityInfo.flags&ActivityInfo.FLAG_SYSTEM_USER_ONLY) != 0) {
17810                             newReceivers.remove(i);
17811                             i--;
17812                         }
17813                     }
17814                 }
17815                 if (newReceivers != null && newReceivers.size() == 0) {
17816                     newReceivers = null;
17817                 }
17818                 if (receivers == null) {
17819                     receivers = newReceivers;
17820                 } else if (newReceivers != null) {
17821                     // We need to concatenate the additional receivers
17822                     // found with what we have do far.  This would be easy,
17823                     // but we also need to de-dup any receivers that are
17824                     // singleUser.
17825                     if (!scannedFirstReceivers) {
17826                         // Collect any single user receivers we had already retrieved.
17827                         scannedFirstReceivers = true;
17828                         for (int i=0; i<receivers.size(); i++) {
17829                             ResolveInfo ri = receivers.get(i);
17830                             if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) {
17831                                 ComponentName cn = new ComponentName(
17832                                         ri.activityInfo.packageName, ri.activityInfo.name);
17833                                 if (singleUserReceivers == null) {
17834                                     singleUserReceivers = new HashSet<ComponentName>();
17835                                 }
17836                                 singleUserReceivers.add(cn);
17837                             }
17838                         }
17839                     }
17840                     // Add the new results to the existing results, tracking
17841                     // and de-dupping single user receivers.
17842                     for (int i=0; i<newReceivers.size(); i++) {
17843                         ResolveInfo ri = newReceivers.get(i);
17844                         if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) {
17845                             ComponentName cn = new ComponentName(
17846                                     ri.activityInfo.packageName, ri.activityInfo.name);
17847                             if (singleUserReceivers == null) {
17848                                 singleUserReceivers = new HashSet<ComponentName>();
17849                             }
17850                             if (!singleUserReceivers.contains(cn)) {
17851                                 singleUserReceivers.add(cn);
17852                                 receivers.add(ri);
17853                             }
17854                         } else {
17855                             receivers.add(ri);
17856                         }
17857                     }
17858                 }
17859             }
17860         } catch (RemoteException ex) {
17861             // pm is in same process, this will never happen.
17862         }
17863         return receivers;
17864     }
17865
17866     private boolean isPermittedShellBroadcast(Intent intent) {
17867         // remote bugreport should always be allowed to be taken
17868         return INTENT_REMOTE_BUGREPORT_FINISHED.equals(intent.getAction());
17869     }
17870
17871     private void checkBroadcastFromSystem(Intent intent, ProcessRecord callerApp,
17872             String callerPackage, int callingUid, boolean isProtectedBroadcast, List receivers) {
17873         final String action = intent.getAction();
17874         if (isProtectedBroadcast
17875                 || Intent.ACTION_CLOSE_SYSTEM_DIALOGS.equals(action)
17876                 || Intent.ACTION_DISMISS_KEYBOARD_SHORTCUTS.equals(action)
17877                 || Intent.ACTION_MEDIA_BUTTON.equals(action)
17878                 || Intent.ACTION_MEDIA_SCANNER_SCAN_FILE.equals(action)
17879                 || Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS.equals(action)
17880                 || Intent.ACTION_MASTER_CLEAR.equals(action)
17881                 || AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action)
17882                 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action)
17883                 || LocationManager.HIGH_POWER_REQUEST_CHANGE_ACTION.equals(action)
17884                 || TelephonyIntents.ACTION_REQUEST_OMADM_CONFIGURATION_UPDATE.equals(action)
17885                 || SuggestionSpan.ACTION_SUGGESTION_PICKED.equals(action)) {
17886             // Broadcast is either protected, or it's a public action that
17887             // we've relaxed, so it's fine for system internals to send.
17888             return;
17889         }
17890
17891         // This broadcast may be a problem...  but there are often system components that
17892         // want to send an internal broadcast to themselves, which is annoying to have to
17893         // explicitly list each action as a protected broadcast, so we will check for that
17894         // one safe case and allow it: an explicit broadcast, only being received by something
17895         // that has protected itself.
17896         if (receivers != null && receivers.size() > 0
17897                 && (intent.getPackage() != null || intent.getComponent() != null)) {
17898             boolean allProtected = true;
17899             for (int i = receivers.size()-1; i >= 0; i--) {
17900                 Object target = receivers.get(i);
17901                 if (target instanceof ResolveInfo) {
17902                     ResolveInfo ri = (ResolveInfo)target;
17903                     if (ri.activityInfo.exported && ri.activityInfo.permission == null) {
17904                         allProtected = false;
17905                         break;
17906                     }
17907                 } else {
17908                     BroadcastFilter bf = (BroadcastFilter)target;
17909                     if (bf.requiredPermission == null) {
17910                         allProtected = false;
17911                         break;
17912                     }
17913                 }
17914             }
17915             if (allProtected) {
17916                 // All safe!
17917                 return;
17918             }
17919         }
17920
17921         // The vast majority of broadcasts sent from system internals
17922         // should be protected to avoid security holes, so yell loudly
17923         // to ensure we examine these cases.
17924         if (callerApp != null) {
17925             Log.wtf(TAG, "Sending non-protected broadcast " + action
17926                             + " from system " + callerApp.toShortString() + " pkg " + callerPackage,
17927                     new Throwable());
17928         } else {
17929             Log.wtf(TAG, "Sending non-protected broadcast " + action
17930                             + " from system uid " + UserHandle.formatUid(callingUid)
17931                             + " pkg " + callerPackage,
17932                     new Throwable());
17933         }
17934     }
17935
17936     final int broadcastIntentLocked(ProcessRecord callerApp,
17937             String callerPackage, Intent intent, String resolvedType,
17938             IIntentReceiver resultTo, int resultCode, String resultData,
17939             Bundle resultExtras, String[] requiredPermissions, int appOp, Bundle bOptions,
17940             boolean ordered, boolean sticky, int callingPid, int callingUid, int userId) {
17941         intent = new Intent(intent);
17942
17943         // By default broadcasts do not go to stopped apps.
17944         intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES);
17945
17946         // If we have not finished booting, don't allow this to launch new processes.
17947         if (!mProcessesReady && (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) {
17948             intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
17949         }
17950
17951         if (DEBUG_BROADCAST_LIGHT) Slog.v(TAG_BROADCAST,
17952                 (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent
17953                 + " ordered=" + ordered + " userid=" + userId);
17954         if ((resultTo != null) && !ordered) {
17955             Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!");
17956         }
17957
17958         userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true,
17959                 ALLOW_NON_FULL, "broadcast", callerPackage);
17960
17961         // Make sure that the user who is receiving this broadcast is running.
17962         // If not, we will just skip it. Make an exception for shutdown broadcasts
17963         // and upgrade steps.
17964
17965         if (userId != UserHandle.USER_ALL && !mUserController.isUserRunningLocked(userId, 0)) {
17966             if ((callingUid != Process.SYSTEM_UID
17967                     || (intent.getFlags() & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0)
17968                     && !Intent.ACTION_SHUTDOWN.equals(intent.getAction())) {
17969                 Slog.w(TAG, "Skipping broadcast of " + intent
17970                         + ": user " + userId + " is stopped");
17971                 return ActivityManager.BROADCAST_FAILED_USER_STOPPED;
17972             }
17973         }
17974
17975         BroadcastOptions brOptions = null;
17976         if (bOptions != null) {
17977             brOptions = new BroadcastOptions(bOptions);
17978             if (brOptions.getTemporaryAppWhitelistDuration() > 0) {
17979                 // See if the caller is allowed to do this.  Note we are checking against
17980                 // the actual real caller (not whoever provided the operation as say a
17981                 // PendingIntent), because that who is actually supplied the arguments.
17982                 if (checkComponentPermission(
17983                         android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST,
17984                         Binder.getCallingPid(), Binder.getCallingUid(), -1, true)
17985                         != PackageManager.PERMISSION_GRANTED) {
17986                     String msg = "Permission Denial: " + intent.getAction()
17987                             + " broadcast from " + callerPackage + " (pid=" + callingPid
17988                             + ", uid=" + callingUid + ")"
17989                             + " requires "
17990                             + android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST;
17991                     Slog.w(TAG, msg);
17992                     throw new SecurityException(msg);
17993                 }
17994             }
17995         }
17996
17997         // Verify that protected broadcasts are only being sent by system code,
17998         // and that system code is only sending protected broadcasts.
17999         final String action = intent.getAction();
18000         final boolean isProtectedBroadcast;
18001         try {
18002             isProtectedBroadcast = AppGlobals.getPackageManager().isProtectedBroadcast(action);
18003         } catch (RemoteException e) {
18004             Slog.w(TAG, "Remote exception", e);
18005             return ActivityManager.BROADCAST_SUCCESS;
18006         }
18007
18008         final boolean isCallerSystem;
18009         switch (UserHandle.getAppId(callingUid)) {
18010             case Process.ROOT_UID:
18011             case Process.SYSTEM_UID:
18012             case Process.PHONE_UID:
18013             case Process.BLUETOOTH_UID:
18014             case Process.NFC_UID:
18015                 isCallerSystem = true;
18016                 break;
18017             default:
18018                 isCallerSystem = (callerApp != null) && callerApp.persistent;
18019                 break;
18020         }
18021
18022         // First line security check before anything else: stop non-system apps from
18023         // sending protected broadcasts.
18024         if (!isCallerSystem) {
18025             if (isProtectedBroadcast) {
18026                 String msg = "Permission Denial: not allowed to send broadcast "
18027                         + action + " from pid="
18028                         + callingPid + ", uid=" + callingUid;
18029                 Slog.w(TAG, msg);
18030                 throw new SecurityException(msg);
18031
18032             } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action)
18033                     || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action)) {
18034                 // Special case for compatibility: we don't want apps to send this,
18035                 // but historically it has not been protected and apps may be using it
18036                 // to poke their own app widget.  So, instead of making it protected,
18037                 // just limit it to the caller.
18038                 if (callerPackage == null) {
18039                     String msg = "Permission Denial: not allowed to send broadcast "
18040                             + action + " from unknown caller.";
18041                     Slog.w(TAG, msg);
18042                     throw new SecurityException(msg);
18043                 } else if (intent.getComponent() != null) {
18044                     // They are good enough to send to an explicit component...  verify
18045                     // it is being sent to the calling app.
18046                     if (!intent.getComponent().getPackageName().equals(
18047                             callerPackage)) {
18048                         String msg = "Permission Denial: not allowed to send broadcast "
18049                                 + action + " to "
18050                                 + intent.getComponent().getPackageName() + " from "
18051                                 + callerPackage;
18052                         Slog.w(TAG, msg);
18053                         throw new SecurityException(msg);
18054                     }
18055                 } else {
18056                     // Limit broadcast to their own package.
18057                     intent.setPackage(callerPackage);
18058                 }
18059             }
18060         }
18061
18062         if (action != null) {
18063             switch (action) {
18064                 case Intent.ACTION_UID_REMOVED:
18065                 case Intent.ACTION_PACKAGE_REMOVED:
18066                 case Intent.ACTION_PACKAGE_CHANGED:
18067                 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE:
18068                 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE:
18069                 case Intent.ACTION_PACKAGES_SUSPENDED:
18070                 case Intent.ACTION_PACKAGES_UNSUSPENDED:
18071                     // Handle special intents: if this broadcast is from the package
18072                     // manager about a package being removed, we need to remove all of
18073                     // its activities from the history stack.
18074                     if (checkComponentPermission(
18075                             android.Manifest.permission.BROADCAST_PACKAGE_REMOVED,
18076                             callingPid, callingUid, -1, true)
18077                             != PackageManager.PERMISSION_GRANTED) {
18078                         String msg = "Permission Denial: " + intent.getAction()
18079                                 + " broadcast from " + callerPackage + " (pid=" + callingPid
18080                                 + ", uid=" + callingUid + ")"
18081                                 + " requires "
18082                                 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED;
18083                         Slog.w(TAG, msg);
18084                         throw new SecurityException(msg);
18085                     }
18086                     switch (action) {
18087                         case Intent.ACTION_UID_REMOVED:
18088                             final Bundle intentExtras = intent.getExtras();
18089                             final int uid = intentExtras != null
18090                                     ? intentExtras.getInt(Intent.EXTRA_UID) : -1;
18091                             if (uid >= 0) {
18092                                 mBatteryStatsService.removeUid(uid);
18093                                 mAppOpsService.uidRemoved(uid);
18094                             }
18095                             break;
18096                         case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE:
18097                             // If resources are unavailable just force stop all those packages
18098                             // and flush the attribute cache as well.
18099                             String list[] =
18100                                     intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST);
18101                             if (list != null && list.length > 0) {
18102                                 for (int i = 0; i < list.length; i++) {
18103                                     forceStopPackageLocked(list[i], -1, false, true, true,
18104                                             false, false, userId, "storage unmount");
18105                                 }
18106                                 mRecentTasks.cleanupLocked(UserHandle.USER_ALL);
18107                                 sendPackageBroadcastLocked(
18108                                         IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list,
18109                                         userId);
18110                             }
18111                             break;
18112                         case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE:
18113                             mRecentTasks.cleanupLocked(UserHandle.USER_ALL);
18114                             break;
18115                         case Intent.ACTION_PACKAGE_REMOVED:
18116                         case Intent.ACTION_PACKAGE_CHANGED:
18117                             Uri data = intent.getData();
18118                             String ssp;
18119                             if (data != null && (ssp=data.getSchemeSpecificPart()) != null) {
18120                                 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals(action);
18121                                 final boolean replacing =
18122                                         intent.getBooleanExtra(Intent.EXTRA_REPLACING, false);
18123                                 final boolean killProcess =
18124                                         !intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false);
18125                                 final boolean fullUninstall = removed && !replacing;
18126                                 if (removed) {
18127                                     if (killProcess) {
18128                                         forceStopPackageLocked(ssp, UserHandle.getAppId(
18129                                                 intent.getIntExtra(Intent.EXTRA_UID, -1)),
18130                                                 false, true, true, false, fullUninstall, userId,
18131                                                 removed ? "pkg removed" : "pkg changed");
18132                                     }
18133                                     final int cmd = killProcess
18134                                             ? IApplicationThread.PACKAGE_REMOVED
18135                                             : IApplicationThread.PACKAGE_REMOVED_DONT_KILL;
18136                                     sendPackageBroadcastLocked(cmd,
18137                                             new String[] {ssp}, userId);
18138                                     if (fullUninstall) {
18139                                         mAppOpsService.packageRemoved(
18140                                                 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp);
18141
18142                                         // Remove all permissions granted from/to this package
18143                                         removeUriPermissionsForPackageLocked(ssp, userId, true);
18144
18145                                         removeTasksByPackageNameLocked(ssp, userId);
18146
18147                                         // Hide the "unsupported display" dialog if necessary.
18148                                         if (mUnsupportedDisplaySizeDialog != null && ssp.equals(
18149                                                 mUnsupportedDisplaySizeDialog.getPackageName())) {
18150                                             mUnsupportedDisplaySizeDialog.dismiss();
18151                                             mUnsupportedDisplaySizeDialog = null;
18152                                         }
18153                                         mCompatModePackages.handlePackageUninstalledLocked(ssp);
18154                                         mBatteryStatsService.notePackageUninstalled(ssp);
18155                                     }
18156                                 } else {
18157                                     if (killProcess) {
18158                                         killPackageProcessesLocked(ssp, UserHandle.getAppId(
18159                                                 intent.getIntExtra(Intent.EXTRA_UID, -1)),
18160                                                 userId, ProcessList.INVALID_ADJ,
18161                                                 false, true, true, false, "change " + ssp);
18162                                     }
18163                                     cleanupDisabledPackageComponentsLocked(ssp, userId, killProcess,
18164                                             intent.getStringArrayExtra(
18165                                                     Intent.EXTRA_CHANGED_COMPONENT_NAME_LIST));
18166                                 }
18167                             }
18168                             break;
18169                         case Intent.ACTION_PACKAGES_SUSPENDED:
18170                         case Intent.ACTION_PACKAGES_UNSUSPENDED:
18171                             final boolean suspended = Intent.ACTION_PACKAGES_SUSPENDED.equals(
18172                                     intent.getAction());
18173                             final String[] packageNames = intent.getStringArrayExtra(
18174                                     Intent.EXTRA_CHANGED_PACKAGE_LIST);
18175                             final int userHandle = intent.getIntExtra(
18176                                     Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL);
18177
18178                             synchronized(ActivityManagerService.this) {
18179                                 mRecentTasks.onPackagesSuspendedChanged(
18180                                         packageNames, suspended, userHandle);
18181                             }
18182                             break;
18183                     }
18184                     break;
18185                 case Intent.ACTION_PACKAGE_REPLACED:
18186                 {
18187                     final Uri data = intent.getData();
18188                     final String ssp;
18189                     if (data != null && (ssp = data.getSchemeSpecificPart()) != null) {
18190                         final ApplicationInfo aInfo =
18191                                 getPackageManagerInternalLocked().getApplicationInfo(
18192                                         ssp,
18193                                         userId);
18194                         if (aInfo == null) {
18195                             Slog.w(TAG, "Dropping ACTION_PACKAGE_REPLACED for non-existent pkg:"
18196                                     + " ssp=" + ssp + " data=" + data);
18197                             return ActivityManager.BROADCAST_SUCCESS;
18198                         }
18199                         mStackSupervisor.updateActivityApplicationInfoLocked(aInfo);
18200                         sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REPLACED,
18201                                 new String[] {ssp}, userId);
18202                     }
18203                     break;
18204                 }
18205                 case Intent.ACTION_PACKAGE_ADDED:
18206                 {
18207                     // Special case for adding a package: by default turn on compatibility mode.
18208                     Uri data = intent.getData();
18209                     String ssp;
18210                     if (data != null && (ssp = data.getSchemeSpecificPart()) != null) {
18211                         final boolean replacing =
18212                                 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false);
18213                         mCompatModePackages.handlePackageAddedLocked(ssp, replacing);
18214
18215                         try {
18216                             ApplicationInfo ai = AppGlobals.getPackageManager().
18217                                     getApplicationInfo(ssp, 0, 0);
18218                             mBatteryStatsService.notePackageInstalled(ssp,
18219                                     ai != null ? ai.versionCode : 0);
18220                         } catch (RemoteException e) {
18221                         }
18222                     }
18223                     break;
18224                 }
18225                 case Intent.ACTION_PACKAGE_DATA_CLEARED:
18226                 {
18227                     Uri data = intent.getData();
18228                     String ssp;
18229                     if (data != null && (ssp = data.getSchemeSpecificPart()) != null) {
18230                         // Hide the "unsupported display" dialog if necessary.
18231                         if (mUnsupportedDisplaySizeDialog != null && ssp.equals(
18232                                 mUnsupportedDisplaySizeDialog.getPackageName())) {
18233                             mUnsupportedDisplaySizeDialog.dismiss();
18234                             mUnsupportedDisplaySizeDialog = null;
18235                         }
18236                         mCompatModePackages.handlePackageDataClearedLocked(ssp);
18237                     }
18238                     break;
18239                 }
18240                 case Intent.ACTION_TIMEZONE_CHANGED:
18241                     // If this is the time zone changed action, queue up a message that will reset
18242                     // the timezone of all currently running processes. This message will get
18243                     // queued up before the broadcast happens.
18244                     mHandler.sendEmptyMessage(UPDATE_TIME_ZONE);
18245                     break;
18246                 case Intent.ACTION_TIME_CHANGED:
18247                     // If the user set the time, let all running processes know.
18248                     final int is24Hour =
18249                             intent.getBooleanExtra(Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1
18250                                     : 0;
18251                     mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0));
18252                     BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
18253                     synchronized (stats) {
18254                         stats.noteCurrentTimeChangedLocked();
18255                     }
18256                     break;
18257                 case Intent.ACTION_CLEAR_DNS_CACHE:
18258                     mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG);
18259                     break;
18260                 case Proxy.PROXY_CHANGE_ACTION:
18261                     ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO);
18262                     mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy));
18263                     break;
18264                 case android.hardware.Camera.ACTION_NEW_PICTURE:
18265                 case android.hardware.Camera.ACTION_NEW_VIDEO:
18266                     // These broadcasts are no longer allowed by the system, since they can
18267                     // cause significant thrashing at a crictical point (using the camera).
18268                     // Apps should use JobScehduler to monitor for media provider changes.
18269                     Slog.w(TAG, action + " no longer allowed; dropping from "
18270                             + UserHandle.formatUid(callingUid));
18271                     if (resultTo != null) {
18272                         final BroadcastQueue queue = broadcastQueueForIntent(intent);
18273                         try {
18274                             queue.performReceiveLocked(callerApp, resultTo, intent,
18275                                     Activity.RESULT_CANCELED, null, null,
18276                                     false, false, userId);
18277                         } catch (RemoteException e) {
18278                             Slog.w(TAG, "Failure ["
18279                                     + queue.mQueueName + "] sending broadcast result of "
18280                                     + intent, e);
18281
18282                         }
18283                     }
18284                     // Lie; we don't want to crash the app.
18285                     return ActivityManager.BROADCAST_SUCCESS;
18286             }
18287         }
18288
18289         // Add to the sticky list if requested.
18290         if (sticky) {
18291             if (checkPermission(android.Manifest.permission.BROADCAST_STICKY,
18292                     callingPid, callingUid)
18293                     != PackageManager.PERMISSION_GRANTED) {
18294                 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid="
18295                         + callingPid + ", uid=" + callingUid
18296                         + " requires " + android.Manifest.permission.BROADCAST_STICKY;
18297                 Slog.w(TAG, msg);
18298                 throw new SecurityException(msg);
18299             }
18300             if (requiredPermissions != null && requiredPermissions.length > 0) {
18301                 Slog.w(TAG, "Can't broadcast sticky intent " + intent
18302                         + " and enforce permissions " + Arrays.toString(requiredPermissions));
18303                 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION;
18304             }
18305             if (intent.getComponent() != null) {
18306                 throw new SecurityException(
18307                         "Sticky broadcasts can't target a specific component");
18308             }
18309             // We use userId directly here, since the "all" target is maintained
18310             // as a separate set of sticky broadcasts.
18311             if (userId != UserHandle.USER_ALL) {
18312                 // But first, if this is not a broadcast to all users, then
18313                 // make sure it doesn't conflict with an existing broadcast to
18314                 // all users.
18315                 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(
18316                         UserHandle.USER_ALL);
18317                 if (stickies != null) {
18318                     ArrayList<Intent> list = stickies.get(intent.getAction());
18319                     if (list != null) {
18320                         int N = list.size();
18321                         int i;
18322                         for (i=0; i<N; i++) {
18323                             if (intent.filterEquals(list.get(i))) {
18324                                 throw new IllegalArgumentException(
18325                                         "Sticky broadcast " + intent + " for user "
18326                                         + userId + " conflicts with existing global broadcast");
18327                             }
18328                         }
18329                     }
18330                 }
18331             }
18332             ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId);
18333             if (stickies == null) {
18334                 stickies = new ArrayMap<>();
18335                 mStickyBroadcasts.put(userId, stickies);
18336             }
18337             ArrayList<Intent> list = stickies.get(intent.getAction());
18338             if (list == null) {
18339                 list = new ArrayList<>();
18340                 stickies.put(intent.getAction(), list);
18341             }
18342             final int stickiesCount = list.size();
18343             int i;
18344             for (i = 0; i < stickiesCount; i++) {
18345                 if (intent.filterEquals(list.get(i))) {
18346                     // This sticky already exists, replace it.
18347                     list.set(i, new Intent(intent));
18348                     break;
18349                 }
18350             }
18351             if (i >= stickiesCount) {
18352                 list.add(new Intent(intent));
18353             }
18354         }
18355
18356         int[] users;
18357         if (userId == UserHandle.USER_ALL) {
18358             // Caller wants broadcast to go to all started users.
18359             users = mUserController.getStartedUserArrayLocked();
18360         } else {
18361             // Caller wants broadcast to go to one specific user.
18362             users = new int[] {userId};
18363         }
18364
18365         // Figure out who all will receive this broadcast.
18366         List receivers = null;
18367         List<BroadcastFilter> registeredReceivers = null;
18368         // Need to resolve the intent to interested receivers...
18369         if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY)
18370                  == 0) {
18371             receivers = collectReceiverComponents(intent, resolvedType, callingUid, users);
18372         }
18373         if (intent.getComponent() == null) {
18374             if (userId == UserHandle.USER_ALL && callingUid == Process.SHELL_UID) {
18375                 // Query one target user at a time, excluding shell-restricted users
18376                 for (int i = 0; i < users.length; i++) {
18377                     if (mUserController.hasUserRestriction(
18378                             UserManager.DISALLOW_DEBUGGING_FEATURES, users[i])) {
18379                         continue;
18380                     }
18381                     List<BroadcastFilter> registeredReceiversForUser =
18382                             mReceiverResolver.queryIntent(intent,
18383                                     resolvedType, false, users[i]);
18384                     if (registeredReceivers == null) {
18385                         registeredReceivers = registeredReceiversForUser;
18386                     } else if (registeredReceiversForUser != null) {
18387                         registeredReceivers.addAll(registeredReceiversForUser);
18388                     }
18389                 }
18390             } else {
18391                 registeredReceivers = mReceiverResolver.queryIntent(intent,
18392                         resolvedType, false, userId);
18393             }
18394         }
18395
18396         final boolean replacePending =
18397                 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0;
18398
18399         if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueing broadcast: " + intent.getAction()
18400                 + " replacePending=" + replacePending);
18401
18402         int NR = registeredReceivers != null ? registeredReceivers.size() : 0;
18403         if (!ordered && NR > 0) {
18404             // If we are not serializing this broadcast, then send the
18405             // registered receivers separately so they don't wait for the
18406             // components to be launched.
18407             if (isCallerSystem) {
18408                 checkBroadcastFromSystem(intent, callerApp, callerPackage, callingUid,
18409                         isProtectedBroadcast, registeredReceivers);
18410             }
18411             final BroadcastQueue queue = broadcastQueueForIntent(intent);
18412             BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp,
18413                     callerPackage, callingPid, callingUid, resolvedType, requiredPermissions,
18414                     appOp, brOptions, registeredReceivers, resultTo, resultCode, resultData,
18415                     resultExtras, ordered, sticky, false, userId);
18416             if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing parallel broadcast " + r);
18417             final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r);
18418             if (!replaced) {
18419                 queue.enqueueParallelBroadcastLocked(r);
18420                 queue.scheduleBroadcastsLocked();
18421             }
18422             registeredReceivers = null;
18423             NR = 0;
18424         }
18425
18426         // Merge into one list.
18427         int ir = 0;
18428         if (receivers != null) {
18429             // A special case for PACKAGE_ADDED: do not allow the package
18430             // being added to see this broadcast.  This prevents them from
18431             // using this as a back door to get run as soon as they are
18432             // installed.  Maybe in the future we want to have a special install
18433             // broadcast or such for apps, but we'd like to deliberately make
18434             // this decision.
18435             String skipPackages[] = null;
18436             if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())
18437                     || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction())
18438                     || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) {
18439                 Uri data = intent.getData();
18440                 if (data != null) {
18441                     String pkgName = data.getSchemeSpecificPart();
18442                     if (pkgName != null) {
18443                         skipPackages = new String[] { pkgName };
18444                     }
18445                 }
18446             } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) {
18447                 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST);
18448             }
18449             if (skipPackages != null && (skipPackages.length > 0)) {
18450                 for (String skipPackage : skipPackages) {
18451                     if (skipPackage != null) {
18452                         int NT = receivers.size();
18453                         for (int it=0; it<NT; it++) {
18454                             ResolveInfo curt = (ResolveInfo)receivers.get(it);
18455                             if (curt.activityInfo.packageName.equals(skipPackage)) {
18456                                 receivers.remove(it);
18457                                 it--;
18458                                 NT--;
18459                             }
18460                         }
18461                     }
18462                 }
18463             }
18464
18465             int NT = receivers != null ? receivers.size() : 0;
18466             int it = 0;
18467             ResolveInfo curt = null;
18468             BroadcastFilter curr = null;
18469             while (it < NT && ir < NR) {
18470                 if (curt == null) {
18471                     curt = (ResolveInfo)receivers.get(it);
18472                 }
18473                 if (curr == null) {
18474                     curr = registeredReceivers.get(ir);
18475                 }
18476                 if (curr.getPriority() >= curt.priority) {
18477                     // Insert this broadcast record into the final list.
18478                     receivers.add(it, curr);
18479                     ir++;
18480                     curr = null;
18481                     it++;
18482                     NT++;
18483                 } else {
18484                     // Skip to the next ResolveInfo in the final list.
18485                     it++;
18486                     curt = null;
18487                 }
18488             }
18489         }
18490         while (ir < NR) {
18491             if (receivers == null) {
18492                 receivers = new ArrayList();
18493             }
18494             receivers.add(registeredReceivers.get(ir));
18495             ir++;
18496         }
18497
18498         if (isCallerSystem) {
18499             checkBroadcastFromSystem(intent, callerApp, callerPackage, callingUid,
18500                     isProtectedBroadcast, receivers);
18501         }
18502
18503         if ((receivers != null && receivers.size() > 0)
18504                 || resultTo != null) {
18505             BroadcastQueue queue = broadcastQueueForIntent(intent);
18506             BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp,
18507                     callerPackage, callingPid, callingUid, resolvedType,
18508                     requiredPermissions, appOp, brOptions, receivers, resultTo, resultCode,
18509                     resultData, resultExtras, ordered, sticky, false, userId);
18510
18511             if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing ordered broadcast " + r
18512                     + ": prev had " + queue.mOrderedBroadcasts.size());
18513             if (DEBUG_BROADCAST) Slog.i(TAG_BROADCAST,
18514                     "Enqueueing broadcast " + r.intent.getAction());
18515
18516             boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r);
18517             if (!replaced) {
18518                 queue.enqueueOrderedBroadcastLocked(r);
18519                 queue.scheduleBroadcastsLocked();
18520             }
18521         } else {
18522             // There was nobody interested in the broadcast, but we still want to record
18523             // that it happened.
18524             if (intent.getComponent() == null && intent.getPackage() == null
18525                     && (intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) {
18526                 // This was an implicit broadcast... let's record it for posterity.
18527                 addBroadcastStatLocked(intent.getAction(), callerPackage, 0, 0, 0);
18528             }
18529         }
18530
18531         return ActivityManager.BROADCAST_SUCCESS;
18532     }
18533
18534     final void addBroadcastStatLocked(String action, String srcPackage, int receiveCount,
18535             int skipCount, long dispatchTime) {
18536         final long now = SystemClock.elapsedRealtime();
18537         if (mCurBroadcastStats == null ||
18538                 (mCurBroadcastStats.mStartRealtime +(24*60*60*1000) < now)) {
18539             mLastBroadcastStats = mCurBroadcastStats;
18540             if (mLastBroadcastStats != null) {
18541                 mLastBroadcastStats.mEndRealtime = SystemClock.elapsedRealtime();
18542                 mLastBroadcastStats.mEndUptime = SystemClock.uptimeMillis();
18543             }
18544             mCurBroadcastStats = new BroadcastStats();
18545         }
18546         mCurBroadcastStats.addBroadcast(action, srcPackage, receiveCount, skipCount, dispatchTime);
18547     }
18548
18549     final Intent verifyBroadcastLocked(Intent intent) {
18550         // Refuse possible leaked file descriptors
18551         if (intent != null && intent.hasFileDescriptors() == true) {
18552             throw new IllegalArgumentException("File descriptors passed in Intent");
18553         }
18554
18555         int flags = intent.getFlags();
18556
18557         if (!mProcessesReady) {
18558             // if the caller really truly claims to know what they're doing, go
18559             // ahead and allow the broadcast without launching any receivers
18560             if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) {
18561                 // This will be turned into a FLAG_RECEIVER_REGISTERED_ONLY later on if needed.
18562             } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) {
18563                 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent
18564                         + " before boot completion");
18565                 throw new IllegalStateException("Cannot broadcast before boot completed");
18566             }
18567         }
18568
18569         if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) {
18570             throw new IllegalArgumentException(
18571                     "Can't use FLAG_RECEIVER_BOOT_UPGRADE here");
18572         }
18573
18574         return intent;
18575     }
18576
18577     public final int broadcastIntent(IApplicationThread caller,
18578             Intent intent, String resolvedType, IIntentReceiver resultTo,
18579             int resultCode, String resultData, Bundle resultExtras,
18580             String[] requiredPermissions, int appOp, Bundle bOptions,
18581             boolean serialized, boolean sticky, int userId) {
18582         enforceNotIsolatedCaller("broadcastIntent");
18583         synchronized(this) {
18584             intent = verifyBroadcastLocked(intent);
18585
18586             final ProcessRecord callerApp = getRecordForAppLocked(caller);
18587             final int callingPid = Binder.getCallingPid();
18588             final int callingUid = Binder.getCallingUid();
18589             final long origId = Binder.clearCallingIdentity();
18590             int res = broadcastIntentLocked(callerApp,
18591                     callerApp != null ? callerApp.info.packageName : null,
18592                     intent, resolvedType, resultTo, resultCode, resultData, resultExtras,
18593                     requiredPermissions, appOp, bOptions, serialized, sticky,
18594                     callingPid, callingUid, userId);
18595             Binder.restoreCallingIdentity(origId);
18596             return res;
18597         }
18598     }
18599
18600
18601     int broadcastIntentInPackage(String packageName, int uid,
18602             Intent intent, String resolvedType, IIntentReceiver resultTo,
18603             int resultCode, String resultData, Bundle resultExtras,
18604             String requiredPermission, Bundle bOptions, boolean serialized, boolean sticky,
18605             int userId) {
18606         synchronized(this) {
18607             intent = verifyBroadcastLocked(intent);
18608
18609             final long origId = Binder.clearCallingIdentity();
18610             String[] requiredPermissions = requiredPermission == null ? null
18611                     : new String[] {requiredPermission};
18612             int res = broadcastIntentLocked(null, packageName, intent, resolvedType,
18613                     resultTo, resultCode, resultData, resultExtras,
18614                     requiredPermissions, AppOpsManager.OP_NONE, bOptions, serialized,
18615                     sticky, -1, uid, userId);
18616             Binder.restoreCallingIdentity(origId);
18617             return res;
18618         }
18619     }
18620
18621     public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) {
18622         // Refuse possible leaked file descriptors
18623         if (intent != null && intent.hasFileDescriptors() == true) {
18624             throw new IllegalArgumentException("File descriptors passed in Intent");
18625         }
18626
18627         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
18628                 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null);
18629
18630         synchronized(this) {
18631             if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY)
18632                     != PackageManager.PERMISSION_GRANTED) {
18633                 String msg = "Permission Denial: unbroadcastIntent() from pid="
18634                         + Binder.getCallingPid()
18635                         + ", uid=" + Binder.getCallingUid()
18636                         + " requires " + android.Manifest.permission.BROADCAST_STICKY;
18637                 Slog.w(TAG, msg);
18638                 throw new SecurityException(msg);
18639             }
18640             ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId);
18641             if (stickies != null) {
18642                 ArrayList<Intent> list = stickies.get(intent.getAction());
18643                 if (list != null) {
18644                     int N = list.size();
18645                     int i;
18646                     for (i=0; i<N; i++) {
18647                         if (intent.filterEquals(list.get(i))) {
18648                             list.remove(i);
18649                             break;
18650                         }
18651                     }
18652                     if (list.size() <= 0) {
18653                         stickies.remove(intent.getAction());
18654                     }
18655                 }
18656                 if (stickies.size() <= 0) {
18657                     mStickyBroadcasts.remove(userId);
18658                 }
18659             }
18660         }
18661     }
18662
18663     void backgroundServicesFinishedLocked(int userId) {
18664         for (BroadcastQueue queue : mBroadcastQueues) {
18665             queue.backgroundServicesFinishedLocked(userId);
18666         }
18667     }
18668
18669     public void finishReceiver(IBinder who, int resultCode, String resultData,
18670             Bundle resultExtras, boolean resultAbort, int flags) {
18671         if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Finish receiver: " + who);
18672
18673         // Refuse possible leaked file descriptors
18674         if (resultExtras != null && resultExtras.hasFileDescriptors()) {
18675             throw new IllegalArgumentException("File descriptors passed in Bundle");
18676         }
18677
18678         final long origId = Binder.clearCallingIdentity();
18679         try {
18680             boolean doNext = false;
18681             BroadcastRecord r;
18682
18683             synchronized(this) {
18684                 BroadcastQueue queue = (flags & Intent.FLAG_RECEIVER_FOREGROUND) != 0
18685                         ? mFgBroadcastQueue : mBgBroadcastQueue;
18686                 r = queue.getMatchingOrderedReceiver(who);
18687                 if (r != null) {
18688                     doNext = r.queue.finishReceiverLocked(r, resultCode,
18689                         resultData, resultExtras, resultAbort, true);
18690                 }
18691             }
18692
18693             if (doNext) {
18694                 r.queue.processNextBroadcast(false);
18695             }
18696             trimApplications();
18697         } finally {
18698             Binder.restoreCallingIdentity(origId);
18699         }
18700     }
18701
18702     // =========================================================
18703     // INSTRUMENTATION
18704     // =========================================================
18705
18706     public boolean startInstrumentation(ComponentName className,
18707             String profileFile, int flags, Bundle arguments,
18708             IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection,
18709             int userId, String abiOverride) {
18710         enforceNotIsolatedCaller("startInstrumentation");
18711         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
18712                 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null);
18713         // Refuse possible leaked file descriptors
18714         if (arguments != null && arguments.hasFileDescriptors()) {
18715             throw new IllegalArgumentException("File descriptors passed in Bundle");
18716         }
18717
18718         synchronized(this) {
18719             InstrumentationInfo ii = null;
18720             ApplicationInfo ai = null;
18721             try {
18722                 ii = mContext.getPackageManager().getInstrumentationInfo(
18723                     className, STOCK_PM_FLAGS);
18724                 ai = AppGlobals.getPackageManager().getApplicationInfo(
18725                         ii.targetPackage, STOCK_PM_FLAGS, userId);
18726             } catch (PackageManager.NameNotFoundException e) {
18727             } catch (RemoteException e) {
18728             }
18729             if (ii == null) {
18730                 reportStartInstrumentationFailureLocked(watcher, className,
18731                         "Unable to find instrumentation info for: " + className);
18732                 return false;
18733             }
18734             if (ai == null) {
18735                 reportStartInstrumentationFailureLocked(watcher, className,
18736                         "Unable to find instrumentation target package: " + ii.targetPackage);
18737                 return false;
18738             }
18739             if (!ai.hasCode()) {
18740                 reportStartInstrumentationFailureLocked(watcher, className,
18741                         "Instrumentation target has no code: " + ii.targetPackage);
18742                 return false;
18743             }
18744
18745             int match = mContext.getPackageManager().checkSignatures(
18746                     ii.targetPackage, ii.packageName);
18747             if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) {
18748                 String msg = "Permission Denial: starting instrumentation "
18749                         + className + " from pid="
18750                         + Binder.getCallingPid()
18751                         + ", uid=" + Binder.getCallingPid()
18752                         + " not allowed because package " + ii.packageName
18753                         + " does not have a signature matching the target "
18754                         + ii.targetPackage;
18755                 reportStartInstrumentationFailureLocked(watcher, className, msg);
18756                 throw new SecurityException(msg);
18757             }
18758
18759             final long origId = Binder.clearCallingIdentity();
18760             // Instrumentation can kill and relaunch even persistent processes
18761             forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId,
18762                     "start instr");
18763             ProcessRecord app = addAppLocked(ai, false, abiOverride);
18764             app.instrumentationClass = className;
18765             app.instrumentationInfo = ai;
18766             app.instrumentationProfileFile = profileFile;
18767             app.instrumentationArguments = arguments;
18768             app.instrumentationWatcher = watcher;
18769             app.instrumentationUiAutomationConnection = uiAutomationConnection;
18770             app.instrumentationResultClass = className;
18771             Binder.restoreCallingIdentity(origId);
18772         }
18773
18774         return true;
18775     }
18776
18777     /**
18778      * Report errors that occur while attempting to start Instrumentation.  Always writes the
18779      * error to the logs, but if somebody is watching, send the report there too.  This enables
18780      * the "am" command to report errors with more information.
18781      *
18782      * @param watcher The IInstrumentationWatcher.  Null if there isn't one.
18783      * @param cn The component name of the instrumentation.
18784      * @param report The error report.
18785      */
18786     private void reportStartInstrumentationFailureLocked(IInstrumentationWatcher watcher,
18787             ComponentName cn, String report) {
18788         Slog.w(TAG, report);
18789         if (watcher != null) {
18790             Bundle results = new Bundle();
18791             results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService");
18792             results.putString("Error", report);
18793             mInstrumentationReporter.reportStatus(watcher, cn, -1, results);
18794         }
18795     }
18796
18797     void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) {
18798         if (app.instrumentationWatcher != null) {
18799             mInstrumentationReporter.reportFinished(app.instrumentationWatcher,
18800                     app.instrumentationClass, resultCode, results);
18801         }
18802
18803         // Can't call out of the system process with a lock held, so post a message.
18804         if (app.instrumentationUiAutomationConnection != null) {
18805             mHandler.obtainMessage(SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG,
18806                     app.instrumentationUiAutomationConnection).sendToTarget();
18807         }
18808
18809         app.instrumentationWatcher = null;
18810         app.instrumentationUiAutomationConnection = null;
18811         app.instrumentationClass = null;
18812         app.instrumentationInfo = null;
18813         app.instrumentationProfileFile = null;
18814         app.instrumentationArguments = null;
18815
18816         forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId,
18817                 "finished inst");
18818     }
18819
18820     public void finishInstrumentation(IApplicationThread target,
18821             int resultCode, Bundle results) {
18822         int userId = UserHandle.getCallingUserId();
18823         // Refuse possible leaked file descriptors
18824         if (results != null && results.hasFileDescriptors()) {
18825             throw new IllegalArgumentException("File descriptors passed in Intent");
18826         }
18827
18828         synchronized(this) {
18829             ProcessRecord app = getRecordForAppLocked(target);
18830             if (app == null) {
18831                 Slog.w(TAG, "finishInstrumentation: no app for " + target);
18832                 return;
18833             }
18834             final long origId = Binder.clearCallingIdentity();
18835             finishInstrumentationLocked(app, resultCode, results);
18836             Binder.restoreCallingIdentity(origId);
18837         }
18838     }
18839
18840     // =========================================================
18841     // CONFIGURATION
18842     // =========================================================
18843
18844     public ConfigurationInfo getDeviceConfigurationInfo() {
18845         ConfigurationInfo config = new ConfigurationInfo();
18846         synchronized (this) {
18847             config.reqTouchScreen = mConfiguration.touchscreen;
18848             config.reqKeyboardType = mConfiguration.keyboard;
18849             config.reqNavigation = mConfiguration.navigation;
18850             if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD
18851                     || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) {
18852                 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV;
18853             }
18854             if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED
18855                     && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) {
18856                 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD;
18857             }
18858             config.reqGlEsVersion = GL_ES_VERSION;
18859         }
18860         return config;
18861     }
18862
18863     ActivityStack getFocusedStack() {
18864         return mStackSupervisor.getFocusedStack();
18865     }
18866
18867     @Override
18868     public int getFocusedStackId() throws RemoteException {
18869         ActivityStack focusedStack = getFocusedStack();
18870         if (focusedStack != null) {
18871             return focusedStack.getStackId();
18872         }
18873         return -1;
18874     }
18875
18876     public Configuration getConfiguration() {
18877         Configuration ci;
18878         synchronized(this) {
18879             ci = new Configuration(mConfiguration);
18880             ci.userSetLocale = false;
18881         }
18882         return ci;
18883     }
18884
18885     @Override
18886     public void suppressResizeConfigChanges(boolean suppress) throws RemoteException {
18887         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "suppressResizeConfigChanges()");
18888         synchronized (this) {
18889             mSuppressResizeConfigChanges = suppress;
18890         }
18891     }
18892
18893     @Override
18894     public void moveTasksToFullscreenStack(int fromStackId, boolean onTop) {
18895         enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTasksToFullscreenStack()");
18896         if (fromStackId == HOME_STACK_ID) {
18897             throw new IllegalArgumentException("You can't move tasks from the home stack.");
18898         }
18899         synchronized (this) {
18900             final long origId = Binder.clearCallingIdentity();
18901             try {
18902                 mStackSupervisor.moveTasksToFullscreenStackLocked(fromStackId, onTop);
18903             } finally {
18904                 Binder.restoreCallingIdentity(origId);
18905             }
18906         }
18907     }
18908
18909     @Override
18910     public void updatePersistentConfiguration(Configuration values) {
18911         enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION,
18912                 "updateConfiguration()");
18913         enforceWriteSettingsPermission("updateConfiguration()");
18914         if (values == null) {
18915             throw new NullPointerException("Configuration must not be null");
18916         }
18917
18918         int userId = UserHandle.getCallingUserId();
18919
18920         synchronized(this) {
18921             updatePersistentConfigurationLocked(values, userId);
18922         }
18923     }
18924
18925     private void updatePersistentConfigurationLocked(Configuration values, @UserIdInt int userId) {
18926         final long origId = Binder.clearCallingIdentity();
18927         try {
18928             updateConfigurationLocked(values, null, false, true, userId, false /* deferResume */);
18929         } finally {
18930             Binder.restoreCallingIdentity(origId);
18931         }
18932     }
18933
18934     private void updateFontScaleIfNeeded(@UserIdInt int userId) {
18935         final float scaleFactor = Settings.System.getFloatForUser(mContext.getContentResolver(),
18936                 FONT_SCALE, 1.0f, userId);
18937         if (mConfiguration.fontScale != scaleFactor) {
18938             final Configuration configuration = mWindowManager.computeNewConfiguration();
18939             configuration.fontScale = scaleFactor;
18940             synchronized (this) {
18941                 updatePersistentConfigurationLocked(configuration, userId);
18942             }
18943         }
18944     }
18945
18946     private void enforceWriteSettingsPermission(String func) {
18947         int uid = Binder.getCallingUid();
18948         if (uid == Process.ROOT_UID) {
18949             return;
18950         }
18951
18952         if (Settings.checkAndNoteWriteSettingsOperation(mContext, uid,
18953                 Settings.getPackageNameForUid(mContext, uid), false)) {
18954             return;
18955         }
18956
18957         String msg = "Permission Denial: " + func + " from pid="
18958                 + Binder.getCallingPid()
18959                 + ", uid=" + uid
18960                 + " requires " + android.Manifest.permission.WRITE_SETTINGS;
18961         Slog.w(TAG, msg);
18962         throw new SecurityException(msg);
18963     }
18964
18965     public void updateConfiguration(Configuration values) {
18966         enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION,
18967                 "updateConfiguration()");
18968
18969         synchronized(this) {
18970             if (values == null && mWindowManager != null) {
18971                 // sentinel: fetch the current configuration from the window manager
18972                 values = mWindowManager.computeNewConfiguration();
18973             }
18974
18975             if (mWindowManager != null) {
18976                 mProcessList.applyDisplaySize(mWindowManager);
18977             }
18978
18979             final long origId = Binder.clearCallingIdentity();
18980             if (values != null) {
18981                 Settings.System.clearConfiguration(values);
18982             }
18983             updateConfigurationLocked(values, null, false);
18984             Binder.restoreCallingIdentity(origId);
18985         }
18986     }
18987
18988     void updateUserConfigurationLocked() {
18989         Configuration configuration = new Configuration(mConfiguration);
18990         Settings.System.adjustConfigurationForUser(mContext.getContentResolver(), configuration,
18991                 mUserController.getCurrentUserIdLocked(), Settings.System.canWrite(mContext));
18992         updateConfigurationLocked(configuration, null, false);
18993     }
18994
18995     boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
18996             boolean initLocale) {
18997         return updateConfigurationLocked(values, starting, initLocale, false /* deferResume */);
18998     }
18999
19000     boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
19001             boolean initLocale, boolean deferResume) {
19002         // pass UserHandle.USER_NULL as userId because we don't persist configuration for any user
19003         return updateConfigurationLocked(values, starting, initLocale, false /* persistent */,
19004                 UserHandle.USER_NULL, deferResume);
19005     }
19006
19007     // To cache the list of supported system locales
19008     private String[] mSupportedSystemLocales = null;
19009
19010     /**
19011      * Do either or both things: (1) change the current configuration, and (2)
19012      * make sure the given activity is running with the (now) current
19013      * configuration.  Returns true if the activity has been left running, or
19014      * false if <var>starting</var> is being destroyed to match the new
19015      * configuration.
19016      *
19017      * @param userId is only used when persistent parameter is set to true to persist configuration
19018      *               for that particular user
19019      */
19020     private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting,
19021             boolean initLocale, boolean persistent, int userId, boolean deferResume) {
19022         int changes = 0;
19023
19024         if (mWindowManager != null) {
19025             mWindowManager.deferSurfaceLayout();
19026         }
19027         if (values != null) {
19028             Configuration newConfig = new Configuration(mConfiguration);
19029             changes = newConfig.updateFrom(values);
19030             if (changes != 0) {
19031                 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) Slog.i(TAG_CONFIGURATION,
19032                         "Updating configuration to: " + values);
19033
19034                 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes);
19035
19036                 if (!initLocale && !values.getLocales().isEmpty() && values.userSetLocale) {
19037                     final LocaleList locales = values.getLocales();
19038                     int bestLocaleIndex = 0;
19039                     if (locales.size() > 1) {
19040                         if (mSupportedSystemLocales == null) {
19041                             mSupportedSystemLocales =
19042                                     Resources.getSystem().getAssets().getLocales();
19043                         }
19044                         bestLocaleIndex = Math.max(0,
19045                                 locales.getFirstMatchIndex(mSupportedSystemLocales));
19046                     }
19047                     SystemProperties.set("persist.sys.locale",
19048                             locales.get(bestLocaleIndex).toLanguageTag());
19049                     LocaleList.setDefault(locales, bestLocaleIndex);
19050                     mHandler.sendMessage(mHandler.obtainMessage(SEND_LOCALE_TO_MOUNT_DAEMON_MSG,
19051                             locales.get(bestLocaleIndex)));
19052                 }
19053
19054                 mConfigurationSeq++;
19055                 if (mConfigurationSeq <= 0) {
19056                     mConfigurationSeq = 1;
19057                 }
19058                 newConfig.seq = mConfigurationSeq;
19059                 mConfiguration = newConfig;
19060                 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig);
19061                 mUsageStatsService.reportConfigurationChange(newConfig,
19062                         mUserController.getCurrentUserIdLocked());
19063                 //mUsageStatsService.noteStartConfig(newConfig);
19064
19065                 final Configuration configCopy = new Configuration(mConfiguration);
19066
19067                 // TODO: If our config changes, should we auto dismiss any currently
19068                 // showing dialogs?
19069                 mShowDialogs = shouldShowDialogs(newConfig, mInVrMode);
19070
19071                 AttributeCache ac = AttributeCache.instance();
19072                 if (ac != null) {
19073                     ac.updateConfiguration(configCopy);
19074                 }
19075
19076                 // Make sure all resources in our process are updated
19077                 // right now, so that anyone who is going to retrieve
19078                 // resource values after we return will be sure to get
19079                 // the new ones.  This is especially important during
19080                 // boot, where the first config change needs to guarantee
19081                 // all resources have that config before following boot
19082                 // code is executed.
19083                 mSystemThread.applyConfigurationToResources(configCopy);
19084
19085                 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) {
19086                     Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG);
19087                     msg.obj = new Configuration(configCopy);
19088                     msg.arg1 = userId;
19089                     mHandler.sendMessage(msg);
19090                 }
19091
19092                 final boolean isDensityChange = (changes & ActivityInfo.CONFIG_DENSITY) != 0;
19093                 if (isDensityChange) {
19094                     // Reset the unsupported display size dialog.
19095                     mUiHandler.sendEmptyMessage(SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG);
19096
19097                     killAllBackgroundProcessesExcept(Build.VERSION_CODES.N,
19098                             ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE);
19099                 }
19100
19101                 for (int i=mLruProcesses.size()-1; i>=0; i--) {
19102                     ProcessRecord app = mLruProcesses.get(i);
19103                     try {
19104                         if (app.thread != null) {
19105                             if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Sending to proc "
19106                                     + app.processName + " new config " + mConfiguration);
19107                             app.thread.scheduleConfigurationChanged(configCopy);
19108                         }
19109                     } catch (Exception e) {
19110                     }
19111                 }
19112                 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED);
19113                 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY
19114                         | Intent.FLAG_RECEIVER_REPLACE_PENDING
19115                         | Intent.FLAG_RECEIVER_FOREGROUND);
19116                 broadcastIntentLocked(null, null, intent, null, null, 0, null, null,
19117                         null, AppOpsManager.OP_NONE, null, false, false,
19118                         MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL);
19119                 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) {
19120                     intent = new Intent(Intent.ACTION_LOCALE_CHANGED);
19121                     intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
19122                     if (initLocale || !mProcessesReady) {
19123                         intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
19124                     }
19125                     broadcastIntentLocked(null, null, intent,
19126                             null, null, 0, null, null, null, AppOpsManager.OP_NONE,
19127                             null, false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL);
19128                 }
19129             }
19130             // Update the configuration with WM first and check if any of the stacks need to be
19131             // resized due to the configuration change. If so, resize the stacks now and do any
19132             // relaunches if necessary. This way we don't need to relaunch again below in
19133             // ensureActivityConfigurationLocked().
19134             if (mWindowManager != null) {
19135                 final int[] resizedStacks = mWindowManager.setNewConfiguration(mConfiguration);
19136                 if (resizedStacks != null) {
19137                     for (int stackId : resizedStacks) {
19138                         final Rect newBounds = mWindowManager.getBoundsForNewConfiguration(stackId);
19139                         mStackSupervisor.resizeStackLocked(
19140                                 stackId, newBounds, null, null, false, false, deferResume);
19141                     }
19142                 }
19143             }
19144         }
19145
19146         boolean kept = true;
19147         final ActivityStack mainStack = mStackSupervisor.getFocusedStack();
19148         // mainStack is null during startup.
19149         if (mainStack != null) {
19150             if (changes != 0 && starting == null) {
19151                 // If the configuration changed, and the caller is not already
19152                 // in the process of starting an activity, then find the top
19153                 // activity to check if its configuration needs to change.
19154                 starting = mainStack.topRunningActivityLocked();
19155             }
19156
19157             if (starting != null) {
19158                 kept = mainStack.ensureActivityConfigurationLocked(starting, changes, false);
19159                 // And we need to make sure at this point that all other activities
19160                 // are made visible with the correct configuration.
19161                 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes,
19162                         !PRESERVE_WINDOWS);
19163             }
19164         }
19165         if (mWindowManager != null) {
19166             mWindowManager.continueSurfaceLayout();
19167         }
19168         return kept;
19169     }
19170
19171     /**
19172      * Decide based on the configuration whether we should shouw the ANR,
19173      * crash, etc dialogs.  The idea is that if there is no affordence to
19174      * press the on-screen buttons, or the user experience would be more
19175      * greatly impacted than the crash itself, we shouldn't show the dialog.
19176      *
19177      * A thought: SystemUI might also want to get told about this, the Power
19178      * dialog / global actions also might want different behaviors.
19179      */
19180     private static final boolean shouldShowDialogs(Configuration config, boolean inVrMode) {
19181         final boolean inputMethodExists = !(config.keyboard == Configuration.KEYBOARD_NOKEYS
19182                                    && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH
19183                                    && config.navigation == Configuration.NAVIGATION_NONAV);
19184         int modeType = config.uiMode & Configuration.UI_MODE_TYPE_MASK;
19185         final boolean uiModeSupportsDialogs = (modeType != Configuration.UI_MODE_TYPE_CAR
19186                 && !(modeType == Configuration.UI_MODE_TYPE_WATCH && "user".equals(Build.TYPE)));
19187         return inputMethodExists && uiModeSupportsDialogs && !inVrMode;
19188     }
19189
19190     @Override
19191     public boolean shouldUpRecreateTask(IBinder token, String destAffinity) {
19192         synchronized (this) {
19193             ActivityRecord srec = ActivityRecord.forTokenLocked(token);
19194             if (srec != null) {
19195                 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity);
19196             }
19197         }
19198         return false;
19199     }
19200
19201     public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode,
19202             Intent resultData) {
19203
19204         synchronized (this) {
19205             final ActivityRecord r = ActivityRecord.forTokenLocked(token);
19206             if (r != null) {
19207                 return r.task.stack.navigateUpToLocked(r, destIntent, resultCode, resultData);
19208             }
19209             return false;
19210         }
19211     }
19212
19213     public int getLaunchedFromUid(IBinder activityToken) {
19214         ActivityRecord srec;
19215         synchronized (this) {
19216             srec = ActivityRecord.forTokenLocked(activityToken);
19217         }
19218         if (srec == null) {
19219             return -1;
19220         }
19221         return srec.launchedFromUid;
19222     }
19223
19224     public String getLaunchedFromPackage(IBinder activityToken) {
19225         ActivityRecord srec;
19226         synchronized (this) {
19227             srec = ActivityRecord.forTokenLocked(activityToken);
19228         }
19229         if (srec == null) {
19230             return null;
19231         }
19232         return srec.launchedFromPackage;
19233     }
19234
19235     // =========================================================
19236     // LIFETIME MANAGEMENT
19237     // =========================================================
19238
19239     // Returns which broadcast queue the app is the current [or imminent] receiver
19240     // on, or 'null' if the app is not an active broadcast recipient.
19241     private BroadcastQueue isReceivingBroadcast(ProcessRecord app) {
19242         BroadcastRecord r = app.curReceiver;
19243         if (r != null) {
19244             return r.queue;
19245         }
19246
19247         // It's not the current receiver, but it might be starting up to become one
19248         synchronized (this) {
19249             for (BroadcastQueue queue : mBroadcastQueues) {
19250                 r = queue.mPendingBroadcast;
19251                 if (r != null && r.curApp == app) {
19252                     // found it; report which queue it's in
19253                     return queue;
19254                 }
19255             }
19256         }
19257
19258         return null;
19259     }
19260
19261     Association startAssociationLocked(int sourceUid, String sourceProcess, int sourceState,
19262             int targetUid, ComponentName targetComponent, String targetProcess) {
19263         if (!mTrackingAssociations) {
19264             return null;
19265         }
19266         ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components
19267                 = mAssociations.get(targetUid);
19268         if (components == null) {
19269             components = new ArrayMap<>();
19270             mAssociations.put(targetUid, components);
19271         }
19272         SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent);
19273         if (sourceUids == null) {
19274             sourceUids = new SparseArray<>();
19275             components.put(targetComponent, sourceUids);
19276         }
19277         ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid);
19278         if (sourceProcesses == null) {
19279             sourceProcesses = new ArrayMap<>();
19280             sourceUids.put(sourceUid, sourceProcesses);
19281         }
19282         Association ass = sourceProcesses.get(sourceProcess);
19283         if (ass == null) {
19284             ass = new Association(sourceUid, sourceProcess, targetUid, targetComponent,
19285                     targetProcess);
19286             sourceProcesses.put(sourceProcess, ass);
19287         }
19288         ass.mCount++;
19289         ass.mNesting++;
19290         if (ass.mNesting == 1) {
19291             ass.mStartTime = ass.mLastStateUptime = SystemClock.uptimeMillis();
19292             ass.mLastState = sourceState;
19293         }
19294         return ass;
19295     }
19296
19297     void stopAssociationLocked(int sourceUid, String sourceProcess, int targetUid,
19298             ComponentName targetComponent) {
19299         if (!mTrackingAssociations) {
19300             return;
19301         }
19302         ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components
19303                 = mAssociations.get(targetUid);
19304         if (components == null) {
19305             return;
19306         }
19307         SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent);
19308         if (sourceUids == null) {
19309             return;
19310         }
19311         ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid);
19312         if (sourceProcesses == null) {
19313             return;
19314         }
19315         Association ass = sourceProcesses.get(sourceProcess);
19316         if (ass == null || ass.mNesting <= 0) {
19317             return;
19318         }
19319         ass.mNesting--;
19320         if (ass.mNesting == 0) {
19321             long uptime = SystemClock.uptimeMillis();
19322             ass.mTime += uptime - ass.mStartTime;
19323             ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE]
19324                     += uptime - ass.mLastStateUptime;
19325             ass.mLastState = ActivityManager.MAX_PROCESS_STATE + 2;
19326         }
19327     }
19328
19329     private void noteUidProcessState(final int uid, final int state) {
19330         mBatteryStatsService.noteUidProcessState(uid, state);
19331         if (mTrackingAssociations) {
19332             for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) {
19333                 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents
19334                         = mAssociations.valueAt(i1);
19335                 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) {
19336                     SparseArray<ArrayMap<String, Association>> sourceUids
19337                             = targetComponents.valueAt(i2);
19338                     ArrayMap<String, Association> sourceProcesses = sourceUids.get(uid);
19339                     if (sourceProcesses != null) {
19340                         for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) {
19341                             Association ass = sourceProcesses.valueAt(i4);
19342                             if (ass.mNesting >= 1) {
19343                                 // currently associated
19344                                 long uptime = SystemClock.uptimeMillis();
19345                                 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE]
19346                                         += uptime - ass.mLastStateUptime;
19347                                 ass.mLastState = state;
19348                                 ass.mLastStateUptime = uptime;
19349                             }
19350                         }
19351                     }
19352                 }
19353             }
19354         }
19355     }
19356
19357     private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP,
19358             boolean doingAll, long now) {
19359         if (mAdjSeq == app.adjSeq) {
19360             // This adjustment has already been computed.
19361             return app.curRawAdj;
19362         }
19363
19364         if (app.thread == null) {
19365             app.adjSeq = mAdjSeq;
19366             app.curSchedGroup = ProcessList.SCHED_GROUP_BACKGROUND;
19367             app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY;
19368             return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ);
19369         }
19370
19371         app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN;
19372         app.adjSource = null;
19373         app.adjTarget = null;
19374         app.empty = false;
19375         app.cached = false;
19376
19377         final int activitiesSize = app.activities.size();
19378
19379         if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) {
19380             // The max adjustment doesn't allow this app to be anything
19381             // below foreground, so it is not worth doing work for it.
19382             app.adjType = "fixed";
19383             app.adjSeq = mAdjSeq;
19384             app.curRawAdj = app.maxAdj;
19385             app.foregroundActivities = false;
19386             app.curSchedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19387             app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT;
19388             // System processes can do UI, and when they do we want to have
19389             // them trim their memory after the user leaves the UI.  To
19390             // facilitate this, here we need to determine whether or not it
19391             // is currently showing UI.
19392             app.systemNoUi = true;
19393             if (app == TOP_APP) {
19394                 app.systemNoUi = false;
19395                 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP;
19396                 app.adjType = "pers-top-activity";
19397             } else if (app.hasTopUi) {
19398                 app.systemNoUi = false;
19399                 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP;
19400                 app.adjType = "pers-top-ui";
19401             } else if (activitiesSize > 0) {
19402                 for (int j = 0; j < activitiesSize; j++) {
19403                     final ActivityRecord r = app.activities.get(j);
19404                     if (r.visible) {
19405                         app.systemNoUi = false;
19406                     }
19407                 }
19408             }
19409             if (!app.systemNoUi) {
19410                 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI;
19411             }
19412             return (app.curAdj=app.maxAdj);
19413         }
19414
19415         app.systemNoUi = false;
19416
19417         final int PROCESS_STATE_CUR_TOP = mTopProcessState;
19418
19419         // Determine the importance of the process, starting with most
19420         // important to least, and assign an appropriate OOM adjustment.
19421         int adj;
19422         int schedGroup;
19423         int procState;
19424         boolean foregroundActivities = false;
19425         BroadcastQueue queue;
19426         if (app == TOP_APP) {
19427             // The last app on the list is the foreground app.
19428             adj = ProcessList.FOREGROUND_APP_ADJ;
19429             schedGroup = ProcessList.SCHED_GROUP_TOP_APP;
19430             app.adjType = "top-activity";
19431             foregroundActivities = true;
19432             procState = PROCESS_STATE_CUR_TOP;
19433         } else if (app.instrumentationClass != null) {
19434             // Don't want to kill running instrumentation.
19435             adj = ProcessList.FOREGROUND_APP_ADJ;
19436             schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19437             app.adjType = "instrumentation";
19438             procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE;
19439         } else if ((queue = isReceivingBroadcast(app)) != null) {
19440             // An app that is currently receiving a broadcast also
19441             // counts as being in the foreground for OOM killer purposes.
19442             // It's placed in a sched group based on the nature of the
19443             // broadcast as reflected by which queue it's active in.
19444             adj = ProcessList.FOREGROUND_APP_ADJ;
19445             schedGroup = (queue == mFgBroadcastQueue)
19446                     ? ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND;
19447             app.adjType = "broadcast";
19448             procState = ActivityManager.PROCESS_STATE_RECEIVER;
19449         } else if (app.executingServices.size() > 0) {
19450             // An app that is currently executing a service callback also
19451             // counts as being in the foreground.
19452             adj = ProcessList.FOREGROUND_APP_ADJ;
19453             schedGroup = app.execServicesFg ?
19454                     ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND;
19455             app.adjType = "exec-service";
19456             procState = ActivityManager.PROCESS_STATE_SERVICE;
19457             //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app);
19458         } else {
19459             // As far as we know the process is empty.  We may change our mind later.
19460             schedGroup = ProcessList.SCHED_GROUP_BACKGROUND;
19461             // At this point we don't actually know the adjustment.  Use the cached adj
19462             // value that the caller wants us to.
19463             adj = cachedAdj;
19464             procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY;
19465             app.cached = true;
19466             app.empty = true;
19467             app.adjType = "cch-empty";
19468         }
19469
19470         // Examine all activities if not already foreground.
19471         if (!foregroundActivities && activitiesSize > 0) {
19472             int minLayer = ProcessList.VISIBLE_APP_LAYER_MAX;
19473             for (int j = 0; j < activitiesSize; j++) {
19474                 final ActivityRecord r = app.activities.get(j);
19475                 if (r.app != app) {
19476                     Log.e(TAG, "Found activity " + r + " in proc activity list using " + r.app
19477                             + " instead of expected " + app);
19478                     if (r.app == null || (r.app.uid == app.uid)) {
19479                         // Only fix things up when they look sane
19480                         r.app = app;
19481                     } else {
19482                         continue;
19483                     }
19484                 }
19485                 if (r.visible) {
19486                     // App has a visible activity; only upgrade adjustment.
19487                     if (adj > ProcessList.VISIBLE_APP_ADJ) {
19488                         adj = ProcessList.VISIBLE_APP_ADJ;
19489                         app.adjType = "visible";
19490                     }
19491                     if (procState > PROCESS_STATE_CUR_TOP) {
19492                         procState = PROCESS_STATE_CUR_TOP;
19493                     }
19494                     schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19495                     app.cached = false;
19496                     app.empty = false;
19497                     foregroundActivities = true;
19498                     if (r.task != null && minLayer > 0) {
19499                         final int layer = r.task.mLayerRank;
19500                         if (layer >= 0 && minLayer > layer) {
19501                             minLayer = layer;
19502                         }
19503                     }
19504                     break;
19505                 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) {
19506                     if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) {
19507                         adj = ProcessList.PERCEPTIBLE_APP_ADJ;
19508                         app.adjType = "pausing";
19509                     }
19510                     if (procState > PROCESS_STATE_CUR_TOP) {
19511                         procState = PROCESS_STATE_CUR_TOP;
19512                     }
19513                     schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19514                     app.cached = false;
19515                     app.empty = false;
19516                     foregroundActivities = true;
19517                 } else if (r.state == ActivityState.STOPPING) {
19518                     if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) {
19519                         adj = ProcessList.PERCEPTIBLE_APP_ADJ;
19520                         app.adjType = "stopping";
19521                     }
19522                     // For the process state, we will at this point consider the
19523                     // process to be cached.  It will be cached either as an activity
19524                     // or empty depending on whether the activity is finishing.  We do
19525                     // this so that we can treat the process as cached for purposes of
19526                     // memory trimming (determing current memory level, trim command to
19527                     // send to process) since there can be an arbitrary number of stopping
19528                     // processes and they should soon all go into the cached state.
19529                     if (!r.finishing) {
19530                         if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) {
19531                             procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY;
19532                         }
19533                     }
19534                     app.cached = false;
19535                     app.empty = false;
19536                     foregroundActivities = true;
19537                 } else {
19538                     if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) {
19539                         procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY;
19540                         app.adjType = "cch-act";
19541                     }
19542                 }
19543             }
19544             if (adj == ProcessList.VISIBLE_APP_ADJ) {
19545                 adj += minLayer;
19546             }
19547         }
19548
19549         if (adj > ProcessList.PERCEPTIBLE_APP_ADJ
19550                 || procState > ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE) {
19551             if (app.foregroundServices) {
19552                 // The user is aware of this app, so make it visible.
19553                 adj = ProcessList.PERCEPTIBLE_APP_ADJ;
19554                 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE;
19555                 app.cached = false;
19556                 app.adjType = "fg-service";
19557                 schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19558             } else if (app.forcingToForeground != null) {
19559                 // The user is aware of this app, so make it visible.
19560                 adj = ProcessList.PERCEPTIBLE_APP_ADJ;
19561                 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND;
19562                 app.cached = false;
19563                 app.adjType = "force-fg";
19564                 app.adjSource = app.forcingToForeground;
19565                 schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19566             }
19567         }
19568
19569         if (app == mHeavyWeightProcess) {
19570             if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) {
19571                 // We don't want to kill the current heavy-weight process.
19572                 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ;
19573                 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND;
19574                 app.cached = false;
19575                 app.adjType = "heavy";
19576             }
19577             if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) {
19578                 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT;
19579             }
19580         }
19581
19582         if (app == mHomeProcess) {
19583             if (adj > ProcessList.HOME_APP_ADJ) {
19584                 // This process is hosting what we currently consider to be the
19585                 // home app, so we don't want to let it go into the background.
19586                 adj = ProcessList.HOME_APP_ADJ;
19587                 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND;
19588                 app.cached = false;
19589                 app.adjType = "home";
19590             }
19591             if (procState > ActivityManager.PROCESS_STATE_HOME) {
19592                 procState = ActivityManager.PROCESS_STATE_HOME;
19593             }
19594         }
19595
19596         if (app == mPreviousProcess && app.activities.size() > 0) {
19597             if (adj > ProcessList.PREVIOUS_APP_ADJ) {
19598                 // This was the previous process that showed UI to the user.
19599                 // We want to try to keep it around more aggressively, to give
19600                 // a good experience around switching between two apps.
19601                 adj = ProcessList.PREVIOUS_APP_ADJ;
19602                 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND;
19603                 app.cached = false;
19604                 app.adjType = "previous";
19605             }
19606             if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) {
19607                 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY;
19608             }
19609         }
19610
19611         if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj
19612                 + " reason=" + app.adjType);
19613
19614         // By default, we use the computed adjustment.  It may be changed if
19615         // there are applications dependent on our services or providers, but
19616         // this gives us a baseline and makes sure we don't get into an
19617         // infinite recursion.
19618         app.adjSeq = mAdjSeq;
19619         app.curRawAdj = adj;
19620         app.hasStartedServices = false;
19621
19622         if (mBackupTarget != null && app == mBackupTarget.app) {
19623             // If possible we want to avoid killing apps while they're being backed up
19624             if (adj > ProcessList.BACKUP_APP_ADJ) {
19625                 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "oom BACKUP_APP_ADJ for " + app);
19626                 adj = ProcessList.BACKUP_APP_ADJ;
19627                 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) {
19628                     procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND;
19629                 }
19630                 app.adjType = "backup";
19631                 app.cached = false;
19632             }
19633             if (procState > ActivityManager.PROCESS_STATE_BACKUP) {
19634                 procState = ActivityManager.PROCESS_STATE_BACKUP;
19635             }
19636         }
19637
19638         boolean mayBeTop = false;
19639
19640         for (int is = app.services.size()-1;
19641                 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ
19642                         || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND
19643                         || procState > ActivityManager.PROCESS_STATE_TOP);
19644                 is--) {
19645             ServiceRecord s = app.services.valueAt(is);
19646             if (s.startRequested) {
19647                 app.hasStartedServices = true;
19648                 if (procState > ActivityManager.PROCESS_STATE_SERVICE) {
19649                     procState = ActivityManager.PROCESS_STATE_SERVICE;
19650                 }
19651                 if (app.hasShownUi && app != mHomeProcess) {
19652                     // If this process has shown some UI, let it immediately
19653                     // go to the LRU list because it may be pretty heavy with
19654                     // UI stuff.  We'll tag it with a label just to help
19655                     // debug and understand what is going on.
19656                     if (adj > ProcessList.SERVICE_ADJ) {
19657                         app.adjType = "cch-started-ui-services";
19658                     }
19659                 } else {
19660                     if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) {
19661                         // This service has seen some activity within
19662                         // recent memory, so we will keep its process ahead
19663                         // of the background processes.
19664                         if (adj > ProcessList.SERVICE_ADJ) {
19665                             adj = ProcessList.SERVICE_ADJ;
19666                             app.adjType = "started-services";
19667                             app.cached = false;
19668                         }
19669                     }
19670                     // If we have let the service slide into the background
19671                     // state, still have some text describing what it is doing
19672                     // even though the service no longer has an impact.
19673                     if (adj > ProcessList.SERVICE_ADJ) {
19674                         app.adjType = "cch-started-services";
19675                     }
19676                 }
19677             }
19678
19679             for (int conni = s.connections.size()-1;
19680                     conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ
19681                             || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND
19682                             || procState > ActivityManager.PROCESS_STATE_TOP);
19683                     conni--) {
19684                 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni);
19685                 for (int i = 0;
19686                         i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ
19687                                 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND
19688                                 || procState > ActivityManager.PROCESS_STATE_TOP);
19689                         i++) {
19690                     // XXX should compute this based on the max of
19691                     // all connected clients.
19692                     ConnectionRecord cr = clist.get(i);
19693                     if (cr.binding.client == app) {
19694                         // Binding to ourself is not interesting.
19695                         continue;
19696                     }
19697
19698                     if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) {
19699                         ProcessRecord client = cr.binding.client;
19700                         int clientAdj = computeOomAdjLocked(client, cachedAdj,
19701                                 TOP_APP, doingAll, now);
19702                         int clientProcState = client.curProcState;
19703                         if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) {
19704                             // If the other app is cached for any reason, for purposes here
19705                             // we are going to consider it empty.  The specific cached state
19706                             // doesn't propagate except under certain conditions.
19707                             clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY;
19708                         }
19709                         String adjType = null;
19710                         if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) {
19711                             // Not doing bind OOM management, so treat
19712                             // this guy more like a started service.
19713                             if (app.hasShownUi && app != mHomeProcess) {
19714                                 // If this process has shown some UI, let it immediately
19715                                 // go to the LRU list because it may be pretty heavy with
19716                                 // UI stuff.  We'll tag it with a label just to help
19717                                 // debug and understand what is going on.
19718                                 if (adj > clientAdj) {
19719                                     adjType = "cch-bound-ui-services";
19720                                 }
19721                                 app.cached = false;
19722                                 clientAdj = adj;
19723                                 clientProcState = procState;
19724                             } else {
19725                                 if (now >= (s.lastActivity
19726                                         + ActiveServices.MAX_SERVICE_INACTIVITY)) {
19727                                     // This service has not seen activity within
19728                                     // recent memory, so allow it to drop to the
19729                                     // LRU list if there is no other reason to keep
19730                                     // it around.  We'll also tag it with a label just
19731                                     // to help debug and undertand what is going on.
19732                                     if (adj > clientAdj) {
19733                                         adjType = "cch-bound-services";
19734                                     }
19735                                     clientAdj = adj;
19736                                 }
19737                             }
19738                         }
19739                         if (adj > clientAdj) {
19740                             // If this process has recently shown UI, and
19741                             // the process that is binding to it is less
19742                             // important than being visible, then we don't
19743                             // care about the binding as much as we care
19744                             // about letting this process get into the LRU
19745                             // list to be killed and restarted if needed for
19746                             // memory.
19747                             if (app.hasShownUi && app != mHomeProcess
19748                                     && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) {
19749                                 adjType = "cch-bound-ui-services";
19750                             } else {
19751                                 if ((cr.flags&(Context.BIND_ABOVE_CLIENT
19752                                         |Context.BIND_IMPORTANT)) != 0) {
19753                                     adj = clientAdj >= ProcessList.PERSISTENT_SERVICE_ADJ
19754                                             ? clientAdj : ProcessList.PERSISTENT_SERVICE_ADJ;
19755                                 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0
19756                                         && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ
19757                                         && adj > ProcessList.PERCEPTIBLE_APP_ADJ) {
19758                                     adj = ProcessList.PERCEPTIBLE_APP_ADJ;
19759                                 } else if (clientAdj >= ProcessList.PERCEPTIBLE_APP_ADJ) {
19760                                     adj = clientAdj;
19761                                 } else {
19762                                     if (adj > ProcessList.VISIBLE_APP_ADJ) {
19763                                         adj = Math.max(clientAdj, ProcessList.VISIBLE_APP_ADJ);
19764                                     }
19765                                 }
19766                                 if (!client.cached) {
19767                                     app.cached = false;
19768                                 }
19769                                 adjType = "service";
19770                             }
19771                         }
19772                         if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) {
19773                             // This will treat important bound services identically to
19774                             // the top app, which may behave differently than generic
19775                             // foreground work.
19776                             if (client.curSchedGroup > schedGroup) {
19777                                 if ((cr.flags&Context.BIND_IMPORTANT) != 0) {
19778                                     schedGroup = client.curSchedGroup;
19779                                 } else {
19780                                     schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19781                                 }
19782                             }
19783                             if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) {
19784                                 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) {
19785                                     // Special handling of clients who are in the top state.
19786                                     // We *may* want to consider this process to be in the
19787                                     // top state as well, but only if there is not another
19788                                     // reason for it to be running.  Being on the top is a
19789                                     // special state, meaning you are specifically running
19790                                     // for the current top app.  If the process is already
19791                                     // running in the background for some other reason, it
19792                                     // is more important to continue considering it to be
19793                                     // in the background state.
19794                                     mayBeTop = true;
19795                                     clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY;
19796                                 } else {
19797                                     // Special handling for above-top states (persistent
19798                                     // processes).  These should not bring the current process
19799                                     // into the top state, since they are not on top.  Instead
19800                                     // give them the best state after that.
19801                                     if ((cr.flags&Context.BIND_FOREGROUND_SERVICE) != 0) {
19802                                         clientProcState =
19803                                                 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE;
19804                                     } else if (mWakefulness
19805                                                     == PowerManagerInternal.WAKEFULNESS_AWAKE &&
19806                                             (cr.flags&Context.BIND_FOREGROUND_SERVICE_WHILE_AWAKE)
19807                                                     != 0) {
19808                                         clientProcState =
19809                                                 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE;
19810                                     } else {
19811                                         clientProcState =
19812                                                 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND;
19813                                     }
19814                                 }
19815                             }
19816                         } else {
19817                             if (clientProcState <
19818                                     ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) {
19819                                 clientProcState =
19820                                         ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND;
19821                             }
19822                         }
19823                         if (procState > clientProcState) {
19824                             procState = clientProcState;
19825                         }
19826                         if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND
19827                                 && (cr.flags&Context.BIND_SHOWING_UI) != 0) {
19828                             app.pendingUiClean = true;
19829                         }
19830                         if (adjType != null) {
19831                             app.adjType = adjType;
19832                             app.adjTypeCode = ActivityManager.RunningAppProcessInfo
19833                                     .REASON_SERVICE_IN_USE;
19834                             app.adjSource = cr.binding.client;
19835                             app.adjSourceProcState = clientProcState;
19836                             app.adjTarget = s.name;
19837                         }
19838                     }
19839                     if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) {
19840                         app.treatLikeActivity = true;
19841                     }
19842                     final ActivityRecord a = cr.activity;
19843                     if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) {
19844                         if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ &&
19845                             (a.visible || a.state == ActivityState.RESUMED ||
19846                              a.state == ActivityState.PAUSING)) {
19847                             adj = ProcessList.FOREGROUND_APP_ADJ;
19848                             if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) {
19849                                 if ((cr.flags&Context.BIND_IMPORTANT) != 0) {
19850                                     schedGroup = ProcessList.SCHED_GROUP_TOP_APP_BOUND;
19851                                 } else {
19852                                     schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19853                                 }
19854                             }
19855                             app.cached = false;
19856                             app.adjType = "service";
19857                             app.adjTypeCode = ActivityManager.RunningAppProcessInfo
19858                                     .REASON_SERVICE_IN_USE;
19859                             app.adjSource = a;
19860                             app.adjSourceProcState = procState;
19861                             app.adjTarget = s.name;
19862                         }
19863                     }
19864                 }
19865             }
19866         }
19867
19868         for (int provi = app.pubProviders.size()-1;
19869                 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ
19870                         || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND
19871                         || procState > ActivityManager.PROCESS_STATE_TOP);
19872                 provi--) {
19873             ContentProviderRecord cpr = app.pubProviders.valueAt(provi);
19874             for (int i = cpr.connections.size()-1;
19875                     i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ
19876                             || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND
19877                             || procState > ActivityManager.PROCESS_STATE_TOP);
19878                     i--) {
19879                 ContentProviderConnection conn = cpr.connections.get(i);
19880                 ProcessRecord client = conn.client;
19881                 if (client == app) {
19882                     // Being our own client is not interesting.
19883                     continue;
19884                 }
19885                 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now);
19886                 int clientProcState = client.curProcState;
19887                 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) {
19888                     // If the other app is cached for any reason, for purposes here
19889                     // we are going to consider it empty.
19890                     clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY;
19891                 }
19892                 if (adj > clientAdj) {
19893                     if (app.hasShownUi && app != mHomeProcess
19894                             && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) {
19895                         app.adjType = "cch-ui-provider";
19896                     } else {
19897                         adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ
19898                                 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ;
19899                         app.adjType = "provider";
19900                     }
19901                     app.cached &= client.cached;
19902                     app.adjTypeCode = ActivityManager.RunningAppProcessInfo
19903                             .REASON_PROVIDER_IN_USE;
19904                     app.adjSource = client;
19905                     app.adjSourceProcState = clientProcState;
19906                     app.adjTarget = cpr.name;
19907                 }
19908                 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) {
19909                     if (clientProcState == ActivityManager.PROCESS_STATE_TOP) {
19910                         // Special handling of clients who are in the top state.
19911                         // We *may* want to consider this process to be in the
19912                         // top state as well, but only if there is not another
19913                         // reason for it to be running.  Being on the top is a
19914                         // special state, meaning you are specifically running
19915                         // for the current top app.  If the process is already
19916                         // running in the background for some other reason, it
19917                         // is more important to continue considering it to be
19918                         // in the background state.
19919                         mayBeTop = true;
19920                         clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY;
19921                     } else {
19922                         // Special handling for above-top states (persistent
19923                         // processes).  These should not bring the current process
19924                         // into the top state, since they are not on top.  Instead
19925                         // give them the best state after that.
19926                         clientProcState =
19927                                 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE;
19928                     }
19929                 }
19930                 if (procState > clientProcState) {
19931                     procState = clientProcState;
19932                 }
19933                 if (client.curSchedGroup > schedGroup) {
19934                     schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19935                 }
19936             }
19937             // If the provider has external (non-framework) process
19938             // dependencies, ensure that its adjustment is at least
19939             // FOREGROUND_APP_ADJ.
19940             if (cpr.hasExternalProcessHandles()) {
19941                 if (adj > ProcessList.FOREGROUND_APP_ADJ) {
19942                     adj = ProcessList.FOREGROUND_APP_ADJ;
19943                     schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
19944                     app.cached = false;
19945                     app.adjType = "provider";
19946                     app.adjTarget = cpr.name;
19947                 }
19948                 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) {
19949                     procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND;
19950                 }
19951             }
19952         }
19953
19954         if (app.lastProviderTime > 0 && (app.lastProviderTime+CONTENT_PROVIDER_RETAIN_TIME) > now) {
19955             if (adj > ProcessList.PREVIOUS_APP_ADJ) {
19956                 adj = ProcessList.PREVIOUS_APP_ADJ;
19957                 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND;
19958                 app.cached = false;
19959                 app.adjType = "provider";
19960             }
19961             if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) {
19962                 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY;
19963             }
19964         }
19965
19966         if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) {
19967             // A client of one of our services or providers is in the top state.  We
19968             // *may* want to be in the top state, but not if we are already running in
19969             // the background for some other reason.  For the decision here, we are going
19970             // to pick out a few specific states that we want to remain in when a client
19971             // is top (states that tend to be longer-term) and otherwise allow it to go
19972             // to the top state.
19973             switch (procState) {
19974                 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND:
19975                 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND:
19976                 case ActivityManager.PROCESS_STATE_SERVICE:
19977                     // These all are longer-term states, so pull them up to the top
19978                     // of the background states, but not all the way to the top state.
19979                     procState = ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE;
19980                     break;
19981                 default:
19982                     // Otherwise, top is a better choice, so take it.
19983                     procState = ActivityManager.PROCESS_STATE_TOP;
19984                     break;
19985             }
19986         }
19987
19988         if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) {
19989             if (app.hasClientActivities) {
19990                 // This is a cached process, but with client activities.  Mark it so.
19991                 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT;
19992                 app.adjType = "cch-client-act";
19993             } else if (app.treatLikeActivity) {
19994                 // This is a cached process, but somebody wants us to treat it like it has
19995                 // an activity, okay!
19996                 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY;
19997                 app.adjType = "cch-as-act";
19998             }
19999         }
20000
20001         if (adj == ProcessList.SERVICE_ADJ) {
20002             if (doingAll) {
20003                 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3);
20004                 mNewNumServiceProcs++;
20005                 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb);
20006                 if (!app.serviceb) {
20007                     // This service isn't far enough down on the LRU list to
20008                     // normally be a B service, but if we are low on RAM and it
20009                     // is large we want to force it down since we would prefer to
20010                     // keep launcher over it.
20011                     if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL
20012                             && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) {
20013                         app.serviceHighRam = true;
20014                         app.serviceb = true;
20015                         //Slog.i(TAG, "ADJ " + app + " high ram!");
20016                     } else {
20017                         mNewNumAServiceProcs++;
20018                         //Slog.i(TAG, "ADJ " + app + " not high ram!");
20019                     }
20020                 } else {
20021                     app.serviceHighRam = false;
20022                 }
20023             }
20024             if (app.serviceb) {
20025                 adj = ProcessList.SERVICE_B_ADJ;
20026             }
20027         }
20028
20029         app.curRawAdj = adj;
20030
20031         //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid +
20032         //      " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj);
20033         if (adj > app.maxAdj) {
20034             adj = app.maxAdj;
20035             if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) {
20036                 schedGroup = ProcessList.SCHED_GROUP_DEFAULT;
20037             }
20038         }
20039
20040         // Do final modification to adj.  Everything we do between here and applying
20041         // the final setAdj must be done in this function, because we will also use
20042         // it when computing the final cached adj later.  Note that we don't need to
20043         // worry about this for max adj above, since max adj will always be used to
20044         // keep it out of the cached vaues.
20045         app.curAdj = app.modifyRawOomAdj(adj);
20046         app.curSchedGroup = schedGroup;
20047         app.curProcState = procState;
20048         app.foregroundActivities = foregroundActivities;
20049
20050         return app.curRawAdj;
20051     }
20052
20053     /**
20054      * Record new PSS sample for a process.
20055      */
20056     void recordPssSampleLocked(ProcessRecord proc, int procState, long pss, long uss, long swapPss,
20057             long now) {
20058         EventLogTags.writeAmPss(proc.pid, proc.uid, proc.processName, pss * 1024, uss * 1024,
20059                 swapPss * 1024);
20060         proc.lastPssTime = now;
20061         proc.baseProcessTracker.addPss(pss, uss, true, proc.pkgList);
20062         if (DEBUG_PSS) Slog.d(TAG_PSS,
20063                 "PSS of " + proc.toShortString() + ": " + pss + " lastPss=" + proc.lastPss
20064                 + " state=" + ProcessList.makeProcStateString(procState));
20065         if (proc.initialIdlePss == 0) {
20066             proc.initialIdlePss = pss;
20067         }
20068         proc.lastPss = pss;
20069         proc.lastSwapPss = swapPss;
20070         if (procState >= ActivityManager.PROCESS_STATE_HOME) {
20071             proc.lastCachedPss = pss;
20072             proc.lastCachedSwapPss = swapPss;
20073         }
20074
20075         final SparseArray<Pair<Long, String>> watchUids
20076                 = mMemWatchProcesses.getMap().get(proc.processName);
20077         Long check = null;
20078         if (watchUids != null) {
20079             Pair<Long, String> val = watchUids.get(proc.uid);
20080             if (val == null) {
20081                 val = watchUids.get(0);
20082             }
20083             if (val != null) {
20084                 check = val.first;
20085             }
20086         }
20087         if (check != null) {
20088             if ((pss * 1024) >= check && proc.thread != null && mMemWatchDumpProcName == null) {
20089                 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
20090                 if (!isDebuggable) {
20091                     if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) != 0) {
20092                         isDebuggable = true;
20093                     }
20094                 }
20095                 if (isDebuggable) {
20096                     Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check + "; reporting");
20097                     final ProcessRecord myProc = proc;
20098                     final File heapdumpFile = DumpHeapProvider.getJavaFile();
20099                     mMemWatchDumpProcName = proc.processName;
20100                     mMemWatchDumpFile = heapdumpFile.toString();
20101                     mMemWatchDumpPid = proc.pid;
20102                     mMemWatchDumpUid = proc.uid;
20103                     BackgroundThread.getHandler().post(new Runnable() {
20104                         @Override
20105                         public void run() {
20106                             revokeUriPermission(ActivityThread.currentActivityThread()
20107                                             .getApplicationThread(),
20108                                     DumpHeapActivity.JAVA_URI,
20109                                     Intent.FLAG_GRANT_READ_URI_PERMISSION
20110                                             | Intent.FLAG_GRANT_WRITE_URI_PERMISSION,
20111                                     UserHandle.myUserId());
20112                             ParcelFileDescriptor fd = null;
20113                             try {
20114                                 heapdumpFile.delete();
20115                                 fd = ParcelFileDescriptor.open(heapdumpFile,
20116                                         ParcelFileDescriptor.MODE_CREATE |
20117                                                 ParcelFileDescriptor.MODE_TRUNCATE |
20118                                                 ParcelFileDescriptor.MODE_WRITE_ONLY |
20119                                                 ParcelFileDescriptor.MODE_APPEND);
20120                                 IApplicationThread thread = myProc.thread;
20121                                 if (thread != null) {
20122                                     try {
20123                                         if (DEBUG_PSS) Slog.d(TAG_PSS,
20124                                                 "Requesting dump heap from "
20125                                                 + myProc + " to " + heapdumpFile);
20126                                         thread.dumpHeap(true, heapdumpFile.toString(), fd);
20127                                     } catch (RemoteException e) {
20128                                     }
20129                                 }
20130                             } catch (FileNotFoundException e) {
20131                                 e.printStackTrace();
20132                             } finally {
20133                                 if (fd != null) {
20134                                     try {
20135                                         fd.close();
20136                                     } catch (IOException e) {
20137                                     }
20138                                 }
20139                             }
20140                         }
20141                     });
20142                 } else {
20143                     Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check
20144                             + ", but debugging not enabled");
20145                 }
20146             }
20147         }
20148     }
20149
20150     /**
20151      * Schedule PSS collection of a process.
20152      */
20153     void requestPssLocked(ProcessRecord proc, int procState) {
20154         if (mPendingPssProcesses.contains(proc)) {
20155             return;
20156         }
20157         if (mPendingPssProcesses.size() == 0) {
20158             mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG);
20159         }
20160         if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting PSS of: " + proc);
20161         proc.pssProcState = procState;
20162         mPendingPssProcesses.add(proc);
20163     }
20164
20165     /**
20166      * Schedule PSS collection of all processes.
20167      */
20168     void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) {
20169         if (!always) {
20170             if (now < (mLastFullPssTime +
20171                     (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) {
20172                 return;
20173             }
20174         }
20175         if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting PSS of all procs!  memLowered=" + memLowered);
20176         mLastFullPssTime = now;
20177         mFullPssPending = true;
20178         mPendingPssProcesses.ensureCapacity(mLruProcesses.size());
20179         mPendingPssProcesses.clear();
20180         for (int i = mLruProcesses.size() - 1; i >= 0; i--) {
20181             ProcessRecord app = mLruProcesses.get(i);
20182             if (app.thread == null
20183                     || app.curProcState == ActivityManager.PROCESS_STATE_NONEXISTENT) {
20184                 continue;
20185             }
20186             if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) {
20187                 app.pssProcState = app.setProcState;
20188                 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true,
20189                         mTestPssMode, isSleepingLocked(), now);
20190                 mPendingPssProcesses.add(app);
20191             }
20192         }
20193         mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG);
20194     }
20195
20196     public void setTestPssMode(boolean enabled) {
20197         synchronized (this) {
20198             mTestPssMode = enabled;
20199             if (enabled) {
20200                 // Whenever we enable the mode, we want to take a snapshot all of current
20201                 // process mem use.
20202                 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, true);
20203             }
20204         }
20205     }
20206
20207     /**
20208      * Ask a given process to GC right now.
20209      */
20210     final void performAppGcLocked(ProcessRecord app) {
20211         try {
20212             app.lastRequestedGc = SystemClock.uptimeMillis();
20213             if (app.thread != null) {
20214                 if (app.reportLowMemory) {
20215                     app.reportLowMemory = false;
20216                     app.thread.scheduleLowMemory();
20217                 } else {
20218                     app.thread.processInBackground();
20219                 }
20220             }
20221         } catch (Exception e) {
20222             // whatever.
20223         }
20224     }
20225
20226     /**
20227      * Returns true if things are idle enough to perform GCs.
20228      */
20229     private final boolean canGcNowLocked() {
20230         boolean processingBroadcasts = false;
20231         for (BroadcastQueue q : mBroadcastQueues) {
20232             if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) {
20233                 processingBroadcasts = true;
20234             }
20235         }
20236         return !processingBroadcasts
20237                 && (isSleepingLocked() || mStackSupervisor.allResumedActivitiesIdle());
20238     }
20239
20240     /**
20241      * Perform GCs on all processes that are waiting for it, but only
20242      * if things are idle.
20243      */
20244     final void performAppGcsLocked() {
20245         final int N = mProcessesToGc.size();
20246         if (N <= 0) {
20247             return;
20248         }
20249         if (canGcNowLocked()) {
20250             while (mProcessesToGc.size() > 0) {
20251                 ProcessRecord proc = mProcessesToGc.remove(0);
20252                 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) {
20253                     if ((proc.lastRequestedGc+GC_MIN_INTERVAL)
20254                             <= SystemClock.uptimeMillis()) {
20255                         // To avoid spamming the system, we will GC processes one
20256                         // at a time, waiting a few seconds between each.
20257                         performAppGcLocked(proc);
20258                         scheduleAppGcsLocked();
20259                         return;
20260                     } else {
20261                         // It hasn't been long enough since we last GCed this
20262                         // process...  put it in the list to wait for its time.
20263                         addProcessToGcListLocked(proc);
20264                         break;
20265                     }
20266                 }
20267             }
20268
20269             scheduleAppGcsLocked();
20270         }
20271     }
20272
20273     /**
20274      * If all looks good, perform GCs on all processes waiting for them.
20275      */
20276     final void performAppGcsIfAppropriateLocked() {
20277         if (canGcNowLocked()) {
20278             performAppGcsLocked();
20279             return;
20280         }
20281         // Still not idle, wait some more.
20282         scheduleAppGcsLocked();
20283     }
20284
20285     /**
20286      * Schedule the execution of all pending app GCs.
20287      */
20288     final void scheduleAppGcsLocked() {
20289         mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG);
20290
20291         if (mProcessesToGc.size() > 0) {
20292             // Schedule a GC for the time to the next process.
20293             ProcessRecord proc = mProcessesToGc.get(0);
20294             Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG);
20295
20296             long when = proc.lastRequestedGc + GC_MIN_INTERVAL;
20297             long now = SystemClock.uptimeMillis();
20298             if (when < (now+GC_TIMEOUT)) {
20299                 when = now + GC_TIMEOUT;
20300             }
20301             mHandler.sendMessageAtTime(msg, when);
20302         }
20303     }
20304
20305     /**
20306      * Add a process to the array of processes waiting to be GCed.  Keeps the
20307      * list in sorted order by the last GC time.  The process can't already be
20308      * on the list.
20309      */
20310     final void addProcessToGcListLocked(ProcessRecord proc) {
20311         boolean added = false;
20312         for (int i=mProcessesToGc.size()-1; i>=0; i--) {
20313             if (mProcessesToGc.get(i).lastRequestedGc <
20314                     proc.lastRequestedGc) {
20315                 added = true;
20316                 mProcessesToGc.add(i+1, proc);
20317                 break;
20318             }
20319         }
20320         if (!added) {
20321             mProcessesToGc.add(0, proc);
20322         }
20323     }
20324
20325     /**
20326      * Set up to ask a process to GC itself.  This will either do it
20327      * immediately, or put it on the list of processes to gc the next
20328      * time things are idle.
20329      */
20330     final void scheduleAppGcLocked(ProcessRecord app) {
20331         long now = SystemClock.uptimeMillis();
20332         if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) {
20333             return;
20334         }
20335         if (!mProcessesToGc.contains(app)) {
20336             addProcessToGcListLocked(app);
20337             scheduleAppGcsLocked();
20338         }
20339     }
20340
20341     final void checkExcessivePowerUsageLocked(boolean doKills) {
20342         updateCpuStatsNow();
20343
20344         BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
20345         boolean doWakeKills = doKills;
20346         boolean doCpuKills = doKills;
20347         if (mLastPowerCheckRealtime == 0) {
20348             doWakeKills = false;
20349         }
20350         if (mLastPowerCheckUptime == 0) {
20351             doCpuKills = false;
20352         }
20353         if (stats.isScreenOn()) {
20354             doWakeKills = false;
20355         }
20356         final long curRealtime = SystemClock.elapsedRealtime();
20357         final long realtimeSince = curRealtime - mLastPowerCheckRealtime;
20358         final long curUptime = SystemClock.uptimeMillis();
20359         final long uptimeSince = curUptime - mLastPowerCheckUptime;
20360         mLastPowerCheckRealtime = curRealtime;
20361         mLastPowerCheckUptime = curUptime;
20362         if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) {
20363             doWakeKills = false;
20364         }
20365         if (uptimeSince < CPU_MIN_CHECK_DURATION) {
20366             doCpuKills = false;
20367         }
20368         int i = mLruProcesses.size();
20369         while (i > 0) {
20370             i--;
20371             ProcessRecord app = mLruProcesses.get(i);
20372             if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) {
20373                 long wtime;
20374                 synchronized (stats) {
20375                     wtime = stats.getProcessWakeTime(app.info.uid,
20376                             app.pid, curRealtime);
20377                 }
20378                 long wtimeUsed = wtime - app.lastWakeTime;
20379                 long cputimeUsed = app.curCpuTime - app.lastCpuTime;
20380                 if (DEBUG_POWER) {
20381                     StringBuilder sb = new StringBuilder(128);
20382                     sb.append("Wake for ");
20383                     app.toShortString(sb);
20384                     sb.append(": over ");
20385                     TimeUtils.formatDuration(realtimeSince, sb);
20386                     sb.append(" used ");
20387                     TimeUtils.formatDuration(wtimeUsed, sb);
20388                     sb.append(" (");
20389                     sb.append((wtimeUsed*100)/realtimeSince);
20390                     sb.append("%)");
20391                     Slog.i(TAG_POWER, sb.toString());
20392                     sb.setLength(0);
20393                     sb.append("CPU for ");
20394                     app.toShortString(sb);
20395                     sb.append(": over ");
20396                     TimeUtils.formatDuration(uptimeSince, sb);
20397                     sb.append(" used ");
20398                     TimeUtils.formatDuration(cputimeUsed, sb);
20399                     sb.append(" (");
20400                     sb.append((cputimeUsed*100)/uptimeSince);
20401                     sb.append("%)");
20402                     Slog.i(TAG_POWER, sb.toString());
20403                 }
20404                 // If a process has held a wake lock for more
20405                 // than 50% of the time during this period,
20406                 // that sounds bad.  Kill!
20407                 if (doWakeKills && realtimeSince > 0
20408                         && ((wtimeUsed*100)/realtimeSince) >= 50) {
20409                     synchronized (stats) {
20410                         stats.reportExcessiveWakeLocked(app.info.uid, app.processName,
20411                                 realtimeSince, wtimeUsed);
20412                     }
20413                     app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true);
20414                     app.baseProcessTracker.reportExcessiveWake(app.pkgList);
20415                 } else if (doCpuKills && uptimeSince > 0
20416                         && ((cputimeUsed*100)/uptimeSince) >= 25) {
20417                     synchronized (stats) {
20418                         stats.reportExcessiveCpuLocked(app.info.uid, app.processName,
20419                                 uptimeSince, cputimeUsed);
20420                     }
20421                     app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true);
20422                     app.baseProcessTracker.reportExcessiveCpu(app.pkgList);
20423                 } else {
20424                     app.lastWakeTime = wtime;
20425                     app.lastCpuTime = app.curCpuTime;
20426                 }
20427             }
20428         }
20429     }
20430
20431     private final boolean applyOomAdjLocked(ProcessRecord app, boolean doingAll, long now,
20432             long nowElapsed) {
20433         boolean success = true;
20434
20435         if (app.curRawAdj != app.setRawAdj) {
20436             app.setRawAdj = app.curRawAdj;
20437         }
20438
20439         int changes = 0;
20440
20441         if (app.curAdj != app.setAdj) {
20442             ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj);
20443             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
20444                     "Set " + app.pid + " " + app.processName + " adj " + app.curAdj + ": "
20445                     + app.adjType);
20446             app.setAdj = app.curAdj;
20447             app.verifiedAdj = ProcessList.INVALID_ADJ;
20448         }
20449
20450         if (app.setSchedGroup != app.curSchedGroup) {
20451             int oldSchedGroup = app.setSchedGroup;
20452             app.setSchedGroup = app.curSchedGroup;
20453             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
20454                     "Setting sched group of " + app.processName
20455                     + " to " + app.curSchedGroup);
20456             if (app.waitingToKill != null && app.curReceiver == null
20457                     && app.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND) {
20458                 app.kill(app.waitingToKill, true);
20459                 success = false;
20460             } else {
20461                 int processGroup;
20462                 switch (app.curSchedGroup) {
20463                     case ProcessList.SCHED_GROUP_BACKGROUND:
20464                         processGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE;
20465                         break;
20466                     case ProcessList.SCHED_GROUP_TOP_APP:
20467                     case ProcessList.SCHED_GROUP_TOP_APP_BOUND:
20468                         processGroup = Process.THREAD_GROUP_TOP_APP;
20469                         break;
20470                     default:
20471                         processGroup = Process.THREAD_GROUP_DEFAULT;
20472                         break;
20473                 }
20474                 long oldId = Binder.clearCallingIdentity();
20475                 try {
20476                     Process.setProcessGroup(app.pid, processGroup);
20477                     if (app.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) {
20478                         // do nothing if we already switched to RT
20479                         if (oldSchedGroup != ProcessList.SCHED_GROUP_TOP_APP) {
20480                             // Switch VR thread for app to SCHED_FIFO
20481                             if (mInVrMode && app.vrThreadTid != 0) {
20482                                 try {
20483                                     Process.setThreadScheduler(app.vrThreadTid,
20484                                         Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1);
20485                                 } catch (IllegalArgumentException e) {
20486                                     // thread died, ignore
20487                                 }
20488                             }
20489                             if (mUseFifoUiScheduling) {
20490                                 // Switch UI pipeline for app to SCHED_FIFO
20491                                 app.savedPriority = Process.getThreadPriority(app.pid);
20492                                 try {
20493                                     Process.setThreadScheduler(app.pid,
20494                                         Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1);
20495                                 } catch (IllegalArgumentException e) {
20496                                     // thread died, ignore
20497                                 }
20498                                 if (app.renderThreadTid != 0) {
20499                                     try {
20500                                         Process.setThreadScheduler(app.renderThreadTid,
20501                                             Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1);
20502                                     } catch (IllegalArgumentException e) {
20503                                         // thread died, ignore
20504                                     }
20505                                     if (DEBUG_OOM_ADJ) {
20506                                         Slog.d("UI_FIFO", "Set RenderThread (TID " +
20507                                             app.renderThreadTid + ") to FIFO");
20508                                     }
20509                                 } else {
20510                                     if (DEBUG_OOM_ADJ) {
20511                                         Slog.d("UI_FIFO", "Not setting RenderThread TID");
20512                                     }
20513                                 }
20514                             } else {
20515                                 // Boost priority for top app UI and render threads
20516                                 Process.setThreadPriority(app.pid, -10);
20517                                 if (app.renderThreadTid != 0) {
20518                                     try {
20519                                         Process.setThreadPriority(app.renderThreadTid, -10);
20520                                     } catch (IllegalArgumentException e) {
20521                                         // thread died, ignore
20522                                     }
20523                                 }
20524                             }
20525                         }
20526                     } else if (oldSchedGroup == ProcessList.SCHED_GROUP_TOP_APP &&
20527                                app.curSchedGroup != ProcessList.SCHED_GROUP_TOP_APP) {
20528                         // Reset VR thread to SCHED_OTHER
20529                         // Safe to do even if we're not in VR mode
20530                         if (app.vrThreadTid != 0) {
20531                             Process.setThreadScheduler(app.vrThreadTid, Process.SCHED_OTHER, 0);
20532                         }
20533                         if (mUseFifoUiScheduling) {
20534                             // Reset UI pipeline to SCHED_OTHER
20535                             Process.setThreadScheduler(app.pid, Process.SCHED_OTHER, 0);
20536                             Process.setThreadPriority(app.pid, app.savedPriority);
20537                             if (app.renderThreadTid != 0) {
20538                                 Process.setThreadScheduler(app.renderThreadTid,
20539                                     Process.SCHED_OTHER, 0);
20540                                 Process.setThreadPriority(app.renderThreadTid, -4);
20541                             }
20542                         } else {
20543                             // Reset priority for top app UI and render threads
20544                             Process.setThreadPriority(app.pid, 0);
20545                             if (app.renderThreadTid != 0) {
20546                                 Process.setThreadPriority(app.renderThreadTid, 0);
20547                             }
20548                         }
20549                     }
20550                 } catch (Exception e) {
20551                     Slog.w(TAG, "Failed setting process group of " + app.pid
20552                             + " to " + app.curSchedGroup);
20553                     e.printStackTrace();
20554                 } finally {
20555                     Binder.restoreCallingIdentity(oldId);
20556                 }
20557             }
20558         }
20559         if (app.repForegroundActivities != app.foregroundActivities) {
20560             app.repForegroundActivities = app.foregroundActivities;
20561             changes |= ProcessChangeItem.CHANGE_ACTIVITIES;
20562         }
20563         if (app.repProcState != app.curProcState) {
20564             app.repProcState = app.curProcState;
20565             changes |= ProcessChangeItem.CHANGE_PROCESS_STATE;
20566             if (app.thread != null) {
20567                 try {
20568                     if (false) {
20569                         //RuntimeException h = new RuntimeException("here");
20570                         Slog.i(TAG, "Sending new process state " + app.repProcState
20571                                 + " to " + app /*, h*/);
20572                     }
20573                     app.thread.setProcessState(app.repProcState);
20574                 } catch (RemoteException e) {
20575                 }
20576             }
20577         }
20578         if (app.setProcState == ActivityManager.PROCESS_STATE_NONEXISTENT
20579                 || ProcessList.procStatesDifferForMem(app.curProcState, app.setProcState)) {
20580             if (false && mTestPssMode && app.setProcState >= 0 && app.lastStateTime <= (now-200)) {
20581                 // Experimental code to more aggressively collect pss while
20582                 // running test...  the problem is that this tends to collect
20583                 // the data right when a process is transitioning between process
20584                 // states, which well tend to give noisy data.
20585                 long start = SystemClock.uptimeMillis();
20586                 long pss = Debug.getPss(app.pid, mTmpLong, null);
20587                 recordPssSampleLocked(app, app.curProcState, pss, mTmpLong[0], mTmpLong[1], now);
20588                 mPendingPssProcesses.remove(app);
20589                 Slog.i(TAG, "Recorded pss for " + app + " state " + app.setProcState
20590                         + " to " + app.curProcState + ": "
20591                         + (SystemClock.uptimeMillis()-start) + "ms");
20592             }
20593             app.lastStateTime = now;
20594             app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true,
20595                     mTestPssMode, isSleepingLocked(), now);
20596             if (DEBUG_PSS) Slog.d(TAG_PSS, "Process state change from "
20597                     + ProcessList.makeProcStateString(app.setProcState) + " to "
20598                     + ProcessList.makeProcStateString(app.curProcState) + " next pss in "
20599                     + (app.nextPssTime-now) + ": " + app);
20600         } else {
20601             if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL)
20602                     && now > (app.lastStateTime+ProcessList.minTimeFromStateChange(
20603                     mTestPssMode)))) {
20604                 requestPssLocked(app, app.setProcState);
20605                 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false,
20606                         mTestPssMode, isSleepingLocked(), now);
20607             } else if (false && DEBUG_PSS) Slog.d(TAG_PSS,
20608                     "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now));
20609         }
20610         if (app.setProcState != app.curProcState) {
20611             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
20612                     "Proc state change of " + app.processName
20613                             + " to " + app.curProcState);
20614             boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE;
20615             boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE;
20616             if (setImportant && !curImportant) {
20617                 // This app is no longer something we consider important enough to allow to
20618                 // use arbitrary amounts of battery power.  Note
20619                 // its current wake lock time to later know to kill it if
20620                 // it is not behaving well.
20621                 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
20622                 synchronized (stats) {
20623                     app.lastWakeTime = stats.getProcessWakeTime(app.info.uid,
20624                             app.pid, nowElapsed);
20625                 }
20626                 app.lastCpuTime = app.curCpuTime;
20627
20628             }
20629             // Inform UsageStats of important process state change
20630             // Must be called before updating setProcState
20631             maybeUpdateUsageStatsLocked(app, nowElapsed);
20632
20633             app.setProcState = app.curProcState;
20634             if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) {
20635                 app.notCachedSinceIdle = false;
20636             }
20637             if (!doingAll) {
20638                 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now);
20639             } else {
20640                 app.procStateChanged = true;
20641             }
20642         } else if (app.reportedInteraction && (nowElapsed-app.interactionEventTime)
20643                 > USAGE_STATS_INTERACTION_INTERVAL) {
20644             // For apps that sit around for a long time in the interactive state, we need
20645             // to report this at least once a day so they don't go idle.
20646             maybeUpdateUsageStatsLocked(app, nowElapsed);
20647         }
20648
20649         if (changes != 0) {
20650             if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
20651                     "Changes in " + app + ": " + changes);
20652             int i = mPendingProcessChanges.size()-1;
20653             ProcessChangeItem item = null;
20654             while (i >= 0) {
20655                 item = mPendingProcessChanges.get(i);
20656                 if (item.pid == app.pid) {
20657                     if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
20658                             "Re-using existing item: " + item);
20659                     break;
20660                 }
20661                 i--;
20662             }
20663             if (i < 0) {
20664                 // No existing item in pending changes; need a new one.
20665                 final int NA = mAvailProcessChanges.size();
20666                 if (NA > 0) {
20667                     item = mAvailProcessChanges.remove(NA-1);
20668                     if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
20669                             "Retrieving available item: " + item);
20670                 } else {
20671                     item = new ProcessChangeItem();
20672                     if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
20673                             "Allocating new item: " + item);
20674                 }
20675                 item.changes = 0;
20676                 item.pid = app.pid;
20677                 item.uid = app.info.uid;
20678                 if (mPendingProcessChanges.size() == 0) {
20679                     if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
20680                             "*** Enqueueing dispatch processes changed!");
20681                     mUiHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED_UI_MSG).sendToTarget();
20682                 }
20683                 mPendingProcessChanges.add(item);
20684             }
20685             item.changes |= changes;
20686             item.processState = app.repProcState;
20687             item.foregroundActivities = app.repForegroundActivities;
20688             if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS,
20689                     "Item " + Integer.toHexString(System.identityHashCode(item))
20690                     + " " + app.toShortString() + ": changes=" + item.changes
20691                     + " procState=" + item.processState
20692                     + " foreground=" + item.foregroundActivities
20693                     + " type=" + app.adjType + " source=" + app.adjSource
20694                     + " target=" + app.adjTarget);
20695         }
20696
20697         return success;
20698     }
20699
20700     private final void enqueueUidChangeLocked(UidRecord uidRec, int uid, int change) {
20701         final UidRecord.ChangeItem pendingChange;
20702         if (uidRec == null || uidRec.pendingChange == null) {
20703             if (mPendingUidChanges.size() == 0) {
20704                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
20705                         "*** Enqueueing dispatch uid changed!");
20706                 mUiHandler.obtainMessage(DISPATCH_UIDS_CHANGED_UI_MSG).sendToTarget();
20707             }
20708             final int NA = mAvailUidChanges.size();
20709             if (NA > 0) {
20710                 pendingChange = mAvailUidChanges.remove(NA-1);
20711                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
20712                         "Retrieving available item: " + pendingChange);
20713             } else {
20714                 pendingChange = new UidRecord.ChangeItem();
20715                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
20716                         "Allocating new item: " + pendingChange);
20717             }
20718             if (uidRec != null) {
20719                 uidRec.pendingChange = pendingChange;
20720                 if (change == UidRecord.CHANGE_GONE && !uidRec.idle) {
20721                     // If this uid is going away, and we haven't yet reported it is gone,
20722                     // then do so now.
20723                     change = UidRecord.CHANGE_GONE_IDLE;
20724                 }
20725             } else if (uid < 0) {
20726                 throw new IllegalArgumentException("No UidRecord or uid");
20727             }
20728             pendingChange.uidRecord = uidRec;
20729             pendingChange.uid = uidRec != null ? uidRec.uid : uid;
20730             mPendingUidChanges.add(pendingChange);
20731         } else {
20732             pendingChange = uidRec.pendingChange;
20733             if (change == UidRecord.CHANGE_GONE && pendingChange.change == UidRecord.CHANGE_IDLE) {
20734                 change = UidRecord.CHANGE_GONE_IDLE;
20735             }
20736         }
20737         pendingChange.change = change;
20738         pendingChange.processState = uidRec != null
20739                 ? uidRec.setProcState : ActivityManager.PROCESS_STATE_NONEXISTENT;
20740     }
20741
20742     private void maybeUpdateProviderUsageStatsLocked(ProcessRecord app, String providerPkgName,
20743             String authority) {
20744         if (app == null) return;
20745         if (app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) {
20746             UserState userState = mUserController.getStartedUserStateLocked(app.userId);
20747             if (userState == null) return;
20748             final long now = SystemClock.elapsedRealtime();
20749             Long lastReported = userState.mProviderLastReportedFg.get(authority);
20750             if (lastReported == null || lastReported < now - 60 * 1000L) {
20751                 if (mSystemReady) {
20752                     // Cannot touch the user stats if not system ready
20753                     mUsageStatsService.reportContentProviderUsage(
20754                             authority, providerPkgName, app.userId);
20755                 }
20756                 userState.mProviderLastReportedFg.put(authority, now);
20757             }
20758         }
20759     }
20760
20761     private void maybeUpdateUsageStatsLocked(ProcessRecord app, long nowElapsed) {
20762         if (DEBUG_USAGE_STATS) {
20763             Slog.d(TAG, "Checking proc [" + Arrays.toString(app.getPackageList())
20764                     + "] state changes: old = " + app.setProcState + ", new = "
20765                     + app.curProcState);
20766         }
20767         if (mUsageStatsService == null) {
20768             return;
20769         }
20770         boolean isInteraction;
20771         // To avoid some abuse patterns, we are going to be careful about what we consider
20772         // to be an app interaction.  Being the top activity doesn't count while the display
20773         // is sleeping, nor do short foreground services.
20774         if (app.curProcState <= ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE) {
20775             isInteraction = true;
20776             app.fgInteractionTime = 0;
20777         } else if (app.curProcState <= ActivityManager.PROCESS_STATE_TOP_SLEEPING) {
20778             if (app.fgInteractionTime == 0) {
20779                 app.fgInteractionTime = nowElapsed;
20780                 isInteraction = false;
20781             } else {
20782                 isInteraction = nowElapsed > app.fgInteractionTime + SERVICE_USAGE_INTERACTION_TIME;
20783             }
20784         } else {
20785             // If the app was being forced to the foreground, by say a Toast, then
20786             // no need to treat it as an interaction
20787             isInteraction = app.forcingToForeground == null
20788                     && app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND;
20789             app.fgInteractionTime = 0;
20790         }
20791         if (isInteraction && (!app.reportedInteraction
20792                 || (nowElapsed-app.interactionEventTime) > USAGE_STATS_INTERACTION_INTERVAL)) {
20793             app.interactionEventTime = nowElapsed;
20794             String[] packages = app.getPackageList();
20795             if (packages != null) {
20796                 for (int i = 0; i < packages.length; i++) {
20797                     mUsageStatsService.reportEvent(packages[i], app.userId,
20798                             UsageEvents.Event.SYSTEM_INTERACTION);
20799                 }
20800             }
20801         }
20802         app.reportedInteraction = isInteraction;
20803         if (!isInteraction) {
20804             app.interactionEventTime = 0;
20805         }
20806     }
20807
20808     private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) {
20809         if (proc.thread != null) {
20810             if (proc.baseProcessTracker != null) {
20811                 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList);
20812             }
20813         }
20814     }
20815
20816     private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj,
20817             ProcessRecord TOP_APP, boolean doingAll, long now) {
20818         if (app.thread == null) {
20819             return false;
20820         }
20821
20822         computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now);
20823
20824         return applyOomAdjLocked(app, doingAll, now, SystemClock.elapsedRealtime());
20825     }
20826
20827     final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground,
20828             boolean oomAdj) {
20829         if (isForeground != proc.foregroundServices) {
20830             proc.foregroundServices = isForeground;
20831             ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName,
20832                     proc.info.uid);
20833             if (isForeground) {
20834                 if (curProcs == null) {
20835                     curProcs = new ArrayList<ProcessRecord>();
20836                     mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs);
20837                 }
20838                 if (!curProcs.contains(proc)) {
20839                     curProcs.add(proc);
20840                     mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START,
20841                             proc.info.packageName, proc.info.uid);
20842                 }
20843             } else {
20844                 if (curProcs != null) {
20845                     if (curProcs.remove(proc)) {
20846                         mBatteryStatsService.noteEvent(
20847                                 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH,
20848                                 proc.info.packageName, proc.info.uid);
20849                         if (curProcs.size() <= 0) {
20850                             mForegroundPackages.remove(proc.info.packageName, proc.info.uid);
20851                         }
20852                     }
20853                 }
20854             }
20855             if (oomAdj) {
20856                 updateOomAdjLocked();
20857             }
20858         }
20859     }
20860
20861     private final ActivityRecord resumedAppLocked() {
20862         ActivityRecord act = mStackSupervisor.resumedAppLocked();
20863         String pkg;
20864         int uid;
20865         if (act != null) {
20866             pkg = act.packageName;
20867             uid = act.info.applicationInfo.uid;
20868         } else {
20869             pkg = null;
20870             uid = -1;
20871         }
20872         // Has the UID or resumed package name changed?
20873         if (uid != mCurResumedUid || (pkg != mCurResumedPackage
20874                 && (pkg == null || !pkg.equals(mCurResumedPackage)))) {
20875             if (mCurResumedPackage != null) {
20876                 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH,
20877                         mCurResumedPackage, mCurResumedUid);
20878             }
20879             mCurResumedPackage = pkg;
20880             mCurResumedUid = uid;
20881             if (mCurResumedPackage != null) {
20882                 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START,
20883                         mCurResumedPackage, mCurResumedUid);
20884             }
20885         }
20886         return act;
20887     }
20888
20889     final boolean updateOomAdjLocked(ProcessRecord app) {
20890         final ActivityRecord TOP_ACT = resumedAppLocked();
20891         final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null;
20892         final boolean wasCached = app.cached;
20893
20894         mAdjSeq++;
20895
20896         // This is the desired cached adjusment we want to tell it to use.
20897         // If our app is currently cached, we know it, and that is it.  Otherwise,
20898         // we don't know it yet, and it needs to now be cached we will then
20899         // need to do a complete oom adj.
20900         final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ
20901                 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ;
20902         boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false,
20903                 SystemClock.uptimeMillis());
20904         if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) {
20905             // Changed to/from cached state, so apps after it in the LRU
20906             // list may also be changed.
20907             updateOomAdjLocked();
20908         }
20909         return success;
20910     }
20911
20912     final void updateOomAdjLocked() {
20913         final ActivityRecord TOP_ACT = resumedAppLocked();
20914         final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null;
20915         final long now = SystemClock.uptimeMillis();
20916         final long nowElapsed = SystemClock.elapsedRealtime();
20917         final long oldTime = now - ProcessList.MAX_EMPTY_TIME;
20918         final int N = mLruProcesses.size();
20919
20920         if (false) {
20921             RuntimeException e = new RuntimeException();
20922             e.fillInStackTrace();
20923             Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e);
20924         }
20925
20926         // Reset state in all uid records.
20927         for (int i=mActiveUids.size()-1; i>=0; i--) {
20928             final UidRecord uidRec = mActiveUids.valueAt(i);
20929             if (false && DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
20930                     "Starting update of " + uidRec);
20931             uidRec.reset();
20932         }
20933
20934         mStackSupervisor.rankTaskLayersIfNeeded();
20935
20936         mAdjSeq++;
20937         mNewNumServiceProcs = 0;
20938         mNewNumAServiceProcs = 0;
20939
20940         final int emptyProcessLimit;
20941         final int cachedProcessLimit;
20942         if (mProcessLimit <= 0) {
20943             emptyProcessLimit = cachedProcessLimit = 0;
20944         } else if (mProcessLimit == 1) {
20945             emptyProcessLimit = 1;
20946             cachedProcessLimit = 0;
20947         } else {
20948             emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit);
20949             cachedProcessLimit = mProcessLimit - emptyProcessLimit;
20950         }
20951
20952         // Let's determine how many processes we have running vs.
20953         // how many slots we have for background processes; we may want
20954         // to put multiple processes in a slot of there are enough of
20955         // them.
20956         int numSlots = (ProcessList.CACHED_APP_MAX_ADJ
20957                 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2;
20958         int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs;
20959         if (numEmptyProcs > cachedProcessLimit) {
20960             // If there are more empty processes than our limit on cached
20961             // processes, then use the cached process limit for the factor.
20962             // This ensures that the really old empty processes get pushed
20963             // down to the bottom, so if we are running low on memory we will
20964             // have a better chance at keeping around more cached processes
20965             // instead of a gazillion empty processes.
20966             numEmptyProcs = cachedProcessLimit;
20967         }
20968         int emptyFactor = numEmptyProcs/numSlots;
20969         if (emptyFactor < 1) emptyFactor = 1;
20970         int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots;
20971         if (cachedFactor < 1) cachedFactor = 1;
20972         int stepCached = 0;
20973         int stepEmpty = 0;
20974         int numCached = 0;
20975         int numEmpty = 0;
20976         int numTrimming = 0;
20977
20978         mNumNonCachedProcs = 0;
20979         mNumCachedHiddenProcs = 0;
20980
20981         // First update the OOM adjustment for each of the
20982         // application processes based on their current state.
20983         int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ;
20984         int nextCachedAdj = curCachedAdj+1;
20985         int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ;
20986         int nextEmptyAdj = curEmptyAdj+2;
20987         for (int i=N-1; i>=0; i--) {
20988             ProcessRecord app = mLruProcesses.get(i);
20989             if (app == null) {
20990                 continue;
20991             }
20992             if (!app.killedByAm && app.thread != null) {
20993                 app.procStateChanged = false;
20994                 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now);
20995
20996                 // If we haven't yet assigned the final cached adj
20997                 // to the process, do that now.
20998                 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) {
20999                     switch (app.curProcState) {
21000                         case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY:
21001                         case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT:
21002                             // This process is a cached process holding activities...
21003                             // assign it the next cached value for that type, and then
21004                             // step that cached level.
21005                             app.curRawAdj = curCachedAdj;
21006                             app.curAdj = app.modifyRawOomAdj(curCachedAdj);
21007                             if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning activity LRU #" + i
21008                                     + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj
21009                                     + ")");
21010                             if (curCachedAdj != nextCachedAdj) {
21011                                 stepCached++;
21012                                 if (stepCached >= cachedFactor) {
21013                                     stepCached = 0;
21014                                     curCachedAdj = nextCachedAdj;
21015                                     nextCachedAdj += 2;
21016                                     if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) {
21017                                         nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ;
21018                                     }
21019                                 }
21020                             }
21021                             break;
21022                         default:
21023                             // For everything else, assign next empty cached process
21024                             // level and bump that up.  Note that this means that
21025                             // long-running services that have dropped down to the
21026                             // cached level will be treated as empty (since their process
21027                             // state is still as a service), which is what we want.
21028                             app.curRawAdj = curEmptyAdj;
21029                             app.curAdj = app.modifyRawOomAdj(curEmptyAdj);
21030                             if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning empty LRU #" + i
21031                                     + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj
21032                                     + ")");
21033                             if (curEmptyAdj != nextEmptyAdj) {
21034                                 stepEmpty++;
21035                                 if (stepEmpty >= emptyFactor) {
21036                                     stepEmpty = 0;
21037                                     curEmptyAdj = nextEmptyAdj;
21038                                     nextEmptyAdj += 2;
21039                                     if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) {
21040                                         nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ;
21041                                     }
21042                                 }
21043                             }
21044                             break;
21045                     }
21046                 }
21047
21048                 applyOomAdjLocked(app, true, now, nowElapsed);
21049
21050                 // Count the number of process types.
21051                 switch (app.curProcState) {
21052                     case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY:
21053                     case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT:
21054                         mNumCachedHiddenProcs++;
21055                         numCached++;
21056                         if (numCached > cachedProcessLimit) {
21057                             app.kill("cached #" + numCached, true);
21058                         }
21059                         break;
21060                     case ActivityManager.PROCESS_STATE_CACHED_EMPTY:
21061                         if (numEmpty > ProcessList.TRIM_EMPTY_APPS
21062                                 && app.lastActivityTime < oldTime) {
21063                             app.kill("empty for "
21064                                     + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime)
21065                                     / 1000) + "s", true);
21066                         } else {
21067                             numEmpty++;
21068                             if (numEmpty > emptyProcessLimit) {
21069                                 app.kill("empty #" + numEmpty, true);
21070                             }
21071                         }
21072                         break;
21073                     default:
21074                         mNumNonCachedProcs++;
21075                         break;
21076                 }
21077
21078                 if (app.isolated && app.services.size() <= 0) {
21079                     // If this is an isolated process, and there are no
21080                     // services running in it, then the process is no longer
21081                     // needed.  We agressively kill these because we can by
21082                     // definition not re-use the same process again, and it is
21083                     // good to avoid having whatever code was running in them
21084                     // left sitting around after no longer needed.
21085                     app.kill("isolated not needed", true);
21086                 } else {
21087                     // Keeping this process, update its uid.
21088                     final UidRecord uidRec = app.uidRecord;
21089                     if (uidRec != null && uidRec.curProcState > app.curProcState) {
21090                         uidRec.curProcState = app.curProcState;
21091                     }
21092                 }
21093
21094                 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME
21095                         && !app.killedByAm) {
21096                     numTrimming++;
21097                 }
21098             }
21099         }
21100
21101         mNumServiceProcs = mNewNumServiceProcs;
21102
21103         // Now determine the memory trimming level of background processes.
21104         // Unfortunately we need to start at the back of the list to do this
21105         // properly.  We only do this if the number of background apps we
21106         // are managing to keep around is less than half the maximum we desire;
21107         // if we are keeping a good number around, we'll let them use whatever
21108         // memory they want.
21109         final int numCachedAndEmpty = numCached + numEmpty;
21110         int memFactor;
21111         if (numCached <= ProcessList.TRIM_CACHED_APPS
21112                 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) {
21113             if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) {
21114                 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL;
21115             } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) {
21116                 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW;
21117             } else {
21118                 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE;
21119             }
21120         } else {
21121             memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL;
21122         }
21123         // We always allow the memory level to go up (better).  We only allow it to go
21124         // down if we are in a state where that is allowed, *and* the total number of processes
21125         // has gone down since last time.
21126         if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "oom: memFactor=" + memFactor
21127                 + " last=" + mLastMemoryLevel + " allowLow=" + mAllowLowerMemLevel
21128                 + " numProcs=" + mLruProcesses.size() + " last=" + mLastNumProcesses);
21129         if (memFactor > mLastMemoryLevel) {
21130             if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) {
21131                 memFactor = mLastMemoryLevel;
21132                 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "Keeping last mem factor!");
21133             }
21134         }
21135         if (memFactor != mLastMemoryLevel) {
21136             EventLogTags.writeAmMemFactor(memFactor, mLastMemoryLevel);
21137         }
21138         mLastMemoryLevel = memFactor;
21139         mLastNumProcesses = mLruProcesses.size();
21140         boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleepingLocked(), now);
21141         final int trackerMemFactor = mProcessStats.getMemFactorLocked();
21142         if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) {
21143             if (mLowRamStartTime == 0) {
21144                 mLowRamStartTime = now;
21145             }
21146             int step = 0;
21147             int fgTrimLevel;
21148             switch (memFactor) {
21149                 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL:
21150                     fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL;
21151                     break;
21152                 case ProcessStats.ADJ_MEM_FACTOR_LOW:
21153                     fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW;
21154                     break;
21155                 default:
21156                     fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE;
21157                     break;
21158             }
21159             int factor = numTrimming/3;
21160             int minFactor = 2;
21161             if (mHomeProcess != null) minFactor++;
21162             if (mPreviousProcess != null) minFactor++;
21163             if (factor < minFactor) factor = minFactor;
21164             int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE;
21165             for (int i=N-1; i>=0; i--) {
21166                 ProcessRecord app = mLruProcesses.get(i);
21167                 if (app == null) {
21168                     continue;
21169                 }
21170                 if (allChanged || app.procStateChanged) {
21171                     setProcessTrackerStateLocked(app, trackerMemFactor, now);
21172                     app.procStateChanged = false;
21173                 }
21174                 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME
21175                         && !app.killedByAm) {
21176                     if (app.trimMemoryLevel < curLevel && app.thread != null) {
21177                         try {
21178                             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
21179                                     "Trimming memory of " + app.processName + " to " + curLevel);
21180                             app.thread.scheduleTrimMemory(curLevel);
21181                         } catch (RemoteException e) {
21182                         }
21183                         if (false) {
21184                             // For now we won't do this; our memory trimming seems
21185                             // to be good enough at this point that destroying
21186                             // activities causes more harm than good.
21187                             if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE
21188                                     && app != mHomeProcess && app != mPreviousProcess) {
21189                                 // Need to do this on its own message because the stack may not
21190                                 // be in a consistent state at this point.
21191                                 // For these apps we will also finish their activities
21192                                 // to help them free memory.
21193                                 mStackSupervisor.scheduleDestroyAllActivities(app, "trim");
21194                             }
21195                         }
21196                     }
21197                     app.trimMemoryLevel = curLevel;
21198                     step++;
21199                     if (step >= factor) {
21200                         step = 0;
21201                         switch (curLevel) {
21202                             case ComponentCallbacks2.TRIM_MEMORY_COMPLETE:
21203                                 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE;
21204                                 break;
21205                             case ComponentCallbacks2.TRIM_MEMORY_MODERATE:
21206                                 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND;
21207                                 break;
21208                         }
21209                     }
21210                 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) {
21211                     if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND
21212                             && app.thread != null) {
21213                         try {
21214                             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
21215                                     "Trimming memory of heavy-weight " + app.processName
21216                                     + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND);
21217                             app.thread.scheduleTrimMemory(
21218                                     ComponentCallbacks2.TRIM_MEMORY_BACKGROUND);
21219                         } catch (RemoteException e) {
21220                         }
21221                     }
21222                     app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND;
21223                 } else {
21224                     if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND
21225                             || app.systemNoUi) && app.pendingUiClean) {
21226                         // If this application is now in the background and it
21227                         // had done UI, then give it the special trim level to
21228                         // have it free UI resources.
21229                         final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN;
21230                         if (app.trimMemoryLevel < level && app.thread != null) {
21231                             try {
21232                                 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
21233                                         "Trimming memory of bg-ui " + app.processName
21234                                         + " to " + level);
21235                                 app.thread.scheduleTrimMemory(level);
21236                             } catch (RemoteException e) {
21237                             }
21238                         }
21239                         app.pendingUiClean = false;
21240                     }
21241                     if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) {
21242                         try {
21243                             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
21244                                     "Trimming memory of fg " + app.processName
21245                                     + " to " + fgTrimLevel);
21246                             app.thread.scheduleTrimMemory(fgTrimLevel);
21247                         } catch (RemoteException e) {
21248                         }
21249                     }
21250                     app.trimMemoryLevel = fgTrimLevel;
21251                 }
21252             }
21253         } else {
21254             if (mLowRamStartTime != 0) {
21255                 mLowRamTimeSinceLastIdle += now - mLowRamStartTime;
21256                 mLowRamStartTime = 0;
21257             }
21258             for (int i=N-1; i>=0; i--) {
21259                 ProcessRecord app = mLruProcesses.get(i);
21260                 if (allChanged || app.procStateChanged) {
21261                     setProcessTrackerStateLocked(app, trackerMemFactor, now);
21262                     app.procStateChanged = false;
21263                 }
21264                 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND
21265                         || app.systemNoUi) && app.pendingUiClean) {
21266                     if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN
21267                             && app.thread != null) {
21268                         try {
21269                             if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ,
21270                                     "Trimming memory of ui hidden " + app.processName
21271                                     + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN);
21272                             app.thread.scheduleTrimMemory(
21273                                     ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN);
21274                         } catch (RemoteException e) {
21275                         }
21276                     }
21277                     app.pendingUiClean = false;
21278                 }
21279                 app.trimMemoryLevel = 0;
21280             }
21281         }
21282
21283         if (mAlwaysFinishActivities) {
21284             // Need to do this on its own message because the stack may not
21285             // be in a consistent state at this point.
21286             mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish");
21287         }
21288
21289         if (allChanged) {
21290             requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered());
21291         }
21292
21293         // Update from any uid changes.
21294         for (int i=mActiveUids.size()-1; i>=0; i--) {
21295             final UidRecord uidRec = mActiveUids.valueAt(i);
21296             int uidChange = UidRecord.CHANGE_PROCSTATE;
21297             if (uidRec.setProcState != uidRec.curProcState) {
21298                 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS,
21299                         "Changes in " + uidRec + ": proc state from " + uidRec.setProcState
21300                         + " to " + uidRec.curProcState);
21301                 if (ActivityManager.isProcStateBackground(uidRec.curProcState)) {
21302                     if (!ActivityManager.isProcStateBackground(uidRec.setProcState)) {
21303                         uidRec.lastBackgroundTime = nowElapsed;
21304                         if (!mHandler.hasMessages(IDLE_UIDS_MSG)) {
21305                             // Note: the background settle time is in elapsed realtime, while
21306                             // the handler time base is uptime.  All this means is that we may
21307                             // stop background uids later than we had intended, but that only
21308                             // happens because the device was sleeping so we are okay anyway.
21309                             mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, BACKGROUND_SETTLE_TIME);
21310                         }
21311                     }
21312                 } else {
21313                     if (uidRec.idle) {
21314                         uidChange = UidRecord.CHANGE_ACTIVE;
21315                         uidRec.idle = false;
21316                     }
21317                     uidRec.lastBackgroundTime = 0;
21318                 }
21319                 uidRec.setProcState = uidRec.curProcState;
21320                 enqueueUidChangeLocked(uidRec, -1, uidChange);
21321                 noteUidProcessState(uidRec.uid, uidRec.curProcState);
21322             }
21323         }
21324
21325         if (mProcessStats.shouldWriteNowLocked(now)) {
21326             mHandler.post(new Runnable() {
21327                 @Override public void run() {
21328                     synchronized (ActivityManagerService.this) {
21329                         mProcessStats.writeStateAsyncLocked();
21330                     }
21331                 }
21332             });
21333         }
21334
21335         if (DEBUG_OOM_ADJ) {
21336             final long duration = SystemClock.uptimeMillis() - now;
21337             if (false) {
21338                 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms",
21339                         new RuntimeException("here").fillInStackTrace());
21340             } else {
21341                 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms");
21342             }
21343         }
21344     }
21345
21346     final void idleUids() {
21347         synchronized (this) {
21348             final long nowElapsed = SystemClock.elapsedRealtime();
21349             final long maxBgTime = nowElapsed - BACKGROUND_SETTLE_TIME;
21350             long nextTime = 0;
21351             for (int i=mActiveUids.size()-1; i>=0; i--) {
21352                 final UidRecord uidRec = mActiveUids.valueAt(i);
21353                 final long bgTime = uidRec.lastBackgroundTime;
21354                 if (bgTime > 0 && !uidRec.idle) {
21355                     if (bgTime <= maxBgTime) {
21356                         uidRec.idle = true;
21357                         doStopUidLocked(uidRec.uid, uidRec);
21358                     } else {
21359                         if (nextTime == 0 || nextTime > bgTime) {
21360                             nextTime = bgTime;
21361                         }
21362                     }
21363                 }
21364             }
21365             if (nextTime > 0) {
21366                 mHandler.removeMessages(IDLE_UIDS_MSG);
21367                 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG,
21368                         nextTime + BACKGROUND_SETTLE_TIME - nowElapsed);
21369             }
21370         }
21371     }
21372
21373     final void runInBackgroundDisabled(int uid) {
21374         synchronized (this) {
21375             UidRecord uidRec = mActiveUids.get(uid);
21376             if (uidRec != null) {
21377                 // This uid is actually running...  should it be considered background now?
21378                 if (uidRec.idle) {
21379                     doStopUidLocked(uidRec.uid, uidRec);
21380                 }
21381             } else {
21382                 // This uid isn't actually running...  still send a report about it being "stopped".
21383                 doStopUidLocked(uid, null);
21384             }
21385         }
21386     }
21387
21388     final void doStopUidLocked(int uid, final UidRecord uidRec) {
21389         mServices.stopInBackgroundLocked(uid);
21390         enqueueUidChangeLocked(uidRec, uid, UidRecord.CHANGE_IDLE);
21391     }
21392
21393     final void trimApplications() {
21394         synchronized (this) {
21395             int i;
21396
21397             // First remove any unused application processes whose package
21398             // has been removed.
21399             for (i=mRemovedProcesses.size()-1; i>=0; i--) {
21400                 final ProcessRecord app = mRemovedProcesses.get(i);
21401                 if (app.activities.size() == 0
21402                         && app.curReceiver == null && app.services.size() == 0) {
21403                     Slog.i(
21404                         TAG, "Exiting empty application process "
21405                         + app.toShortString() + " ("
21406                         + (app.thread != null ? app.thread.asBinder() : null)
21407                         + ")\n");
21408                     if (app.pid > 0 && app.pid != MY_PID) {
21409                         app.kill("empty", false);
21410                     } else {
21411                         try {
21412                             app.thread.scheduleExit();
21413                         } catch (Exception e) {
21414                             // Ignore exceptions.
21415                         }
21416                     }
21417                     cleanUpApplicationRecordLocked(app, false, true, -1, false /*replacingPid*/);
21418                     mRemovedProcesses.remove(i);
21419
21420                     if (app.persistent) {
21421                         addAppLocked(app.info, false, null /* ABI override */);
21422                     }
21423                 }
21424             }
21425
21426             // Now update the oom adj for all processes.
21427             updateOomAdjLocked();
21428         }
21429     }
21430
21431     /** This method sends the specified signal to each of the persistent apps */
21432     public void signalPersistentProcesses(int sig) throws RemoteException {
21433         if (sig != Process.SIGNAL_USR1) {
21434             throw new SecurityException("Only SIGNAL_USR1 is allowed");
21435         }
21436
21437         synchronized (this) {
21438             if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES)
21439                     != PackageManager.PERMISSION_GRANTED) {
21440                 throw new SecurityException("Requires permission "
21441                         + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES);
21442             }
21443
21444             for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) {
21445                 ProcessRecord r = mLruProcesses.get(i);
21446                 if (r.thread != null && r.persistent) {
21447                     Process.sendSignal(r.pid, sig);
21448                 }
21449             }
21450         }
21451     }
21452
21453     private void stopProfilerLocked(ProcessRecord proc, int profileType) {
21454         if (proc == null || proc == mProfileProc) {
21455             proc = mProfileProc;
21456             profileType = mProfileType;
21457             clearProfilerLocked();
21458         }
21459         if (proc == null) {
21460             return;
21461         }
21462         try {
21463             proc.thread.profilerControl(false, null, profileType);
21464         } catch (RemoteException e) {
21465             throw new IllegalStateException("Process disappeared");
21466         }
21467     }
21468
21469     private void clearProfilerLocked() {
21470         if (mProfileFd != null) {
21471             try {
21472                 mProfileFd.close();
21473             } catch (IOException e) {
21474             }
21475         }
21476         mProfileApp = null;
21477         mProfileProc = null;
21478         mProfileFile = null;
21479         mProfileType = 0;
21480         mAutoStopProfiler = false;
21481         mSamplingInterval = 0;
21482     }
21483
21484     public boolean profileControl(String process, int userId, boolean start,
21485             ProfilerInfo profilerInfo, int profileType) throws RemoteException {
21486
21487         try {
21488             synchronized (this) {
21489                 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to
21490                 // its own permission.
21491                 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
21492                         != PackageManager.PERMISSION_GRANTED) {
21493                     throw new SecurityException("Requires permission "
21494                             + android.Manifest.permission.SET_ACTIVITY_WATCHER);
21495                 }
21496
21497                 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) {
21498                     throw new IllegalArgumentException("null profile info or fd");
21499                 }
21500
21501                 ProcessRecord proc = null;
21502                 if (process != null) {
21503                     proc = findProcessLocked(process, userId, "profileControl");
21504                 }
21505
21506                 if (start && (proc == null || proc.thread == null)) {
21507                     throw new IllegalArgumentException("Unknown process: " + process);
21508                 }
21509
21510                 if (start) {
21511                     stopProfilerLocked(null, 0);
21512                     setProfileApp(proc.info, proc.processName, profilerInfo);
21513                     mProfileProc = proc;
21514                     mProfileType = profileType;
21515                     ParcelFileDescriptor fd = profilerInfo.profileFd;
21516                     try {
21517                         fd = fd.dup();
21518                     } catch (IOException e) {
21519                         fd = null;
21520                     }
21521                     profilerInfo.profileFd = fd;
21522                     proc.thread.profilerControl(start, profilerInfo, profileType);
21523                     fd = null;
21524                     mProfileFd = null;
21525                 } else {
21526                     stopProfilerLocked(proc, profileType);
21527                     if (profilerInfo != null && profilerInfo.profileFd != null) {
21528                         try {
21529                             profilerInfo.profileFd.close();
21530                         } catch (IOException e) {
21531                         }
21532                     }
21533                 }
21534
21535                 return true;
21536             }
21537         } catch (RemoteException e) {
21538             throw new IllegalStateException("Process disappeared");
21539         } finally {
21540             if (profilerInfo != null && profilerInfo.profileFd != null) {
21541                 try {
21542                     profilerInfo.profileFd.close();
21543                 } catch (IOException e) {
21544                 }
21545             }
21546         }
21547     }
21548
21549     private ProcessRecord findProcessLocked(String process, int userId, String callName) {
21550         userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(),
21551                 userId, true, ALLOW_FULL_ONLY, callName, null);
21552         ProcessRecord proc = null;
21553         try {
21554             int pid = Integer.parseInt(process);
21555             synchronized (mPidsSelfLocked) {
21556                 proc = mPidsSelfLocked.get(pid);
21557             }
21558         } catch (NumberFormatException e) {
21559         }
21560
21561         if (proc == null) {
21562             ArrayMap<String, SparseArray<ProcessRecord>> all
21563                     = mProcessNames.getMap();
21564             SparseArray<ProcessRecord> procs = all.get(process);
21565             if (procs != null && procs.size() > 0) {
21566                 proc = procs.valueAt(0);
21567                 if (userId != UserHandle.USER_ALL && proc.userId != userId) {
21568                     for (int i=1; i<procs.size(); i++) {
21569                         ProcessRecord thisProc = procs.valueAt(i);
21570                         if (thisProc.userId == userId) {
21571                             proc = thisProc;
21572                             break;
21573                         }
21574                     }
21575                 }
21576             }
21577         }
21578
21579         return proc;
21580     }
21581
21582     public boolean dumpHeap(String process, int userId, boolean managed,
21583             String path, ParcelFileDescriptor fd) throws RemoteException {
21584
21585         try {
21586             synchronized (this) {
21587                 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to
21588                 // its own permission (same as profileControl).
21589                 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
21590                         != PackageManager.PERMISSION_GRANTED) {
21591                     throw new SecurityException("Requires permission "
21592                             + android.Manifest.permission.SET_ACTIVITY_WATCHER);
21593                 }
21594
21595                 if (fd == null) {
21596                     throw new IllegalArgumentException("null fd");
21597                 }
21598
21599                 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap");
21600                 if (proc == null || proc.thread == null) {
21601                     throw new IllegalArgumentException("Unknown process: " + process);
21602                 }
21603
21604                 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
21605                 if (!isDebuggable) {
21606                     if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) {
21607                         throw new SecurityException("Process not debuggable: " + proc);
21608                     }
21609                 }
21610
21611                 proc.thread.dumpHeap(managed, path, fd);
21612                 fd = null;
21613                 return true;
21614             }
21615         } catch (RemoteException e) {
21616             throw new IllegalStateException("Process disappeared");
21617         } finally {
21618             if (fd != null) {
21619                 try {
21620                     fd.close();
21621                 } catch (IOException e) {
21622                 }
21623             }
21624         }
21625     }
21626
21627     @Override
21628     public void setDumpHeapDebugLimit(String processName, int uid, long maxMemSize,
21629             String reportPackage) {
21630         if (processName != null) {
21631             enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP,
21632                     "setDumpHeapDebugLimit()");
21633         } else {
21634             synchronized (mPidsSelfLocked) {
21635                 ProcessRecord proc = mPidsSelfLocked.get(Binder.getCallingPid());
21636                 if (proc == null) {
21637                     throw new SecurityException("No process found for calling pid "
21638                             + Binder.getCallingPid());
21639                 }
21640                 if (!Build.IS_DEBUGGABLE
21641                         && (proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) {
21642                     throw new SecurityException("Not running a debuggable build");
21643                 }
21644                 processName = proc.processName;
21645                 uid = proc.uid;
21646                 if (reportPackage != null && !proc.pkgList.containsKey(reportPackage)) {
21647                     throw new SecurityException("Package " + reportPackage + " is not running in "
21648                             + proc);
21649                 }
21650             }
21651         }
21652         synchronized (this) {
21653             if (maxMemSize > 0) {
21654                 mMemWatchProcesses.put(processName, uid, new Pair(maxMemSize, reportPackage));
21655             } else {
21656                 if (uid != 0) {
21657                     mMemWatchProcesses.remove(processName, uid);
21658                 } else {
21659                     mMemWatchProcesses.getMap().remove(processName);
21660                 }
21661             }
21662         }
21663     }
21664
21665     @Override
21666     public void dumpHeapFinished(String path) {
21667         synchronized (this) {
21668             if (Binder.getCallingPid() != mMemWatchDumpPid) {
21669                 Slog.w(TAG, "dumpHeapFinished: Calling pid " + Binder.getCallingPid()
21670                         + " does not match last pid " + mMemWatchDumpPid);
21671                 return;
21672             }
21673             if (mMemWatchDumpFile == null || !mMemWatchDumpFile.equals(path)) {
21674                 Slog.w(TAG, "dumpHeapFinished: Calling path " + path
21675                         + " does not match last path " + mMemWatchDumpFile);
21676                 return;
21677             }
21678             if (DEBUG_PSS) Slog.d(TAG_PSS, "Dump heap finished for " + path);
21679             mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG);
21680         }
21681     }
21682
21683     /** In this method we try to acquire our lock to make sure that we have not deadlocked */
21684     public void monitor() {
21685         synchronized (this) { }
21686     }
21687
21688     void onCoreSettingsChange(Bundle settings) {
21689         for (int i = mLruProcesses.size() - 1; i >= 0; i--) {
21690             ProcessRecord processRecord = mLruProcesses.get(i);
21691             try {
21692                 if (processRecord.thread != null) {
21693                     processRecord.thread.setCoreSettings(settings);
21694                 }
21695             } catch (RemoteException re) {
21696                 /* ignore */
21697             }
21698         }
21699     }
21700
21701     // Multi-user methods
21702
21703     /**
21704      * Start user, if its not already running, but don't bring it to foreground.
21705      */
21706     @Override
21707     public boolean startUserInBackground(final int userId) {
21708         return mUserController.startUser(userId, /* foreground */ false);
21709     }
21710
21711     @Override
21712     public boolean unlockUser(int userId, byte[] token, byte[] secret, IProgressListener listener) {
21713         return mUserController.unlockUser(userId, token, secret, listener);
21714     }
21715
21716     @Override
21717     public boolean switchUser(final int targetUserId) {
21718         enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, targetUserId);
21719         UserInfo currentUserInfo;
21720         UserInfo targetUserInfo;
21721         synchronized (this) {
21722             int currentUserId = mUserController.getCurrentUserIdLocked();
21723             currentUserInfo = mUserController.getUserInfo(currentUserId);
21724             targetUserInfo = mUserController.getUserInfo(targetUserId);
21725             if (targetUserInfo == null) {
21726                 Slog.w(TAG, "No user info for user #" + targetUserId);
21727                 return false;
21728             }
21729             if (!targetUserInfo.isDemo() && UserManager.isDeviceInDemoMode(mContext)) {
21730                 Slog.w(TAG, "Cannot switch to non-demo user #" + targetUserId
21731                         + " when device is in demo mode");
21732                 return false;
21733             }
21734             if (!targetUserInfo.supportsSwitchTo()) {
21735                 Slog.w(TAG, "Cannot switch to User #" + targetUserId + ": not supported");
21736                 return false;
21737             }
21738             if (targetUserInfo.isManagedProfile()) {
21739                 Slog.w(TAG, "Cannot switch to User #" + targetUserId + ": not a full user");
21740                 return false;
21741             }
21742             mUserController.setTargetUserIdLocked(targetUserId);
21743         }
21744         Pair<UserInfo, UserInfo> userNames = new Pair<>(currentUserInfo, targetUserInfo);
21745         mUiHandler.removeMessages(START_USER_SWITCH_UI_MSG);
21746         mUiHandler.sendMessage(mUiHandler.obtainMessage(START_USER_SWITCH_UI_MSG, userNames));
21747         return true;
21748     }
21749
21750     void scheduleStartProfilesLocked() {
21751         if (!mHandler.hasMessages(START_PROFILES_MSG)) {
21752             mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG),
21753                     DateUtils.SECOND_IN_MILLIS);
21754         }
21755     }
21756
21757     @Override
21758     public int stopUser(final int userId, boolean force, final IStopUserCallback callback) {
21759         return mUserController.stopUser(userId, force, callback);
21760     }
21761
21762     @Override
21763     public UserInfo getCurrentUser() {
21764         return mUserController.getCurrentUser();
21765     }
21766
21767     @Override
21768     public boolean isUserRunning(int userId, int flags) {
21769         if (!mUserController.isSameProfileGroup(userId, UserHandle.getCallingUserId())
21770                 && checkCallingPermission(INTERACT_ACROSS_USERS)
21771                     != PackageManager.PERMISSION_GRANTED) {
21772             String msg = "Permission Denial: isUserRunning() from pid="
21773                     + Binder.getCallingPid()
21774                     + ", uid=" + Binder.getCallingUid()
21775                     + " requires " + INTERACT_ACROSS_USERS;
21776             Slog.w(TAG, msg);
21777             throw new SecurityException(msg);
21778         }
21779         synchronized (this) {
21780             return mUserController.isUserRunningLocked(userId, flags);
21781         }
21782     }
21783
21784     @Override
21785     public int[] getRunningUserIds() {
21786         if (checkCallingPermission(INTERACT_ACROSS_USERS)
21787                 != PackageManager.PERMISSION_GRANTED) {
21788             String msg = "Permission Denial: isUserRunning() from pid="
21789                     + Binder.getCallingPid()
21790                     + ", uid=" + Binder.getCallingUid()
21791                     + " requires " + INTERACT_ACROSS_USERS;
21792             Slog.w(TAG, msg);
21793             throw new SecurityException(msg);
21794         }
21795         synchronized (this) {
21796             return mUserController.getStartedUserArrayLocked();
21797         }
21798     }
21799
21800     @Override
21801     public void registerUserSwitchObserver(IUserSwitchObserver observer, String name) {
21802         mUserController.registerUserSwitchObserver(observer, name);
21803     }
21804
21805     @Override
21806     public void unregisterUserSwitchObserver(IUserSwitchObserver observer) {
21807         mUserController.unregisterUserSwitchObserver(observer);
21808     }
21809
21810     ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) {
21811         if (info == null) return null;
21812         ApplicationInfo newInfo = new ApplicationInfo(info);
21813         newInfo.initForUser(userId);
21814         return newInfo;
21815     }
21816
21817     public boolean isUserStopped(int userId) {
21818         synchronized (this) {
21819             return mUserController.getStartedUserStateLocked(userId) == null;
21820         }
21821     }
21822
21823     ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) {
21824         if (aInfo == null
21825                 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) {
21826             return aInfo;
21827         }
21828
21829         ActivityInfo info = new ActivityInfo(aInfo);
21830         info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId);
21831         return info;
21832     }
21833
21834     private boolean processSanityChecksLocked(ProcessRecord process) {
21835         if (process == null || process.thread == null) {
21836             return false;
21837         }
21838
21839         boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0"));
21840         if (!isDebuggable) {
21841             if ((process.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) {
21842                 return false;
21843             }
21844         }
21845
21846         return true;
21847     }
21848
21849     public boolean startBinderTracking() throws RemoteException {
21850         synchronized (this) {
21851             mBinderTransactionTrackingEnabled = true;
21852             // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own
21853             // permission (same as profileControl).
21854             if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
21855                     != PackageManager.PERMISSION_GRANTED) {
21856                 throw new SecurityException("Requires permission "
21857                         + android.Manifest.permission.SET_ACTIVITY_WATCHER);
21858             }
21859
21860             for (int i = 0; i < mLruProcesses.size(); i++) {
21861                 ProcessRecord process = mLruProcesses.get(i);
21862                 if (!processSanityChecksLocked(process)) {
21863                     continue;
21864                 }
21865                 try {
21866                     process.thread.startBinderTracking();
21867                 } catch (RemoteException e) {
21868                     Log.v(TAG, "Process disappared");
21869                 }
21870             }
21871             return true;
21872         }
21873     }
21874
21875     public boolean stopBinderTrackingAndDump(ParcelFileDescriptor fd) throws RemoteException {
21876         try {
21877             synchronized (this) {
21878                 mBinderTransactionTrackingEnabled = false;
21879                 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own
21880                 // permission (same as profileControl).
21881                 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER)
21882                         != PackageManager.PERMISSION_GRANTED) {
21883                     throw new SecurityException("Requires permission "
21884                             + android.Manifest.permission.SET_ACTIVITY_WATCHER);
21885                 }
21886
21887                 if (fd == null) {
21888                     throw new IllegalArgumentException("null fd");
21889                 }
21890
21891                 PrintWriter pw = new FastPrintWriter(new FileOutputStream(fd.getFileDescriptor()));
21892                 pw.println("Binder transaction traces for all processes.\n");
21893                 for (ProcessRecord process : mLruProcesses) {
21894                     if (!processSanityChecksLocked(process)) {
21895                         continue;
21896                     }
21897
21898                     pw.println("Traces for process: " + process.processName);
21899                     pw.flush();
21900                     try {
21901                         TransferPipe tp = new TransferPipe();
21902                         try {
21903                             process.thread.stopBinderTrackingAndDump(
21904                                     tp.getWriteFd().getFileDescriptor());
21905                             tp.go(fd.getFileDescriptor());
21906                         } finally {
21907                             tp.kill();
21908                         }
21909                     } catch (IOException e) {
21910                         pw.println("Failure while dumping IPC traces from " + process +
21911                                 ".  Exception: " + e);
21912                         pw.flush();
21913                     } catch (RemoteException e) {
21914                         pw.println("Got a RemoteException while dumping IPC traces from " +
21915                                 process + ".  Exception: " + e);
21916                         pw.flush();
21917                     }
21918                 }
21919                 fd = null;
21920                 return true;
21921             }
21922         } finally {
21923             if (fd != null) {
21924                 try {
21925                     fd.close();
21926                 } catch (IOException e) {
21927                 }
21928             }
21929         }
21930     }
21931
21932     private final class LocalService extends ActivityManagerInternal {
21933         @Override
21934         public void grantUriPermissionFromIntent(int callingUid, String targetPkg, Intent intent,
21935                 int targetUserId) {
21936             synchronized (ActivityManagerService.this) {
21937                 ActivityManagerService.this.grantUriPermissionFromIntentLocked(callingUid,
21938                         targetPkg, intent, null, targetUserId);
21939             }
21940         }
21941
21942         @Override
21943         public String checkContentProviderAccess(String authority, int userId) {
21944             return ActivityManagerService.this.checkContentProviderAccess(authority, userId);
21945         }
21946
21947         @Override
21948         public void onWakefulnessChanged(int wakefulness) {
21949             ActivityManagerService.this.onWakefulnessChanged(wakefulness);
21950         }
21951
21952         @Override
21953         public int startIsolatedProcess(String entryPoint, String[] entryPointArgs,
21954                 String processName, String abiOverride, int uid, Runnable crashHandler) {
21955             return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs,
21956                     processName, abiOverride, uid, crashHandler);
21957         }
21958
21959         @Override
21960         public SleepToken acquireSleepToken(String tag) {
21961             Preconditions.checkNotNull(tag);
21962
21963             synchronized (ActivityManagerService.this) {
21964                 SleepTokenImpl token = new SleepTokenImpl(tag);
21965                 mSleepTokens.add(token);
21966                 updateSleepIfNeededLocked();
21967                 return token;
21968             }
21969         }
21970
21971         @Override
21972         public ComponentName getHomeActivityForUser(int userId) {
21973             synchronized (ActivityManagerService.this) {
21974                 ActivityRecord homeActivity = mStackSupervisor.getHomeActivityForUser(userId);
21975                 return homeActivity == null ? null : homeActivity.realActivity;
21976             }
21977         }
21978
21979         @Override
21980         public void onUserRemoved(int userId) {
21981             synchronized (ActivityManagerService.this) {
21982                 ActivityManagerService.this.onUserStoppedLocked(userId);
21983             }
21984         }
21985
21986         @Override
21987         public void onLocalVoiceInteractionStarted(IBinder activity,
21988                 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
21989             synchronized (ActivityManagerService.this) {
21990                 ActivityManagerService.this.onLocalVoiceInteractionStartedLocked(activity,
21991                         voiceSession, voiceInteractor);
21992             }
21993         }
21994
21995         @Override
21996         public void notifyStartingWindowDrawn() {
21997             synchronized (ActivityManagerService.this) {
21998                 mStackSupervisor.mActivityMetricsLogger.notifyStartingWindowDrawn();
21999             }
22000         }
22001
22002         @Override
22003         public void notifyAppTransitionStarting(int reason) {
22004             synchronized (ActivityManagerService.this) {
22005                 mStackSupervisor.mActivityMetricsLogger.notifyTransitionStarting(reason);
22006             }
22007         }
22008
22009         @Override
22010         public void notifyAppTransitionFinished() {
22011             synchronized (ActivityManagerService.this) {
22012                 mStackSupervisor.notifyAppTransitionDone();
22013             }
22014         }
22015
22016         @Override
22017         public void notifyAppTransitionCancelled() {
22018             synchronized (ActivityManagerService.this) {
22019                 mStackSupervisor.notifyAppTransitionDone();
22020             }
22021         }
22022
22023         @Override
22024         public List<IBinder> getTopVisibleActivities() {
22025             synchronized (ActivityManagerService.this) {
22026                 return mStackSupervisor.getTopVisibleActivities();
22027             }
22028         }
22029
22030         @Override
22031         public void notifyDockedStackMinimizedChanged(boolean minimized) {
22032             synchronized (ActivityManagerService.this) {
22033                 mStackSupervisor.setDockedStackMinimized(minimized);
22034             }
22035         }
22036
22037         @Override
22038         public void killForegroundAppsForUser(int userHandle) {
22039             synchronized (ActivityManagerService.this) {
22040                 final ArrayList<ProcessRecord> procs = new ArrayList<>();
22041                 final int NP = mProcessNames.getMap().size();
22042                 for (int ip = 0; ip < NP; ip++) {
22043                     final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip);
22044                     final int NA = apps.size();
22045                     for (int ia = 0; ia < NA; ia++) {
22046                         final ProcessRecord app = apps.valueAt(ia);
22047                         if (app.persistent) {
22048                             // We don't kill persistent processes.
22049                             continue;
22050                         }
22051                         if (app.removed) {
22052                             procs.add(app);
22053                         } else if (app.userId == userHandle && app.foregroundActivities) {
22054                             app.removed = true;
22055                             procs.add(app);
22056                         }
22057                     }
22058                 }
22059
22060                 final int N = procs.size();
22061                 for (int i = 0; i < N; i++) {
22062                     removeProcessLocked(procs.get(i), false, true, "kill all fg");
22063                 }
22064             }
22065         }
22066
22067         @Override
22068         public void setPendingIntentWhitelistDuration(IIntentSender target, long duration) {
22069             if (!(target instanceof PendingIntentRecord)) {
22070                 Slog.w(TAG, "markAsSentFromNotification(): not a PendingIntentRecord: " + target);
22071                 return;
22072             }
22073             ((PendingIntentRecord) target).setWhitelistDuration(duration);
22074         }
22075
22076         @Override
22077         public void updatePersistentConfigurationForUser(@NonNull Configuration values,
22078                 int userId) {
22079             Preconditions.checkNotNull(values, "Configuration must not be null");
22080             Preconditions.checkArgumentNonnegative(userId, "userId " + userId + " not supported");
22081             synchronized (ActivityManagerService.this) {
22082                 updateConfigurationLocked(values, null, false, true, userId,
22083                         false /* deferResume */);
22084             }
22085         }
22086
22087         @Override
22088         public int startActivitiesAsPackage(String packageName, int userId, Intent[] intents,
22089                 Bundle bOptions) {
22090             Preconditions.checkNotNull(intents, "intents");
22091             final String[] resolvedTypes = new String[intents.length];
22092             for (int i = 0; i < intents.length; i++) {
22093                 resolvedTypes[i] = intents[i].resolveTypeIfNeeded(mContext.getContentResolver());
22094             }
22095
22096             // UID of the package on user userId.
22097             // "= 0" is needed because otherwise catch(RemoteException) would make it look like
22098             // packageUid may not be initialized.
22099             int packageUid = 0;
22100             try {
22101                 packageUid = AppGlobals.getPackageManager().getPackageUid(
22102                         packageName, PackageManager.MATCH_DEBUG_TRIAGED_MISSING, userId);
22103             } catch (RemoteException e) {
22104                 // Shouldn't happen.
22105             }
22106
22107             synchronized (ActivityManagerService.this) {
22108                 return startActivitiesInPackage(packageUid, packageName, intents, resolvedTypes,
22109                         /*resultTo*/ null, bOptions, userId);
22110             }
22111         }
22112
22113         @Override
22114         public int getUidProcessState(int uid) {
22115             return getUidState(uid);
22116         }
22117     }
22118
22119     private final class SleepTokenImpl extends SleepToken {
22120         private final String mTag;
22121         private final long mAcquireTime;
22122
22123         public SleepTokenImpl(String tag) {
22124             mTag = tag;
22125             mAcquireTime = SystemClock.uptimeMillis();
22126         }
22127
22128         @Override
22129         public void release() {
22130             synchronized (ActivityManagerService.this) {
22131                 if (mSleepTokens.remove(this)) {
22132                     updateSleepIfNeededLocked();
22133                 }
22134             }
22135         }
22136
22137         @Override
22138         public String toString() {
22139             return "{\"" + mTag + "\", acquire at " + TimeUtils.formatUptime(mAcquireTime) + "}";
22140         }
22141     }
22142
22143     /**
22144      * An implementation of IAppTask, that allows an app to manage its own tasks via
22145      * {@link android.app.ActivityManager.AppTask}.  We keep track of the callingUid to ensure that
22146      * only the process that calls getAppTasks() can call the AppTask methods.
22147      */
22148     class AppTaskImpl extends IAppTask.Stub {
22149         private int mTaskId;
22150         private int mCallingUid;
22151
22152         public AppTaskImpl(int taskId, int callingUid) {
22153             mTaskId = taskId;
22154             mCallingUid = callingUid;
22155         }
22156
22157         private void checkCaller() {
22158             if (mCallingUid != Binder.getCallingUid()) {
22159                 throw new SecurityException("Caller " + mCallingUid
22160                         + " does not match caller of getAppTasks(): " + Binder.getCallingUid());
22161             }
22162         }
22163
22164         @Override
22165         public void finishAndRemoveTask() {
22166             checkCaller();
22167
22168             synchronized (ActivityManagerService.this) {
22169                 long origId = Binder.clearCallingIdentity();
22170                 try {
22171                     // We remove the task from recents to preserve backwards
22172                     if (!removeTaskByIdLocked(mTaskId, false, REMOVE_FROM_RECENTS)) {
22173                         throw new IllegalArgumentException("Unable to find task ID " + mTaskId);
22174                     }
22175                 } finally {
22176                     Binder.restoreCallingIdentity(origId);
22177                 }
22178             }
22179         }
22180
22181         @Override
22182         public ActivityManager.RecentTaskInfo getTaskInfo() {
22183             checkCaller();
22184
22185             synchronized (ActivityManagerService.this) {
22186                 long origId = Binder.clearCallingIdentity();
22187                 try {
22188                     TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(mTaskId);
22189                     if (tr == null) {
22190                         throw new IllegalArgumentException("Unable to find task ID " + mTaskId);
22191                     }
22192                     return createRecentTaskInfoFromTaskRecord(tr);
22193                 } finally {
22194                     Binder.restoreCallingIdentity(origId);
22195                 }
22196             }
22197         }
22198
22199         @Override
22200         public void moveToFront() {
22201             checkCaller();
22202             // Will bring task to front if it already has a root activity.
22203             final long origId = Binder.clearCallingIdentity();
22204             try {
22205                 synchronized (this) {
22206                     mStackSupervisor.startActivityFromRecentsInner(mTaskId, null);
22207                 }
22208             } finally {
22209                 Binder.restoreCallingIdentity(origId);
22210             }
22211         }
22212
22213         @Override
22214         public int startActivity(IBinder whoThread, String callingPackage,
22215                 Intent intent, String resolvedType, Bundle bOptions) {
22216             checkCaller();
22217
22218             int callingUser = UserHandle.getCallingUserId();
22219             TaskRecord tr;
22220             IApplicationThread appThread;
22221             synchronized (ActivityManagerService.this) {
22222                 tr = mStackSupervisor.anyTaskForIdLocked(mTaskId);
22223                 if (tr == null) {
22224                     throw new IllegalArgumentException("Unable to find task ID " + mTaskId);
22225                 }
22226                 appThread = ApplicationThreadNative.asInterface(whoThread);
22227                 if (appThread == null) {
22228                     throw new IllegalArgumentException("Bad app thread " + appThread);
22229                 }
22230             }
22231             return mActivityStarter.startActivityMayWait(appThread, -1, callingPackage, intent,
22232                     resolvedType, null, null, null, null, 0, 0, null, null,
22233                     null, bOptions, false, callingUser, null, tr);
22234         }
22235
22236         @Override
22237         public void setExcludeFromRecents(boolean exclude) {
22238             checkCaller();
22239
22240             synchronized (ActivityManagerService.this) {
22241                 long origId = Binder.clearCallingIdentity();
22242                 try {
22243                     TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(mTaskId);
22244                     if (tr == null) {
22245                         throw new IllegalArgumentException("Unable to find task ID " + mTaskId);
22246                     }
22247                     Intent intent = tr.getBaseIntent();
22248                     if (exclude) {
22249                         intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
22250                     } else {
22251                         intent.setFlags(intent.getFlags()
22252                                 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
22253                     }
22254                 } finally {
22255                     Binder.restoreCallingIdentity(origId);
22256                 }
22257             }
22258         }
22259     }
22260
22261     /**
22262      * Kill processes for the user with id userId and that depend on the package named packageName
22263      */
22264     @Override
22265     public void killPackageDependents(String packageName, int userId) {
22266         enforceCallingPermission(android.Manifest.permission.KILL_UID, "killPackageDependents()");
22267         if (packageName == null) {
22268             throw new NullPointerException(
22269                     "Cannot kill the dependents of a package without its name.");
22270         }
22271
22272         long callingId = Binder.clearCallingIdentity();
22273         IPackageManager pm = AppGlobals.getPackageManager();
22274         int pkgUid = -1;
22275         try {
22276             pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId);
22277         } catch (RemoteException e) {
22278         }
22279         if (userId != UserHandle.USER_ALL && pkgUid == -1) {
22280             throw new IllegalArgumentException(
22281                     "Cannot kill dependents of non-existing package " + packageName);
22282         }
22283         try {
22284             synchronized(this) {
22285                 killPackageProcessesLocked(packageName, UserHandle.getAppId(pkgUid), userId,
22286                         ProcessList.FOREGROUND_APP_ADJ, false, true, true, false,
22287                         "dep: " + packageName);
22288             }
22289         } finally {
22290             Binder.restoreCallingIdentity(callingId);
22291         }
22292     }
22293
22294     @Override
22295     public boolean canBypassWorkChallenge(PendingIntent intent) throws RemoteException {
22296         final int userId = intent.getCreatorUserHandle().getIdentifier();
22297         if (!mUserController.isUserRunningLocked(userId, ActivityManager.FLAG_AND_LOCKED)) {
22298             return false;
22299         }
22300         IIntentSender target = intent.getTarget();
22301         if (!(target instanceof PendingIntentRecord)) {
22302             return false;
22303         }
22304         final PendingIntentRecord record = (PendingIntentRecord) target;
22305         final ResolveInfo rInfo = mStackSupervisor.resolveIntent(record.key.requestIntent,
22306                 record.key.requestResolvedType, userId, PackageManager.MATCH_DIRECT_BOOT_AWARE);
22307         // For direct boot aware activities, they can be shown without triggering a work challenge
22308         // before the profile user is unlocked.
22309         return rInfo != null && rInfo.activityInfo != null;
22310     }
22311 }