Merge "Revert^2 "Filter memory tombstone fields before DropBox logging"" into main
diff --git a/core/java/android/app/NotificationManager.java b/core/java/android/app/NotificationManager.java
index 05b3316..1e1ec60 100644
--- a/core/java/android/app/NotificationManager.java
+++ b/core/java/android/app/NotificationManager.java
@@ -1656,7 +1656,8 @@
         if (Flags.modesApi() && Flags.modesUi()) {
             PackageManager pm = mContext.getPackageManager();
             return !pm.hasSystemFeature(PackageManager.FEATURE_WATCH)
-                    && !pm.hasSystemFeature(PackageManager.FEATURE_AUTOMOTIVE);
+                    && !pm.hasSystemFeature(PackageManager.FEATURE_AUTOMOTIVE)
+                    && !pm.hasSystemFeature(PackageManager.FEATURE_LEANBACK);
         } else {
             return false;
         }
diff --git a/core/java/android/app/supervision/flags.aconfig b/core/java/android/app/supervision/flags.aconfig
index 4ee3a03..18182b8 100644
--- a/core/java/android/app/supervision/flags.aconfig
+++ b/core/java/android/app/supervision/flags.aconfig
@@ -40,3 +40,11 @@
   description: "Flag to enable the SupervisionAppService"
   bug: "389123070"
 }
+
+flag {
+  name: "enable_supervision_settings_screen"
+  is_exported: true
+  namespace: "supervision"
+  description: "Flag that enables the Supervision settings screen with top-level Android settings entry point"
+  bug: "383404606"
+}
diff --git a/core/java/android/os/Parcel.java b/core/java/android/os/Parcel.java
index 4aa7462..c6a63a7 100644
--- a/core/java/android/os/Parcel.java
+++ b/core/java/android/os/Parcel.java
@@ -50,6 +50,7 @@
 
 import dalvik.annotation.optimization.CriticalNative;
 import dalvik.annotation.optimization.FastNative;
+import dalvik.annotation.optimization.NeverInline;
 
 import libcore.util.SneakyThrow;
 
@@ -628,6 +629,19 @@
         }
     }
 
+    @NeverInline
+    private void errorUsedWhileRecycling() {
+        String error = "Parcel used while recycled. "
+                + Log.getStackTraceString(new Throwable())
+                + " Original recycle call (if DEBUG_RECYCLE): ", mStack;
+        Log.wtf(TAG, error);
+        // TODO(b/381155347): harder error
+    }
+
+    private void assertNotRecycled() {
+        if (mRecycled) errorUsedWhileRecycling();
+    }
+
     /**
      * Set a {@link ReadWriteHelper}, which can be used to avoid having duplicate strings, for
      * example.
@@ -1180,6 +1194,7 @@
      * growing dataCapacity() if needed.
      */
     public final void writeInt(int val) {
+        assertNotRecycled();
         int err = nativeWriteInt(mNativePtr, val);
         if (err != OK) {
             nativeSignalExceptionForError(err);
@@ -3282,6 +3297,7 @@
      * Read an integer value from the parcel at the current dataPosition().
      */
     public final int readInt() {
+        assertNotRecycled();
         return nativeReadInt(mNativePtr);
     }
 
diff --git a/core/java/android/permission/flags.aconfig b/core/java/android/permission/flags.aconfig
index 70d8891..a480a3b 100644
--- a/core/java/android/permission/flags.aconfig
+++ b/core/java/android/permission/flags.aconfig
@@ -493,3 +493,9 @@
     bug: "341941666"
 }
 
+flag {
+    name: "sqlite_discrete_op_event_logging_enabled"
+    namespace: "permissions"
+    description: "Collect sqlite performance metrics for discrete ops."
+    bug: "377584611"
+}
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index a22333b..9626808 100644
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -353,6 +353,18 @@
      */
     public static final String ACTION_ONE_HANDED_SETTINGS =
             "android.settings.action.ONE_HANDED_SETTINGS";
+
+    /**
+     * Activity Action: Show Double tap power gesture Settings page.
+     * <p>
+     * Input: Nothing
+     * <p>
+     * Output: Nothing
+     * @hide
+     */
+    public static final String ACTION_DOUBLE_TAP_POWER_SETTINGS =
+            "android.settings.action.DOUBLE_TAP_POWER_SETTINGS";
+
     /**
      * The return values for {@link Settings.Config#set}
      * @hide
@@ -12356,12 +12368,6 @@
         public static final String CAMERA_EXTENSIONS_FALLBACK = "camera_extensions_fallback";
 
         /**
-         * Controls whether contextual suggestions can be shown in the media controls.
-         * @hide
-         */
-        public static final String MEDIA_CONTROLS_RECOMMENDATION = "qs_media_recommend";
-
-        /**
          * Controls magnification mode when magnification is enabled via a system-wide triple tap
          * gesture or the accessibility shortcut.
          *
diff --git a/core/java/android/view/Choreographer.java b/core/java/android/view/Choreographer.java
index 992790e..053ccdd 100644
--- a/core/java/android/view/Choreographer.java
+++ b/core/java/android/view/Choreographer.java
@@ -250,11 +250,14 @@
 
     /**
      * Set flag to indicate that client is blocked waiting for buffer release and
-     * buffer stuffing recovery should soon begin.
+     * buffer stuffing recovery should soon begin. This is provided with the
+     * duration of time in nanoseconds that the client was blocked for.
      * @hide
      */
-    public void onWaitForBufferRelease() {
-        mBufferStuffingState.isStuffed.set(true);
+    public void onWaitForBufferRelease(long durationNanos) {
+        if (durationNanos > mLastFrameIntervalNanos / 2) {
+            mBufferStuffingState.isStuffed.set(true);
+        }
     }
 
     /**
diff --git a/core/java/android/view/SurfaceView.java b/core/java/android/view/SurfaceView.java
index 780e761..dd32947 100644
--- a/core/java/android/view/SurfaceView.java
+++ b/core/java/android/view/SurfaceView.java
@@ -2391,4 +2391,9 @@
             }
         }
     }
+
+    @Override
+    public CharSequence getAccessibilityClassName() {
+        return SurfaceView.class.getName();
+    }
 }
diff --git a/core/java/android/view/TextureView.java b/core/java/android/view/TextureView.java
index ebc86ee..0c6eaae 100644
--- a/core/java/android/view/TextureView.java
+++ b/core/java/android/view/TextureView.java
@@ -918,6 +918,11 @@
         mLastFrameTimeMillis = now;
     }
 
+    @Override
+    public CharSequence getAccessibilityClassName() {
+        return TextureView.class.getName();
+    }
+
     @UnsupportedAppUsage
     private final SurfaceTexture.OnFrameAvailableListener mUpdateListener =
             surfaceTexture -> {
diff --git a/core/java/android/window/flags/windowing_sdk.aconfig b/core/java/android/window/flags/windowing_sdk.aconfig
index f178b0e..1b946af 100644
--- a/core/java/android/window/flags/windowing_sdk.aconfig
+++ b/core/java/android/window/flags/windowing_sdk.aconfig
@@ -178,3 +178,10 @@
         purpose: PURPOSE_BUGFIX
     }
 }
+
+flag {
+    namespace: "windowing_sdk"
+    name: "safe_region_letterboxing"
+    description: "Enables letterboxing for a safe region"
+    bug: "380132497"
+}
diff --git a/core/jni/android_graphics_BLASTBufferQueue.cpp b/core/jni/android_graphics_BLASTBufferQueue.cpp
index 7b61a5d..10d6d33 100644
--- a/core/jni/android_graphics_BLASTBufferQueue.cpp
+++ b/core/jni/android_graphics_BLASTBufferQueue.cpp
@@ -107,10 +107,11 @@
         }
     }
 
-    void onWaitForBufferRelease() {
+    void onWaitForBufferRelease(const nsecs_t durationNanos) {
         JNIEnv* env = getenv(mVm);
         getenv(mVm)->CallVoidMethod(mWaitForBufferReleaseObject,
-                                    gWaitForBufferReleaseCallback.onWaitForBufferRelease);
+                                    gWaitForBufferReleaseCallback.onWaitForBufferRelease,
+                                    durationNanos);
         DieIfException(env, "Uncaught exception in WaitForBufferReleaseCallback.");
     }
 
@@ -255,7 +256,9 @@
     } else {
         sp<WaitForBufferReleaseCallbackWrapper> wrapper =
                 new WaitForBufferReleaseCallbackWrapper{env, waitForBufferReleaseCallback};
-        queue->setWaitForBufferReleaseCallback([wrapper]() { wrapper->onWaitForBufferRelease(); });
+        queue->setWaitForBufferReleaseCallback([wrapper](const nsecs_t durationNanos) {
+            wrapper->onWaitForBufferRelease(durationNanos);
+        });
     }
 }
 
@@ -305,7 +308,7 @@
     jclass waitForBufferReleaseClass =
             FindClassOrDie(env, "android/graphics/BLASTBufferQueue$WaitForBufferReleaseCallback");
     gWaitForBufferReleaseCallback.onWaitForBufferRelease =
-            GetMethodIDOrDie(env, waitForBufferReleaseClass, "onWaitForBufferRelease", "()V");
+            GetMethodIDOrDie(env, waitForBufferReleaseClass, "onWaitForBufferRelease", "(J)V");
 
     return 0;
 }
diff --git a/core/tests/coretests/src/android/app/NotificationManagerTest.java b/core/tests/coretests/src/android/app/NotificationManagerTest.java
index a201f1f..4143229 100644
--- a/core/tests/coretests/src/android/app/NotificationManagerTest.java
+++ b/core/tests/coretests/src/android/app/NotificationManagerTest.java
@@ -30,8 +30,10 @@
 import static org.mockito.Mockito.verify;
 import static org.mockito.Mockito.when;
 
+import android.annotation.Nullable;
 import android.content.Context;
 import android.content.ContextWrapper;
+import android.content.pm.PackageManager;
 import android.content.pm.ParceledListSlice;
 import android.os.UserHandle;
 import android.platform.test.annotations.EnableFlags;
@@ -441,6 +443,46 @@
                 .getOrCreateNotificationChannels(any(), any(), anyInt(), anyBoolean());
     }
 
+    @Test
+    @EnableFlags({Flags.FLAG_MODES_API, Flags.FLAG_MODES_UI})
+    public void areAutomaticZenRulesUserManaged_handheld_isTrue() {
+        PackageManager pm = mock(PackageManager.class);
+        when(pm.hasSystemFeature(any())).thenReturn(false);
+        mContext.setPackageManager(pm);
+
+        assertThat(mNotificationManager.areAutomaticZenRulesUserManaged()).isTrue();
+    }
+
+    @Test
+    @EnableFlags({Flags.FLAG_MODES_API, Flags.FLAG_MODES_UI})
+    public void areAutomaticZenRulesUserManaged_auto_isFalse() {
+        PackageManager pm = mock(PackageManager.class);
+        when(pm.hasSystemFeature(eq(PackageManager.FEATURE_AUTOMOTIVE))).thenReturn(true);
+        mContext.setPackageManager(pm);
+
+        assertThat(mNotificationManager.areAutomaticZenRulesUserManaged()).isFalse();
+    }
+
+    @Test
+    @EnableFlags({Flags.FLAG_MODES_API, Flags.FLAG_MODES_UI})
+    public void areAutomaticZenRulesUserManaged_tv_isFalse() {
+        PackageManager pm = mock(PackageManager.class);
+        when(pm.hasSystemFeature(eq(PackageManager.FEATURE_LEANBACK))).thenReturn(true);
+        mContext.setPackageManager(pm);
+
+        assertThat(mNotificationManager.areAutomaticZenRulesUserManaged()).isFalse();
+    }
+
+    @Test
+    @EnableFlags({Flags.FLAG_MODES_API, Flags.FLAG_MODES_UI})
+    public void areAutomaticZenRulesUserManaged_watch_isFalse() {
+        PackageManager pm = mock(PackageManager.class);
+        when(pm.hasSystemFeature(eq(PackageManager.FEATURE_WATCH))).thenReturn(true);
+        mContext.setPackageManager(pm);
+
+        assertThat(mNotificationManager.areAutomaticZenRulesUserManaged()).isFalse();
+    }
+
     private Notification exampleNotification() {
         return new Notification.Builder(mContext, "channel")
                 .setSmallIcon(android.R.drawable.star_big_on)
@@ -470,6 +512,7 @@
     // Helper context wrapper class where we can control just the return values of getPackageName,
     // getOpPackageName, and getUserId (used in getNotificationChannels).
     private static class PackageTestableContext extends ContextWrapper {
+        private PackageManager mPm;
         private String mPackage;
         private String mOpPackage;
         private Integer mUserId;
@@ -478,6 +521,10 @@
             super(base);
         }
 
+        void setPackageManager(@Nullable PackageManager pm) {
+            mPm = pm;
+        }
+
         void setParameters(String packageName, String opPackageName, int userId) {
             mPackage = packageName;
             mOpPackage = opPackageName;
@@ -485,6 +532,12 @@
         }
 
         @Override
+        public PackageManager getPackageManager() {
+            if (mPm != null) return mPm;
+            return super.getPackageManager();
+        }
+
+        @Override
         public String getPackageName() {
             if (mPackage != null) return mPackage;
             return super.getPackageName();
diff --git a/graphics/java/android/graphics/BLASTBufferQueue.java b/graphics/java/android/graphics/BLASTBufferQueue.java
index 1c34e0d..9b9be244 100644
--- a/graphics/java/android/graphics/BLASTBufferQueue.java
+++ b/graphics/java/android/graphics/BLASTBufferQueue.java
@@ -61,8 +61,10 @@
         /**
          * Indicates that the client is waiting on buffer release
          * due to no free buffers being available to render into.
+         * @param durationNanos The length of time in nanoseconds
+         * that the client was blocked on buffer release.
          */
-        void onWaitForBufferRelease();
+        void onWaitForBufferRelease(long durationNanos);
     }
 
     /** Create a new connection with the surface flinger. */
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleController.java b/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleController.java
index 12dfbd9..30d6790 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleController.java
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleController.java
@@ -1440,9 +1440,9 @@
      *
      * @param intent the intent for the bubble.
      */
-    public void expandStackAndSelectBubble(Intent intent) {
+    public void expandStackAndSelectBubble(Intent intent, UserHandle user) {
         if (!Flags.enableBubbleAnything()) return;
-        Bubble b = mBubbleData.getOrCreateBubble(intent); // Removes from overflow
+        Bubble b = mBubbleData.getOrCreateBubble(intent, user); // Removes from overflow
         ProtoLog.v(WM_SHELL_BUBBLES, "expandStackAndSelectBubble - intent=%s", intent);
         if (b.isInflated()) {
             mBubbleData.setSelectedBubbleAndExpandStack(b);
@@ -2649,8 +2649,8 @@
         }
 
         @Override
-        public void showAppBubble(Intent intent) {
-            mMainExecutor.execute(() -> mController.expandStackAndSelectBubble(intent));
+        public void showAppBubble(Intent intent, UserHandle user) {
+            mMainExecutor.execute(() -> mController.expandStackAndSelectBubble(intent, user));
         }
 
         @Override
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleData.java b/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleData.java
index dc2025b..76d91ed 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleData.java
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleData.java
@@ -461,10 +461,8 @@
         return bubbleToReturn;
     }
 
-    Bubble getOrCreateBubble(Intent intent) {
-        UserHandle user = UserHandle.of(mCurrentUserId);
-        String bubbleKey = Bubble.getAppBubbleKeyForApp(intent.getPackage(),
-                user);
+    Bubble getOrCreateBubble(Intent intent, UserHandle user) {
+        String bubbleKey = Bubble.getAppBubbleKeyForApp(intent.getPackage(), user);
         Bubble bubbleToReturn = findAndRemoveBubbleFromOverflow(bubbleKey);
         if (bubbleToReturn == null) {
             bubbleToReturn = Bubble.createAppBubble(intent, user, null, mMainExecutor, mBgExecutor);
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/IBubbles.aidl b/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/IBubbles.aidl
index 9c2d3543..0a4d79a 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/IBubbles.aidl
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/IBubbles.aidl
@@ -17,8 +17,9 @@
 package com.android.wm.shell.bubbles;
 
 import android.content.Intent;
-import android.graphics.Rect;
 import android.content.pm.ShortcutInfo;
+import android.graphics.Rect;
+import android.os.UserHandle;
 import com.android.wm.shell.bubbles.IBubblesListener;
 import com.android.wm.shell.shared.bubbles.BubbleBarLocation;
 
@@ -52,7 +53,7 @@
 
     oneway void showShortcutBubble(in ShortcutInfo info) = 12;
 
-    oneway void showAppBubble(in Intent intent) = 13;
+    oneway void showAppBubble(in Intent intent, in UserHandle user) = 13;
 
     oneway void showExpandedView() = 14;
 }
\ No newline at end of file
diff --git a/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/bubbles/BubbleDataTest.java b/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/bubbles/BubbleDataTest.java
index ce640b5..ffcc344 100644
--- a/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/bubbles/BubbleDataTest.java
+++ b/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/bubbles/BubbleDataTest.java
@@ -445,6 +445,15 @@
         assertThat(update.updatedBubble.showFlyout()).isFalse();
     }
 
+    @Test
+    public void getOrCreateBubble_withIntent_usesCorrectUser() {
+        Intent intent = new Intent();
+        intent.setPackage(mContext.getPackageName());
+        Bubble b = mBubbleData.getOrCreateBubble(intent, UserHandle.of(/* userId= */ 10));
+
+        assertThat(b.getUser().getIdentifier()).isEqualTo(10);
+    }
+
     //
     // Overflow
     //
@@ -1441,12 +1450,6 @@
         assertWithMessage("selectedBubble").that(update.selectedBubble).isEqualTo(bubble);
     }
 
-    private void assertSelectionCleared() {
-        BubbleData.Update update = mUpdateCaptor.getValue();
-        assertWithMessage("selectionChanged").that(update.selectionChanged).isTrue();
-        assertWithMessage("selectedBubble").that(update.selectedBubble).isNull();
-    }
-
     private void assertExpandedChangedTo(boolean expected) {
         BubbleData.Update update = mUpdateCaptor.getValue();
         assertWithMessage("expandedChanged").that(update.expandedChanged).isTrue();
diff --git a/media/java/android/media/MediaCodecInfo.java b/media/java/android/media/MediaCodecInfo.java
index 302969f..9bb31d0 100644
--- a/media/java/android/media/MediaCodecInfo.java
+++ b/media/java/android/media/MediaCodecInfo.java
@@ -908,13 +908,13 @@
         /** @hide */
         public String[] validFeatures() {
             Feature[] features = getValidFeatures();
-            String[] res = new String[features.length];
-            for (int i = 0; i < res.length; i++) {
+            ArrayList<String> res = new ArrayList();
+            for (int i = 0; i < features.length; i++) {
                 if (!features[i].mInternal) {
-                    res[i] = features[i].mName;
+                    res.add(features[i].mName);
                 }
             }
-            return res;
+            return res.toArray(new String[0]);
         }
 
         private Feature[] getValidFeatures() {
diff --git a/media/java/android/media/tv/TvInputService.java b/media/java/android/media/tv/TvInputService.java
index abfc244..f352a41 100644
--- a/media/java/android/media/tv/TvInputService.java
+++ b/media/java/android/media/tv/TvInputService.java
@@ -161,11 +161,6 @@
             new RemoteCallbackList<>();
 
     private TvInputManager mTvInputManager;
-    /**
-     * @hide
-     */
-    protected TvInputServiceExtensionManager mTvInputServiceExtensionManager =
-            new TvInputServiceExtensionManager();
 
     @Override
     public final IBinder onBind(Intent intent) {
@@ -230,12 +225,20 @@
 
             @Override
             public IBinder getExtensionInterface(String name) {
-                if (tifExtensionStandardization() && name != null) {
-                    if (TvInputServiceExtensionManager.checkIsStandardizedInterfaces(name)) {
-                        return mTvInputServiceExtensionManager.getExtensionIBinder(name);
+                IBinder binder = TvInputService.this.getExtensionInterface(name);
+                if (tifExtensionStandardization()) {
+                    if (name != null
+                            && TvInputServiceExtensionManager.checkIsStandardizedInterfaces(name)) {
+                        if (TvInputServiceExtensionManager.checkIsStandardizedIBinder(name,
+                                binder)) {
+                            return binder;
+                        } else {
+                            // binder with standardized name is not standardized
+                            return null;
+                        }
                     }
                 }
-                return TvInputService.this.getExtensionInterface(name);
+                return binder;
             }
 
             @Override
diff --git a/media/java/android/media/tv/TvInputServiceExtensionManager.java b/media/java/android/media/tv/TvInputServiceExtensionManager.java
index d33ac92..02d2616 100644
--- a/media/java/android/media/tv/TvInputServiceExtensionManager.java
+++ b/media/java/android/media/tv/TvInputServiceExtensionManager.java
@@ -16,13 +16,9 @@
 
 package android.media.tv;
 
-import android.annotation.FlaggedApi;
-import android.annotation.IntDef;
 import android.annotation.NonNull;
 import android.annotation.Nullable;
-import android.annotation.RequiresPermission;
 import android.annotation.StringDef;
-import android.media.tv.flags.Flags;
 import android.os.IBinder;
 import android.os.RemoteException;
 import android.util.Log;
@@ -30,21 +26,17 @@
 import java.lang.annotation.Retention;
 import java.lang.annotation.RetentionPolicy;
 import java.util.ArrayList;
-import java.util.HashMap;
 import java.util.HashSet;
 import java.util.List;
-import java.util.Map;
 import java.util.Set;
 
 
 /**
  * This class provides a list of available standardized TvInputService extension interface names
- * and a container storing IBinder objects that implement these interfaces created by SoC/OEMs.
- * It also provides an API for SoC/OEMs to register implemented IBinder objects.
+ * and checks if IBinder objects created by SoC/OEMs implement these interfaces.
  *
  * @hide
  */
-@FlaggedApi(Flags.FLAG_TIF_EXTENSION_STANDARDIZATION)
 public final class TvInputServiceExtensionManager {
     private static final String TAG = "TvInputServiceExtensionManager";
     private static final String SCAN_PACKAGE = "android.media.tv.extension.scan.";
@@ -63,33 +55,6 @@
     private static final String ANALOG_PACKAGE = "android.media.tv.extension.analog.";
     private static final String TUNE_PACKAGE = "android.media.tv.extension.tune.";
 
-    @IntDef(prefix = {"REGISTER_"}, value = {
-            REGISTER_SUCCESS,
-            REGISTER_FAIL_NAME_NOT_STANDARDIZED,
-            REGISTER_FAIL_IMPLEMENTATION_NOT_STANDARDIZED,
-            REGISTER_FAIL_REMOTE_EXCEPTION
-    })
-    @Retention(RetentionPolicy.SOURCE)
-    public @interface RegisterResult {}
-
-    /**
-     * Registering binder returns success when it abides standardized interface structure
-     */
-    public static final int REGISTER_SUCCESS = 0;
-    /**
-     * Registering binder returns failure when the extension name is not in the standardization
-     * list
-     */
-    public static final int REGISTER_FAIL_NAME_NOT_STANDARDIZED = 1;
-    /**
-     * Registering binder returns failure when the IBinder does not implement standardized interface
-     */
-    public static final int REGISTER_FAIL_IMPLEMENTATION_NOT_STANDARDIZED = 2;
-    /**
-     * Registering binder returns failure when remote server is not available
-     */
-    public static final int REGISTER_FAIL_REMOTE_EXCEPTION = 3;
-
     @StringDef({
             ISCAN_INTERFACE,
             ISCAN_SESSION,
@@ -673,12 +638,6 @@
             IMUX_TUNE
     ));
 
-    // Store the mapping between interface names and IBinder
-    private Map<String, IBinder> mExtensionInterfaceIBinderMapping = new HashMap<>();
-
-    TvInputServiceExtensionManager() {
-    }
-
     /**
      * Function to return available extension interface names
      */
@@ -694,43 +653,18 @@
     }
 
     /**
-     * Registers IBinder objects that implement standardized AIDL interfaces.
-     * <p>This function should be used by SoCs/OEMs
-     *
-     * @param extensionName Extension Interface Name
-     * @param binder        IBinder object to be registered
-     * @return {@link #REGISTER_SUCCESS} on success of registering IBinder object
-     *         {@link #REGISTER_FAIL_NAME_NOT_STANDARDIZED} on failure due to registering extension
-     *              with non-standardized name
-     *         {@link #REGISTER_FAIL_IMPLEMENTATION_NOT_STANDARDIZED} on failure due to IBinder not
-     *              implementing standardized AIDL interface
-     *         {@link #REGISTER_FAIL_REMOTE_EXCEPTION} on failure due to remote exception
+     * Function check if the IBinder object implements standardized interface
      */
-    @RequiresPermission(android.Manifest.permission.TV_INPUT_HARDWARE)
-    @RegisterResult
-    public int registerExtensionIBinder(@StandardizedExtensionName @NonNull String extensionName,
-            @NonNull IBinder binder) {
-        if (!checkIsStandardizedInterfaces(extensionName)) {
-            return REGISTER_FAIL_NAME_NOT_STANDARDIZED;
-        }
-        try {
-            if (binder.getInterfaceDescriptor().equals(extensionName)) {
-                mExtensionInterfaceIBinderMapping.put(extensionName, binder);
-                return REGISTER_SUCCESS;
-            } else {
-                return REGISTER_FAIL_IMPLEMENTATION_NOT_STANDARDIZED;
+    public static boolean checkIsStandardizedIBinder(@NonNull String extensionName,
+            @Nullable IBinder binder) {
+        if (binder != null) {
+            try {
+                return binder.getInterfaceDescriptor().equals(extensionName);
+            } catch (RemoteException e) {
+                Log.e(TAG, "Fetching IBinder object failure due to " + e);
             }
-        } catch (RemoteException e) {
-            Log.e(TAG, "Fetching IBinder object failure due to " + e);
-            return REGISTER_FAIL_REMOTE_EXCEPTION;
         }
-    }
-
-    /**
-     * Function to get corresponding IBinder object
-     */
-    @Nullable IBinder getExtensionIBinder(@NonNull String extensionName) {
-        return mExtensionInterfaceIBinderMapping.get(extensionName);
+        return false;
     }
 
 }
diff --git a/packages/SettingsProvider/src/android/provider/settings/backup/SecureSettings.java b/packages/SettingsProvider/src/android/provider/settings/backup/SecureSettings.java
index d367748..640829e 100644
--- a/packages/SettingsProvider/src/android/provider/settings/backup/SecureSettings.java
+++ b/packages/SettingsProvider/src/android/provider/settings/backup/SecureSettings.java
@@ -204,7 +204,6 @@
         Settings.Secure.AWARE_TAP_PAUSE_TOUCH_COUNT,
         Settings.Secure.PEOPLE_STRIP,
         Settings.Secure.MEDIA_CONTROLS_RESUME,
-        Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
         Settings.Secure.MEDIA_CONTROLS_LOCK_SCREEN,
         Settings.Secure.ACCESSIBILITY_MAGNIFICATION_MODE,
         Settings.Secure.ACCESSIBILITY_BUTTON_TARGETS,
diff --git a/packages/SettingsProvider/src/android/provider/settings/validators/SecureSettingsValidators.java b/packages/SettingsProvider/src/android/provider/settings/validators/SecureSettingsValidators.java
index 242bdce..9fd0cc8 100644
--- a/packages/SettingsProvider/src/android/provider/settings/validators/SecureSettingsValidators.java
+++ b/packages/SettingsProvider/src/android/provider/settings/validators/SecureSettingsValidators.java
@@ -312,7 +312,6 @@
         VALIDATORS.put(Secure.TAP_GESTURE, BOOLEAN_VALIDATOR);
         VALIDATORS.put(Secure.PEOPLE_STRIP, BOOLEAN_VALIDATOR);
         VALIDATORS.put(Secure.MEDIA_CONTROLS_RESUME, BOOLEAN_VALIDATOR);
-        VALIDATORS.put(Secure.MEDIA_CONTROLS_RECOMMENDATION, BOOLEAN_VALIDATOR);
         VALIDATORS.put(Secure.MEDIA_CONTROLS_LOCK_SCREEN, BOOLEAN_VALIDATOR);
         VALIDATORS.put(Secure.ACCESSIBILITY_MAGNIFICATION_MODE,
                 new InclusiveIntegerRangeValidator(
diff --git a/packages/SystemUI/aconfig/systemui.aconfig b/packages/SystemUI/aconfig/systemui.aconfig
index 1a7ae72..f753316 100644
--- a/packages/SystemUI/aconfig/systemui.aconfig
+++ b/packages/SystemUI/aconfig/systemui.aconfig
@@ -1940,3 +1940,10 @@
     description: "Force promoted notifications to always be expanded"
     bug: "380901479"
 }
+
+flag {
+    name: "aod_ui_rich_ongoing"
+    namespace: "systemui"
+    description: "Show a rich ongoing notification on the always-on display (depends on ui_rich_ongoing)"
+    bug: "369151941"
+}
\ No newline at end of file
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/communal/CommunalDreamStartableTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/communal/CommunalDreamStartableTest.kt
index e531e65..00d5afe 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/communal/CommunalDreamStartableTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/communal/CommunalDreamStartableTest.kt
@@ -16,14 +16,17 @@
 
 package com.android.systemui.communal
 
+import android.platform.test.annotations.DisableFlags
 import android.platform.test.annotations.EnableFlags
+import android.platform.test.flag.junit.FlagsParameterization
 import android.service.dream.dreamManager
-import androidx.test.ext.junit.runners.AndroidJUnit4
 import androidx.test.filters.SmallTest
 import com.android.systemui.Flags
+import com.android.systemui.Flags.FLAG_GLANCEABLE_HUB_V2
 import com.android.systemui.SysuiTestCase
 import com.android.systemui.communal.domain.interactor.communalSceneInteractor
 import com.android.systemui.communal.domain.interactor.communalSettingsInteractor
+import com.android.systemui.communal.domain.interactor.setCommunalV2Enabled
 import com.android.systemui.flags.Flags.COMMUNAL_SERVICE_ENABLED
 import com.android.systemui.flags.fakeFeatureFlagsClassic
 import com.android.systemui.keyguard.data.repository.fakeKeyguardRepository
@@ -48,12 +51,14 @@
 import org.junit.runner.RunWith
 import org.mockito.Mockito.never
 import org.mockito.Mockito.verify
+import platform.test.runner.parameterized.ParameterizedAndroidJunit4
+import platform.test.runner.parameterized.Parameters
 
 @OptIn(ExperimentalCoroutinesApi::class)
 @SmallTest
 @EnableFlags(Flags.FLAG_COMMUNAL_HUB)
-@RunWith(AndroidJUnit4::class)
-class CommunalDreamStartableTest : SysuiTestCase() {
+@RunWith(ParameterizedAndroidJunit4::class)
+class CommunalDreamStartableTest(flags: FlagsParameterization) : SysuiTestCase() {
     private val kosmos = testKosmos()
     private val testScope = kosmos.testScope
 
@@ -63,26 +68,50 @@
     private val keyguardRepository by lazy { kosmos.fakeKeyguardRepository }
     private val powerRepository by lazy { kosmos.fakePowerRepository }
 
+    init {
+        mSetFlagsRule.setFlagsParameterization(flags)
+    }
+
     @Before
     fun setUp() {
         kosmos.fakeFeatureFlagsClassic.set(COMMUNAL_SERVICE_ENABLED, true)
 
         underTest =
             CommunalDreamStartable(
-                    powerInteractor = kosmos.powerInteractor,
-                    communalSettingsInteractor = kosmos.communalSettingsInteractor,
-                    keyguardInteractor = kosmos.keyguardInteractor,
-                    keyguardTransitionInteractor = kosmos.keyguardTransitionInteractor,
-                    dreamManager = dreamManager,
-                    communalSceneInteractor = kosmos.communalSceneInteractor,
-                    bgScope = kosmos.applicationCoroutineScope,
-                )
-                .apply { start() }
+                powerInteractor = kosmos.powerInteractor,
+                communalSettingsInteractor = kosmos.communalSettingsInteractor,
+                keyguardInteractor = kosmos.keyguardInteractor,
+                keyguardTransitionInteractor = kosmos.keyguardTransitionInteractor,
+                dreamManager = dreamManager,
+                communalSceneInteractor = kosmos.communalSceneInteractor,
+                bgScope = kosmos.applicationCoroutineScope,
+            )
     }
 
+    @EnableFlags(FLAG_GLANCEABLE_HUB_V2)
+    @Test
+    fun dreamNotStartedWhenTransitioningToHub() =
+        testScope.runTest {
+            // Enable v2 flag and recreate + rerun start method.
+            kosmos.setCommunalV2Enabled(true)
+            underTest.start()
+
+            keyguardRepository.setKeyguardShowing(true)
+            keyguardRepository.setDreaming(false)
+            powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
+            whenever(dreamManager.canStartDreaming(/* isScreenOn= */ true)).thenReturn(true)
+            runCurrent()
+
+            transition(from = KeyguardState.DREAMING, to = KeyguardState.GLANCEABLE_HUB)
+
+            verify(dreamManager, never()).startDream()
+        }
+
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Test
     fun startDreamWhenTransitioningToHub() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setKeyguardShowing(true)
             keyguardRepository.setDreaming(false)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
@@ -100,6 +129,7 @@
     @EnableFlags(Flags.FLAG_RESTART_DREAM_ON_UNOCCLUDE)
     fun restartDreamingWhenTransitioningFromDreamingToOccludedToDreaming() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setDreaming(false)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
             whenever(dreamManager.canStartDreaming(/* isScreenOn= */ true)).thenReturn(true)
@@ -122,9 +152,11 @@
             verify(dreamManager).startDream()
         }
 
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Test
     fun shouldNotStartDreamWhenIneligibleToDream() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setDreaming(false)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
             // Not eligible to dream
@@ -134,9 +166,11 @@
             verify(dreamManager, never()).startDream()
         }
 
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Test
     fun shouldNotStartDreamIfAlreadyDreaming() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setDreaming(true)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
             whenever(dreamManager.canStartDreaming(/* isScreenOn= */ true)).thenReturn(true)
@@ -145,9 +179,11 @@
             verify(dreamManager, never()).startDream()
         }
 
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Test
     fun shouldNotStartDreamForInvalidTransition() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setDreaming(true)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
             whenever(dreamManager.canStartDreaming(/* isScreenOn= */ true)).thenReturn(true)
@@ -160,9 +196,11 @@
             }
         }
 
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Test
     fun shouldNotStartDreamWhenLaunchingWidget() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setKeyguardShowing(true)
             keyguardRepository.setDreaming(false)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
@@ -175,9 +213,11 @@
             verify(dreamManager, never()).startDream()
         }
 
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Test
     fun shouldNotStartDreamWhenOccluded() =
         testScope.runTest {
+            underTest.start()
             keyguardRepository.setKeyguardShowing(true)
             keyguardRepository.setDreaming(false)
             powerRepository.setScreenPowerState(ScreenPowerState.SCREEN_ON)
@@ -194,8 +234,16 @@
         kosmos.fakeKeyguardTransitionRepository.sendTransitionSteps(
             from = from,
             to = to,
-            testScope = this
+            testScope = this,
         )
         runCurrent()
     }
+
+    companion object {
+        @JvmStatic
+        @Parameters(name = "{0}")
+        fun getParams(): List<FlagsParameterization> {
+            return FlagsParameterization.allCombinationsOf(FLAG_GLANCEABLE_HUB_V2)
+        }
+    }
 }
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/dreams/DreamOverlayServiceTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/dreams/DreamOverlayServiceTest.kt
index 5921e94..0df584f 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/dreams/DreamOverlayServiceTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/dreams/DreamOverlayServiceTest.kt
@@ -58,6 +58,7 @@
 import com.android.systemui.communal.domain.interactor.communalSettingsInteractor
 import com.android.systemui.communal.domain.interactor.setCommunalAvailable
 import com.android.systemui.communal.domain.interactor.setCommunalV2ConfigEnabled
+import com.android.systemui.communal.domain.interactor.setCommunalV2Enabled
 import com.android.systemui.communal.shared.log.CommunalUiEvent
 import com.android.systemui.communal.shared.model.CommunalScenes
 import com.android.systemui.complication.ComplicationHostViewController
@@ -747,7 +748,7 @@
 
     @Test
     @EnableFlags(Flags.FLAG_DREAM_WAKE_REDIRECT, FLAG_COMMUNAL_HUB)
-    @DisableFlags(FLAG_SCENE_CONTAINER)
+    @DisableFlags(FLAG_SCENE_CONTAINER, FLAG_GLANCEABLE_HUB_V2)
     @kotlin.Throws(RemoteException::class)
     fun testTransitionToGlanceableHub() =
         testScope.runTest {
@@ -774,6 +775,7 @@
 
     @Test
     @EnableFlags(Flags.FLAG_DREAM_WAKE_REDIRECT, FLAG_SCENE_CONTAINER, FLAG_COMMUNAL_HUB)
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @kotlin.Throws(RemoteException::class)
     fun testTransitionToGlanceableHub_sceneContainer() =
         testScope.runTest {
@@ -802,7 +804,29 @@
         }
 
     @Test
+    @EnableFlags(Flags.FLAG_DREAM_WAKE_REDIRECT, FLAG_COMMUNAL_HUB, FLAG_GLANCEABLE_HUB_V2)
+    @Throws(RemoteException::class)
+    fun testRedirect_v2Enabled_notTriggered() =
+        testScope.runTest {
+            kosmos.setCommunalV2Enabled(true)
+            // Inform the overlay service of dream starting. Do not show dream complications.
+            client.startDream(
+                mWindowParams,
+                mDreamOverlayCallback,
+                DREAM_COMPONENT,
+                false /*isPreview*/,
+                false, /*shouldShowComplication*/
+            )
+            // Set communal available, verify that onRedirectWake is never called.
+            kosmos.setCommunalAvailable(true)
+            mMainExecutor.runAllReady()
+            runCurrent()
+            verify(mDreamOverlayCallback, never()).onRedirectWake(any())
+        }
+
+    @Test
     @EnableFlags(Flags.FLAG_DREAM_WAKE_REDIRECT, FLAG_COMMUNAL_HUB)
+    @DisableFlags(FLAG_GLANCEABLE_HUB_V2)
     @Throws(RemoteException::class)
     fun testRedirectExit() =
         testScope.runTest {
@@ -1347,7 +1371,11 @@
         @JvmStatic
         @Parameters(name = "{0}")
         fun getParams(): List<FlagsParameterization> {
-            return FlagsParameterization.allCombinationsOf(FLAG_COMMUNAL_HUB).andSceneContainer()
+            return FlagsParameterization.allCombinationsOf(
+                    FLAG_COMMUNAL_HUB,
+                    FLAG_GLANCEABLE_HUB_V2,
+                )
+                .andSceneContainer()
         }
     }
 }
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorTest.kt
index fe9da0d..88c8b1f 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorTest.kt
@@ -19,6 +19,7 @@
 
 import android.app.admin.DevicePolicyManager
 import android.os.UserHandle
+import android.view.accessibility.AccessibilityManager
 import androidx.test.ext.junit.runners.AndroidJUnit4
 import androidx.test.filters.SmallTest
 import com.android.internal.widget.LockPatternUtils
@@ -96,6 +97,7 @@
     @Mock private lateinit var shadeInteractor: ShadeInteractor
     @Mock private lateinit var logger: KeyguardQuickAffordancesLogger
     @Mock private lateinit var metricsLogger: KeyguardQuickAffordancesMetricsLogger
+    @Mock private lateinit var accessibilityManager: AccessibilityManager
 
     private lateinit var underTest: KeyguardQuickAffordanceInteractor
 
@@ -199,11 +201,13 @@
                 backgroundDispatcher = kosmos.testDispatcher,
                 appContext = context,
                 communalSettingsInteractor = kosmos.communalSettingsInteractor,
+                accessibilityManager = accessibilityManager,
                 sceneInteractor = { kosmos.sceneInteractor },
             )
         kosmos.keyguardQuickAffordanceInteractor = underTest
 
         whenever(shadeInteractor.anyExpansion).thenReturn(MutableStateFlow(0f))
+        whenever(accessibilityManager.isEnabled()).thenReturn(false)
     }
 
     @Test
@@ -672,6 +676,22 @@
         }
 
     @Test
+    fun useLongPress_withA11yEnabled_isFalse() =
+        testScope.runTest {
+            whenever(accessibilityManager.isEnabled()).thenReturn(true)
+            val useLongPress by collectLastValue(underTest.useLongPress())
+            assertThat(useLongPress).isFalse()
+        }
+
+    @Test
+    fun useLongPress_withA11yDisabled_isFalse() =
+        testScope.runTest {
+            whenever(accessibilityManager.isEnabled()).thenReturn(false)
+            val useLongPress by collectLastValue(underTest.useLongPress())
+            assertThat(useLongPress).isTrue()
+        }
+
+    @Test
     fun useLongPress_whenDocked_isFalse() =
         testScope.runTest {
             dockManager.setIsDocked(true)
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModelTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModelTest.kt
index b0af8b1..75262a4 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModelTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModelTest.kt
@@ -23,6 +23,7 @@
 import androidx.test.ext.junit.runners.AndroidJUnit4
 import androidx.test.filters.SmallTest
 import com.android.systemui.SysuiTestCase
+import com.android.systemui.animation.Expandable
 import com.android.systemui.common.shared.model.Icon
 import com.android.systemui.coroutines.collectLastValue
 import com.android.systemui.kosmos.Kosmos
@@ -35,7 +36,14 @@
 import com.android.systemui.statusbar.chips.ui.model.OngoingActivityChipModel
 import com.android.systemui.statusbar.chips.ui.view.ChipBackgroundContainer
 import com.android.systemui.statusbar.core.StatusBarConnectedDisplays
+import com.android.systemui.statusbar.core.StatusBarRootModernization
+import com.android.systemui.statusbar.notification.data.model.activeNotificationModel
+import com.android.systemui.statusbar.notification.data.repository.ActiveNotificationListRepository
+import com.android.systemui.statusbar.notification.data.repository.ActiveNotificationsStore
+import com.android.systemui.statusbar.notification.data.repository.activeNotificationListRepository
 import com.android.systemui.statusbar.notification.promoted.shared.model.PromotedNotificationContentModel
+import com.android.systemui.statusbar.notification.shared.CallType
+import com.android.systemui.statusbar.phone.ongoingcall.StatusBarChipsModernization
 import com.android.systemui.statusbar.phone.ongoingcall.data.repository.ongoingCallRepository
 import com.android.systemui.statusbar.phone.ongoingcall.shared.model.OngoingCallModel
 import com.android.systemui.statusbar.phone.ongoingcall.shared.model.inCallModel
@@ -44,6 +52,7 @@
 import kotlin.test.Test
 import kotlinx.coroutines.test.runTest
 import org.junit.runner.RunWith
+import org.mockito.kotlin.any
 import org.mockito.kotlin.mock
 import org.mockito.kotlin.verify
 import org.mockito.kotlin.whenever
@@ -52,6 +61,7 @@
 @RunWith(AndroidJUnit4::class)
 class CallChipViewModelTest : SysuiTestCase() {
     private val kosmos = Kosmos()
+    private val notificationListRepository = kosmos.activeNotificationListRepository
     private val testScope = kosmos.testScope
     private val repo = kosmos.ongoingCallRepository
 
@@ -65,6 +75,8 @@
                 )
                 .thenReturn(chipBackgroundView)
         }
+    private val mockExpandable: Expandable =
+        mock<Expandable>().apply { whenever(dialogTransitionController(any())).thenReturn(mock()) }
 
     private val underTest by lazy { kosmos.callChipViewModel }
 
@@ -337,6 +349,7 @@
         }
 
     @Test
+    @DisableFlags(StatusBarChipsModernization.FLAG_NAME)
     fun chip_inCall_nullIntent_nullClickListener() =
         testScope.runTest {
             val latest by collectLastValue(underTest.chip)
@@ -347,6 +360,7 @@
         }
 
     @Test
+    @DisableFlags(StatusBarChipsModernization.FLAG_NAME)
     fun chip_inCall_positiveStartTime_validIntent_clickListenerLaunchesIntent() =
         testScope.runTest {
             val latest by collectLastValue(underTest.chip)
@@ -364,6 +378,7 @@
         }
 
     @Test
+    @DisableFlags(StatusBarChipsModernization.FLAG_NAME)
     fun chip_inCall_zeroStartTime_validIntent_clickListenerLaunchesIntent() =
         testScope.runTest {
             val latest by collectLastValue(underTest.chip)
@@ -381,6 +396,72 @@
             verify(kosmos.activityStarter).postStartActivityDismissingKeyguard(pendingIntent, null)
         }
 
+    @Test
+    @EnableFlags(StatusBarRootModernization.FLAG_NAME, StatusBarChipsModernization.FLAG_NAME)
+    fun chip_inCall_nullIntent_noneClickBehavior() =
+        testScope.runTest {
+            val latest by collectLastValue(underTest.chip)
+
+            postOngoingCallNotification(
+                repository = notificationListRepository,
+                startTimeMs = 1000L,
+                intent = null,
+            )
+
+            assertThat((latest as OngoingActivityChipModel.Shown).clickBehavior)
+                .isInstanceOf(OngoingActivityChipModel.ClickBehavior.None::class.java)
+        }
+
+    @Test
+    @EnableFlags(StatusBarRootModernization.FLAG_NAME, StatusBarChipsModernization.FLAG_NAME)
+    fun chip_inCall_positiveStartTime_validIntent_clickBehaviorLaunchesIntent() =
+        testScope.runTest {
+            val latest by collectLastValue(underTest.chip)
+
+            val pendingIntent = mock<PendingIntent>()
+            postOngoingCallNotification(
+                repository = notificationListRepository,
+                startTimeMs = 1000L,
+                intent = pendingIntent,
+            )
+
+            val clickBehavior = (latest as OngoingActivityChipModel.Shown).clickBehavior
+            assertThat(clickBehavior)
+                .isInstanceOf(OngoingActivityChipModel.ClickBehavior.ExpandAction::class.java)
+            (clickBehavior as OngoingActivityChipModel.ClickBehavior.ExpandAction).onClick(
+                mockExpandable
+            )
+
+            // Ensure that the SysUI didn't modify the notification's intent by verifying it
+            // directly matches the `PendingIntent` set -- see b/212467440.
+            verify(kosmos.activityStarter).postStartActivityDismissingKeyguard(pendingIntent, null)
+        }
+
+    @Test
+    @EnableFlags(StatusBarRootModernization.FLAG_NAME, StatusBarChipsModernization.FLAG_NAME)
+    fun chip_inCall_zeroStartTime_validIntent_clickBehaviorLaunchesIntent() =
+        testScope.runTest {
+            val latest by collectLastValue(underTest.chip)
+
+            val pendingIntent = mock<PendingIntent>()
+            postOngoingCallNotification(
+                repository = notificationListRepository,
+                startTimeMs = 0L,
+                intent = pendingIntent,
+            )
+
+            val clickBehavior = (latest as OngoingActivityChipModel.Shown).clickBehavior
+            assertThat(clickBehavior)
+                .isInstanceOf(OngoingActivityChipModel.ClickBehavior.ExpandAction::class.java)
+            (clickBehavior as OngoingActivityChipModel.ClickBehavior.ExpandAction).onClick(
+                mockExpandable
+            )
+
+            // Ensure that the SysUI didn't modify the notification's intent by verifying it
+            // directly matches the `PendingIntent` set -- see b/212467440.
+            verify(kosmos.activityStarter).postStartActivityDismissingKeyguard(pendingIntent, null)
+        }
+
     companion object {
         fun createStatusBarIconViewOrNull(): StatusBarIconView? =
             if (StatusBarConnectedDisplays.isEnabled) {
@@ -389,6 +470,27 @@
                 mock<StatusBarIconView>()
             }
 
+        fun postOngoingCallNotification(
+            repository: ActiveNotificationListRepository,
+            startTimeMs: Long,
+            intent: PendingIntent?,
+        ) {
+            repository.activeNotifications.value =
+                ActiveNotificationsStore.Builder()
+                    .apply {
+                        addIndividualNotif(
+                            activeNotificationModel(
+                                key = "notif1",
+                                whenTime = startTimeMs,
+                                callType = CallType.Ongoing,
+                                statusBarChipIcon = null,
+                                contentIntent = intent,
+                            )
+                        )
+                    }
+                    .build()
+        }
+
         private val PROMOTED_CONTENT_WITH_COLOR =
             PromotedNotificationContentModel.Builder("notif")
                 .apply {
diff --git a/packages/SystemUI/src/com/android/systemui/common/ui/view/ViewExt.kt b/packages/SystemUI/src/com/android/systemui/common/ui/view/ViewExt.kt
index f7ea25c..b248043 100644
--- a/packages/SystemUI/src/com/android/systemui/common/ui/view/ViewExt.kt
+++ b/packages/SystemUI/src/com/android/systemui/common/ui/view/ViewExt.kt
@@ -68,3 +68,11 @@
     setOnTouchListener(listener)
     return DisposableHandle { setOnTouchListener(null) }
 }
+
+/** A null listener should also set the longClickable property to false */
+fun View.updateLongClickListener(listener: View.OnLongClickListener?) {
+    setOnLongClickListener(listener)
+    if (listener == null) {
+        setLongClickable(false)
+    }
+}
diff --git a/packages/SystemUI/src/com/android/systemui/communal/CommunalDreamStartable.kt b/packages/SystemUI/src/com/android/systemui/communal/CommunalDreamStartable.kt
index 1bd541e..6dc7c97 100644
--- a/packages/SystemUI/src/com/android/systemui/communal/CommunalDreamStartable.kt
+++ b/packages/SystemUI/src/com/android/systemui/communal/CommunalDreamStartable.kt
@@ -91,13 +91,19 @@
                 .launchIn(bgScope)
         }
 
-        // Restart the dream underneath the hub in order to support the ability to swipe
-        // away the hub to enter the dream.
-        startDream
-            .sampleFilter(powerInteractor.isAwake) { isAwake ->
-                !glanceableHubAllowKeyguardWhenDreaming() && dreamManager.canStartDreaming(isAwake)
-            }
-            .onEach { dreamManager.startDream() }
-            .launchIn(bgScope)
+        // With hub v2, we no longer need to keep the dream running underneath the hub as there is
+        // no more swipe between the hub and dream. We can just start the dream on-demand when the
+        // user presses the dream coin.
+        if (!communalSettingsInteractor.isV2FlagEnabled()) {
+            // Restart the dream underneath the hub in order to support the ability to swipe away
+            // the hub to enter the dream.
+            startDream
+                .sampleFilter(powerInteractor.isAwake) { isAwake ->
+                    !glanceableHubAllowKeyguardWhenDreaming() &&
+                        dreamManager.canStartDreaming(isAwake)
+                }
+                .onEach { dreamManager.startDream() }
+                .launchIn(bgScope)
+        }
     }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/dreams/DreamOverlayService.java b/packages/SystemUI/src/com/android/systemui/dreams/DreamOverlayService.java
index 0b2b368..a56a63c 100644
--- a/packages/SystemUI/src/com/android/systemui/dreams/DreamOverlayService.java
+++ b/packages/SystemUI/src/com/android/systemui/dreams/DreamOverlayService.java
@@ -562,6 +562,13 @@
             return;
         }
 
+        if (mCommunalSettingsInteractor.isV2FlagEnabled()) {
+            // Dream wake redirect is not needed in V2 as we do not need to keep the dream awake
+            // underneath the hub anymore as there is no more swipe between the dream and hub. SysUI
+            // will automatically transition to the hub when the dream wakes.
+            return;
+        }
+
         redirectWake(mCommunalAvailable && !glanceableHubAllowKeyguardWhenDreaming());
     }
 
diff --git a/packages/SystemUI/src/com/android/systemui/flags/FlagDependencies.kt b/packages/SystemUI/src/com/android/systemui/flags/FlagDependencies.kt
index 3911c19..e588077 100644
--- a/packages/SystemUI/src/com/android/systemui/flags/FlagDependencies.kt
+++ b/packages/SystemUI/src/com/android/systemui/flags/FlagDependencies.kt
@@ -31,6 +31,7 @@
 import com.android.systemui.statusbar.notification.emptyshade.shared.ModesEmptyShadeFix
 import com.android.systemui.statusbar.notification.interruption.VisualInterruptionRefactor
 import com.android.systemui.statusbar.notification.promoted.PromotedNotificationUi
+import com.android.systemui.statusbar.notification.promoted.PromotedNotificationUiAod
 import com.android.systemui.statusbar.notification.promoted.PromotedNotificationUiForceExpanded
 import com.android.systemui.statusbar.notification.shared.NotificationAvalancheSuppression
 import com.android.systemui.statusbar.notification.shared.NotificationMinimalism
@@ -55,6 +56,9 @@
         ModesEmptyShadeFix.token dependsOn modesUi
 
         PromotedNotificationUiForceExpanded.token dependsOn PromotedNotificationUi.token
+
+        PromotedNotificationUiAod.token dependsOn PromotedNotificationUi.token
+
         // SceneContainer dependencies
         SceneContainerFlag.getFlagDependencies().forEach { (alpha, beta) -> alpha dependsOn beta }
 
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractor.kt b/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractor.kt
index 7d8badd..b866fca 100644
--- a/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractor.kt
+++ b/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractor.kt
@@ -22,6 +22,7 @@
 import android.content.Context
 import android.content.Intent
 import android.util.Log
+import android.view.accessibility.AccessibilityManager
 import com.android.app.tracing.coroutines.withContextTraced as withContext
 import com.android.compose.animation.scene.ObservableTransitionState
 import com.android.internal.widget.LockPatternUtils
@@ -92,6 +93,7 @@
     private val dockManager: DockManager,
     private val biometricSettingsRepository: BiometricSettingsRepository,
     private val communalSettingsInteractor: CommunalSettingsInteractor,
+    private val accessibilityManager: AccessibilityManager,
     @Background private val backgroundDispatcher: CoroutineDispatcher,
     @ShadeDisplayAware private val appContext: Context,
     private val sceneInteractor: Lazy<SceneInteractor>,
@@ -115,7 +117,10 @@
      *
      * If `false`, the UI goes back to using single taps.
      */
-    fun useLongPress(): Flow<Boolean> = dockManager.retrieveIsDocked().map { !it }
+    fun useLongPress(): Flow<Boolean> =
+        dockManager.retrieveIsDocked().map { isDocked ->
+            !isDocked && !accessibilityManager.isEnabled()
+        }
 
     /** Returns an observable for the quick affordance at the given position. */
     suspend fun quickAffordance(
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardQuickAffordanceViewBinder.kt b/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardQuickAffordanceViewBinder.kt
index 8a2e3dd..f396cf9 100644
--- a/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardQuickAffordanceViewBinder.kt
+++ b/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardQuickAffordanceViewBinder.kt
@@ -39,6 +39,7 @@
 import com.android.systemui.animation.view.LaunchableImageView
 import com.android.systemui.common.shared.model.Icon
 import com.android.systemui.common.ui.binder.IconViewBinder
+import com.android.systemui.common.ui.view.updateLongClickListener
 import com.android.systemui.dagger.SysUISingleton
 import com.android.systemui.keyguard.ui.viewmodel.KeyguardQuickAffordanceHapticViewModel
 import com.android.systemui.keyguard.ui.viewmodel.KeyguardQuickAffordanceViewModel
@@ -275,6 +276,7 @@
                     )
             } else {
                 view.setOnClickListener(OnClickListener(viewModel, checkNotNull(falsingManager)))
+                view.updateLongClickListener(null)
             }
         } else {
             view.onLongClickListener = null
diff --git a/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImpl.kt b/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImpl.kt
index 2191f37..f1f299a 100644
--- a/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImpl.kt
+++ b/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImpl.kt
@@ -45,16 +45,15 @@
 import android.media.session.MediaSession
 import android.media.session.PlaybackState
 import android.net.Uri
-import android.os.Parcelable
 import android.os.Process
 import android.os.UserHandle
-import android.provider.Settings
 import android.service.notification.StatusBarNotification
 import android.support.v4.media.MediaMetadataCompat
 import android.text.TextUtils
 import android.util.Log
 import android.util.Pair as APair
 import androidx.media.utils.MediaConstants
+import com.android.app.tracing.coroutines.launchTraced as launch
 import com.android.app.tracing.traceSection
 import com.android.internal.annotations.Keep
 import com.android.internal.logging.InstanceId
@@ -86,11 +85,9 @@
 import com.android.systemui.media.controls.util.MediaFlags
 import com.android.systemui.media.controls.util.MediaUiEventLogger
 import com.android.systemui.media.controls.util.SmallHash
-import com.android.systemui.plugins.BcSmartspaceDataPlugin
 import com.android.systemui.res.R
 import com.android.systemui.statusbar.NotificationMediaManager.isPlayingState
 import com.android.systemui.statusbar.notification.row.HybridGroupManager
-import com.android.systemui.tuner.TunerService
 import com.android.systemui.util.Assert
 import com.android.systemui.util.Utils
 import com.android.systemui.util.concurrency.DelayableExecutor
@@ -103,7 +100,6 @@
 import javax.inject.Inject
 import kotlinx.coroutines.CoroutineDispatcher
 import kotlinx.coroutines.CoroutineScope
-import com.android.app.tracing.coroutines.launchTraced as launch
 import kotlinx.coroutines.withContext
 
 // URI fields to try loading album art from
@@ -152,22 +148,6 @@
         expiryTimeMs = 0,
     )
 
-const val MEDIA_TITLE_ERROR_MESSAGE = "Invalid media data: title is null or blank."
-
-/**
- * Allow recommendations from smartspace to show in media controls. Requires
- * [Utils.useQsMediaPlayer] to be enabled. On by default, but can be disabled by setting to 0
- */
-private fun allowMediaRecommendations(context: Context): Boolean {
-    val flag =
-        Settings.Secure.getInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            1,
-        )
-    return Utils.useQsMediaPlayer(context) && flag > 0
-}
-
 /** A class that facilitates management and loading of Media Data, ready for binding. */
 @SysUISingleton
 class LegacyMediaDataManagerImpl(
@@ -191,14 +171,13 @@
     private var useMediaResumption: Boolean,
     private val useQsMediaPlayer: Boolean,
     private val systemClock: SystemClock,
-    private val tunerService: TunerService,
     private val mediaFlags: MediaFlags,
     private val logger: MediaUiEventLogger,
     private val smartspaceManager: SmartspaceManager?,
     private val keyguardUpdateMonitor: KeyguardUpdateMonitor,
     private val mediaDataLoader: dagger.Lazy<MediaDataLoader>,
     private val mediaLogger: MediaLogger,
-) : Dumpable, BcSmartspaceDataPlugin.SmartspaceTargetListener, MediaDataManager {
+) : Dumpable, MediaDataManager {
 
     companion object {
         // UI surface label for subscribing Smartspace updates.
@@ -238,7 +217,6 @@
     // There should ONLY be at most one Smartspace media recommendation.
     var smartspaceMediaData: SmartspaceMediaData = EMPTY_SMARTSPACE_MEDIA_DATA
     @Keep private var smartspaceSession: SmartspaceSession? = null
-    private var allowMediaRecommendations = allowMediaRecommendations(context)
 
     private val artworkWidth =
         context.resources.getDimensionPixelSize(
@@ -276,7 +254,6 @@
         mediaDataFilter: LegacyMediaDataFilterImpl,
         smartspaceMediaDataProvider: SmartspaceMediaDataProvider,
         clock: SystemClock,
-        tunerService: TunerService,
         mediaFlags: MediaFlags,
         logger: MediaUiEventLogger,
         smartspaceManager: SmartspaceManager?,
@@ -306,7 +283,6 @@
         Utils.useMediaResumption(context),
         Utils.useQsMediaPlayer(context),
         clock,
-        tunerService,
         mediaFlags,
         logger,
         smartspaceManager,
@@ -372,7 +348,7 @@
         context.registerReceiver(appChangeReceiver, uninstallFilter)
 
         // Register for Smartspace data updates.
-        smartspaceMediaDataProvider.registerListener(this)
+        // TODO(b/382680767): remove
         smartspaceSession =
             smartspaceManager?.createSmartspaceSession(
                 SmartspaceConfig.Builder(context, SMARTSPACE_UI_SURFACE_LABEL).build()
@@ -391,24 +367,9 @@
             )
         }
         smartspaceSession?.let { it.requestSmartspaceUpdate() }
-        tunerService.addTunable(
-            object : TunerService.Tunable {
-                override fun onTuningChanged(key: String?, newValue: String?) {
-                    allowMediaRecommendations = allowMediaRecommendations(context)
-                    if (!allowMediaRecommendations) {
-                        dismissSmartspaceRecommendation(
-                            key = smartspaceMediaData.targetId,
-                            delay = 0L,
-                        )
-                    }
-                }
-            },
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-        )
     }
 
     override fun destroy() {
-        smartspaceMediaDataProvider.unregisterListener(this)
         smartspaceSession?.close()
         smartspaceSession = null
         context.unregisterReceiver(appChangeReceiver)
@@ -1328,61 +1289,6 @@
             }
         }
 
-    override fun onSmartspaceTargetsUpdated(targets: List<Parcelable>) {
-        if (!allowMediaRecommendations) {
-            if (DEBUG) Log.d(TAG, "Smartspace recommendation is disabled in Settings.")
-            return
-        }
-
-        val mediaTargets = targets.filterIsInstance<SmartspaceTarget>()
-        when (mediaTargets.size) {
-            0 -> {
-                if (!smartspaceMediaData.isActive) {
-                    return
-                }
-                if (DEBUG) {
-                    Log.d(TAG, "Set Smartspace media to be inactive for the data update")
-                }
-                if (mediaFlags.isPersistentSsCardEnabled()) {
-                    // Smartspace uses this signal to hide the card (e.g. when it expires or user
-                    // disconnects headphones), so treat as setting inactive when flag is on
-                    smartspaceMediaData = smartspaceMediaData.copy(isActive = false)
-                    notifySmartspaceMediaDataLoaded(
-                        smartspaceMediaData.targetId,
-                        smartspaceMediaData,
-                    )
-                } else {
-                    smartspaceMediaData =
-                        EMPTY_SMARTSPACE_MEDIA_DATA.copy(
-                            targetId = smartspaceMediaData.targetId,
-                            instanceId = smartspaceMediaData.instanceId,
-                        )
-                    notifySmartspaceMediaDataRemoved(
-                        smartspaceMediaData.targetId,
-                        immediately = false,
-                    )
-                }
-            }
-            1 -> {
-                val newMediaTarget = mediaTargets.get(0)
-                if (smartspaceMediaData.targetId == newMediaTarget.smartspaceTargetId) {
-                    // The same Smartspace updates can be received. Skip the duplicate updates.
-                    return
-                }
-                if (DEBUG) Log.d(TAG, "Forwarding Smartspace media update.")
-                smartspaceMediaData = toSmartspaceMediaData(newMediaTarget)
-                notifySmartspaceMediaDataLoaded(smartspaceMediaData.targetId, smartspaceMediaData)
-            }
-            else -> {
-                // There should NOT be more than 1 Smartspace media update. When it happens, it
-                // indicates a bad state or an error. Reset the status accordingly.
-                Log.wtf(TAG, "More than 1 Smartspace Media Update. Resetting the status...")
-                notifySmartspaceMediaDataRemoved(smartspaceMediaData.targetId, immediately = false)
-                smartspaceMediaData = EMPTY_SMARTSPACE_MEDIA_DATA
-            }
-        }
-    }
-
     override fun onNotificationRemoved(key: String) {
         Assert.isMainThread()
         val removed = mediaEntries.remove(key) ?: return
@@ -1641,7 +1547,6 @@
             println("externalListeners: ${mediaDataFilter.listeners}")
             println("mediaEntries: $mediaEntries")
             println("useMediaResumption: $useMediaResumption")
-            println("allowMediaRecommendations: $allowMediaRecommendations")
         }
         mediaDeviceManager.dump(pw)
     }
diff --git a/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessor.kt b/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessor.kt
index 3821f3d..a524db4 100644
--- a/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessor.kt
+++ b/packages/SystemUI/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessor.kt
@@ -45,16 +45,15 @@
 import android.media.session.MediaSession
 import android.media.session.PlaybackState
 import android.net.Uri
-import android.os.Parcelable
 import android.os.Process
 import android.os.UserHandle
-import android.provider.Settings
 import android.service.notification.StatusBarNotification
 import android.support.v4.media.MediaMetadataCompat
 import android.text.TextUtils
 import android.util.Log
 import android.util.Pair as APair
 import androidx.media.utils.MediaConstants
+import com.android.app.tracing.coroutines.launchTraced as launch
 import com.android.app.tracing.traceSection
 import com.android.internal.annotations.Keep
 import com.android.internal.logging.InstanceId
@@ -87,8 +86,6 @@
 import com.android.systemui.media.controls.util.MediaFlags
 import com.android.systemui.media.controls.util.MediaUiEventLogger
 import com.android.systemui.media.controls.util.SmallHash
-import com.android.systemui.plugins.ActivityStarter
-import com.android.systemui.plugins.BcSmartspaceDataPlugin
 import com.android.systemui.res.R
 import com.android.systemui.scene.shared.flag.SceneContainerFlag
 import com.android.systemui.statusbar.NotificationMediaManager.isPlayingState
@@ -97,8 +94,6 @@
 import com.android.systemui.util.Utils
 import com.android.systemui.util.concurrency.DelayableExecutor
 import com.android.systemui.util.concurrency.ThreadFactory
-import com.android.systemui.util.settings.SecureSettings
-import com.android.systemui.util.settings.SettingsProxyExt.observerFlow
 import com.android.systemui.util.time.SystemClock
 import java.io.IOException
 import java.io.PrintWriter
@@ -106,12 +101,6 @@
 import javax.inject.Inject
 import kotlinx.coroutines.CoroutineDispatcher
 import kotlinx.coroutines.CoroutineScope
-import kotlinx.coroutines.flow.collectLatest
-import kotlinx.coroutines.flow.distinctUntilChanged
-import kotlinx.coroutines.flow.flowOn
-import kotlinx.coroutines.flow.map
-import kotlinx.coroutines.flow.onStart
-import com.android.app.tracing.coroutines.launchTraced as launch
 import kotlinx.coroutines.withContext
 
 // URI fields to try loading album art from
@@ -139,12 +128,10 @@
     private val mediaControllerFactory: MediaControllerFactory,
     private val broadcastDispatcher: BroadcastDispatcher,
     private val dumpManager: DumpManager,
-    private val activityStarter: ActivityStarter,
     private val smartspaceMediaDataProvider: SmartspaceMediaDataProvider,
     private var useMediaResumption: Boolean,
     private val useQsMediaPlayer: Boolean,
     private val systemClock: SystemClock,
-    private val secureSettings: SecureSettings,
     private val mediaFlags: MediaFlags,
     private val logger: MediaUiEventLogger,
     private val smartspaceManager: SmartspaceManager?,
@@ -152,7 +139,7 @@
     private val mediaDataRepository: MediaDataRepository,
     private val mediaDataLoader: dagger.Lazy<MediaDataLoader>,
     private val mediaLogger: MediaLogger,
-) : CoreStartable, BcSmartspaceDataPlugin.SmartspaceTargetListener {
+) : CoreStartable {
 
     companion object {
         /**
@@ -191,7 +178,6 @@
 
     // There should ONLY be at most one Smartspace media recommendation.
     @Keep private var smartspaceSession: SmartspaceSession? = null
-    private var allowMediaRecommendations = false
 
     private val artworkWidth =
         context.resources.getDimensionPixelSize(
@@ -221,10 +207,8 @@
         mediaControllerFactory: MediaControllerFactory,
         dumpManager: DumpManager,
         broadcastDispatcher: BroadcastDispatcher,
-        activityStarter: ActivityStarter,
         smartspaceMediaDataProvider: SmartspaceMediaDataProvider,
         clock: SystemClock,
-        secureSettings: SecureSettings,
         mediaFlags: MediaFlags,
         logger: MediaUiEventLogger,
         smartspaceManager: SmartspaceManager?,
@@ -245,12 +229,10 @@
         mediaControllerFactory,
         broadcastDispatcher,
         dumpManager,
-        activityStarter,
         smartspaceMediaDataProvider,
         Utils.useMediaResumption(context),
         Utils.useQsMediaPlayer(context),
         clock,
-        secureSettings,
         mediaFlags,
         logger,
         smartspaceManager,
@@ -296,7 +278,7 @@
         context.registerReceiver(appChangeReceiver, uninstallFilter)
 
         // Register for Smartspace data updates.
-        smartspaceMediaDataProvider.registerListener(this)
+        // TODO(b/382680767): remove
         smartspaceSession =
             smartspaceManager?.createSmartspaceSession(
                 SmartspaceConfig.Builder(context, SMARTSPACE_UI_SURFACE_LABEL).build()
@@ -314,13 +296,9 @@
             }
         }
         smartspaceSession?.requestSmartspaceUpdate()
-
-        // Track media controls recommendation setting.
-        applicationScope.launch { trackMediaControlsRecommendationSetting() }
     }
 
     fun destroy() {
-        smartspaceMediaDataProvider.unregisterListener(this)
         smartspaceSession?.close()
         smartspaceSession = null
         context.unregisterReceiver(appChangeReceiver)
@@ -357,43 +335,6 @@
         }
     }
 
-    /**
-     * Allow recommendations from smartspace to show in media controls. Requires
-     * [Utils.useQsMediaPlayer] to be enabled. On by default, but can be disabled by setting to 0
-     */
-    private suspend fun allowMediaRecommendations(): Boolean {
-        return withContext(backgroundDispatcher) {
-            val flag =
-                secureSettings.getBoolForUser(
-                    Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-                    true,
-                    UserHandle.USER_CURRENT,
-                )
-
-            useQsMediaPlayer && flag
-        }
-    }
-
-    private suspend fun trackMediaControlsRecommendationSetting() {
-        secureSettings
-            .observerFlow(UserHandle.USER_ALL, Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION)
-            // perform a query at the beginning.
-            .onStart { emit(Unit) }
-            .map { allowMediaRecommendations() }
-            .distinctUntilChanged()
-            .flowOn(backgroundDispatcher)
-            // only track the most recent emission
-            .collectLatest {
-                allowMediaRecommendations = it
-                if (!allowMediaRecommendations) {
-                    dismissSmartspaceRecommendation(
-                        key = mediaDataRepository.smartspaceMediaData.value.targetId,
-                        delay = 0L,
-                    )
-                }
-            }
-    }
-
     private fun removeAllForPackage(packageName: String) {
         Assert.isMainThread()
         val toRemove =
@@ -1277,62 +1218,6 @@
             }
         }
 
-    override fun onSmartspaceTargetsUpdated(targets: List<Parcelable>) {
-        if (!allowMediaRecommendations) {
-            if (DEBUG) Log.d(TAG, "Smartspace recommendation is disabled in Settings.")
-            return
-        }
-
-        val mediaTargets = targets.filterIsInstance<SmartspaceTarget>()
-        val smartspaceMediaData = mediaDataRepository.smartspaceMediaData.value
-        when (mediaTargets.size) {
-            0 -> {
-                if (!smartspaceMediaData.isActive) {
-                    return
-                }
-                if (DEBUG) {
-                    Log.d(TAG, "Set Smartspace media to be inactive for the data update")
-                }
-                if (mediaFlags.isPersistentSsCardEnabled()) {
-                    // Smartspace uses this signal to hide the card (e.g. when it expires or user
-                    // disconnects headphones), so treat as setting inactive when flag is on
-                    val recommendation = smartspaceMediaData.copy(isActive = false)
-                    mediaDataRepository.setRecommendation(recommendation)
-                    notifySmartspaceMediaDataLoaded(recommendation.targetId, recommendation)
-                } else {
-                    notifySmartspaceMediaDataRemoved(
-                        smartspaceMediaData.targetId,
-                        immediately = false,
-                    )
-                    mediaDataRepository.setRecommendation(
-                        SmartspaceMediaData(
-                            targetId = smartspaceMediaData.targetId,
-                            instanceId = smartspaceMediaData.instanceId,
-                        )
-                    )
-                }
-            }
-            1 -> {
-                val newMediaTarget = mediaTargets.get(0)
-                if (smartspaceMediaData.targetId == newMediaTarget.smartspaceTargetId) {
-                    // The same Smartspace updates can be received. Skip the duplicate updates.
-                    return
-                }
-                if (DEBUG) Log.d(TAG, "Forwarding Smartspace media update.")
-                val recommendation = toSmartspaceMediaData(newMediaTarget)
-                mediaDataRepository.setRecommendation(recommendation)
-                notifySmartspaceMediaDataLoaded(recommendation.targetId, recommendation)
-            }
-            else -> {
-                // There should NOT be more than 1 Smartspace media update. When it happens, it
-                // indicates a bad state or an error. Reset the status accordingly.
-                Log.wtf(TAG, "More than 1 Smartspace Media Update. Resetting the status...")
-                notifySmartspaceMediaDataRemoved(smartspaceMediaData.targetId, immediately = false)
-                mediaDataRepository.setRecommendation(SmartspaceMediaData())
-            }
-        }
-    }
-
     fun onNotificationRemoved(key: String) {
         Assert.isMainThread()
         val removed = mediaDataRepository.removeMediaEntry(key) ?: return
@@ -1621,7 +1506,6 @@
         pw.apply {
             println("internalListeners: $internalListeners")
             println("useMediaResumption: $useMediaResumption")
-            println("allowMediaRecommendations: $allowMediaRecommendations")
         }
     }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/media/controls/ui/controller/MediaViewController.kt b/packages/SystemUI/src/com/android/systemui/media/controls/ui/controller/MediaViewController.kt
index 86e9294..975f8f4 100644
--- a/packages/SystemUI/src/com/android/systemui/media/controls/ui/controller/MediaViewController.kt
+++ b/packages/SystemUI/src/com/android/systemui/media/controls/ui/controller/MediaViewController.kt
@@ -1042,6 +1042,18 @@
             return null
         }
 
+        if (state.expansion == 1.0f) {
+            val height =
+                if (state.expandedMatchesParentHeight) {
+                    heightInSceneContainerPx
+                } else {
+                    context.resources.getDimensionPixelSize(
+                        R.dimen.qs_media_session_height_expanded
+                    )
+                }
+            setBackgroundHeights(height)
+        }
+
         // Similar to obtainViewState: Let's create a new measurement
         val result =
             transitionLayout?.calculateViewState(
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModel.kt b/packages/SystemUI/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModel.kt
index 108d737..99e8472 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModel.kt
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/chips/call/ui/viewmodel/CallChipViewModel.kt
@@ -37,6 +37,7 @@
 import com.android.systemui.statusbar.chips.ui.view.ChipBackgroundContainer
 import com.android.systemui.statusbar.chips.ui.viewmodel.OngoingActivityChipViewModel
 import com.android.systemui.statusbar.core.StatusBarConnectedDisplays
+import com.android.systemui.statusbar.phone.ongoingcall.StatusBarChipsModernization
 import com.android.systemui.statusbar.phone.ongoingcall.shared.model.OngoingCallModel
 import com.android.systemui.util.time.SystemClock
 import javax.inject.Inject
@@ -93,9 +94,7 @@
                                 icon = icon,
                                 colors = colors,
                                 onClickListenerLegacy = getOnClickListener(state),
-                                // TODO(b/372657935): Add click support for the call chip when
-                                // StatusBarChipModernization is enabled.
-                                clickBehavior = OngoingActivityChipModel.ClickBehavior.None,
+                                clickBehavior = getClickBehavior(state),
                             )
                         } else {
                             val startTimeInElapsedRealtime =
@@ -106,9 +105,7 @@
                                 colors = colors,
                                 startTimeMs = startTimeInElapsedRealtime,
                                 onClickListenerLegacy = getOnClickListener(state),
-                                // TODO(b/372657935): Add click support for the call chip when
-                                // StatusBarChipModernization is enabled.
-                                clickBehavior = OngoingActivityChipModel.ClickBehavior.None,
+                                clickBehavior = getClickBehavior(state),
                             )
                         }
                     }
@@ -122,6 +119,7 @@
         }
 
         return View.OnClickListener { view ->
+            StatusBarChipsModernization.assertInLegacyMode()
             logger.log(TAG, LogLevel.INFO, {}, { "Chip clicked" })
             val backgroundView =
                 view.requireViewById<ChipBackgroundContainer>(R.id.ongoing_activity_chip_background)
@@ -136,6 +134,27 @@
         }
     }
 
+    private fun getClickBehavior(
+        state: OngoingCallModel.InCall
+    ): OngoingActivityChipModel.ClickBehavior =
+        if (state.intent == null) {
+            OngoingActivityChipModel.ClickBehavior.None
+        } else {
+            OngoingActivityChipModel.ClickBehavior.ExpandAction(
+                onClick = { expandable ->
+                    StatusBarChipsModernization.assertInNewMode()
+                    val animationController =
+                        expandable.activityTransitionController(
+                            InteractionJankMonitor.CUJ_STATUS_BAR_APP_LAUNCH_FROM_CALL_CHIP
+                        )
+                    activityStarter.postStartActivityDismissingKeyguard(
+                        state.intent,
+                        animationController,
+                    )
+                }
+            )
+        }
+
     companion object {
         private val phoneIcon =
             Icon.Resource(
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/promoted/PromotedNotificationUiAod.kt b/packages/SystemUI/src/com/android/systemui/statusbar/notification/promoted/PromotedNotificationUiAod.kt
new file mode 100644
index 0000000..fa1f32c
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/promoted/PromotedNotificationUiAod.kt
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2025 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.systemui.statusbar.notification.promoted
+
+import com.android.systemui.Flags
+import com.android.systemui.flags.FlagToken
+import com.android.systemui.flags.RefactorFlagUtils
+
+/** Helper for reading or using the promoted ongoing notifications AOD flag state. */
+object PromotedNotificationUiAod {
+    /** The aconfig flag name */
+    const val FLAG_NAME = Flags.FLAG_AOD_UI_RICH_ONGOING
+
+    /** A token used for dependency declaration */
+    val token: FlagToken
+        get() = FlagToken(FLAG_NAME, isEnabled)
+
+    /** Is the refactor enabled */
+    @JvmStatic
+    inline val isEnabled
+        get() = Flags.aodUiRichOngoing()
+
+    /**
+     * Called to ensure code is only run when the flag is enabled. This protects users from the
+     * unintended behaviors caused by accidentally running new logic, while also crashing on an eng
+     * build to ensure that the refactor author catches issues in testing.
+     */
+    @JvmStatic
+    inline fun isUnexpectedlyInLegacyMode() =
+        RefactorFlagUtils.isUnexpectedlyInLegacyMode(isEnabled, FLAG_NAME)
+
+    /**
+     * Called to ensure code is only run when the flag is disabled. This will throw an exception if
+     * the flag is not enabled to ensure that the refactor author catches issues in testing.
+     * Caution!! Using this check incorrectly will cause crashes in nextfood builds!
+     */
+    @JvmStatic
+    inline fun assertInNewMode() = RefactorFlagUtils.assertInNewMode(isEnabled, FLAG_NAME)
+
+    /**
+     * Called to ensure code is only run when the flag is disabled. This will throw an exception if
+     * the flag is enabled to ensure that the refactor author catches issues in testing.
+     */
+    @JvmStatic
+    inline fun assertInLegacyMode() = RefactorFlagUtils.assertInLegacyMode(isEnabled, FLAG_NAME)
+}
diff --git a/packages/SystemUI/src/com/android/systemui/tuner/TunerServiceImpl.java b/packages/SystemUI/src/com/android/systemui/tuner/TunerServiceImpl.java
index 05ee35b..8f5fccd 100644
--- a/packages/SystemUI/src/com/android/systemui/tuner/TunerServiceImpl.java
+++ b/packages/SystemUI/src/com/android/systemui/tuner/TunerServiceImpl.java
@@ -75,8 +75,7 @@
     private static final String[] RESET_EXCEPTION_LIST = new String[] {
             QSHost.TILES_SETTING,
             Settings.Secure.DOZE_ALWAYS_ON,
-            Settings.Secure.MEDIA_CONTROLS_RESUME,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION
+            Settings.Secure.MEDIA_CONTROLS_RESUME
     };
 
     private final Observer mObserver = new Observer();
diff --git a/packages/SystemUI/tests/src/com/android/systemui/keyguard/CustomizationProviderTest.kt b/packages/SystemUI/tests/src/com/android/systemui/keyguard/CustomizationProviderTest.kt
index 82bf5e2..a3c3d2c 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/keyguard/CustomizationProviderTest.kt
+++ b/packages/SystemUI/tests/src/com/android/systemui/keyguard/CustomizationProviderTest.kt
@@ -205,6 +205,7 @@
                 biometricSettingsRepository = biometricSettingsRepository,
                 backgroundDispatcher = testDispatcher,
                 appContext = mContext,
+                accessibilityManager = mock(),
                 communalSettingsInteractor = kosmos.communalSettingsInteractor,
                 sceneInteractor = { kosmos.sceneInteractor },
             )
diff --git a/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorParameterizedTest.kt b/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorParameterizedTest.kt
index 111d819..21519b0 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorParameterizedTest.kt
+++ b/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorParameterizedTest.kt
@@ -322,6 +322,7 @@
                 biometricSettingsRepository = biometricSettingsRepository,
                 backgroundDispatcher = testDispatcher,
                 appContext = mContext,
+                accessibilityManager = mock(),
                 communalSettingsInteractor = kosmos.communalSettingsInteractor,
                 sceneInteractor = { kosmos.sceneInteractor },
             )
diff --git a/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorSceneContainerTest.kt b/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorSceneContainerTest.kt
index 8c00047..caf08ef 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorSceneContainerTest.kt
+++ b/packages/SystemUI/tests/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorSceneContainerTest.kt
@@ -325,6 +325,7 @@
                 biometricSettingsRepository = biometricSettingsRepository,
                 backgroundDispatcher = testDispatcher,
                 appContext = mContext,
+                accessibilityManager = mock(),
                 communalSettingsInteractor = kosmos.communalSettingsInteractor,
                 sceneInteractor = { kosmos.sceneInteractor },
             )
diff --git a/packages/SystemUI/tests/src/com/android/systemui/keyguard/ui/viewmodel/KeyguardQuickAffordancesCombinedViewModelTest.kt b/packages/SystemUI/tests/src/com/android/systemui/keyguard/ui/viewmodel/KeyguardQuickAffordancesCombinedViewModelTest.kt
index 0b2b867..b5a2271 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/keyguard/ui/viewmodel/KeyguardQuickAffordancesCombinedViewModelTest.kt
+++ b/packages/SystemUI/tests/src/com/android/systemui/keyguard/ui/viewmodel/KeyguardQuickAffordancesCombinedViewModelTest.kt
@@ -294,6 +294,7 @@
                         biometricSettingsRepository = biometricSettingsRepository,
                         backgroundDispatcher = kosmos.testDispatcher,
                         appContext = mContext,
+                        accessibilityManager = mock(),
                         communalSettingsInteractor = kosmos.communalSettingsInteractor,
                         sceneInteractor = { kosmos.sceneInteractor },
                     ),
diff --git a/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImplTest.kt b/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImplTest.kt
index 3ddd4b5..2815b9769 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImplTest.kt
+++ b/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/LegacyMediaDataManagerImplTest.kt
@@ -41,13 +41,11 @@
 import android.platform.test.annotations.DisableFlags
 import android.platform.test.annotations.EnableFlags
 import android.platform.test.flag.junit.FlagsParameterization
-import android.provider.Settings
 import android.service.notification.StatusBarNotification
 import android.testing.TestableLooper.RunWithLooper
 import androidx.media.utils.MediaConstants
 import androidx.test.filters.SmallTest
 import com.android.dx.mockito.inline.extended.ExtendedMockito
-import com.android.internal.logging.InstanceId
 import com.android.keyguard.KeyguardUpdateMonitor
 import com.android.systemui.Flags
 import com.android.systemui.InstanceIdSequenceFake
@@ -65,10 +63,7 @@
 import com.android.systemui.media.controls.domain.resume.ResumeMediaBrowser
 import com.android.systemui.media.controls.shared.mediaLogger
 import com.android.systemui.media.controls.shared.mockMediaLogger
-import com.android.systemui.media.controls.shared.model.EXTRA_KEY_TRIGGER_SOURCE
-import com.android.systemui.media.controls.shared.model.EXTRA_VALUE_TRIGGER_PERIODIC
 import com.android.systemui.media.controls.shared.model.MediaData
-import com.android.systemui.media.controls.shared.model.SmartspaceMediaData
 import com.android.systemui.media.controls.shared.model.SmartspaceMediaDataProvider
 import com.android.systemui.media.controls.util.MediaUiEventLogger
 import com.android.systemui.media.controls.util.fakeMediaControllerFactory
@@ -76,7 +71,6 @@
 import com.android.systemui.res.R
 import com.android.systemui.statusbar.SbnBuilder
 import com.android.systemui.testKosmos
-import com.android.systemui.tuner.TunerService
 import com.android.systemui.util.concurrency.FakeExecutor
 import com.android.systemui.util.time.FakeSystemClock
 import com.google.common.truth.Truth.assertThat
@@ -95,12 +89,10 @@
 import org.mockito.ArgumentMatchers.anyInt
 import org.mockito.Captor
 import org.mockito.Mock
-import org.mockito.Mockito
 import org.mockito.Mockito.mock
 import org.mockito.Mockito.never
 import org.mockito.Mockito.reset
 import org.mockito.Mockito.verify
-import org.mockito.Mockito.verifyNoMoreInteractions
 import org.mockito.Mockito.`when` as whenever
 import org.mockito.MockitoSession
 import org.mockito.junit.MockitoJUnit
@@ -126,10 +118,6 @@
 private const val USER_ID = 0
 private val DISMISS_INTENT = Intent().apply { action = "dismiss" }
 
-private fun <T> anyObject(): T {
-    return Mockito.anyObject<T>()
-}
-
 @OptIn(ExperimentalCoroutinesApi::class)
 @SmallTest
 @RunWithLooper(setAsMainLooper = true)
@@ -168,8 +156,6 @@
     lateinit var remoteCastNotification: StatusBarNotification
     @Captor lateinit var mediaDataCaptor: ArgumentCaptor<MediaData>
     private val clock = FakeSystemClock()
-    @Mock private lateinit var tunerService: TunerService
-    @Captor lateinit var tunableCaptor: ArgumentCaptor<TunerService.Tunable>
     @Captor lateinit var stateCallbackCaptor: ArgumentCaptor<(String, PlaybackState) -> Unit>
     @Captor lateinit var sessionCallbackCaptor: ArgumentCaptor<(String) -> Unit>
     @Captor lateinit var smartSpaceConfigBuilderCaptor: ArgumentCaptor<SmartspaceConfig>
@@ -197,13 +183,6 @@
     private val mediaControllerFactory = kosmos.fakeMediaControllerFactory
     private val instanceIdSequence = InstanceIdSequenceFake(1 shl 20)
 
-    private val originalSmartspaceSetting =
-        Settings.Secure.getInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            1,
-        )
-
     private lateinit var staticMockSession: MockitoSession
 
     @Before
@@ -219,11 +198,6 @@
         backgroundExecutor = FakeExecutor(clock)
         uiExecutor = FakeExecutor(clock)
         smartspaceMediaDataProvider = SmartspaceMediaDataProvider()
-        Settings.Secure.putInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            1,
-        )
         mediaDataManager =
             LegacyMediaDataManagerImpl(
                 context = context,
@@ -246,7 +220,6 @@
                 useMediaResumption = true,
                 useQsMediaPlayer = true,
                 systemClock = clock,
-                tunerService = tunerService,
                 mediaFlags = kosmos.mediaFlags,
                 logger = logger,
                 smartspaceManager = smartspaceManager,
@@ -254,8 +227,6 @@
                 mediaDataLoader = { kosmos.mediaDataLoader },
                 mediaLogger = kosmos.mediaLogger,
             )
-        verify(tunerService)
-            .addTunable(capture(tunableCaptor), eq(Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION))
         verify(mediaTimeoutListener).stateCallback = capture(stateCallbackCaptor)
         verify(mediaTimeoutListener).sessionCallback = capture(sessionCallbackCaptor)
         session = MediaSession(context, "MediaDataManagerTestSession")
@@ -332,11 +303,6 @@
         staticMockSession.finishMocking()
         session.release()
         mediaDataManager.destroy()
-        Settings.Secure.putInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            originalSmartspaceSetting,
-        )
     }
 
     @Test
@@ -1236,272 +1202,6 @@
     }
 
     @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNewValidMediaTarget_callsListener() {
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNewInvalidMediaTarget_callsListener() {
-        whenever(mediaSmartspaceTarget.iconGrid).thenReturn(listOf())
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    EMPTY_SMARTSPACE_MEDIA_DATA.copy(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNullIntent_callsListener() {
-        val recommendationExtras =
-            Bundle().apply {
-                putString("package_name", PACKAGE_NAME)
-                putParcelable("dismiss_intent", null)
-            }
-        whenever(mediaSmartspaceBaseAction.extras).thenReturn(recommendationExtras)
-        whenever(mediaSmartspaceTarget.baseAction).thenReturn(mediaSmartspaceBaseAction)
-        whenever(mediaSmartspaceTarget.iconGrid).thenReturn(listOf())
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    EMPTY_SMARTSPACE_MEDIA_DATA.copy(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        dismissIntent = null,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNoneMediaTarget_notCallsListener() {
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf())
-        verify(logger, never()).getNewInstanceId()
-        verify(listener, never())
-            .onSmartspaceMediaDataLoaded(anyObject(), anyObject(), anyBoolean())
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNoneMediaTarget_callsRemoveListener() {
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf())
-        uiExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-
-        verify(listener).onSmartspaceMediaDataRemoved(eq(KEY_MEDIA_SMARTSPACE), eq(false))
-        verifyNoMoreInteractions(logger)
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_persistentEnabled_headphoneTrigger_isActive() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_persistentEnabled_periodicTrigger_notActive() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-        val extras =
-            Bundle().apply {
-                putString("package_name", PACKAGE_NAME)
-                putParcelable("dismiss_intent", DISMISS_INTENT)
-                putString(EXTRA_KEY_TRIGGER_SOURCE, EXTRA_VALUE_TRIGGER_PERIODIC)
-            }
-        whenever(mediaSmartspaceBaseAction.extras).thenReturn(extras)
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = false,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_persistentEnabled_noTargets_inactive() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf())
-        uiExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = false,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-        verify(listener, never()).onSmartspaceMediaDataRemoved(eq(KEY_MEDIA_SMARTSPACE), eq(false))
-    }
-
-    @Test
-    fun testSetRecommendationInactive_notifiesListeners() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        mediaDataManager.setRecommendationInactive(KEY_MEDIA_SMARTSPACE)
-        uiExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = false,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_settingDisabled_doesNothing() {
-        // WHEN media recommendation setting is off
-        Settings.Secure.putInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            0,
-        )
-        tunableCaptor.value.onTuningChanged(Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, "0")
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-
-        // THEN smartspace signal is ignored
-        verify(listener, never())
-            .onSmartspaceMediaDataLoaded(anyObject(), anyObject(), anyBoolean())
-    }
-
-    @Test
-    fun testMediaRecommendationDisabled_removesSmartspaceData() {
-        // GIVEN a media recommendation card is present
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(eq(KEY_MEDIA_SMARTSPACE), anyObject(), anyBoolean())
-
-        // WHEN the media recommendation setting is turned off
-        Settings.Secure.putInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            0,
-        )
-        tunableCaptor.value.onTuningChanged(Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, "0")
-
-        // THEN listeners are notified
-        uiExecutor.advanceClockToLast()
-        foregroundExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-        foregroundExecutor.runAllReady()
-        verify(listener).onSmartspaceMediaDataRemoved(eq(KEY_MEDIA_SMARTSPACE), eq(true))
-    }
-
-    @Test
     fun testOnMediaDataChanged_updatesLastActiveTime() {
         val currentTime = clock.elapsedRealtime()
         addNotificationAndLoad()
diff --git a/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorTest.kt b/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorTest.kt
index e5483c0..b9ebce8 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorTest.kt
+++ b/packages/SystemUI/tests/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorTest.kt
@@ -42,13 +42,11 @@
 import android.platform.test.annotations.DisableFlags
 import android.platform.test.annotations.EnableFlags
 import android.platform.test.flag.junit.FlagsParameterization
-import android.provider.Settings
 import android.service.notification.StatusBarNotification
 import android.testing.TestableLooper.RunWithLooper
 import androidx.media.utils.MediaConstants
 import androidx.test.filters.SmallTest
 import com.android.dx.mockito.inline.extended.ExtendedMockito
-import com.android.internal.logging.InstanceId
 import com.android.keyguard.KeyguardUpdateMonitor
 import com.android.systemui.Flags
 import com.android.systemui.InstanceIdSequenceFake
@@ -71,21 +69,16 @@
 import com.android.systemui.media.controls.domain.resume.ResumeMediaBrowser
 import com.android.systemui.media.controls.shared.mediaLogger
 import com.android.systemui.media.controls.shared.mockMediaLogger
-import com.android.systemui.media.controls.shared.model.EXTRA_KEY_TRIGGER_SOURCE
-import com.android.systemui.media.controls.shared.model.EXTRA_VALUE_TRIGGER_PERIODIC
 import com.android.systemui.media.controls.shared.model.MediaData
-import com.android.systemui.media.controls.shared.model.SmartspaceMediaData
 import com.android.systemui.media.controls.shared.model.SmartspaceMediaDataProvider
 import com.android.systemui.media.controls.util.MediaUiEventLogger
 import com.android.systemui.media.controls.util.fakeMediaControllerFactory
 import com.android.systemui.media.controls.util.mediaFlags
-import com.android.systemui.plugins.activityStarter
 import com.android.systemui.res.R
 import com.android.systemui.statusbar.SbnBuilder
 import com.android.systemui.statusbar.notificationLockscreenUserManager
 import com.android.systemui.testKosmos
 import com.android.systemui.util.concurrency.FakeExecutor
-import com.android.systemui.util.settings.fakeSettings
 import com.android.systemui.util.time.FakeSystemClock
 import com.google.common.truth.Truth.assertThat
 import kotlinx.coroutines.ExperimentalCoroutinesApi
@@ -102,11 +95,9 @@
 import org.mockito.ArgumentMatchers.anyInt
 import org.mockito.Captor
 import org.mockito.Mock
-import org.mockito.Mockito
 import org.mockito.Mockito.never
 import org.mockito.Mockito.reset
 import org.mockito.Mockito.verify
-import org.mockito.Mockito.verifyNoMoreInteractions
 import org.mockito.MockitoSession
 import org.mockito.junit.MockitoJUnit
 import org.mockito.kotlin.any
@@ -133,10 +124,6 @@
 private const val USER_ID = 0
 private val DISMISS_INTENT = Intent().apply { action = "dismiss" }
 
-private fun <T> anyObject(): T {
-    return Mockito.anyObject<T>()
-}
-
 @OptIn(ExperimentalCoroutinesApi::class)
 @SmallTest
 @RunWithLooper(setAsMainLooper = true)
@@ -146,7 +133,6 @@
     private val kosmos = testKosmos().apply { mediaLogger = mockMediaLogger }
     private val testDispatcher = kosmos.testDispatcher
     private val testScope = kosmos.testScope
-    private val settings = kosmos.fakeSettings
 
     @JvmField @Rule val mockito = MockitoJUnit.rule()
     @Mock lateinit var controller: MediaController
@@ -201,7 +187,6 @@
     }
 
     private val fakeFeatureFlags = kosmos.fakeFeatureFlagsClassic
-    private val activityStarter = kosmos.activityStarter
     private val mediaControllerFactory = kosmos.fakeMediaControllerFactory
     private val notificationLockscreenUserManager = kosmos.notificationLockscreenUserManager
     private val mediaFilterRepository = kosmos.mediaFilterRepository
@@ -209,13 +194,6 @@
 
     private val instanceIdSequence = InstanceIdSequenceFake(1 shl 20)
 
-    private val originalSmartspaceSetting =
-        Settings.Secure.getInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            1,
-        )
-
     private lateinit var staticMockSession: MockitoSession
 
     @Before
@@ -231,11 +209,6 @@
         backgroundExecutor = FakeExecutor(clock)
         uiExecutor = FakeExecutor(clock)
         smartspaceMediaDataProvider = SmartspaceMediaDataProvider()
-        Settings.Secure.putInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            1,
-        )
         mediaDataProcessor =
             MediaDataProcessor(
                 context = context,
@@ -248,12 +221,10 @@
                 mediaControllerFactory = mediaControllerFactory,
                 broadcastDispatcher = broadcastDispatcher,
                 dumpManager = dumpManager,
-                activityStarter = activityStarter,
                 smartspaceMediaDataProvider = smartspaceMediaDataProvider,
                 useMediaResumption = true,
                 useQsMediaPlayer = true,
                 systemClock = clock,
-                secureSettings = settings,
                 mediaFlags = kosmos.mediaFlags,
                 logger = logger,
                 smartspaceManager = smartspaceManager,
@@ -355,11 +326,6 @@
         staticMockSession.finishMocking()
         session.release()
         mediaDataProcessor.destroy()
-        Settings.Secure.putInt(
-            context.contentResolver,
-            Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION,
-            originalSmartspaceSetting,
-        )
     }
 
     @Test
@@ -1255,264 +1221,6 @@
     }
 
     @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNewValidMediaTarget_callsListener() {
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNewInvalidMediaTarget_callsListener() {
-        whenever(mediaSmartspaceTarget.iconGrid).thenReturn(listOf())
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNullIntent_callsListener() {
-        val recommendationExtras =
-            Bundle().apply {
-                putString("package_name", PACKAGE_NAME)
-                putParcelable("dismiss_intent", null)
-            }
-        whenever(mediaSmartspaceBaseAction.extras).thenReturn(recommendationExtras)
-        whenever(mediaSmartspaceTarget.baseAction).thenReturn(mediaSmartspaceBaseAction)
-        whenever(mediaSmartspaceTarget.iconGrid).thenReturn(listOf())
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        dismissIntent = null,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNoneMediaTarget_notCallsListener() {
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf())
-        verify(logger, never()).getNewInstanceId()
-        verify(listener, never())
-            .onSmartspaceMediaDataLoaded(anyObject(), anyObject(), anyBoolean())
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_hasNoneMediaTarget_callsRemoveListener() {
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(logger).getNewInstanceId()
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf())
-        uiExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-
-        verify(listener).onSmartspaceMediaDataRemoved(eq(KEY_MEDIA_SMARTSPACE), eq(false))
-        verifyNoMoreInteractions(logger)
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_persistentEnabled_headphoneTrigger_isActive() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = true,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_persistentEnabled_periodicTrigger_notActive() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-        val extras =
-            Bundle().apply {
-                putString("package_name", PACKAGE_NAME)
-                putParcelable("dismiss_intent", DISMISS_INTENT)
-                putString(EXTRA_KEY_TRIGGER_SOURCE, EXTRA_VALUE_TRIGGER_PERIODIC)
-            }
-        whenever(mediaSmartspaceBaseAction.extras).thenReturn(extras)
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = false,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_persistentEnabled_noTargets_inactive() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf())
-        uiExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = false,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-        verify(listener, never()).onSmartspaceMediaDataRemoved(eq(KEY_MEDIA_SMARTSPACE), eq(false))
-    }
-
-    @Test
-    fun testSetRecommendationInactive_notifiesListeners() {
-        fakeFeatureFlags.set(MEDIA_RETAIN_RECOMMENDATIONS, true)
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        val instanceId = instanceIdSequence.lastInstanceId
-
-        mediaDataProcessor.setRecommendationInactive(KEY_MEDIA_SMARTSPACE)
-        uiExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(
-                eq(KEY_MEDIA_SMARTSPACE),
-                eq(
-                    SmartspaceMediaData(
-                        targetId = KEY_MEDIA_SMARTSPACE,
-                        isActive = false,
-                        packageName = PACKAGE_NAME,
-                        cardAction = mediaSmartspaceBaseAction,
-                        recommendations = validRecommendationList,
-                        dismissIntent = DISMISS_INTENT,
-                        headphoneConnectionTimeMillis = SMARTSPACE_CREATION_TIME,
-                        instanceId = InstanceId.fakeInstanceId(instanceId),
-                        expiryTimeMs = SMARTSPACE_EXPIRY_TIME,
-                    )
-                ),
-                eq(false),
-            )
-    }
-
-    @Test
-    fun testOnSmartspaceMediaDataLoaded_settingDisabled_doesNothing() {
-        // WHEN media recommendation setting is off
-        settings.putInt(Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, 0)
-        testScope.runCurrent()
-
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-
-        // THEN smartspace signal is ignored
-        verify(listener, never())
-            .onSmartspaceMediaDataLoaded(anyObject(), anyObject(), anyBoolean())
-    }
-
-    @Test
-    fun testMediaRecommendationDisabled_removesSmartspaceData() {
-        // GIVEN a media recommendation card is present
-        smartspaceMediaDataProvider.onTargetsAvailable(listOf(mediaSmartspaceTarget))
-        verify(listener)
-            .onSmartspaceMediaDataLoaded(eq(KEY_MEDIA_SMARTSPACE), anyObject(), anyBoolean())
-
-        // WHEN the media recommendation setting is turned off
-        settings.putInt(Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, 0)
-        testScope.runCurrent()
-
-        // THEN listeners are notified
-        uiExecutor.advanceClockToLast()
-        foregroundExecutor.advanceClockToLast()
-        uiExecutor.runAllReady()
-        foregroundExecutor.runAllReady()
-        verify(listener).onSmartspaceMediaDataRemoved(eq(KEY_MEDIA_SMARTSPACE), eq(true))
-    }
-
-    @Test
     fun testOnMediaDataChanged_updatesLastActiveTime() {
         val currentTime = clock.elapsedRealtime()
         addNotificationAndLoad()
diff --git a/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorKosmos.kt b/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorKosmos.kt
index 3b1199a..ba64ed7 100644
--- a/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorKosmos.kt
+++ b/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardQuickAffordanceInteractorKosmos.kt
@@ -18,6 +18,7 @@
 
 import android.app.admin.devicePolicyManager
 import android.content.applicationContext
+import android.view.accessibility.AccessibilityManager
 import com.android.internal.widget.lockPatternUtils
 import com.android.keyguard.logging.KeyguardQuickAffordancesLogger
 import com.android.systemui.animation.dialogTransitionAnimator
@@ -54,6 +55,7 @@
         dockManager = dockManager,
         biometricSettingsRepository = biometricSettingsRepository,
         communalSettingsInteractor = communalSettingsInteractor,
+        accessibilityManager = mock<AccessibilityManager>(),
         backgroundDispatcher = testDispatcher,
         appContext = applicationContext,
         sceneInteractor = { sceneInteractor },
diff --git a/packages/SystemUI/tests/utils/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorKosmos.kt b/packages/SystemUI/tests/utils/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorKosmos.kt
index 174e653..fcaad6b 100644
--- a/packages/SystemUI/tests/utils/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorKosmos.kt
+++ b/packages/SystemUI/tests/utils/src/com/android/systemui/media/controls/domain/pipeline/MediaDataProcessorKosmos.kt
@@ -31,9 +31,7 @@
 import com.android.systemui.media.controls.util.fakeMediaControllerFactory
 import com.android.systemui.media.controls.util.mediaFlags
 import com.android.systemui.media.controls.util.mediaUiEventLogger
-import com.android.systemui.plugins.activityStarter
 import com.android.systemui.util.Utils
-import com.android.systemui.util.settings.fakeSettings
 import com.android.systemui.util.time.systemClock
 
 val Kosmos.mediaDataProcessor by
@@ -49,12 +47,10 @@
             mediaControllerFactory = fakeMediaControllerFactory,
             broadcastDispatcher = broadcastDispatcher,
             dumpManager = dumpManager,
-            activityStarter = activityStarter,
             smartspaceMediaDataProvider = SmartspaceMediaDataProvider(),
             useMediaResumption = Utils.useMediaResumption(applicationContext),
             useQsMediaPlayer = Utils.useQsMediaPlayer(applicationContext),
             systemClock = systemClock,
-            secureSettings = fakeSettings,
             mediaFlags = mediaFlags,
             logger = mediaUiEventLogger,
             smartspaceManager = SmartspaceManager(applicationContext),
diff --git a/services/companion/java/com/android/server/companion/CompanionDeviceShellCommand.java b/services/companion/java/com/android/server/companion/CompanionDeviceShellCommand.java
index 2804945..3508f2f 100644
--- a/services/companion/java/com/android/server/companion/CompanionDeviceShellCommand.java
+++ b/services/companion/java/com/android/server/companion/CompanionDeviceShellCommand.java
@@ -106,7 +106,7 @@
                     boolean selfManaged = getNextBooleanArg();
                     final MacAddress macAddress = MacAddress.fromString(address);
                     mAssociationRequestsProcessor.createAssociation(userId, packageName, macAddress,
-                            deviceProfile, deviceProfile, /* associatedDevice */ null, false,
+                            deviceProfile, deviceProfile, /* associatedDevice */ null, selfManaged,
                             /* callback */ null, /* resultReceiver */ null, /* deviceIcon */ null);
                 }
                 break;
diff --git a/services/companion/java/com/android/server/companion/virtual/VirtualDeviceManagerService.java b/services/companion/java/com/android/server/companion/virtual/VirtualDeviceManagerService.java
index 0b335d3..4dd8b14 100644
--- a/services/companion/java/com/android/server/companion/virtual/VirtualDeviceManagerService.java
+++ b/services/companion/java/com/android/server/companion/virtual/VirtualDeviceManagerService.java
@@ -820,13 +820,12 @@
 
         @Override
         public void onAuthenticationPrompt(int uid) {
-            synchronized (mVirtualDeviceManagerLock) {
-                for (int i = 0; i < mVirtualDevices.size(); i++) {
-                    VirtualDeviceImpl device = mVirtualDevices.valueAt(i);
-                    device.showToastWhereUidIsRunning(uid,
-                            R.string.app_streaming_blocked_message_for_fingerprint_dialog,
-                            Toast.LENGTH_LONG, Looper.getMainLooper());
-                }
+            ArrayList<VirtualDeviceImpl> virtualDevicesSnapshot = getVirtualDevicesSnapshot();
+            for (int i = 0; i < virtualDevicesSnapshot.size(); i++) {
+                VirtualDeviceImpl device = virtualDevicesSnapshot.get(i);
+                device.showToastWhereUidIsRunning(uid,
+                        R.string.app_streaming_blocked_message_for_fingerprint_dialog,
+                        Toast.LENGTH_LONG, Looper.getMainLooper());
             }
         }
 
diff --git a/services/core/java/com/android/server/am/SettingsToPropertiesMapper.java b/services/core/java/com/android/server/am/SettingsToPropertiesMapper.java
index d3a5254..a54a663 100644
--- a/services/core/java/com/android/server/am/SettingsToPropertiesMapper.java
+++ b/services/core/java/com/android/server/am/SettingsToPropertiesMapper.java
@@ -16,12 +16,23 @@
 
 package com.android.server.am;
 
+import static com.android.aconfig_new_storage.Flags.enableAconfigStorageDaemon;
+import static com.android.aconfig_new_storage.Flags.enableAconfigdFromMainline;
+import static com.android.aconfig_new_storage.Flags.supportClearLocalOverridesImmediately;
+import static com.android.aconfig_new_storage.Flags.supportImmediateLocalOverrides;
+
+import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor;
+
+import android.aconfigd.Aconfigd.StorageRequestMessage;
+import android.aconfigd.Aconfigd.StorageRequestMessages;
+import android.aconfigd.Aconfigd.StorageReturnMessage;
+import android.aconfigd.Aconfigd.StorageReturnMessages;
 import android.annotation.NonNull;
 import android.content.ContentResolver;
 import android.database.ContentObserver;
-import android.net.Uri;
-import android.net.LocalSocketAddress;
 import android.net.LocalSocket;
+import android.net.LocalSocketAddress;
+import android.net.Uri;
 import android.os.AsyncTask;
 import android.os.Build;
 import android.os.SystemProperties;
@@ -35,28 +46,13 @@
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.providers.settings.Flags;
 
-import android.aconfigd.Aconfigd.StorageRequestMessage;
-import android.aconfigd.Aconfigd.StorageRequestMessages;
-import android.aconfigd.Aconfigd.StorageReturnMessage;
-import android.aconfigd.Aconfigd.StorageReturnMessages;
-import static com.android.aconfig_new_storage.Flags.enableAconfigStorageDaemon;
-import static com.android.aconfig_new_storage.Flags.supportImmediateLocalOverrides;
-import static com.android.aconfig_new_storage.Flags.supportClearLocalOverridesImmediately;
-import static com.android.aconfig_new_storage.Flags.enableAconfigdFromMainline;
-
+import java.io.BufferedReader;
 import java.io.DataInputStream;
 import java.io.DataOutputStream;
-import java.io.BufferedReader;
 import java.io.File;
 import java.io.FileReader;
 import java.io.IOException;
 import java.util.HashSet;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.List;
-import java.util.ArrayList;
-import java.util.Set;
-import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor;
 
 /**
  * Maps system settings to system properties.
@@ -271,6 +267,7 @@
         "wear_sysui",
         "wear_system_managed_surfaces",
         "wear_watchfaces",
+        "web_apps_on_chromeos_and_android",
         "window_surfaces",
         "windowing_frontend",
         "xr",
diff --git a/services/core/java/com/android/server/appop/DiscreteOpsDbHelper.java b/services/core/java/com/android/server/appop/DiscreteOpsDbHelper.java
index 695032e..86f5d9b 100644
--- a/services/core/java/com/android/server/appop/DiscreteOpsDbHelper.java
+++ b/services/core/java/com/android/server/appop/DiscreteOpsDbHelper.java
@@ -27,9 +27,13 @@
 import android.database.sqlite.SQLiteOpenHelper;
 import android.database.sqlite.SQLiteRawStatement;
 import android.os.Environment;
+import android.os.SystemClock;
+import android.permission.flags.Flags;
 import android.util.IntArray;
 import android.util.Slog;
 
+import com.android.internal.util.FrameworkStatsLog;
+
 import java.io.File;
 import java.util.ArrayList;
 import java.util.List;
@@ -76,6 +80,10 @@
         if (opEvents.isEmpty()) {
             return;
         }
+        long startTime = 0;
+        if (Flags.sqliteDiscreteOpEventLoggingEnabled()) {
+            startTime = SystemClock.elapsedRealtime();
+        }
 
         SQLiteDatabase db = getWritableDatabase();
         // TODO (b/383157289) what if database is busy and can't start a transaction? will read
@@ -117,6 +125,11 @@
                         + " file size (bytes) : " + getDatabaseFile().length(), exception);
             }
         }
+        if (Flags.sqliteDiscreteOpEventLoggingEnabled()) {
+            long timeTaken = SystemClock.elapsedRealtime() - startTime;
+            FrameworkStatsLog.write(FrameworkStatsLog.SQLITE_DISCRETE_OP_EVENT_REPORTED,
+                    -1, timeTaken, getDatabaseFile().length());
+        }
     }
 
     private void bindTextOrNull(SQLiteRawStatement statement, int index, @Nullable String text) {
@@ -181,7 +194,10 @@
                 uidFilter, packageNameFilter,
                 attributionTagFilter, opCodesFilter, opFlagsFilter);
         String sql = buildSql(conditions, orderByColumn, limit);
-
+        long startTime = 0;
+        if (Flags.sqliteDiscreteOpEventLoggingEnabled()) {
+            startTime = SystemClock.elapsedRealtime();
+        }
         SQLiteDatabase db = getReadableDatabase();
         List<DiscreteOpsSqlRegistry.DiscreteOp> results = new ArrayList<>();
         db.beginTransactionReadOnly();
@@ -225,6 +241,11 @@
         } finally {
             db.endTransaction();
         }
+        if (Flags.sqliteDiscreteOpEventLoggingEnabled()) {
+            long timeTaken = SystemClock.elapsedRealtime() - startTime;
+            FrameworkStatsLog.write(FrameworkStatsLog.SQLITE_DISCRETE_OP_EVENT_REPORTED,
+                    timeTaken, -1, getDatabaseFile().length());
+        }
         return results;
     }
 
diff --git a/services/core/java/com/android/server/display/DisplayManagerService.java b/services/core/java/com/android/server/display/DisplayManagerService.java
index 3350109..3598b9b 100644
--- a/services/core/java/com/android/server/display/DisplayManagerService.java
+++ b/services/core/java/com/android/server/display/DisplayManagerService.java
@@ -29,6 +29,7 @@
 import static android.Manifest.permission.RESTRICT_DISPLAY_MODES;
 import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_CACHED;
 import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_GONE;
+import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE;
 import static android.hardware.display.DisplayManagerGlobal.InternalEventFlag;
 import static android.hardware.display.DisplayManager.VIRTUAL_DISPLAY_FLAG_ALWAYS_UNLOCKED;
 import static android.hardware.display.DisplayManager.VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR;
@@ -380,6 +381,8 @@
     private final SparseArray<DisplayPowerController> mDisplayPowerControllers =
             new SparseArray<>();
 
+    private int mMaxImportanceForRRCallbacks = IMPORTANCE_VISIBLE;
+
     /** {@link DisplayBlanker} used by all {@link DisplayPowerController}s. */
     private final DisplayBlanker mDisplayBlanker = new DisplayBlanker() {
         // Synchronized to avoid race conditions when updating multiple display states.
@@ -3636,6 +3639,7 @@
             pw.println("  mWifiDisplayScanRequestCount=" + mWifiDisplayScanRequestCount);
             pw.println("  mStableDisplaySize=" + mStableDisplaySize);
             pw.println("  mMinimumBrightnessCurve=" + mMinimumBrightnessCurve);
+            pw.println("  mMaxImportanceForRRCallbacks=" + mMaxImportanceForRRCallbacks);
 
             if (mUserPreferredMode != null) {
                 pw.println(" mUserPreferredMode=" + mUserPreferredMode);
@@ -3764,6 +3768,10 @@
         }
     }
 
+    void overrideMaxImportanceForRRCallbacks(int importance) {
+        mMaxImportanceForRRCallbacks = importance;
+    }
+
     boolean requestDisplayPower(int displayId, int requestedState) {
         synchronized (mSyncRoot) {
             final var display = mLogicalDisplayMapper.getDisplayLocked(displayId);
@@ -4147,6 +4155,18 @@
             mPackageName = packageNames == null ? null : packageNames[0];
         }
 
+        public boolean shouldReceiveRefreshRateWithChangeUpdate(int event) {
+            if (mFlags.isRefreshRateEventForForegroundAppsEnabled()
+                    && event == DisplayManagerGlobal.EVENT_DISPLAY_REFRESH_RATE_CHANGED) {
+                int procState = mActivityManagerInternal.getUidProcessState(mUid);
+                int importance = ActivityManager.RunningAppProcessInfo
+                        .procStateToImportance(procState);
+                return importance <= mMaxImportanceForRRCallbacks || mUid <= Process.SYSTEM_UID;
+            }
+
+            return true;
+        }
+
         public void updateEventFlagsMask(@InternalEventFlag long internalEventFlag) {
             mInternalEventFlagsMask.set(internalEventFlag);
         }
@@ -4254,6 +4274,11 @@
                 }
             }
 
+            if (!shouldReceiveRefreshRateWithChangeUpdate(event)) {
+                // The client is not visible to the user and is not a system service, so do nothing.
+                return true;
+            }
+
             try {
                 transmitDisplayEvent(displayId, event);
                 return true;
@@ -4405,6 +4430,11 @@
                                 + displayEvent.displayId + "/"
                                 + displayEvent.event + " to " + mUid + "/" + mPid);
                     }
+
+                    if (!shouldReceiveRefreshRateWithChangeUpdate(displayEvent.event)) {
+                        continue;
+                    }
+
                     transmitDisplayEvent(displayEvent.displayId, displayEvent.event);
                 }
                 return true;
diff --git a/services/core/java/com/android/server/display/DisplayManagerShellCommand.java b/services/core/java/com/android/server/display/DisplayManagerShellCommand.java
index f6b2591..e23756f 100644
--- a/services/core/java/com/android/server/display/DisplayManagerShellCommand.java
+++ b/services/core/java/com/android/server/display/DisplayManagerShellCommand.java
@@ -112,6 +112,8 @@
                 return requestDisplayPower(Display.STATE_UNKNOWN);
             case "power-off":
                 return requestDisplayPower(Display.STATE_OFF);
+            case "override-max-importance-rr-callbacks":
+                return overrideMaxImportanceForRRCallbacks();
             default:
                 return handleDefaultCommands(cmd);
         }
@@ -631,4 +633,21 @@
         mService.requestDisplayPower(displayId, state);
         return 0;
     }
+
+    private int overrideMaxImportanceForRRCallbacks() {
+        final String importanceString = getNextArg();
+        if (importanceString == null) {
+            getErrPrintWriter().println("Error: no importance specified");
+            return 1;
+        }
+        final int importance;
+        try {
+            importance = Integer.parseInt(importanceString);
+        } catch (NumberFormatException e) {
+            getErrPrintWriter().println("Error: invalid importance: '" + importanceString + "'");
+            return 1;
+        }
+        mService.overrideMaxImportanceForRRCallbacks(importance);
+        return 0;
+    }
 }
diff --git a/services/core/java/com/android/server/display/feature/DisplayManagerFlags.java b/services/core/java/com/android/server/display/feature/DisplayManagerFlags.java
index 72306ae..d435144 100644
--- a/services/core/java/com/android/server/display/feature/DisplayManagerFlags.java
+++ b/services/core/java/com/android/server/display/feature/DisplayManagerFlags.java
@@ -268,6 +268,11 @@
             Flags::framerateOverrideTriggersRrCallbacks
     );
 
+    private final FlagState mRefreshRateEventForForegroundApps = new FlagState(
+            Flags.FLAG_REFRESH_RATE_EVENT_FOR_FOREGROUND_APPS,
+            Flags::refreshRateEventForForegroundApps
+    );
+
     /**
      * @return {@code true} if 'port' is allowed in display layout configuration file.
      */
@@ -579,6 +584,14 @@
 
 
     /**
+     * @return {@code true} if the flag for sending refresh rate events only for the apps in
+     * foreground is enabled
+     */
+    public boolean isRefreshRateEventForForegroundAppsEnabled() {
+        return mRefreshRateEventForForegroundApps.isEnabled();
+    }
+
+    /**
      * dumps all flagstates
      * @param pw printWriter
      */
@@ -634,7 +647,7 @@
         pw.println(" " + mEnableDisplayContentModeManagementFlagState);
         pw.println(" " + mBaseDensityForExternalDisplays);
         pw.println(" " + mFramerateOverrideTriggersRrCallbacks);
-
+        pw.println(" " + mRefreshRateEventForForegroundApps);
     }
 
     private static class FlagState {
diff --git a/services/core/java/com/android/server/display/feature/display_flags.aconfig b/services/core/java/com/android/server/display/feature/display_flags.aconfig
index 1cd0505..63cd2d7 100644
--- a/services/core/java/com/android/server/display/feature/display_flags.aconfig
+++ b/services/core/java/com/android/server/display/feature/display_flags.aconfig
@@ -486,6 +486,17 @@
     description: "Feature flag to trigger the RR callbacks when framerate overridding happens."
     bug: "390113266"
     is_fixed_read_only: true
+        metadata {
+          purpose: PURPOSE_BUGFIX
+        }
+}
+
+flag {
+    name: "refresh_rate_event_for_foreground_apps"
+    namespace: "display_manager"
+    description: "Send Refresh Rate events only for the apps in foreground."
+    bug: "390107600"
+    is_fixed_read_only: true
     metadata {
       purpose: PURPOSE_BUGFIX
     }
diff --git a/services/core/java/com/android/server/pm/InstallPackageHelper.java b/services/core/java/com/android/server/pm/InstallPackageHelper.java
index b043d13..8eb5b6f 100644
--- a/services/core/java/com/android/server/pm/InstallPackageHelper.java
+++ b/services/core/java/com/android/server/pm/InstallPackageHelper.java
@@ -863,6 +863,9 @@
                 // restore if appropriate, then pass responsibility back to the
                 // Package Manager to run the post-install observer callbacks
                 // and broadcasts.
+                // Note: MUST close freezer before backup/restore, otherwise test
+                // of CtsBackupHostTestCases will fail.
+                request.closeFreezer();
                 doRestore = performBackupManagerRestore(userId, token, request);
             }
 
diff --git a/services/core/java/com/android/server/power/OWNERS b/services/core/java/com/android/server/power/OWNERS
index c1fad33..a1531a8 100644
--- a/services/core/java/com/android/server/power/OWNERS
+++ b/services/core/java/com/android/server/power/OWNERS
@@ -2,6 +2,8 @@
 santoscordon@google.com
 petsjonkin@google.com
 brup@google.com
+flc@google.com
+wilczynskip@google.com
 
 per-file ThermalManagerService.java=file:/THERMAL_OWNERS
 per-file LowPowerStandbyController.java=qingxun@google.com
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java b/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java
index 76d16e1..a81a0b3 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java
@@ -73,9 +73,6 @@
 
 class ActiveAdmin {
 
-    private final int userId;
-    public final boolean isPermissionBased;
-
     private static final String TAG_DISABLE_KEYGUARD_FEATURES = "disable-keyguard-features";
     private static final String TAG_TEST_ONLY_ADMIN = "test-only-admin";
     private static final String TAG_DISABLE_CAMERA = "disable-camera";
@@ -364,23 +361,8 @@
     private static final int PROVISIONING_CONTEXT_LENGTH_LIMIT = 1000;
 
     ActiveAdmin(DeviceAdminInfo info, boolean isParent) {
-        this.userId = -1;
         this.info = info;
         this.isParent = isParent;
-        this.isPermissionBased = false;
-    }
-
-    ActiveAdmin(int userId, boolean permissionBased) {
-        if (Flags.activeAdminCleanup()) {
-            throw new UnsupportedOperationException("permission based admin no longer supported");
-        }
-        if (permissionBased == false) {
-            throw new IllegalArgumentException("Can only pass true for permissionBased admin");
-        }
-        this.userId = userId;
-        this.isPermissionBased = permissionBased;
-        this.isParent = false;
-        this.info = null;
     }
 
     ActiveAdmin getParentActiveAdmin() {
@@ -397,16 +379,10 @@
     }
 
     int getUid() {
-        if (isPermissionBased) {
-            return -1;
-        }
         return info.getActivityInfo().applicationInfo.uid;
     }
 
     public UserHandle getUserHandle() {
-        if (isPermissionBased) {
-            return UserHandle.of(userId);
-        }
         return UserHandle.of(UserHandle.getUserId(info.getActivityInfo().applicationInfo.uid));
     }
 
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyData.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyData.java
index c937e10..89c8b56 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyData.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyData.java
@@ -21,7 +21,6 @@
 import android.annotation.UserIdInt;
 import android.app.admin.DeviceAdminInfo;
 import android.app.admin.DevicePolicyManager;
-import android.app.admin.flags.Flags;
 import android.content.ComponentName;
 import android.os.FileUtils;
 import android.os.PersistableBundle;
@@ -125,24 +124,6 @@
     final ArrayList<ActiveAdmin> mAdminList = new ArrayList<>();
     final ArrayList<ComponentName> mRemovingAdmins = new ArrayList<>();
 
-    /**
-     * @deprecated Do not use. Policies set by permission holders must go into DevicePolicyEngine.
-     */
-    @Deprecated
-    ActiveAdmin mPermissionBasedAdmin;
-
-    // Create or get the permission-based admin. The permission-based admin will not have a
-    // DeviceAdminInfo or ComponentName.
-    ActiveAdmin createOrGetPermissionBasedAdmin(int userId) {
-        if (Flags.activeAdminCleanup()) {
-            throw new UnsupportedOperationException("permission based admin no longer supported");
-        }
-        if (mPermissionBasedAdmin == null) {
-            mPermissionBasedAdmin = new ActiveAdmin(userId, /* permissionBased= */ true);
-        }
-        return mPermissionBasedAdmin;
-    }
-
     // TODO(b/35385311): Keep track of metadata in TrustedCertificateStore instead.
     final ArraySet<String> mAcceptedCaCertificates = new ArraySet<>();
 
@@ -282,12 +263,6 @@
                 }
             }
 
-            if (!Flags.activeAdminCleanup() && policyData.mPermissionBasedAdmin != null) {
-                out.startTag(null, "permission-based-admin");
-                policyData.mPermissionBasedAdmin.writeToXml(out);
-                out.endTag(null, "permission-based-admin");
-            }
-
             if (policyData.mPasswordOwner >= 0) {
                 out.startTag(null, "password-owner");
                 out.attributeInt(null, "value", policyData.mPasswordOwner);
@@ -495,7 +470,6 @@
             policy.mLockTaskPackages.clear();
             policy.mAdminList.clear();
             policy.mAdminMap.clear();
-            policy.mPermissionBasedAdmin = null;
             policy.mAffiliationIds.clear();
             policy.mOwnerInstalledCaCerts.clear();
             policy.mUserControlDisabledPackages = null;
@@ -523,11 +497,6 @@
                     } catch (RuntimeException e) {
                         Slogf.w(TAG, e, "Failed loading admin %s", name);
                     }
-                } else if (!Flags.activeAdminCleanup() && "permission-based-admin".equals(tag)) {
-
-                    ActiveAdmin ap = new ActiveAdmin(policy.mUserId, /* permissionBased= */ true);
-                    ap.readFromXml(parser, /* overwritePolicies= */ false);
-                    policy.mPermissionBasedAdmin = ap;
                 } else if ("delegation".equals(tag)) {
                     // Parse delegation info.
                     final String delegatePackage = parser.getAttributeValue(null,
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
index e960abd..4c2c858 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
@@ -3448,8 +3448,8 @@
         EnforcingAdmin enforcingAdmin =
                 EnforcingAdmin.createEnterpriseEnforcingAdmin(
                         admin.info.getComponent(),
-                        admin.getUserHandle().getIdentifier(),
-                        admin);
+                        admin.getUserHandle().getIdentifier()
+                );
         mDevicePolicyEngine.setGlobalPolicy(
                 PolicyDefinition.SECURITY_LOGGING,
                 enforcingAdmin,
@@ -3692,8 +3692,8 @@
         int userId = admin.getUserHandle().getIdentifier();
         EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
                 admin.info.getComponent(),
-                userId,
-                admin);
+                userId
+        );
 
         Integer passwordComplexity = mDevicePolicyEngine.getLocalPolicySetByAdmin(
                 PolicyDefinition.PASSWORD_COMPLEXITY,
@@ -3985,8 +3985,7 @@
             final int N = admins.size();
             for (int i = 0; i < N; i++) {
                 ActiveAdmin admin = admins.get(i);
-                if (((!Flags.activeAdminCleanup() && admin.isPermissionBased)
-                        || admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD))
+                if ((admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD))
                         && admin.passwordExpirationTimeout > 0L
                         && now >= admin.passwordExpirationDate - EXPIRATION_GRACE_PERIOD_MS
                         && admin.passwordExpirationDate > 0L) {
@@ -4167,10 +4166,10 @@
 
         EnforcingAdmin oldAdmin =
                 EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        outgoingReceiver, userHandle, adminToTransfer);
+                        outgoingReceiver, userHandle);
         EnforcingAdmin newAdmin =
                 EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        incomingReceiver, userHandle, adminToTransfer);
+                        incomingReceiver, userHandle);
 
         mDevicePolicyEngine.transferPolicies(oldAdmin, newAdmin);
 
@@ -4470,7 +4469,7 @@
         }
         mDevicePolicyEngine.removePoliciesForAdmin(
                 EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        adminReceiver, userHandle, admin));
+                        adminReceiver, userHandle));
     }
 
     private boolean canSetPasswordQualityOnParent(String packageName, final CallerIdentity caller) {
@@ -4525,10 +4524,8 @@
                     who, DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD, parent);
 
             if (Flags.unmanagedModeMigration()) {
-                enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(who,
-                        userId,
-                        getActiveAdminForCallerLocked(who,
-                                DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD));
+                getActiveAdminForCallerLocked(who, DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
+                enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(who, userId);
             }
             // If setPasswordQuality is called on the parent, ensure that
             // the primary admin does not have password complexity state (this is an
@@ -5584,17 +5581,13 @@
         Preconditions.checkArgument(!calledOnParent || isProfileOwner(caller));
 
         final ActiveAdmin activeAdmin;
-        if (Flags.activeAdminCleanup()) {
-            if (admin.hasAuthority(EnforcingAdmin.DPC_AUTHORITY)) {
-                synchronized (getLockObject()) {
-                    activeAdmin = getActiveAdminUncheckedLocked(
-                            admin.getComponentName(), admin.getUserId());
-                }
-            } else {
-                activeAdmin = null;
+        if (admin.hasAuthority(EnforcingAdmin.DPC_AUTHORITY)) {
+            synchronized (getLockObject()) {
+                activeAdmin = getActiveAdminUncheckedLocked(
+                        admin.getComponentName(), admin.getUserId());
             }
         } else {
-            activeAdmin = admin.getActiveAdmin();
+            activeAdmin = null;
         }
 
         // We require the caller to explicitly clear any password quality requirements set
@@ -6331,12 +6324,7 @@
                         caller.getPackageName(),
                         getAffectedUser(parent)
                 );
-                if (Flags.activeAdminCleanup()) {
-                    adminComponent = enforcingAdmin.getComponentName();
-                } else {
-                    ActiveAdmin admin = enforcingAdmin.getActiveAdmin();
-                    adminComponent = admin == null ? null : admin.info.getComponent();
-                }
+                adminComponent = enforcingAdmin.getComponentName();
             } else {
                 ActiveAdmin admin = getActiveAdminOrCheckPermissionForCallerLocked(
                         null,
@@ -7824,19 +7812,9 @@
                     calledByProfileOwnerOnOrgOwnedDevice, calledOnParentInstance);
         }
 
-        int userId;
-        ActiveAdmin admin = null;
-        if (Flags.activeAdminCleanup()) {
-            userId = enforcingAdmin.getUserId();
-            Slogf.i(LOG_TAG, "wipeDataWithReason(%s): admin=%s, user=%d", wipeReasonForUser,
-                    enforcingAdmin, userId);
-        } else {
-            admin = enforcingAdmin.getActiveAdmin();
-            userId = admin != null ? admin.getUserHandle().getIdentifier()
-                    : caller.getUserId();
-            Slogf.i(LOG_TAG, "wipeDataWithReason(%s): admin=%s, user=%d", wipeReasonForUser, admin,
-                    userId);
-        }
+        int userId = enforcingAdmin.getUserId();
+        Slogf.i(LOG_TAG, "wipeDataWithReason(%s): admin=%s, user=%d", wipeReasonForUser,
+                enforcingAdmin, userId);
 
         if (calledByProfileOwnerOnOrgOwnedDevice) {
             // When wipeData is called on the parent instance, it implies wiping the entire device.
@@ -7858,38 +7836,14 @@
 
         final String adminName;
         final ComponentName adminComp;
-        if (Flags.activeAdminCleanup()) {
-            adminComp = enforcingAdmin.getComponentName();
-            adminName = adminComp != null
-                    ? adminComp.flattenToShortString()
-                    : enforcingAdmin.getPackageName();
-            event.setAdmin(enforcingAdmin.getPackageName());
-            // Not including any HSUM handling here because the "else" branch in the "flag off"
-            // case below is unreachable under normal circumstances and for permission-based
-            // callers admin won't be null.
-        } else {
-            if (admin != null) {
-                if (admin.isPermissionBased) {
-                    adminComp = null;
-                    adminName = caller.getPackageName();
-                    event.setAdmin(adminName);
-                } else {
-                    adminComp = admin.info.getComponent();
-                    adminName = adminComp.flattenToShortString();
-                    event.setAdmin(adminComp);
-                }
-            } else {
-                adminComp = null;
-                adminName = mInjector.getPackageManager().getPackagesForUid(caller.getUid())[0];
-                Slogf.i(LOG_TAG, "Logging wipeData() event admin as " + adminName);
-                event.setAdmin(adminName);
-                if (mInjector.userManagerIsHeadlessSystemUserMode()) {
-                    // On headless system user mode, the call is meant to factory reset the whole
-                    // device, otherwise the caller could simply remove the current user.
-                    userId = UserHandle.USER_SYSTEM;
-                }
-            }
-        }
+        adminComp = enforcingAdmin.getComponentName();
+        adminName = adminComp != null
+                ? adminComp.flattenToShortString()
+                : enforcingAdmin.getPackageName();
+        event.setAdmin(enforcingAdmin.getPackageName());
+        // Not including any HSUM handling here because the "else" branch in the "flag off"
+        // case below is unreachable under normal circumstances and for permission-based
+        // callers admin won't be null.
         event.write();
 
         String internalReason = String.format(
@@ -8375,8 +8329,7 @@
         List<ActiveAdmin> admins = getActiveAdminsForLockscreenPoliciesLocked(userHandle);
         for (int i = 0; i < admins.size(); i++) {
             ActiveAdmin admin = admins.get(i);
-            if ((!Flags.activeAdminCleanup() && admin.isPermissionBased)
-                    || admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD)) {
+            if (admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD)) {
                 affectedUserIds.add(admin.getUserHandle().getIdentifier());
                 long timeout = admin.passwordExpirationTimeout;
                 admin.passwordExpirationDate =
@@ -8470,9 +8423,6 @@
      */
     private int getUserIdToWipeForFailedPasswords(ActiveAdmin admin) {
         final int userId = admin.getUserHandle().getIdentifier();
-        if (!Flags.activeAdminCleanup() && admin.isPermissionBased) {
-            return userId;
-        }
         final ComponentName component = admin.info.getComponent();
         return isProfileOwnerOfOrganizationOwnedDevice(component, userId)
                 ? getProfileParentId(userId) : userId;
@@ -10282,8 +10232,7 @@
         setGlobalSettingDeviceOwnerType(DEVICE_OWNER_TYPE_DEFAULT);
 
         mDevicePolicyEngine.removePoliciesForAdmin(
-                EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        admin.info.getComponent(), userId, admin));
+                EnforcingAdmin.createEnterpriseEnforcingAdmin(admin.info.getComponent(), userId));
     }
 
     private void clearApplicationRestrictions(int userId) {
@@ -10433,8 +10382,7 @@
         setNetworkLoggingActiveInternal(false);
 
         mDevicePolicyEngine.removePoliciesForAdmin(
-                EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        admin.info.getComponent(), userId, admin));
+                EnforcingAdmin.createEnterpriseEnforcingAdmin(admin.info.getComponent(), userId));
     }
 
     @Override
@@ -16449,8 +16397,7 @@
         if (admin.mPasswordPolicy.quality < minPasswordQuality) {
             return false;
         }
-        return (!Flags.activeAdminCleanup() && admin.isPermissionBased)
-                || admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
+        return admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD);
     }
 
     @Override
@@ -20918,8 +20865,7 @@
         if (profileOwner != null) {
             EnforcingAdmin admin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
                     profileOwner.info.getComponent(),
-                    profileUserId,
-                    profileOwner);
+                    profileUserId);
             mDevicePolicyEngine.setLocalPolicy(
                     PolicyDefinition.PERSONAL_APPS_SUSPENDED,
                     admin,
@@ -23517,27 +23463,6 @@
      *
      * @param callerPackageName The package name  of the calling application.
      * @param adminPolicy The admin policy that should grant holders permission.
-     * @param permission The name of the permission being checked.
-     * @param targetUserId The userId of the user which the caller needs permission to act on.
-     * @throws SecurityException if the caller has not been granted the given permission,
-     * the associated cross-user permission if the caller's user is different to the target user.
-     */
-    private void enforcePermission(String permission, int adminPolicy,
-            String callerPackageName, int targetUserId) throws SecurityException {
-        if (hasAdminPolicy(adminPolicy, callerPackageName)) {
-            return;
-        }
-        enforcePermission(permission, callerPackageName, targetUserId);
-    }
-
-    /**
-     * Checks if the calling process has been granted permission to apply a device policy on a
-     * specific user.
-     * The given permission will be checked along with its associated cross-user permission if it
-     * exists and the target user is different to the calling user.
-     *
-     * @param callerPackageName The package name  of the calling application.
-     * @param adminPolicy The admin policy that should grant holders permission.
      * @param permissions The names of the permissions being checked.
      * @param targetUserId The userId of the user which the caller needs permission to act on.
      * @throws SecurityException if the caller has not been granted the given permission,
@@ -23670,24 +23595,21 @@
             ComponentName component;
             synchronized (getLockObject()) {
                 if (who != null) {
-                    admin = getActiveAdminUncheckedLocked(who, userId);
                     component = who;
                 } else {
                     admin = getDeviceOrProfileOwnerAdminLocked(userId);
                     component = admin.info.getComponent();
                 }
             }
-            return EnforcingAdmin.createEnterpriseEnforcingAdmin(component, userId, admin);
+            return EnforcingAdmin.createEnterpriseEnforcingAdmin(component, userId);
         }
-        // Check for non-DPC active admins.
+        // Check for DA active admins.
         admin = getActiveAdminForCaller(who, caller);
         if (admin != null) {
-            return EnforcingAdmin.createDeviceAdminEnforcingAdmin(admin.info.getComponent(), userId,
-                    admin);
+            return EnforcingAdmin.createDeviceAdminEnforcingAdmin(
+                    admin.info.getComponent(), userId);
         }
-        admin = Flags.activeAdminCleanup()
-                ? null : getUserData(userId).createOrGetPermissionBasedAdmin(userId);
-        return  EnforcingAdmin.createEnforcingAdmin(caller.getPackageName(), userId, admin);
+        return EnforcingAdmin.createEnforcingAdmin(caller.getPackageName(), userId);
     }
 
     private EnforcingAdmin getEnforcingAdminForPackage(@Nullable ComponentName who,
@@ -23699,19 +23621,17 @@
                     admin = getActiveAdminUncheckedLocked(who, userId);
                 }
                 if (admin != null) {
-                    return EnforcingAdmin.createEnterpriseEnforcingAdmin(who, userId, admin);
+                    return EnforcingAdmin.createEnterpriseEnforcingAdmin(who, userId);
                 }
             } else {
-                // Check for non-DPC active admins.
+                // Check for DA active admins.
                 admin = getActiveAdminUncheckedLocked(who, userId);
                 if (admin != null) {
-                    return EnforcingAdmin.createDeviceAdminEnforcingAdmin(who, userId, admin);
+                    return EnforcingAdmin.createDeviceAdminEnforcingAdmin(who, userId);
                 }
             }
         }
-        admin = Flags.activeAdminCleanup()
-                ? null : getUserData(userId).createOrGetPermissionBasedAdmin(userId);
-        return  EnforcingAdmin.createEnforcingAdmin(packageName, userId, admin);
+        return EnforcingAdmin.createEnforcingAdmin(packageName, userId);
     }
 
     private int getAffectedUser(boolean calledOnParent) {
@@ -24427,9 +24347,7 @@
                     && admin.getParentActiveAdmin().disableScreenCapture))) {
 
                 EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        admin.info.getComponent(),
-                        admin.getUserHandle().getIdentifier(),
-                        admin);
+                        admin.info.getComponent(), admin.getUserHandle().getIdentifier());
                 mDevicePolicyEngine.setGlobalPolicy(
                         PolicyDefinition.SCREEN_CAPTURE_DISABLED,
                         enforcingAdmin,
@@ -24442,8 +24360,7 @@
                 if (profileOwner != null && profileOwner.disableScreenCapture) {
                     EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
                             profileOwner.info.getComponent(),
-                            profileOwner.getUserHandle().getIdentifier(),
-                            profileOwner);
+                            profileOwner.getUserHandle().getIdentifier());
                     mDevicePolicyEngine.setLocalPolicy(
                             PolicyDefinition.SCREEN_CAPTURE_DISABLED,
                             enforcingAdmin,
@@ -24485,10 +24402,7 @@
     private void setLockTaskPolicyInPolicyEngine(
             ActiveAdmin admin, int userId, List<String> packages, int features) {
         EnforcingAdmin enforcingAdmin =
-                EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        admin.info.getComponent(),
-                        userId,
-                        admin);
+                EnforcingAdmin.createEnterpriseEnforcingAdmin(admin.info.getComponent(), userId);
         mDevicePolicyEngine.setLocalPolicy(
                 PolicyDefinition.LOCK_TASK,
                 enforcingAdmin,
@@ -24503,9 +24417,7 @@
                 ActiveAdmin admin = getProfileOwnerOrDeviceOwnerLocked(userInfo.id);
                 if (admin != null) {
                     EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                            admin.info.getComponent(),
-                            admin.getUserHandle().getIdentifier(),
-                            admin);
+                            admin.info.getComponent(), admin.getUserHandle().getIdentifier());
                     if (admin.permittedInputMethods != null) {
                         mDevicePolicyEngine.setLocalPolicy(
                                 PolicyDefinition.PERMITTED_INPUT_METHODS,
@@ -24536,9 +24448,7 @@
                 ActiveAdmin admin = getProfileOwnerOrDeviceOwnerLocked(userInfo.id);
                 if (admin != null) {
                     EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                            admin.info.getComponent(),
-                            admin.getUserHandle().getIdentifier(),
-                            admin);
+                            admin.info.getComponent(), admin.getUserHandle().getIdentifier());
                     for (String accountType : admin.accountTypesWithManagementDisabled) {
                         mDevicePolicyEngine.setLocalPolicy(
                                 PolicyDefinition.ACCOUNT_MANAGEMENT_DISABLED(accountType),
@@ -24569,9 +24479,7 @@
                 ActiveAdmin admin = getProfileOwnerOrDeviceOwnerLocked(userInfo.id);
                 if (admin != null && admin.protectedPackages != null) {
                     EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                            admin.info.getComponent(),
-                            admin.getUserHandle().getIdentifier(),
-                            admin);
+                            admin.info.getComponent(), admin.getUserHandle().getIdentifier());
                     if (isDeviceOwner(admin)) {
                         mDevicePolicyEngine.setGlobalPolicy(
                                 PolicyDefinition.USER_CONTROLLED_DISABLED_PACKAGES,
@@ -24599,10 +24507,8 @@
                 if (admin == null) continue;
                 ComponentName adminComponent = admin.info.getComponent();
                 int userId = userInfo.id;
-                EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        adminComponent,
-                        userId,
-                        admin);
+                EnforcingAdmin enforcingAdmin =
+                        EnforcingAdmin.createEnterpriseEnforcingAdmin(adminComponent, userId);
                 int ownerType;
                 if (isDeviceOwner(admin)) {
                     ownerType = OWNER_TYPE_DEVICE_OWNER;
@@ -24635,9 +24541,7 @@
                 ActiveAdmin admin = getProfileOwnerOrDeviceOwnerLocked(userInfo.id);
                 if (admin == null) continue;
                 EnforcingAdmin enforcingAdmin = EnforcingAdmin.createEnterpriseEnforcingAdmin(
-                        admin.info.getComponent(),
-                        userInfo.id,
-                        admin);
+                        admin.info.getComponent(), userInfo.id);
 
                 runner.accept(admin, enforcingAdmin);
             }
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/EnforcingAdmin.java b/services/devicepolicy/java/com/android/server/devicepolicy/EnforcingAdmin.java
index 5a0b079..aca3315 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/EnforcingAdmin.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/EnforcingAdmin.java
@@ -23,7 +23,6 @@
 import android.app.admin.DpcAuthority;
 import android.app.admin.RoleAuthority;
 import android.app.admin.UnknownAuthority;
-import android.app.admin.flags.Flags;
 import android.content.ComponentName;
 import android.os.UserHandle;
 
@@ -80,36 +79,24 @@
     private final int mUserId;
     private final boolean mIsRoleAuthority;
     private final boolean mIsSystemAuthority;
-    private final ActiveAdmin mActiveAdmin;
 
-    static EnforcingAdmin createEnforcingAdmin(@NonNull String packageName, int userId,
-            ActiveAdmin admin) {
+    static EnforcingAdmin createEnforcingAdmin(@NonNull String packageName, int userId) {
         Objects.requireNonNull(packageName);
-        return new EnforcingAdmin(packageName, userId, admin);
+        return new EnforcingAdmin(packageName, userId);
     }
 
     static EnforcingAdmin createEnterpriseEnforcingAdmin(
             @NonNull ComponentName componentName, int userId) {
         Objects.requireNonNull(componentName);
         return new EnforcingAdmin(
-                componentName.getPackageName(), componentName, Set.of(DPC_AUTHORITY), userId,
-                /* activeAdmin=*/ null);
+                componentName.getPackageName(), componentName, Set.of(DPC_AUTHORITY), userId);
     }
 
-    static EnforcingAdmin createEnterpriseEnforcingAdmin(
-            @NonNull ComponentName componentName, int userId, ActiveAdmin activeAdmin) {
-        Objects.requireNonNull(componentName);
-        return new EnforcingAdmin(
-                componentName.getPackageName(), componentName, Set.of(DPC_AUTHORITY), userId,
-                activeAdmin);
-    }
-
-    static EnforcingAdmin createDeviceAdminEnforcingAdmin(ComponentName componentName, int userId,
-            ActiveAdmin activeAdmin) {
+    static EnforcingAdmin createDeviceAdminEnforcingAdmin(ComponentName componentName, int userId) {
         Objects.requireNonNull(componentName);
         return new EnforcingAdmin(
                 componentName.getPackageName(), componentName, Set.of(DEVICE_ADMIN_AUTHORITY),
-                userId, activeAdmin);
+                userId);
     }
 
     static EnforcingAdmin createSystemEnforcingAdmin(@NonNull String systemEntity) {
@@ -124,24 +111,20 @@
         if (DpcAuthority.DPC_AUTHORITY.equals(authority)) {
             return new EnforcingAdmin(
                     admin.getPackageName(), admin.getComponentName(),
-                    Set.of(DPC_AUTHORITY), admin.getUserHandle().getIdentifier(),
-                    /* activeAdmin = */ null);
+                    Set.of(DPC_AUTHORITY), admin.getUserHandle().getIdentifier());
         } else if (DeviceAdminAuthority.DEVICE_ADMIN_AUTHORITY.equals(authority)) {
             return new EnforcingAdmin(
                     admin.getPackageName(), admin.getComponentName(),
-                    Set.of(DEVICE_ADMIN_AUTHORITY), admin.getUserHandle().getIdentifier(),
-                    /* activeAdmin = */ null);
+                    Set.of(DEVICE_ADMIN_AUTHORITY), admin.getUserHandle().getIdentifier());
         } else if (authority instanceof RoleAuthority roleAuthority) {
             return new EnforcingAdmin(
                     admin.getPackageName(), admin.getComponentName(),
                     Set.of(DEVICE_ADMIN_AUTHORITY), admin.getUserHandle().getIdentifier(),
-                    /* activeAdmin = */ null,
                     /* isRoleAuthority = */ true);
         }
         // TODO(b/324899199): Consider supporting android.app.admin.SystemAuthority.
         return new EnforcingAdmin(admin.getPackageName(), admin.getComponentName(),
-                Set.of(), admin.getUserHandle().getIdentifier(),
-                /* activeAdmin = */ null);
+                Set.of(), admin.getUserHandle().getIdentifier());
     }
 
     static String getRoleAuthorityOf(String roleName) {
@@ -167,7 +150,7 @@
 
     private EnforcingAdmin(
             String packageName, @Nullable ComponentName componentName, Set<String> authorities,
-            int userId, @Nullable ActiveAdmin activeAdmin) {
+            int userId) {
         Objects.requireNonNull(packageName);
         Objects.requireNonNull(authorities);
 
@@ -179,10 +162,9 @@
         mComponentName = componentName;
         mAuthorities = new HashSet<>(authorities);
         mUserId = userId;
-        mActiveAdmin = activeAdmin;
     }
 
-    private EnforcingAdmin(String packageName, int userId, ActiveAdmin activeAdmin) {
+    private EnforcingAdmin(String packageName, int userId) {
         Objects.requireNonNull(packageName);
 
         // Only role authorities use this constructor.
@@ -194,7 +176,6 @@
         mComponentName = null;
         // authorities will be loaded when needed
         mAuthorities = null;
-        mActiveAdmin = activeAdmin;
     }
 
     /** Constructor for System authorities. */
@@ -210,12 +191,11 @@
         mUserId = UserHandle.USER_SYSTEM;
         mComponentName = null;
         mAuthorities = getSystemAuthority(systemEntity);
-        mActiveAdmin = null;
     }
 
     private EnforcingAdmin(
             String packageName, @Nullable ComponentName componentName, Set<String> authorities,
-            int userId, @Nullable ActiveAdmin activeAdmin, boolean isRoleAuthority) {
+            int userId, boolean isRoleAuthority) {
         Objects.requireNonNull(packageName);
         Objects.requireNonNull(authorities);
 
@@ -226,7 +206,6 @@
         mComponentName = componentName;
         mAuthorities = new HashSet<>(authorities);
         mUserId = userId;
-        mActiveAdmin = activeAdmin;
     }
 
     private static Set<String> getRoleAuthoritiesOrDefault(String packageName, int userId) {
@@ -295,14 +274,6 @@
     }
 
     @Nullable
-    public ActiveAdmin getActiveAdmin() {
-        if (Flags.activeAdminCleanup()) {
-            throw new UnsupportedOperationException("getActiveAdmin() no longer supported");
-        }
-        return mActiveAdmin;
-    }
-
-    @Nullable
     ComponentName getComponentName() {
         return mComponentName;
     }
@@ -419,7 +390,7 @@
                 return null;
             }
             // TODO(b/281697976): load active admin
-            return new EnforcingAdmin(packageName, userId, null);
+            return new EnforcingAdmin(packageName, userId);
         } else if (isSystemAuthority) {
             if (systemEntity == null) {
                 Slogf.wtf(TAG, "Error parsing EnforcingAdmin with SystemAuthority, "
@@ -439,7 +410,7 @@
                     ? null :  new ComponentName(packageName, className);
             Set<String> authorities = Set.of(authoritiesStr.split(ATTR_AUTHORITIES_SEPARATOR));
             // TODO(b/281697976): load active admin
-            return new EnforcingAdmin(packageName, componentName, authorities, userId, null);
+            return new EnforcingAdmin(packageName, componentName, authorities, userId);
         }
     }
 
diff --git a/services/tests/displayservicetests/src/com/android/server/display/DisplayManagerServiceTest.java b/services/tests/displayservicetests/src/com/android/server/display/DisplayManagerServiceTest.java
index 8e4d8ed..e8b28ac 100644
--- a/services/tests/displayservicetests/src/com/android/server/display/DisplayManagerServiceTest.java
+++ b/services/tests/displayservicetests/src/com/android/server/display/DisplayManagerServiceTest.java
@@ -23,6 +23,7 @@
 import static android.Manifest.permission.CONTROL_DISPLAY_BRIGHTNESS;
 import static android.Manifest.permission.MANAGE_DISPLAYS;
 import static android.Manifest.permission.MODIFY_USER_PREFERRED_DISPLAY_MODE;
+import static android.app.ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND;
 import static android.hardware.display.DisplayManager.SWITCHING_TYPE_NONE;
 import static android.hardware.display.DisplayManager.VIRTUAL_DISPLAY_FLAG_ALWAYS_UNLOCKED;
 import static android.hardware.display.DisplayManager.VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR;
@@ -2344,6 +2345,29 @@
         callback.clear();
     }
 
+    @Test
+    public void test_doesNotNotifyRefreshRateChanged_whenAppInBackground() {
+        when(mMockFlags.isRefreshRateEventForForegroundAppsEnabled()).thenReturn(true);
+        DisplayManagerService displayManager =
+                new DisplayManagerService(mContext, mBasicInjector);
+        DisplayManagerService.BinderService displayManagerBinderService =
+                displayManager.new BinderService();
+        displayManager.windowManagerAndInputReady();
+        registerDefaultDisplays(displayManager);
+        displayManager.onBootPhase(SystemService.PHASE_WAIT_FOR_DEFAULT_DISPLAY);
+
+        FakeDisplayDevice displayDevice = createFakeDisplayDevice(displayManager, new float[]{60f});
+        FakeDisplayManagerCallback callback = registerDisplayListenerCallback(displayManager,
+                displayManagerBinderService, displayDevice);
+
+        when(mMockActivityManagerInternal.getUidProcessState(Process.myUid()))
+                .thenReturn(PROCESS_STATE_TRANSIENT_BACKGROUND);
+        updateRenderFrameRate(displayManager, displayDevice, 30f);
+        waitForIdleHandler(displayManager.getDisplayHandler());
+        assertEquals(0, callback.receivedEvents().size());
+        callback.clear();
+    }
+
     /**
      * Tests that the DisplayInfo is updated correctly with a render frame rate
      */
diff --git a/services/tests/mockingservicestests/src/com/android/server/power/ScreenUndimDetectorTest.java b/services/tests/mockingservicestests/src/com/android/server/power/ScreenUndimDetectorTest.java
index e8e1dac..8ce05e2 100644
--- a/services/tests/mockingservicestests/src/com/android/server/power/ScreenUndimDetectorTest.java
+++ b/services/tests/mockingservicestests/src/com/android/server/power/ScreenUndimDetectorTest.java
@@ -40,6 +40,7 @@
 
 import org.junit.After;
 import org.junit.Before;
+import org.junit.Ignore;
 import org.junit.ClassRule;
 import org.junit.Rule;
 import org.junit.Test;
@@ -329,6 +330,7 @@
         }
     }
 
+    @Ignore("b/387389929")
     @Test
     public void recordScreenPolicy_otherTransitions_doesNotReset() {
         DeviceConfig.setProperty(NAMESPACE_ATTENTION_MANAGER_SERVICE,
diff --git a/telecomm/java/android/telecom/Call.java b/telecomm/java/android/telecom/Call.java
index a52614d..531f516 100644
--- a/telecomm/java/android/telecom/Call.java
+++ b/telecomm/java/android/telecom/Call.java
@@ -52,6 +52,8 @@
  * Represents an ongoing phone call that the in-call app should present to the user.
  */
 public final class Call {
+    private static final String LOG_TAG = "TelecomCall";
+
     /**
      * The state of a {@code Call} when newly created.
      */
@@ -2912,6 +2914,11 @@
                     }
                 } catch (BadParcelableException e) {
                     return false;
+                } catch (ClassCastException e) {
+                    Log.e(LOG_TAG, e, "areBundlesEqual: failure comparing bundle key %s", key);
+                    // until we know what is causing this, we should rethrow -- this is still not
+                    // expected.
+                    throw e;
                 }
             }
         }