summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--services/core/java/com/android/server/dreams/DreamController.java34
1 files changed, 32 insertions, 2 deletions
diff --git a/services/core/java/com/android/server/dreams/DreamController.java b/services/core/java/com/android/server/dreams/DreamController.java
index c3313e0d11ca..e5357f61d076 100644
--- a/services/core/java/com/android/server/dreams/DreamController.java
+++ b/services/core/java/com/android/server/dreams/DreamController.java
@@ -19,6 +19,7 @@ package com.android.server.dreams;
import static android.app.WindowConfiguration.ACTIVITY_TYPE_DREAM;
import android.app.ActivityTaskManager;
+import android.app.BroadcastOptions;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
@@ -45,6 +46,7 @@ import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.NoSuchElementException;
+import java.util.UUID;
/**
* Internal controller for starting and stopping the current dream and managing related state.
@@ -69,6 +71,9 @@ final class DreamController {
.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
private final Intent mDreamingStoppedIntent = new Intent(Intent.ACTION_DREAMING_STOPPED)
.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
+ private static final String DREAMING_DELIVERY_GROUP_NAMESPACE = UUID.randomUUID().toString();
+ private static final String DREAMING_DELIVERY_GROUP_KEY = UUID.randomUUID().toString();
+ private final Bundle mDreamingStartedStoppedOptions = createDreamingStartedStoppedOptions();
private final Intent mCloseNotificationShadeIntent;
@@ -93,6 +98,29 @@ final class DreamController {
mCloseNotificationShadeIntent.putExtra("reason", "dream");
}
+ /**
+ * Create the {@link BroadcastOptions} bundle that will be used with sending the
+ * {@link Intent#ACTION_DREAMING_STARTED} and {@link Intent#ACTION_DREAMING_STOPPED}
+ * broadcasts.
+ */
+ private Bundle createDreamingStartedStoppedOptions() {
+ final BroadcastOptions options = BroadcastOptions.makeBasic();
+ // This allows the broadcasting system to discard any older broadcasts
+ // waiting to be delivered to a process.
+ options.setDeliveryGroupPolicy(BroadcastOptions.DELIVERY_GROUP_POLICY_MOST_RECENT);
+ // Set namespace and key to identify which older broadcasts can be discarded.
+ // We could use any strings here with the following requirements:
+ // - namespace needs to be unlikely to be reused with in
+ // the system_server process, as that could result in potentially discarding some
+ // non-dreaming_started/stopped related broadcast.
+ // - key needs to be the same for both DREAMING_STARTED and DREAMING_STOPPED broadcasts
+ // so that dreaming_stopped can also clear any older dreaming_started broadcasts that
+ // are yet to be delivered.
+ options.setDeliveryGroupMatchingKey(
+ DREAMING_DELIVERY_GROUP_NAMESPACE, DREAMING_DELIVERY_GROUP_KEY);
+ return options.toBundle();
+ }
+
public void dump(PrintWriter pw) {
pw.println("Dreamland:");
if (mCurrentDream != null) {
@@ -244,7 +272,8 @@ final class DreamController {
mCurrentDream = null;
if (mSentStartBroadcast) {
- mContext.sendBroadcastAsUser(mDreamingStoppedIntent, UserHandle.ALL);
+ mContext.sendBroadcastAsUser(mDreamingStoppedIntent, UserHandle.ALL,
+ null /* receiverPermission */, mDreamingStartedStoppedOptions);
mSentStartBroadcast = false;
}
@@ -287,7 +316,8 @@ final class DreamController {
mCurrentDream.mService = service;
if (!mCurrentDream.mIsPreviewMode && !mSentStartBroadcast) {
- mContext.sendBroadcastAsUser(mDreamingStartedIntent, UserHandle.ALL);
+ mContext.sendBroadcastAsUser(mDreamingStartedIntent, UserHandle.ALL,
+ null /* receiverPermission */, mDreamingStartedStoppedOptions);
mSentStartBroadcast = true;
}
}