[DO NOT MERGE] Fix BroadcastDispatcher registering with CURRENT am: e771b7529e
Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/11792343 Change-Id: Ia1d89c5e65915027359b1e6d4b2abdc8c26bf24d
This commit is contained in:
@@ -62,7 +62,7 @@ Acquire the dispatcher by using `@Inject` to obtain a `BroadcastDispatcher`. The
|
||||
* @param executor An executor to dispatch [BroadcastReceiver.onReceive]. Pass null to use an
|
||||
* executor in the main thread (default).
|
||||
* @param user A user handle to determine which broadcast should be dispatched to this receiver.
|
||||
* By default, it is the current user.
|
||||
* By default, it is the user of the context (system user in SystemUI).
|
||||
* @throws IllegalArgumentException if the filter has other constraints that are not actions or
|
||||
* categories or the filter has no actions.
|
||||
*/
|
||||
|
||||
@@ -16,8 +16,10 @@
|
||||
|
||||
package com.android.systemui.broadcast
|
||||
|
||||
import android.app.ActivityManager
|
||||
import android.content.BroadcastReceiver
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.content.IntentFilter
|
||||
import android.os.Handler
|
||||
import android.os.HandlerExecutor
|
||||
@@ -29,14 +31,10 @@ import android.util.SparseArray
|
||||
import com.android.internal.annotations.VisibleForTesting
|
||||
import com.android.systemui.Dumpable
|
||||
import com.android.systemui.broadcast.logging.BroadcastDispatcherLogger
|
||||
import com.android.systemui.dagger.qualifiers.Background
|
||||
import com.android.systemui.dagger.qualifiers.Main
|
||||
import com.android.systemui.dump.DumpManager
|
||||
import java.io.FileDescriptor
|
||||
import java.io.PrintWriter
|
||||
import java.util.concurrent.Executor
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
data class ReceiverData(
|
||||
val receiver: BroadcastReceiver,
|
||||
@@ -48,6 +46,8 @@ data class ReceiverData(
|
||||
private const val MSG_ADD_RECEIVER = 0
|
||||
private const val MSG_REMOVE_RECEIVER = 1
|
||||
private const val MSG_REMOVE_RECEIVER_FOR_USER = 2
|
||||
private const val MSG_USER_SWITCH = 3
|
||||
private const val MSG_SET_STARTING_USER = 99
|
||||
private const val TAG = "BroadcastDispatcher"
|
||||
private const val DEBUG = true
|
||||
|
||||
@@ -62,21 +62,27 @@ private const val DEBUG = true
|
||||
* permissions, schemes, data types, data authorities or priority different than 0.
|
||||
* Cannot be used for getting sticky broadcasts (either as return of registering or as re-delivery).
|
||||
*/
|
||||
@Singleton
|
||||
open class BroadcastDispatcher @Inject constructor (
|
||||
open class BroadcastDispatcher constructor (
|
||||
private val context: Context,
|
||||
@Main private val mainHandler: Handler,
|
||||
@Background private val bgLooper: Looper,
|
||||
dumpManager: DumpManager,
|
||||
private val bgLooper: Looper,
|
||||
private val dumpManager: DumpManager,
|
||||
private val logger: BroadcastDispatcherLogger
|
||||
) : Dumpable {
|
||||
) : Dumpable, BroadcastReceiver() {
|
||||
|
||||
// Only modify in BG thread
|
||||
private val receiversByUser = SparseArray<UserBroadcastDispatcher>(20)
|
||||
|
||||
init {
|
||||
// TODO: Don't do this in the constructor
|
||||
fun initialize() {
|
||||
dumpManager.registerDumpable(javaClass.name, this)
|
||||
handler.sendEmptyMessage(MSG_SET_STARTING_USER)
|
||||
registerReceiver(this, IntentFilter(Intent.ACTION_USER_SWITCHED), null, UserHandle.ALL)
|
||||
}
|
||||
|
||||
override fun onReceive(context: Context, intent: Intent) {
|
||||
if (intent.action == Intent.ACTION_USER_SWITCHED) {
|
||||
val user = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL)
|
||||
handler.obtainMessage(MSG_USER_SWITCH, user, 0).sendToTarget()
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -88,7 +94,7 @@ open class BroadcastDispatcher @Inject constructor (
|
||||
* have at least one action.
|
||||
* @param handler A handler to dispatch [BroadcastReceiver.onReceive].
|
||||
* @param user A user handle to determine which broadcast should be dispatched to this receiver.
|
||||
* By default, it is the current user.
|
||||
* By default, it is the user of the context (system user in SystemUI).
|
||||
* @throws IllegalArgumentException if the filter has other constraints that are not actions or
|
||||
* categories or the filter has no actions.
|
||||
*/
|
||||
@@ -114,7 +120,7 @@ open class BroadcastDispatcher @Inject constructor (
|
||||
* @param executor An executor to dispatch [BroadcastReceiver.onReceive]. Pass null to use an
|
||||
* executor in the main thread (default).
|
||||
* @param user A user handle to determine which broadcast should be dispatched to this receiver.
|
||||
* By default, it is the current user.
|
||||
* By default, it is the user of the context (system user in SystemUI).
|
||||
* @throws IllegalArgumentException if the filter has other constraints that are not actions or
|
||||
* categories or the filter has no actions.
|
||||
*/
|
||||
@@ -171,6 +177,7 @@ open class BroadcastDispatcher @Inject constructor (
|
||||
|
||||
override fun dump(fd: FileDescriptor, pw: PrintWriter, args: Array<out String>) {
|
||||
pw.println("Broadcast dispatcher:")
|
||||
pw.println(" Current user: ${handler.currentUser}")
|
||||
for (index in 0 until receiversByUser.size()) {
|
||||
pw.println(" User ${receiversByUser.keyAt(index)}")
|
||||
receiversByUser.valueAt(index).dump(fd, pw, args)
|
||||
@@ -178,6 +185,8 @@ open class BroadcastDispatcher @Inject constructor (
|
||||
}
|
||||
|
||||
private val handler = object : Handler(bgLooper) {
|
||||
var currentUser = UserHandle.USER_SYSTEM
|
||||
|
||||
override fun handleMessage(msg: Message) {
|
||||
when (msg.what) {
|
||||
MSG_ADD_RECEIVER -> {
|
||||
@@ -185,7 +194,7 @@ open class BroadcastDispatcher @Inject constructor (
|
||||
// If the receiver asked to be registered under the current user, we register
|
||||
// under the actual current user.
|
||||
val userId = if (data.user.identifier == UserHandle.USER_CURRENT) {
|
||||
context.userId
|
||||
currentUser
|
||||
} else {
|
||||
data.user.identifier
|
||||
}
|
||||
@@ -208,6 +217,13 @@ open class BroadcastDispatcher @Inject constructor (
|
||||
receiversByUser.get(msg.arg1)?.unregisterReceiver(msg.obj as BroadcastReceiver)
|
||||
}
|
||||
|
||||
MSG_USER_SWITCH -> {
|
||||
currentUser = msg.arg1
|
||||
}
|
||||
MSG_SET_STARTING_USER -> {
|
||||
currentUser = ActivityManager.getCurrentUser()
|
||||
}
|
||||
|
||||
else -> super.handleMessage(msg)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -25,6 +25,7 @@ import android.hardware.display.AmbientDisplayConfiguration;
|
||||
import android.hardware.display.NightDisplayListener;
|
||||
import android.os.Handler;
|
||||
import android.os.HandlerThread;
|
||||
import android.os.Looper;
|
||||
import android.os.ServiceManager;
|
||||
import android.util.DisplayMetrics;
|
||||
import android.view.Choreographer;
|
||||
@@ -39,9 +40,12 @@ import com.android.internal.util.NotificationMessagingUtil;
|
||||
import com.android.internal.widget.LockPatternUtils;
|
||||
import com.android.keyguard.ViewMediatorCallback;
|
||||
import com.android.systemui.Prefs;
|
||||
import com.android.systemui.broadcast.BroadcastDispatcher;
|
||||
import com.android.systemui.broadcast.logging.BroadcastDispatcherLogger;
|
||||
import com.android.systemui.dagger.qualifiers.Background;
|
||||
import com.android.systemui.dagger.qualifiers.Main;
|
||||
import com.android.systemui.doze.AlwaysOnDisplayPolicy;
|
||||
import com.android.systemui.dump.DumpManager;
|
||||
import com.android.systemui.keyguard.KeyguardViewMediator;
|
||||
import com.android.systemui.plugins.PluginInitializerImpl;
|
||||
import com.android.systemui.shared.plugins.PluginManager;
|
||||
@@ -178,6 +182,21 @@ public class DependencyProvider {
|
||||
return ActivityManagerWrapper.getInstance();
|
||||
}
|
||||
|
||||
/** Provides and initializes the {#link BroadcastDispatcher} for SystemUI */
|
||||
@Singleton
|
||||
@Provides
|
||||
public BroadcastDispatcher providesBroadcastDispatcher(
|
||||
Context context,
|
||||
@Background Looper backgroundLooper,
|
||||
DumpManager dumpManager,
|
||||
BroadcastDispatcherLogger logger
|
||||
) {
|
||||
BroadcastDispatcher bD =
|
||||
new BroadcastDispatcher(context, backgroundLooper, dumpManager, logger);
|
||||
bD.initialize();
|
||||
return bD;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
public DevicePolicyManagerWrapper provideDevicePolicyManagerWrapper() {
|
||||
|
||||
@@ -73,8 +73,8 @@ public abstract class SysuiTestCase {
|
||||
public void SysuiSetup() throws Exception {
|
||||
SystemUIFactory.createFromConfig(mContext);
|
||||
mDependency = new TestableDependency(mContext);
|
||||
mFakeBroadcastDispatcher = new FakeBroadcastDispatcher(mContext, mock(Handler.class),
|
||||
mock(Looper.class), mock(DumpManager.class), mock(BroadcastDispatcherLogger.class));
|
||||
mFakeBroadcastDispatcher = new FakeBroadcastDispatcher(mContext, mock(Looper.class),
|
||||
mock(DumpManager.class), mock(BroadcastDispatcherLogger.class));
|
||||
|
||||
mRealInstrumentation = InstrumentationRegistry.getInstrumentation();
|
||||
Instrumentation inst = spy(mRealInstrumentation);
|
||||
|
||||
@@ -18,6 +18,7 @@ package com.android.systemui.broadcast
|
||||
|
||||
import android.content.BroadcastReceiver
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.content.IntentFilter
|
||||
import android.os.Handler
|
||||
import android.os.Looper
|
||||
@@ -96,7 +97,6 @@ class BroadcastDispatcherTest : SysuiTestCase() {
|
||||
|
||||
broadcastDispatcher = TestBroadcastDispatcher(
|
||||
mockContext,
|
||||
Handler(testableLooper.looper),
|
||||
testableLooper.looper,
|
||||
mock(DumpManager::class.java),
|
||||
logger,
|
||||
@@ -177,7 +177,12 @@ class BroadcastDispatcherTest : SysuiTestCase() {
|
||||
|
||||
@Test
|
||||
fun testRegisterCurrentAsActualUser() {
|
||||
setUserMock(mockContext, user1)
|
||||
val intent = Intent(Intent.ACTION_USER_SWITCHED).apply {
|
||||
putExtra(Intent.EXTRA_USER_HANDLE, user1.identifier)
|
||||
}
|
||||
broadcastDispatcher.onReceive(mockContext, intent)
|
||||
testableLooper.processAllMessages()
|
||||
|
||||
broadcastDispatcher.registerReceiverWithHandler(broadcastReceiver, intentFilter,
|
||||
mockHandler, UserHandle.CURRENT)
|
||||
|
||||
@@ -240,12 +245,11 @@ class BroadcastDispatcherTest : SysuiTestCase() {
|
||||
|
||||
private class TestBroadcastDispatcher(
|
||||
context: Context,
|
||||
mainHandler: Handler,
|
||||
bgLooper: Looper,
|
||||
dumpManager: DumpManager,
|
||||
logger: BroadcastDispatcherLogger,
|
||||
var mockUBRMap: Map<Int, UserBroadcastDispatcher>
|
||||
) : BroadcastDispatcher(context, mainHandler, bgLooper, dumpManager, logger) {
|
||||
) : BroadcastDispatcher(context, bgLooper, dumpManager, logger) {
|
||||
override fun createUBRForUser(userId: Int): UserBroadcastDispatcher {
|
||||
return mockUBRMap.getOrDefault(userId, mock(UserBroadcastDispatcher::class.java))
|
||||
}
|
||||
|
||||
@@ -30,11 +30,10 @@ import java.util.concurrent.Executor
|
||||
|
||||
class FakeBroadcastDispatcher(
|
||||
context: SysuiTestableContext,
|
||||
handler: Handler,
|
||||
looper: Looper,
|
||||
dumpManager: DumpManager,
|
||||
logger: BroadcastDispatcherLogger
|
||||
) : BroadcastDispatcher(context, handler, looper, dumpManager, logger) {
|
||||
) : BroadcastDispatcher(context, looper, dumpManager, logger) {
|
||||
|
||||
private val registeredReceivers = ArraySet<BroadcastReceiver>()
|
||||
|
||||
|
||||
Reference in New Issue
Block a user