From bd012f4109bd0d5a349eee29c48280d16c85beac Mon Sep 17 00:00:00 2001 From: Jacob Hobbie Date: Wed, 1 Sep 2021 13:11:49 -0700 Subject: [PATCH] Adding support for FLAG_EXPORTED and FLAG_NOT_EXPORTED to registerReceiverAsUser and registerReceiverForAllUsers Test: not needed, added an override method. Manually tested Bug: 161145287 CTS-Coverage-Bug: 197772228 Change-Id: I2c8220c8d54b9ec5cb9481cef98735395db76e27 Topic: registerReceiverAsUser --- core/api/system-current.txt | 1 + core/java/android/app/ContextImpl.java | 14 ++++ core/java/android/content/Context.java | 71 +++++++++++++++++++ core/java/android/content/ContextWrapper.java | 20 ++++++ .../src/android/test/mock/MockContext.java | 15 ++++ 5 files changed, 121 insertions(+) diff --git a/core/api/system-current.txt b/core/api/system-current.txt index 37bbebf2ae0c4..0d70bba06ccdf 100755 --- a/core/api/system-current.txt +++ b/core/api/system-current.txt @@ -2319,6 +2319,7 @@ package android.content { method @Nullable public abstract java.io.File getPreloadsFileCache(); method public abstract boolean isCredentialProtectedStorage(); method @Nullable @RequiresPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) public android.content.Intent registerReceiverForAllUsers(@Nullable android.content.BroadcastReceiver, @NonNull android.content.IntentFilter, @Nullable String, @Nullable android.os.Handler); + method @Nullable @RequiresPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) public android.content.Intent registerReceiverForAllUsers(@Nullable android.content.BroadcastReceiver, @NonNull android.content.IntentFilter, @Nullable String, @Nullable android.os.Handler, int); method public abstract void sendBroadcast(android.content.Intent, @Nullable String, @Nullable android.os.Bundle); method @RequiresPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) public abstract void sendBroadcastAsUser(@RequiresPermission android.content.Intent, android.os.UserHandle, @Nullable String, @Nullable android.os.Bundle); method public abstract void sendOrderedBroadcast(@NonNull android.content.Intent, @Nullable String, @Nullable android.os.Bundle, @Nullable android.content.BroadcastReceiver, @Nullable android.os.Handler, int, @Nullable String, @Nullable android.os.Bundle); diff --git a/core/java/android/app/ContextImpl.java b/core/java/android/app/ContextImpl.java index d0acacf20a897..63f7d76ac8e72 100644 --- a/core/java/android/app/ContextImpl.java +++ b/core/java/android/app/ContextImpl.java @@ -1738,6 +1738,13 @@ class ContextImpl extends Context { filter, broadcastPermission, scheduler); } + @Override + public Intent registerReceiverForAllUsers(BroadcastReceiver receiver, + IntentFilter filter, String broadcastPermission, Handler scheduler, int flags) { + return registerReceiverAsUser(receiver, UserHandle.ALL, + filter, broadcastPermission, scheduler, flags); + } + @Override public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, IntentFilter filter, String broadcastPermission, Handler scheduler) { @@ -1745,6 +1752,13 @@ class ContextImpl extends Context { filter, broadcastPermission, scheduler, getOuterContext(), 0); } + @Override + public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, + IntentFilter filter, String broadcastPermission, Handler scheduler, int flags) { + return registerReceiverInternal(receiver, user.getIdentifier(), + filter, broadcastPermission, scheduler, getOuterContext(), flags); + } + private Intent registerReceiverInternal(BroadcastReceiver receiver, int userId, IntentFilter filter, String broadcastPermission, Handler scheduler, Context context, int flags) { diff --git a/core/java/android/content/Context.java b/core/java/android/content/Context.java index 9ff13a4723179..1df4b207e1c6c 100644 --- a/core/java/android/content/Context.java +++ b/core/java/android/content/Context.java @@ -3129,6 +3129,42 @@ public abstract class Context { throw new RuntimeException("Not implemented. Must override in a subclass."); } + /** + * Same as {@link #registerReceiver(BroadcastReceiver, IntentFilter, String, Handler, int)} + * but this receiver will receive broadcasts that are sent to all users. The receiver can + * use {@link BroadcastReceiver#getSendingUser} to determine on which user the broadcast + * was sent. + * + * @param receiver The BroadcastReceiver to handle the broadcast. + * @param filter Selects the Intent broadcasts to be received. + * @param broadcastPermission String naming a permissions that a + * broadcaster must hold in order to send an Intent to you. If {@code null}, + * no permission is required. + * @param scheduler Handler identifying the thread that will receive + * the Intent. If {@code null}, the main thread of the process will be used. + * @param flags Additional options for the receiver. As of + * {@link android.os.Build.VERSION_CODES#TIRAMISU}, either {@link #RECEIVER_EXPORTED} or + * {@link #RECEIVER_NOT_EXPORTED} must be specified if the receiver isn't being + * registered for protected broadcasts + * + * @return The first sticky intent found that matches filter, + * or {@code null} if there are none. + * + * @see #registerReceiver(BroadcastReceiver, IntentFilter, String, Handler, int) + * @see #sendBroadcast + * @see #unregisterReceiver + * @hide + */ + @SuppressLint("IntentBuilderName") + @Nullable + @RequiresPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) + @SystemApi + public Intent registerReceiverForAllUsers(@Nullable BroadcastReceiver receiver, + @NonNull IntentFilter filter, @Nullable String broadcastPermission, + @Nullable Handler scheduler, @RegisterReceiverFlags int flags) { + throw new RuntimeException("Not implemented. Must override in a subclass."); + } + /** * @hide * Same as {@link #registerReceiver(BroadcastReceiver, IntentFilter, String, Handler) @@ -3159,6 +3195,41 @@ public abstract class Context { UserHandle user, IntentFilter filter, @Nullable String broadcastPermission, @Nullable Handler scheduler); + /** + * @hide + * Same as {@link #registerReceiver(BroadcastReceiver, IntentFilter, String, Handler, int) + * but for a specific user. This receiver will receiver broadcasts that + * are sent to the requested user. + * + * @param receiver The BroadcastReceiver to handle the broadcast. + * @param user UserHandle to send the intent to. + * @param filter Selects the Intent broadcasts to be received. + * @param broadcastPermission String naming a permissions that a + * broadcaster must hold in order to send an Intent to you. If null, + * no permission is required. + * @param scheduler Handler identifying the thread that will receive + * the Intent. If null, the main thread of the process will be used. + * @param flags Additional options for the receiver. As of + * {@link android.os.Build.VERSION_CODES#TIRAMISU}, either {@link #RECEIVER_EXPORTED} or + * {@link #RECEIVER_NOT_EXPORTED} must be specified if the receiver isn't being + * registered for protected broadcasts + * + * @return The first sticky intent found that matches filter, + * or null if there are none. + * + * @see #registerReceiver(BroadcastReceiver, IntentFilter, String, Handler, int) + * @see #sendBroadcast + * @see #unregisterReceiver + */ + @SuppressWarnings("HiddenAbstractMethod") + @SuppressLint("IntentBuilderName") + @Nullable + @RequiresPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) + @UnsupportedAppUsage + public abstract Intent registerReceiverAsUser(BroadcastReceiver receiver, + UserHandle user, IntentFilter filter, @Nullable String broadcastPermission, + @Nullable Handler scheduler, @RegisterReceiverFlags int flags); + /** * Unregister a previously registered BroadcastReceiver. All * filters that have been registered for this BroadcastReceiver will be diff --git a/core/java/android/content/ContextWrapper.java b/core/java/android/content/ContextWrapper.java index 6324d0ecb0e07..3a02004edb1f9 100644 --- a/core/java/android/content/ContextWrapper.java +++ b/core/java/android/content/ContextWrapper.java @@ -754,6 +754,16 @@ public class ContextWrapper extends Context { scheduler); } + /** @hide */ + @Override + @Nullable + public Intent registerReceiverForAllUsers(@Nullable BroadcastReceiver receiver, + @NonNull IntentFilter filter, @Nullable String broadcastPermission, + @Nullable Handler scheduler, int flags) { + return mBase.registerReceiverForAllUsers(receiver, filter, broadcastPermission, + scheduler, flags); + } + /** @hide */ @Override @UnsupportedAppUsage @@ -764,6 +774,16 @@ public class ContextWrapper extends Context { scheduler); } + /** @hide */ + @Override + @UnsupportedAppUsage + public Intent registerReceiverAsUser(@Nullable BroadcastReceiver receiver, UserHandle user, + IntentFilter filter, @Nullable String broadcastPermission, + @Nullable Handler scheduler, int flags) { + return mBase.registerReceiverAsUser(receiver, user, filter, broadcastPermission, + scheduler, flags); + } + @Override public void unregisterReceiver(BroadcastReceiver receiver) { mBase.unregisterReceiver(receiver); diff --git a/test-mock/src/android/test/mock/MockContext.java b/test-mock/src/android/test/mock/MockContext.java index 7a1dda37de70e..49daad324bd11 100644 --- a/test-mock/src/android/test/mock/MockContext.java +++ b/test-mock/src/android/test/mock/MockContext.java @@ -571,6 +571,14 @@ public class MockContext extends Context { throw new UnsupportedOperationException(); } + /** @hide */ + @Override + @SystemApi + public Intent registerReceiverForAllUsers(BroadcastReceiver receiver, + IntentFilter filter, String broadcastPermission, Handler scheduler, int flags) { + throw new UnsupportedOperationException(); + } + /** @hide */ @Override public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, @@ -578,6 +586,13 @@ public class MockContext extends Context { throw new UnsupportedOperationException(); } + /** @hide */ + @Override + public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, + IntentFilter filter, String broadcastPermission, Handler scheduler, int flags) { + throw new UnsupportedOperationException(); + } + @Override public void unregisterReceiver(BroadcastReceiver receiver) { throw new UnsupportedOperationException();