1 /*
2  * Copyright (C) 2006 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 android.app;
18 
19 import android.annotation.CallSuper;
20 import android.annotation.NonNull;
21 import android.annotation.Nullable;
22 import android.compat.annotation.UnsupportedAppUsage;
23 import android.content.ComponentCallbacks;
24 import android.content.ComponentCallbacks2;
25 import android.content.ComponentCallbacksController;
26 import android.content.Context;
27 import android.content.ContextWrapper;
28 import android.content.Intent;
29 import android.content.res.Configuration;
30 import android.os.Build;
31 import android.os.Bundle;
32 import android.util.Log;
33 import android.view.autofill.AutofillManager;
34 
35 import java.util.ArrayList;
36 
37 /**
38  * Base class for maintaining global application state. You can provide your own
39  * implementation by creating a subclass and specifying the fully-qualified name
40  * of this subclass as the <code>"android:name"</code> attribute in your
41  * AndroidManifest.xml's <code>&lt;application&gt;</code> tag. The Application
42  * class, or your subclass of the Application class, is instantiated before any
43  * other class when the process for your application/package is created.
44  *
45  * <p class="note"><strong>Note: </strong>There is normally no need to subclass
46  * Application.  In most situations, static singletons can provide the same
47  * functionality in a more modular way.  If your singleton needs a global
48  * context (for example to register broadcast receivers), include
49  * {@link android.content.Context#getApplicationContext() Context.getApplicationContext()}
50  * as a {@link android.content.Context} argument when invoking your singleton's
51  * <code>getInstance()</code> method.
52  * </p>
53  */
54 public class Application extends ContextWrapper implements ComponentCallbacks2 {
55     private static final String TAG = "Application";
56 
57     @UnsupportedAppUsage
58     private ArrayList<ActivityLifecycleCallbacks> mActivityLifecycleCallbacks =
59             new ArrayList<ActivityLifecycleCallbacks>();
60     @UnsupportedAppUsage
61     private ArrayList<OnProvideAssistDataListener> mAssistCallbacks = null;
62 
63     private final ComponentCallbacksController mCallbacksController =
64             new ComponentCallbacksController();
65 
66     /** @hide */
67     @UnsupportedAppUsage
68     public LoadedApk mLoadedApk;
69 
70     public interface ActivityLifecycleCallbacks {
71 
72         /**
73          * Called as the first step of the Activity being created. This is always called before
74          * {@link Activity#onCreate}.
75          */
onActivityPreCreated(@onNull Activity activity, @Nullable Bundle savedInstanceState)76         default void onActivityPreCreated(@NonNull Activity activity,
77                 @Nullable Bundle savedInstanceState) {
78         }
79 
80         /**
81          * Called when the Activity calls {@link Activity#onCreate super.onCreate()}.
82          */
onActivityCreated(@onNull Activity activity, @Nullable Bundle savedInstanceState)83         void onActivityCreated(@NonNull Activity activity, @Nullable Bundle savedInstanceState);
84 
85         /**
86          * Called as the last step of the Activity being created. This is always called after
87          * {@link Activity#onCreate}.
88          */
onActivityPostCreated(@onNull Activity activity, @Nullable Bundle savedInstanceState)89         default void onActivityPostCreated(@NonNull Activity activity,
90                 @Nullable Bundle savedInstanceState) {
91         }
92 
93         /**
94          * Called as the first step of the Activity being started. This is always called before
95          * {@link Activity#onStart}.
96          */
onActivityPreStarted(@onNull Activity activity)97         default void onActivityPreStarted(@NonNull Activity activity) {
98         }
99 
100         /**
101          * Called when the Activity calls {@link Activity#onStart super.onStart()}.
102          */
onActivityStarted(@onNull Activity activity)103         void onActivityStarted(@NonNull Activity activity);
104 
105         /**
106          * Called as the last step of the Activity being started. This is always called after
107          * {@link Activity#onStart}.
108          */
onActivityPostStarted(@onNull Activity activity)109         default void onActivityPostStarted(@NonNull Activity activity) {
110         }
111 
112         /**
113          * Called as the first step of the Activity being resumed. This is always called before
114          * {@link Activity#onResume}.
115          */
onActivityPreResumed(@onNull Activity activity)116         default void onActivityPreResumed(@NonNull Activity activity) {
117         }
118 
119         /**
120          * Called when the Activity calls {@link Activity#onResume super.onResume()}.
121          */
onActivityResumed(@onNull Activity activity)122         void onActivityResumed(@NonNull Activity activity);
123 
124         /**
125          * Called as the last step of the Activity being resumed. This is always called after
126          * {@link Activity#onResume} and {@link Activity#onPostResume}.
127          */
onActivityPostResumed(@onNull Activity activity)128         default void onActivityPostResumed(@NonNull Activity activity) {
129         }
130 
131         /**
132          * Called as the first step of the Activity being paused. This is always called before
133          * {@link Activity#onPause}.
134          */
onActivityPrePaused(@onNull Activity activity)135         default void onActivityPrePaused(@NonNull Activity activity) {
136         }
137 
138         /**
139          * Called when the Activity calls {@link Activity#onPause super.onPause()}.
140          */
onActivityPaused(@onNull Activity activity)141         void onActivityPaused(@NonNull Activity activity);
142 
143         /**
144          * Called as the last step of the Activity being paused. This is always called after
145          * {@link Activity#onPause}.
146          */
onActivityPostPaused(@onNull Activity activity)147         default void onActivityPostPaused(@NonNull Activity activity) {
148         }
149 
150         /**
151          * Called as the first step of the Activity being stopped. This is always called before
152          * {@link Activity#onStop}.
153          */
onActivityPreStopped(@onNull Activity activity)154         default void onActivityPreStopped(@NonNull Activity activity) {
155         }
156 
157         /**
158          * Called when the Activity calls {@link Activity#onStop super.onStop()}.
159          */
onActivityStopped(@onNull Activity activity)160         void onActivityStopped(@NonNull Activity activity);
161 
162         /**
163          * Called as the last step of the Activity being stopped. This is always called after
164          * {@link Activity#onStop}.
165          */
onActivityPostStopped(@onNull Activity activity)166         default void onActivityPostStopped(@NonNull Activity activity) {
167         }
168 
169         /**
170          * Called as the first step of the Activity saving its instance state. This is always
171          * called before {@link Activity#onSaveInstanceState}.
172          */
onActivityPreSaveInstanceState(@onNull Activity activity, @NonNull Bundle outState)173         default void onActivityPreSaveInstanceState(@NonNull Activity activity,
174                 @NonNull Bundle outState) {
175         }
176 
177         /**
178          * Called when the Activity calls
179          * {@link Activity#onSaveInstanceState super.onSaveInstanceState()}.
180          */
onActivitySaveInstanceState(@onNull Activity activity, @NonNull Bundle outState)181         void onActivitySaveInstanceState(@NonNull Activity activity, @NonNull Bundle outState);
182 
183         /**
184          * Called as the last step of the Activity saving its instance state. This is always
185          * called after{@link Activity#onSaveInstanceState}.
186          */
onActivityPostSaveInstanceState(@onNull Activity activity, @NonNull Bundle outState)187         default void onActivityPostSaveInstanceState(@NonNull Activity activity,
188                 @NonNull Bundle outState) {
189         }
190 
191         /**
192          * Called as the first step of the Activity being destroyed. This is always called before
193          * {@link Activity#onDestroy}.
194          */
onActivityPreDestroyed(@onNull Activity activity)195         default void onActivityPreDestroyed(@NonNull Activity activity) {
196         }
197 
198         /**
199          * Called when the Activity calls {@link Activity#onDestroy super.onDestroy()}.
200          */
onActivityDestroyed(@onNull Activity activity)201         void onActivityDestroyed(@NonNull Activity activity);
202 
203         /**
204          * Called as the last step of the Activity being destroyed. This is always called after
205          * {@link Activity#onDestroy}.
206          */
onActivityPostDestroyed(@onNull Activity activity)207         default void onActivityPostDestroyed(@NonNull Activity activity) {
208         }
209 
210         /**
211          * Called when the Activity configuration was changed.
212          * @hide
213          */
onActivityConfigurationChanged(@onNull Activity activity)214         default void onActivityConfigurationChanged(@NonNull Activity activity) {
215         }
216     }
217 
218     /**
219      * Callback interface for use with {@link Application#registerOnProvideAssistDataListener}
220      * and {@link Application#unregisterOnProvideAssistDataListener}.
221      */
222     public interface OnProvideAssistDataListener {
223         /**
224          * This is called when the user is requesting an assist, to build a full
225          * {@link Intent#ACTION_ASSIST} Intent with all of the context of the current
226          * application.  You can override this method to place into the bundle anything
227          * you would like to appear in the {@link Intent#EXTRA_ASSIST_CONTEXT} part
228          * of the assist Intent.
229          */
onProvideAssistData(Activity activity, Bundle data)230         public void onProvideAssistData(Activity activity, Bundle data);
231     }
232 
Application()233     public Application() {
234         super(null);
235     }
236 
getLoadedApkInfo()237     private String getLoadedApkInfo() {
238         if (mLoadedApk == null) {
239             return "null";
240         }
241         return mLoadedApk + "/pkg=" + mLoadedApk.mPackageName;
242     }
243 
244     /**
245      * Called when the application is starting, before any activity, service,
246      * or receiver objects (excluding content providers) have been created.
247      *
248      * <p>Implementations should be as quick as possible (for example using
249      * lazy initialization of state) since the time spent in this function
250      * directly impacts the performance of starting the first activity,
251      * service, or receiver in a process.</p>
252      *
253      * <p>If you override this method, be sure to call {@code super.onCreate()}.</p>
254      *
255      * <p class="note">Be aware that direct boot may also affect callback order on
256      * Android {@link android.os.Build.VERSION_CODES#N} and later devices.
257      * Until the user unlocks the device, only direct boot aware components are
258      * allowed to run. You should consider that all direct boot unaware
259      * components, including such {@link android.content.ContentProvider}, are
260      * disabled until user unlock happens, especially when component callback
261      * order matters.</p>
262      */
263     @CallSuper
onCreate()264     public void onCreate() {
265     }
266 
267     /**
268      * This method is for use in emulated process environments.  It will
269      * never be called on a production Android device, where processes are
270      * removed by simply killing them; no user code (including this callback)
271      * is executed when doing so.
272      */
273     @CallSuper
onTerminate()274     public void onTerminate() {
275     }
276 
277     @CallSuper
onConfigurationChanged(@onNull Configuration newConfig)278     public void onConfigurationChanged(@NonNull Configuration newConfig) {
279         mCallbacksController.dispatchConfigurationChanged(newConfig);
280     }
281 
282     @CallSuper
onLowMemory()283     public void onLowMemory() {
284         mCallbacksController.dispatchLowMemory();
285     }
286 
287     @CallSuper
onTrimMemory(int level)288     public void onTrimMemory(int level) {
289         mCallbacksController.dispatchTrimMemory(level);
290     }
291 
registerComponentCallbacks(ComponentCallbacks callback)292     public void registerComponentCallbacks(ComponentCallbacks callback) {
293         mCallbacksController.registerCallbacks(callback);
294     }
295 
unregisterComponentCallbacks(ComponentCallbacks callback)296     public void unregisterComponentCallbacks(ComponentCallbacks callback) {
297         mCallbacksController.unregisterCallbacks(callback);
298     }
299 
registerActivityLifecycleCallbacks(ActivityLifecycleCallbacks callback)300     public void registerActivityLifecycleCallbacks(ActivityLifecycleCallbacks callback) {
301         synchronized (mActivityLifecycleCallbacks) {
302             mActivityLifecycleCallbacks.add(callback);
303         }
304     }
305 
unregisterActivityLifecycleCallbacks(ActivityLifecycleCallbacks callback)306     public void unregisterActivityLifecycleCallbacks(ActivityLifecycleCallbacks callback) {
307         synchronized (mActivityLifecycleCallbacks) {
308             mActivityLifecycleCallbacks.remove(callback);
309         }
310     }
311 
registerOnProvideAssistDataListener(OnProvideAssistDataListener callback)312     public void registerOnProvideAssistDataListener(OnProvideAssistDataListener callback) {
313         synchronized (this) {
314             if (mAssistCallbacks == null) {
315                 mAssistCallbacks = new ArrayList<OnProvideAssistDataListener>();
316             }
317             mAssistCallbacks.add(callback);
318         }
319     }
320 
unregisterOnProvideAssistDataListener(OnProvideAssistDataListener callback)321     public void unregisterOnProvideAssistDataListener(OnProvideAssistDataListener callback) {
322         synchronized (this) {
323             if (mAssistCallbacks != null) {
324                 mAssistCallbacks.remove(callback);
325             }
326         }
327     }
328 
329     /**
330      * Returns the name of the current process. A package's default process name
331      * is the same as its package name. Non-default processes will look like
332      * "$PACKAGE_NAME:$NAME", where $NAME corresponds to an android:process
333      * attribute within AndroidManifest.xml.
334      */
getProcessName()335     public static String getProcessName() {
336         return ActivityThread.currentProcessName();
337     }
338 
339     // ------------------ Internal API ------------------
340 
341     /**
342      * @hide
343      */
344     @UnsupportedAppUsage
attach(Context context)345     /* package */ final void attach(Context context) {
346         attachBaseContext(context);
347         mLoadedApk = ContextImpl.getImpl(context).mPackageInfo;
348     }
349 
350     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPreCreated(@onNull Activity activity, @Nullable Bundle savedInstanceState)351         /* package */ void dispatchActivityPreCreated(@NonNull Activity activity,
352             @Nullable Bundle savedInstanceState) {
353         Object[] callbacks = collectActivityLifecycleCallbacks();
354         if (callbacks != null) {
355             for (int i = 0; i < callbacks.length; i++) {
356                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPreCreated(activity,
357                         savedInstanceState);
358             }
359         }
360     }
361 
362     @UnsupportedAppUsage
dispatchActivityCreated(@onNull Activity activity, @Nullable Bundle savedInstanceState)363     /* package */ void dispatchActivityCreated(@NonNull Activity activity,
364             @Nullable Bundle savedInstanceState) {
365         Object[] callbacks = collectActivityLifecycleCallbacks();
366         if (callbacks != null) {
367             for (int i=0; i<callbacks.length; i++) {
368                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivityCreated(activity,
369                         savedInstanceState);
370             }
371         }
372     }
373 
374     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostCreated(@onNull Activity activity, @Nullable Bundle savedInstanceState)375         /* package */ void dispatchActivityPostCreated(@NonNull Activity activity,
376             @Nullable Bundle savedInstanceState) {
377         Object[] callbacks = collectActivityLifecycleCallbacks();
378         if (callbacks != null) {
379             for (int i = 0; i < callbacks.length; i++) {
380                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostCreated(activity,
381                         savedInstanceState);
382             }
383         }
384     }
385 
386     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPreStarted(@onNull Activity activity)387         /* package */ void dispatchActivityPreStarted(@NonNull Activity activity) {
388         Object[] callbacks = collectActivityLifecycleCallbacks();
389         if (callbacks != null) {
390             for (int i = 0; i < callbacks.length; i++) {
391                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPreStarted(activity);
392             }
393         }
394     }
395 
396     @UnsupportedAppUsage
dispatchActivityStarted(@onNull Activity activity)397     /* package */ void dispatchActivityStarted(@NonNull Activity activity) {
398         Object[] callbacks = collectActivityLifecycleCallbacks();
399         if (callbacks != null) {
400             for (int i=0; i<callbacks.length; i++) {
401                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivityStarted(activity);
402             }
403         }
404     }
405 
406     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostStarted(@onNull Activity activity)407         /* package */ void dispatchActivityPostStarted(@NonNull Activity activity) {
408         Object[] callbacks = collectActivityLifecycleCallbacks();
409         if (callbacks != null) {
410             for (int i = 0; i < callbacks.length; i++) {
411                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostStarted(activity);
412             }
413         }
414     }
415 
416     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPreResumed(@onNull Activity activity)417         /* package */ void dispatchActivityPreResumed(@NonNull Activity activity) {
418         Object[] callbacks = collectActivityLifecycleCallbacks();
419         if (callbacks != null) {
420             for (int i = 0; i < callbacks.length; i++) {
421                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPreResumed(activity);
422             }
423         }
424     }
425 
426     @UnsupportedAppUsage
dispatchActivityResumed(@onNull Activity activity)427     /* package */ void dispatchActivityResumed(@NonNull Activity activity) {
428         Object[] callbacks = collectActivityLifecycleCallbacks();
429         if (callbacks != null) {
430             for (int i=0; i<callbacks.length; i++) {
431                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivityResumed(activity);
432             }
433         }
434     }
435 
436     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostResumed(@onNull Activity activity)437         /* package */ void dispatchActivityPostResumed(@NonNull Activity activity) {
438         Object[] callbacks = collectActivityLifecycleCallbacks();
439         if (callbacks != null) {
440             for (int i = 0; i < callbacks.length; i++) {
441                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostResumed(activity);
442             }
443         }
444     }
445 
446     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPrePaused(@onNull Activity activity)447         /* package */ void dispatchActivityPrePaused(@NonNull Activity activity) {
448         Object[] callbacks = collectActivityLifecycleCallbacks();
449         if (callbacks != null) {
450             for (int i = 0; i < callbacks.length; i++) {
451                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPrePaused(activity);
452             }
453         }
454     }
455 
456     @UnsupportedAppUsage
dispatchActivityPaused(@onNull Activity activity)457     /* package */ void dispatchActivityPaused(@NonNull Activity activity) {
458         Object[] callbacks = collectActivityLifecycleCallbacks();
459         if (callbacks != null) {
460             for (int i=0; i<callbacks.length; i++) {
461                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivityPaused(activity);
462             }
463         }
464     }
465 
466     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostPaused(@onNull Activity activity)467         /* package */ void dispatchActivityPostPaused(@NonNull Activity activity) {
468         Object[] callbacks = collectActivityLifecycleCallbacks();
469         if (callbacks != null) {
470             for (int i = 0; i < callbacks.length; i++) {
471                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostPaused(activity);
472             }
473         }
474     }
475 
476     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPreStopped(@onNull Activity activity)477         /* package */ void dispatchActivityPreStopped(@NonNull Activity activity) {
478         Object[] callbacks = collectActivityLifecycleCallbacks();
479         if (callbacks != null) {
480             for (int i = 0; i < callbacks.length; i++) {
481                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPreStopped(activity);
482             }
483         }
484     }
485 
486     @UnsupportedAppUsage
dispatchActivityStopped(@onNull Activity activity)487     /* package */ void dispatchActivityStopped(@NonNull Activity activity) {
488         Object[] callbacks = collectActivityLifecycleCallbacks();
489         if (callbacks != null) {
490             for (int i=0; i<callbacks.length; i++) {
491                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivityStopped(activity);
492             }
493         }
494     }
495 
496     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostStopped(@onNull Activity activity)497         /* package */ void dispatchActivityPostStopped(@NonNull Activity activity) {
498         Object[] callbacks = collectActivityLifecycleCallbacks();
499         if (callbacks != null) {
500             for (int i = 0; i < callbacks.length; i++) {
501                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostStopped(activity);
502             }
503         }
504     }
505 
506     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPreSaveInstanceState(@onNull Activity activity, @NonNull Bundle outState)507         /* package */ void dispatchActivityPreSaveInstanceState(@NonNull Activity activity,
508             @NonNull Bundle outState) {
509         Object[] callbacks = collectActivityLifecycleCallbacks();
510         if (callbacks != null) {
511             for (int i = 0; i < callbacks.length; i++) {
512                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPreSaveInstanceState(
513                         activity, outState);
514             }
515         }
516     }
517 
518     @UnsupportedAppUsage
dispatchActivitySaveInstanceState(@onNull Activity activity, @NonNull Bundle outState)519     /* package */ void dispatchActivitySaveInstanceState(@NonNull Activity activity,
520             @NonNull Bundle outState) {
521         Object[] callbacks = collectActivityLifecycleCallbacks();
522         if (callbacks != null) {
523             for (int i=0; i<callbacks.length; i++) {
524                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivitySaveInstanceState(activity,
525                         outState);
526             }
527         }
528     }
529 
530     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostSaveInstanceState(@onNull Activity activity, @NonNull Bundle outState)531         /* package */ void dispatchActivityPostSaveInstanceState(@NonNull Activity activity,
532             @NonNull Bundle outState) {
533         Object[] callbacks = collectActivityLifecycleCallbacks();
534         if (callbacks != null) {
535             for (int i = 0; i < callbacks.length; i++) {
536                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostSaveInstanceState(
537                         activity, outState);
538             }
539         }
540     }
541 
542     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPreDestroyed(@onNull Activity activity)543         /* package */ void dispatchActivityPreDestroyed(@NonNull Activity activity) {
544         Object[] callbacks = collectActivityLifecycleCallbacks();
545         if (callbacks != null) {
546             for (int i = 0; i < callbacks.length; i++) {
547                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPreDestroyed(activity);
548             }
549         }
550     }
551 
552     @UnsupportedAppUsage
dispatchActivityDestroyed(@onNull Activity activity)553     /* package */ void dispatchActivityDestroyed(@NonNull Activity activity) {
554         Object[] callbacks = collectActivityLifecycleCallbacks();
555         if (callbacks != null) {
556             for (int i=0; i<callbacks.length; i++) {
557                 ((ActivityLifecycleCallbacks)callbacks[i]).onActivityDestroyed(activity);
558             }
559         }
560     }
561 
562     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
dispatchActivityPostDestroyed(@onNull Activity activity)563         /* package */ void dispatchActivityPostDestroyed(@NonNull Activity activity) {
564         Object[] callbacks = collectActivityLifecycleCallbacks();
565         if (callbacks != null) {
566             for (int i = 0; i < callbacks.length; i++) {
567                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityPostDestroyed(activity);
568             }
569         }
570     }
571 
dispatchActivityConfigurationChanged(@onNull Activity activity)572     /* package */ void dispatchActivityConfigurationChanged(@NonNull Activity activity) {
573         Object[] callbacks = collectActivityLifecycleCallbacks();
574         if (callbacks != null) {
575             for (int i = 0; i < callbacks.length; i++) {
576                 ((ActivityLifecycleCallbacks) callbacks[i]).onActivityConfigurationChanged(
577                         activity);
578             }
579         }
580     }
581 
582     @UnsupportedAppUsage
collectActivityLifecycleCallbacks()583     private Object[] collectActivityLifecycleCallbacks() {
584         Object[] callbacks = null;
585         synchronized (mActivityLifecycleCallbacks) {
586             if (mActivityLifecycleCallbacks.size() > 0) {
587                 callbacks = mActivityLifecycleCallbacks.toArray();
588             }
589         }
590         return callbacks;
591     }
592 
dispatchOnProvideAssistData(Activity activity, Bundle data)593     /* package */ void dispatchOnProvideAssistData(Activity activity, Bundle data) {
594         Object[] callbacks;
595         synchronized (this) {
596             if (mAssistCallbacks == null) {
597                 return;
598             }
599             callbacks = mAssistCallbacks.toArray();
600         }
601         if (callbacks != null) {
602             for (int i=0; i<callbacks.length; i++) {
603                 ((OnProvideAssistDataListener)callbacks[i]).onProvideAssistData(activity, data);
604             }
605         }
606     }
607 
608     /** @hide */
609     @Override
getAutofillClient()610     public AutofillManager.AutofillClient getAutofillClient() {
611         final AutofillManager.AutofillClient client = super.getAutofillClient();
612         if (client != null) {
613             return client;
614         }
615         if (android.view.autofill.Helper.sVerbose) {
616             Log.v(TAG, "getAutofillClient(): null on super, trying to find activity thread");
617         }
618         // Okay, ppl use the application context when they should not. This breaks
619         // autofill among other things. Below is a mitigation to find the top resumed
620         // activity.
621         final ActivityThread activityThread = ActivityThread.currentActivityThread();
622         if (activityThread == null) {
623             return null;
624         }
625         final int activityCount = activityThread.mActivities.size();
626         for (int i = 0; i < activityCount; i++) {
627             final ActivityThread.ActivityClientRecord record =
628                     activityThread.mActivities.valueAt(i);
629             if (record == null) {
630                 continue;
631             }
632             final Activity activity = record.activity;
633             if (activity == null) {
634                 continue;
635             }
636             if (record.isTopResumedActivity) {
637                 if (android.view.autofill.Helper.sVerbose) {
638                     Log.v(TAG, "getAutofillClient(): found top resumed activity for " + this +
639                             ": " + activity);
640                 }
641                 return activity.getAutofillClient();
642             }
643             // As a back up option, we pick the focused activity since autofill interacts only
644             // with the currently focused activity and we need the fill client only if a call
645             // comes from the focused activity.
646             if (activity.getWindow().getDecorView().hasFocus()) {
647                 if (android.view.autofill.Helper.sVerbose) {
648                     Log.v(TAG, "getAutofillClient(): found focused activity for " + this +
649                             ": " + activity);
650                 }
651                 return activity.getAutofillClient();
652             }
653         }
654         if (android.view.autofill.Helper.sVerbose) {
655             Log.v(TAG, "getAutofillClient(): none of the " + activityCount + " activities on "
656                     + this + " are top resumed nor have focus");
657         }
658         return null;
659     }
660 }
661