Merge "Ensure device unlocked for screenshot tests." into tm-dev
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgradeWrongSHA_apk.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgradeWrongSHA_apk.asciipb
index f866875..a9d7348 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgradeWrongSHA_apk.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgradeWrongSHA_apk.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/CtsShimPrivUpgradeWrongSHA.apk"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgrade_apk.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgrade_apk.asciipb
index ccefcc1..62ab040 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgrade_apk.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__arm_CtsShimPrivUpgrade_apk.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/CtsShimPrivUpgrade.apk"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgradeWrongSHA_apk.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgradeWrongSHA_apk.asciipb
index 264169d..a20b738 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgradeWrongSHA_apk.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgradeWrongSHA_apk.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/CtsShimPrivUpgradeWrongSHA.apk"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgrade_apk.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgrade_apk.asciipb
index 543d7cc..3371432 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgrade_apk.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_appsecurity_test-apps_PrivilegedUpdateApp_apk__x86_CtsShimPrivUpgrade_apk.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/CtsShimPrivUpgrade.apk"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_not_pre_installed_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_not_pre_installed_apex.asciipb
index 6a1a592..7806ac3 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_not_pre_installed_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_not_pre_installed_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim_not_pre_installed.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v1_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v1_apex.asciipb
index c01e04d..280dc99 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v1_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v1_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v1.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_file_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_file_apex.asciipb
index 91c5d50..2b13a41 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_file_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_file_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_additional_file.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb
index d7e36fc..c852f2c 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_additional_folder.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apex.asciipb
index 849bab8..566d73d 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb
index e59bbb1..7f394da 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_upgrades_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_upgrades_apex.asciipb
new file mode 100644
index 0000000..c3b3d1c
--- /dev/null
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_apk_in_apex_upgrades_apex.asciipb
@@ -0,0 +1,15 @@
+drops {
+  android_build_drop {
+    build_id: "8572644"
+    target: "CtsShim"
+    source_file: "aosp_arm64/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex"
+  }
+  dest_file: "hostsidetests/stagedinstall/testdata/apex//arm/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex"
+  version: ""
+  version_group: ""
+  git_project: "platform/cts"
+  git_branch: "tm-dev"
+  transform: TRANSFORM_NONE
+  transform_options {
+  }
+}
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb
index 4aeed69..8ad7148 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_different_certificate.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb
index 21717fc..c5bf540 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_different_package_name.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb
index 74573f6..b43824e4 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_no_hashtree.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_rebootless_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_rebootless_apex.asciipb
index 5672e5c..86dd2d0 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_rebootless_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_rebootless_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_rebootless.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb
index acc83c0..63e244b 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_sdk_target_p.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb
index 13268eb..d301677 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb
index 355f90b..0a0fa3a 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_signed_bob.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb
index b840674..cde81d7 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_signed_bob_rot.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb
index 60a8a3e..4b7066b 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb
index c360e44..64f31fb 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_unsigned_payload.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb
index 9941db2..6430590 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_with_post_install_hook.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb
index e041816..b103b78 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_with_pre_install_hook.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb
index 987a82a..b3f859b 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_without_apk_in_apex.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb
index 2531fbb..eced4cc 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v2_wrong_sha.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_apex.asciipb
index 6e6b103..f0a1f9a 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v3.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_rebootless_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_rebootless_apex.asciipb
index 655689a..d730662 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_rebootless_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_rebootless_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v3_rebootless.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb
index ba0e7b80..f617b9a 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v3_signed_bob.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb
index c470fe8..21a4921 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__arm_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/com.android.apex.cts.shim.v3_signed_bob_rot.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_not_pre_installed_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_not_pre_installed_apex.asciipb
index 09b85f6..9fee80e 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_not_pre_installed_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_not_pre_installed_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim_not_pre_installed.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v1_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v1_apex.asciipb
index c057c89..e00e0c0 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v1_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v1_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v1.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_file_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_file_apex.asciipb
index 82422cb..70ea7a4 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_file_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_file_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_additional_file.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb
index f29ff0d..fe22126 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_additional_folder_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_additional_folder.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apex.asciipb
index 8f2a136..4f7f762 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb
index 766bf19..76f970a 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_sdk_target_p_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_upgrades_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_upgrades_apex.asciipb
new file mode 100644
index 0000000..405905e
--- /dev/null
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_apk_in_apex_upgrades_apex.asciipb
@@ -0,0 +1,15 @@
+drops {
+  android_build_drop {
+    build_id: "8572644"
+    target: "CtsShim"
+    source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex"
+  }
+  dest_file: "hostsidetests/stagedinstall/testdata/apex//x86/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex"
+  version: ""
+  version_group: ""
+  git_project: "platform/cts"
+  git_branch: "tm-dev"
+  transform: TRANSFORM_NONE
+  transform_options {
+  }
+}
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb
index b88b655..ba4d65d 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_certificate_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_different_certificate.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb
index 9d7558d..a0cc1809 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_different_package_name_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_different_package_name.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb
index e5c6b65..a491c76 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_no_hashtree_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_no_hashtree.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_rebootless_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_rebootless_apex.asciipb
index 0be6a59..bc87363 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_rebootless_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_rebootless_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_rebootless.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb
index f1e7a2c..1399178 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sdk_target_p_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_sdk_target_p.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb
index a986691..70a1d02 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_sign_payload_with_different_key_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb
index be1b3a8..10f11a4 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_signed_bob.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb
index be9efdc..ec33561 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_signed_bob_rot.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb
index d675fce..57bd84b 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_signed_bob_rot_rollback_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb
index f3774cc..d2dd61b 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_unsigned_payload_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_unsigned_payload.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb
index 2f7c565..3ec6a81 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_post_install_hook_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_with_post_install_hook.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb
index 5bbee67..43416aa 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_with_pre_install_hook_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_with_pre_install_hook.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb
index d8a6bd5..f6e5294 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_without_apk_in_apex_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_without_apk_in_apex.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb
index 207fa1d..4e9edcd 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v2_wrong_sha_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v2_wrong_sha.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_apex.asciipb
index 6ef3eb5..5391c48 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v3.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_rebootless_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_rebootless_apex.asciipb
index 5264200..bc44538 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_rebootless_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_rebootless_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v3_rebootless.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb
index face859..4257f29 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v3_signed_bob.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb
index 84a1dbe..022a4bb 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apex__x86_com_android_apex_cts_shim_v3_signed_bob_rot_apex.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/com.android.apex.cts.shim.v3_signed_bob_rot.apex"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__arm_CtsShimTargetPSdk_apk.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__arm_CtsShimTargetPSdk_apk.asciipb
index d62c281..3f1c95d 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__arm_CtsShimTargetPSdk_apk.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__arm_CtsShimTargetPSdk_apk.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_arm64/CtsShimTargetPSdk.apk"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__x86_CtsShimTargetPSdk_apk.asciipb b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__x86_CtsShimTargetPSdk_apk.asciipb
index cb1fd5f..d4a6c09 100644
--- a/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__x86_CtsShimTargetPSdk_apk.asciipb
+++ b/.prebuilt_info/prebuilt_info_hostsidetests_stagedinstall_testdata_apk_CtsShimTargetPSdk__x86_CtsShimTargetPSdk_apk.asciipb
@@ -1,6 +1,6 @@
 drops {
   android_build_drop {
-    build_id: "7552332"
+    build_id: "8572644"
     target: "CtsShim"
     source_file: "aosp_x86_64/CtsShimTargetPSdk.apk"
   }
@@ -8,7 +8,7 @@
   version: ""
   version_group: ""
   git_project: "platform/cts"
-  git_branch: "sc-dev"
+  git_branch: "tm-dev"
   transform: TRANSFORM_NONE
   transform_options {
   }
diff --git a/apps/CtsVerifier/AndroidManifest.xml b/apps/CtsVerifier/AndroidManifest.xml
index 96eb23b..45eb773 100644
--- a/apps/CtsVerifier/AndroidManifest.xml
+++ b/apps/CtsVerifier/AndroidManifest.xml
@@ -6014,8 +6014,6 @@
             <intent-filter>
                 <action android:name="android.telephony.VisualVoicemailService"/>
             </intent-filter>
-            <meta-data android:name="ApiTest"
-                android:value="android.telephony.VisualVoicemailService#onCellServiceConnected|android.telephony.VisualVoicemailService#onSimRemoved"/>
         </service>
 
         <activity
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/logcat/ReadLogsTestActivity.java b/apps/CtsVerifier/src/com/android/cts/verifier/logcat/ReadLogsTestActivity.java
index 2fe31d4..ea3b9b7 100644
--- a/apps/CtsVerifier/src/com/android/cts/verifier/logcat/ReadLogsTestActivity.java
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/logcat/ReadLogsTestActivity.java
@@ -36,6 +36,8 @@
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
 
 
 /**
@@ -64,6 +66,7 @@
     private static ActivityManager sActivityManager;
 
     private static String sAppPackageName;
+    private static ExecutorService sExecutorService;
 
     @Override
     protected void onCreate(Bundle savedInstanceState) {
@@ -71,6 +74,7 @@
 
         sContext = this;
         sActivityManager = sContext.getSystemService(ActivityManager.class);
+        sExecutorService = Executors.newSingleThreadExecutor();
 
         // Setup the UI.
         setContentView(R.layout.logcat_read_logs);
@@ -106,65 +110,74 @@
      */
     public void runLogcatInForegroundAllowOnlyOnce() {
         Log.d(TAG, "Inside runLogcatInForeground()");
-        BufferedReader reader = null;
-        try {
-            // Dump the logcat most recent 10 lines before the compile command,
-            // and check if there are logs about compiling the test package.
-            java.lang.Process logcat = new ProcessBuilder(
-                    Arrays.asList("logcat", "-b", "system", "-t",
-                        Integer.toString(NUM_OF_LINES_FG))).start();
-            reader = new BufferedReader(new InputStreamReader(logcat.getInputStream()));
-            logcat.waitFor();
 
-            List<String> logcatOutput = new ArrayList<>();
-            String current;
-            Integer lineCount = 0;
-            while ((current = reader.readLine()) != null) {
-                logcatOutput.add(current);
-                lineCount++;
-            }
+        sExecutorService.execute(new Runnable() {
 
-            Log.d(TAG, "Logcat system allow line count: " + lineCount);
-            Log.d(TAG, "Logcat system allow output: " + logcatOutput);
+            public void run() {
+                BufferedReader reader = null;
+                try {
 
-            try {
+                    // Dump the logcat most recent 10 lines before the compile command,
+                    // and check if there are logs about compiling the test package.
+                    java.lang.Process logcat = new ProcessBuilder(
+                            Arrays.asList("logcat", "-b", "system", "-t",
+                                    Integer.toString(NUM_OF_LINES_FG))).start();
+                    reader = new BufferedReader(new InputStreamReader(logcat.getInputStream()));
+                    logcat.waitFor();
 
-                assertTrue("System log output is null", logcatOutput.size() != 0);
+                    List<String> logcatOutput = new ArrayList<>();
+                    String current;
+                    Integer lineCount = 0;
+                    while ((current = reader.readLine()) != null) {
+                        logcatOutput.add(current);
+                        lineCount++;
+                    }
 
-                // Check if the logcatOutput is not null. If logcatOutput is null,
-                // it throws an assertion error
-                assertNotNull(logcatOutput.get(0), "logcat output should not be null");
+                    Log.d(TAG, "Logcat system allow line count: " + lineCount);
+                    Log.d(TAG, "Logcat system allow output: " + logcatOutput);
 
-                boolean allowLog = logcatOutput.get(0).contains(SYSTEM_LOG_START);
-                assertTrue("Allow system log access containe log", allowLog);
+                    try {
 
-                boolean allowLineCount = lineCount > NUM_OF_LINES_FG;
-                assertTrue("Allow system log access count", allowLineCount);
+                        assertTrue("System log output is null", logcatOutput.size() != 0);
 
-                Log.d(TAG, "Logcat system allow log contains: " + allowLog + " lineCount: "
-                        + lineCount + " larger than: " + allowLineCount);
+                        // Check if the logcatOutput is not null. If logcatOutput is null,
+                        // it throws an assertion error
+                        assertNotNull(logcatOutput.get(0), "logcat output should not be null");
 
-            } catch (AssertionError e) {
-                fail("User Consent Allow Testing failed");
-            }
+                        boolean allowLog = logcatOutput.get(0).contains(SYSTEM_LOG_START);
+                        assertTrue("Allow system log access containe log", allowLog);
 
-        } catch (Exception e) {
-            Log.e(TAG, "User Consent Testing failed");
-        } finally {
-            try {
-                if (reader != null) {
-                    reader.close();
+                        boolean allowLineCount = lineCount > NUM_OF_LINES_FG;
+                        assertTrue("Allow system log access count", allowLineCount);
+
+                        Log.d(TAG, "Logcat system allow log contains: " + allowLog + " lineCount: "
+                                + lineCount + " larger than: " + allowLineCount);
+
+                    } catch (AssertionError e) {
+                        fail("User Consent Allow Testing failed");
+                    }
+
+                } catch (Exception e) {
+                    Log.e(TAG, "User Consent Testing failed");
+                } finally {
+                    try {
+                        if (reader != null) {
+                            reader.close();
+                        }
+                    } catch (IOException e) {
+                        Log.d(TAG, "Could not close reader: " + e.getMessage());
+                    }
                 }
-            } catch (IOException e) {
-                Log.d(TAG, "Could not close reader: " + e.getMessage());
             }
-        }
+        });
     }
 
     private void fail(CharSequence reason) {
-        Toast.makeText(this, reason, Toast.LENGTH_LONG).show();
-        Log.e(TAG, reason.toString());
-        setTestResultAndFinish(false);
+        runOnUiThread(() -> {
+            Toast.makeText(this, reason, Toast.LENGTH_LONG).show();
+            Log.e(TAG, reason.toString());
+            setTestResultAndFinish(false);
+        });
     }
 
     /**
@@ -172,44 +185,51 @@
      */
     public void runLogcatInForegroundDontAllow() {
         Log.d(TAG, "Inside runLogcatInForeground()");
-        BufferedReader reader = null;
-        try {
-            java.lang.Process logcat = new ProcessBuilder(
-                    Arrays.asList("logcat", "-b", "system", "-t",
-                        Integer.toString(NUM_OF_LINES_FG))).start();
-            logcat.waitFor();
 
-            // Merge several logcat streams, and take the last N lines
-            reader = new BufferedReader(new InputStreamReader(logcat.getInputStream()));
-            assertNotNull(reader);
+        sExecutorService.execute(new Runnable() {
 
-            List<String> logcatOutput = new ArrayList<>();
-            String current;
-            int lineCount = 0;
-            while ((current = reader.readLine()) != null) {
-                logcatOutput.add(current);
-                lineCount++;
-            }
+            public void run() {
+                BufferedReader reader = null;
+                try {
+                    java.lang.Process logcat = new ProcessBuilder(
+                            Arrays.asList("logcat", "-b", "system", "-t",
+                                    Integer.toString(NUM_OF_LINES_FG))).start();
+                    logcat.waitFor();
 
-            Log.d(TAG, "Logcat system deny line count:" + lineCount);
+                    // Merge several logcat streams, and take the last N lines
+                    reader = new BufferedReader(new InputStreamReader(logcat.getInputStream()));
+                    assertNotNull(reader);
 
-            try {
-                assertTrue("Deny System log access", lineCount == NUM_OF_LINES_BG);
-            }  catch (AssertionError e) {
-                fail("User Consent Deny Testing failed");
-            }
+                    List<String> logcatOutput = new ArrayList<>();
+                    String current;
+                    int lineCount = 0;
+                    while ((current = reader.readLine()) != null) {
+                        logcatOutput.add(current);
+                        lineCount++;
+                    }
 
-        } catch (Exception e) {
-            Log.e(TAG, "User Consent Testing failed");
-        } finally {
-            try {
-                if (reader != null) {
-                    reader.close();
+                    Log.d(TAG, "Logcat system deny line count:" + lineCount);
+
+                    try {
+                        assertTrue("Deny System log access", lineCount == NUM_OF_LINES_BG);
+                    } catch (AssertionError e) {
+                        fail("User Consent Deny Testing failed");
+                    }
+
+                } catch (Exception e) {
+                    Log.e(TAG, "User Consent Testing failed");
+                } finally {
+                    try {
+                        if (reader != null) {
+                            reader.close();
+                        }
+                    } catch (IOException e) {
+                        Log.d(TAG, "Could not close reader: " + e.getMessage());
+                    }
                 }
-            } catch (IOException e) {
-                Log.d(TAG, "Could not close reader: " + e.getMessage());
             }
-        }
+        });
+
     }
 
 }
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/managedprovisioning/ManagedUserPositiveTestActivity.java b/apps/CtsVerifier/src/com/android/cts/verifier/managedprovisioning/ManagedUserPositiveTestActivity.java
index 6ddcf71..8d2fe90 100644
--- a/apps/CtsVerifier/src/com/android/cts/verifier/managedprovisioning/ManagedUserPositiveTestActivity.java
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/managedprovisioning/ManagedUserPositiveTestActivity.java
@@ -214,7 +214,10 @@
     }
 
     private Intent createSetOrganizationNameIntent() {
-        return new Intent(CommandReceiverActivity.COMMAND_SET_ORGANIZATION_NAME)
+        return new Intent(this, CommandReceiverActivity.class)
+                .putExtra(CommandReceiverActivity.EXTRA_COMMAND,
+                        CommandReceiverActivity.COMMAND_SET_ORGANIZATION_NAME)
+                .putExtra(CommandReceiverActivity.EXTRA_USE_CURRENT_USER_DPM, true)
                 .putExtra(CommandReceiverActivity.EXTRA_ORGANIZATION_NAME, "Foo, Inc.");
     }
 }
diff --git a/common/device-side/bedstead/harrier/common/src/main/java/com/android/bedstead/harrier/policies/UserControlDisabledPackages.java b/common/device-side/bedstead/harrier/common/src/main/java/com/android/bedstead/harrier/policies/UserControlDisabledPackages.java
index c47db87..3c57540 100644
--- a/common/device-side/bedstead/harrier/common/src/main/java/com/android/bedstead/harrier/policies/UserControlDisabledPackages.java
+++ b/common/device-side/bedstead/harrier/common/src/main/java/com/android/bedstead/harrier/policies/UserControlDisabledPackages.java
@@ -17,7 +17,9 @@
 package com.android.bedstead.harrier.policies;
 
 import static com.android.bedstead.harrier.annotations.enterprise.EnterprisePolicy.APPLIED_BY_DEVICE_OWNER;
+import static com.android.bedstead.harrier.annotations.enterprise.EnterprisePolicy.APPLIED_BY_PROFILE_OWNER;
 import static com.android.bedstead.harrier.annotations.enterprise.EnterprisePolicy.APPLIES_GLOBALLY;
+import static com.android.bedstead.harrier.annotations.enterprise.EnterprisePolicy.APPLIES_TO_OWN_USER;
 
 import com.android.bedstead.harrier.annotations.enterprise.EnterprisePolicy;
 
@@ -28,6 +30,9 @@
  * {@code DevicePolicyManager#setUserControlDisabledPackages(ComponentName, List)} and
  * {@code DevicePolicyManager#getUserControlDisabledPackages(ComponentName)}.
  */
-@EnterprisePolicy(dpc = APPLIED_BY_DEVICE_OWNER | APPLIES_GLOBALLY)
+@EnterprisePolicy(dpc = {
+        APPLIED_BY_DEVICE_OWNER | APPLIES_GLOBALLY,
+        APPLIED_BY_PROFILE_OWNER | APPLIES_TO_OWN_USER
+})
 public final class UserControlDisabledPackages {
 }
diff --git a/common/device-side/bedstead/nene/src/main/java/com/android/bedstead/nene/utils/Versions.java b/common/device-side/bedstead/nene/src/main/java/com/android/bedstead/nene/utils/Versions.java
index 8444cb2..bd37257 100644
--- a/common/device-side/bedstead/nene/src/main/java/com/android/bedstead/nene/utils/Versions.java
+++ b/common/device-side/bedstead/nene/src/main/java/com/android/bedstead/nene/utils/Versions.java
@@ -34,13 +34,14 @@
 
     private static final String TAG = "Versions";
 
-    public static final int T = CUR_DEVELOPMENT;
+    public static final int T = Build.VERSION_CODES.TIRAMISU;
+    public static final int U = Build.VERSION_CODES.CUR_DEVELOPMENT;
 
     /** Any version. */
     public static final int ANY = -1;
 
     private static final ImmutableSet<String> DEVELOPMENT_CODENAMES =
-            ImmutableSet.of("Sv2", "T", "Tiramisu");
+            ImmutableSet.of("UpsideDownCake");
 
     private Versions() {
 
diff --git a/hostsidetests/appcloning/hostside/src/com/android/cts/appcloning/AppCloningHostTest.java b/hostsidetests/appcloning/hostside/src/com/android/cts/appcloning/AppCloningHostTest.java
index e8da4b0..c3dfb95 100644
--- a/hostsidetests/appcloning/hostside/src/com/android/cts/appcloning/AppCloningHostTest.java
+++ b/hostsidetests/appcloning/hostside/src/com/android/cts/appcloning/AppCloningHostTest.java
@@ -119,6 +119,8 @@
      */
     @Test
     public void testRemoveClonedProfileMediaProviderCleanup() throws Exception {
+        assumeTrue(isAtLeastT());
+
         String cloneProfileImage = NONCE + "cloneProfileImage.png";
 
         // Inserting blank image in clone profile
@@ -178,6 +180,8 @@
 
     @Test
     public void testCrossUserMediaAccess() throws Exception {
+        assumeTrue(isAtLeastT());
+
         // Install the app in both the user spaces
         installPackage(APP_A, "--user all");
 
diff --git a/hostsidetests/appcloning/test-apps/AppCloningTestApp/src/com/android/cts/appcloningtestapp/AppCloningDeviceTest.java b/hostsidetests/appcloning/test-apps/AppCloningTestApp/src/com/android/cts/appcloningtestapp/AppCloningDeviceTest.java
index 37c7b2d..c0b098a 100644
--- a/hostsidetests/appcloning/test-apps/AppCloningTestApp/src/com/android/cts/appcloningtestapp/AppCloningDeviceTest.java
+++ b/hostsidetests/appcloning/test-apps/AppCloningTestApp/src/com/android/cts/appcloningtestapp/AppCloningDeviceTest.java
@@ -178,6 +178,8 @@
         // remove volumes that belong to owner profile
         volumeListIncludingShared.removeAll(volumeList);
 
+        assertThat(volumeListIncludingShared.size()).isGreaterThan(0);
+
         // remaining volumes should belong to the clone user.
         for (StorageVolume vol : volumeListIncludingShared) {
             assertThat(vol.getOwner().getIdentifier()).isEqualTo(cloneUserId);
diff --git a/hostsidetests/appsearch/src/android/appsearch/cts/ContactsIndexerMultiUserTest.java b/hostsidetests/appsearch/src/android/appsearch/cts/ContactsIndexerMultiUserTest.java
index 6ebd2b1..7fba4c9 100644
--- a/hostsidetests/appsearch/src/android/appsearch/cts/ContactsIndexerMultiUserTest.java
+++ b/hostsidetests/appsearch/src/android/appsearch/cts/ContactsIndexerMultiUserTest.java
@@ -40,7 +40,6 @@
 public class ContactsIndexerMultiUserTest extends AppSearchHostTestBase {
 
     private static int sSecondaryUserId;
-    private static int sTertiaryUserId;
 
     @BeforeClassWithInfo
     public static void setUpClass(TestInformation testInfo) throws Exception {
@@ -49,8 +48,6 @@
 
         sSecondaryUserId = testInfo.getDevice().createUser("Test User #1");
         assertThat(testInfo.getDevice().startUser(sSecondaryUserId)).isTrue();
-        sTertiaryUserId = testInfo.getDevice().createUser("Test User #2");
-        assertThat(testInfo.getDevice().startUser(sTertiaryUserId)).isTrue();
     }
 
     @Before
@@ -58,11 +55,7 @@
         if (!getDevice().isUserRunning(sSecondaryUserId)) {
             getDevice().startUser(sSecondaryUserId, /*waitFlag=*/ true);
         }
-        if (!getDevice().isUserRunning(sTertiaryUserId)) {
-            getDevice().startUser(sTertiaryUserId, /*waitFlag=*/ true);
-        }
         installPackageAsUser(TARGET_APK_A, /*grantPermission=*/ true, sSecondaryUserId);
-        installPackageAsUser(TARGET_APK_A, /*grantPermission=*/ true, sTertiaryUserId);
     }
 
     @AfterClassWithInfo
@@ -70,9 +63,6 @@
         if (sSecondaryUserId > 0) {
             testInfo.getDevice().removeUser(sSecondaryUserId);
         }
-        if (sTertiaryUserId > 0) {
-            testInfo.getDevice().removeUser(sTertiaryUserId);
-        }
     }
 
     @Test
@@ -80,8 +70,5 @@
         runContactsIndexerDeviceTestAsUserInPkgA("testFullUpdateJobIsScheduled",
                 sSecondaryUserId,
                 Collections.singletonMap(USER_ID_KEY, String.valueOf(sSecondaryUserId)));
-        runContactsIndexerDeviceTestAsUserInPkgA("testFullUpdateJobIsScheduled",
-                sTertiaryUserId,
-                Collections.singletonMap(USER_ID_KEY, String.valueOf(sTertiaryUserId)));
     }
 }
diff --git a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgrade.apk b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgrade.apk
index 5c8aaa5..f1730f6 100644
--- a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgrade.apk
+++ b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgrade.apk
Binary files differ
diff --git a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgradeWrongSHA.apk b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgradeWrongSHA.apk
index 3cb1a4b..cdb279a 100644
--- a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgradeWrongSHA.apk
+++ b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/arm/CtsShimPrivUpgradeWrongSHA.apk
Binary files differ
diff --git a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgrade.apk b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgrade.apk
index 3bfa2bb..42135bc 100644
--- a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgrade.apk
+++ b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgrade.apk
Binary files differ
diff --git a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgradeWrongSHA.apk b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgradeWrongSHA.apk
index 0c69d99..f9e6f96 100644
--- a/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgradeWrongSHA.apk
+++ b/hostsidetests/appsecurity/test-apps/PrivilegedUpdateApp/apk/x86/CtsShimPrivUpgradeWrongSHA.apk
Binary files differ
diff --git a/hostsidetests/neuralnetworks/app/src/com/android/nn/stats/app/NnapiDeviceActivity.java b/hostsidetests/neuralnetworks/app/src/com/android/nn/stats/app/NnapiDeviceActivity.java
index e372fb9..7dc4015 100644
--- a/hostsidetests/neuralnetworks/app/src/com/android/nn/stats/app/NnapiDeviceActivity.java
+++ b/hostsidetests/neuralnetworks/app/src/com/android/nn/stats/app/NnapiDeviceActivity.java
@@ -21,7 +21,7 @@
 import android.util.Log;
 
 /**
- * A simple activity which triggers libneuralnetworks.so to push WestWorld atoms.
+ * A simple activity which triggers libneuralnetworks.so to push statsd atoms.
  */
 public class NnapiDeviceActivity extends Activity {
     private static final String TAG = NnapiDeviceActivity.class.getSimpleName();
@@ -33,7 +33,7 @@
     @Override
     public void onCreate(Bundle icicle) {
         super.onCreate(icicle);
-        Log.i(TAG, "Triggering libneuralnetworks.so to push WestWorld atoms.");
+        Log.i(TAG, "Triggering libneuralnetworks.so to push statsd atoms.");
         trigger_libneuralnetworks_atoms();
     }
 
diff --git a/hostsidetests/packagemanager/dynamicmime/src/android/dynamicmime/cts/RebootTestCases.java b/hostsidetests/packagemanager/dynamicmime/src/android/dynamicmime/cts/RebootTestCases.java
index a26de84..d6fb65e 100644
--- a/hostsidetests/packagemanager/dynamicmime/src/android/dynamicmime/cts/RebootTestCases.java
+++ b/hostsidetests/packagemanager/dynamicmime/src/android/dynamicmime/cts/RebootTestCases.java
@@ -40,6 +40,8 @@
     private static final String PACKAGE_TEST_APP = "android.dynamicmime.testapp";
     private static final String PACKAGE_REBOOT_TESTS = PACKAGE_TEST_APP + ".reboot";
 
+    private static final int SETTINGS_WRITE_TIMEOUT_MS = 10_000;
+
     @Test
     public void testGroupWithExactType() throws DeviceNotAvailableException {
         runTestWithReboot("SingleAppTest", "testGroupWithExactType");
@@ -213,6 +215,7 @@
     private void runTestWithReboot(String testClassName, String testMethodName)
             throws DeviceNotAvailableException {
         runPreReboot(testClassName, testMethodName);
+        waitForSettingsWrite();
         getDevice().reboot();
         runPostReboot(testClassName, testMethodName);
     }
@@ -223,6 +226,13 @@
             testMethodName);
     }
 
+    private void waitForSettingsWrite() {
+        try {
+            Thread.sleep(SETTINGS_WRITE_TIMEOUT_MS);
+        } catch (InterruptedException ignored) {
+        }
+    }
+
     private void runPreReboot(String testClassName, String testMethodName)
         throws DeviceNotAvailableException {
         runDeviceTests(PACKAGE_TEST_APP, PACKAGE_REBOOT_TESTS + ".PreReboot" + testClassName,
diff --git a/hostsidetests/scopedstorage/Android.bp b/hostsidetests/scopedstorage/Android.bp
index 86383ec..17edaae 100644
--- a/hostsidetests/scopedstorage/Android.bp
+++ b/hostsidetests/scopedstorage/Android.bp
@@ -21,8 +21,7 @@
     manifest: "ScopedStorageTestHelper/TestAppA.xml",
     static_libs: ["cts-scopedstorage-lib"],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     srcs: ["ScopedStorageTestHelper/src/**/*.java"],
     // Tag as a CTS artifact
@@ -54,8 +53,7 @@
     manifest: "ScopedStorageTestHelper/TestAppB.xml",
     static_libs: ["cts-scopedstorage-lib"],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     srcs: ["ScopedStorageTestHelper/src/**/*.java"],
     // Tag as a CTS artifact
@@ -71,8 +69,7 @@
     manifest: "ScopedStorageTestHelper/TestAppC.xml",
     static_libs: ["cts-scopedstorage-lib"],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     srcs: ["ScopedStorageTestHelper/src/**/*.java"],
     // Tag as a CTS artifact
@@ -136,8 +133,7 @@
     manifest: "ScopedStorageTestHelper/TestAppFileManager.xml",
     static_libs: ["cts-scopedstorage-lib"],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     srcs: ["ScopedStorageTestHelper/src/**/*.java"],
     // Tag as a CTS artifact
@@ -153,8 +149,7 @@
     manifest: "ScopedStorageTestHelper/TestAppFileManagerBypassDB.xml",
     static_libs: ["cts-scopedstorage-lib"],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     srcs: ["ScopedStorageTestHelper/src/**/*.java"],
     // Tag as a CTS artifact
@@ -170,8 +165,7 @@
     manifest: "ScopedStorageTestHelper/TestAppSystemGalleryBypassDB.xml",
     static_libs: ["cts-scopedstorage-lib"],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     srcs: ["ScopedStorageTestHelper/src/**/*.java"],
     // Tag as a CTS artifact
@@ -232,8 +226,7 @@
         "cts",
     ],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     java_resources: [
         ":CtsScopedStorageTestAppA",
@@ -378,6 +371,7 @@
         "truth-prebuilt",
         "cts-scopedstorage-lib",
         "androidx.test.uiautomator_uiautomator",
+        "modules-utils-build_system",
     ],
     compile_multilib: "both",
     test_suites: [
@@ -386,8 +380,7 @@
         "cts",
     ],
     sdk_version: "test_current",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     min_sdk_version: "30",
     libs: [
         "android.test.base",
diff --git a/hostsidetests/scopedstorage/device/src/android/scopedstorage/cts/device/ScopedStorageDeviceTest.java b/hostsidetests/scopedstorage/device/src/android/scopedstorage/cts/device/ScopedStorageDeviceTest.java
index 1a3bff9..6e87ad3 100644
--- a/hostsidetests/scopedstorage/device/src/android/scopedstorage/cts/device/ScopedStorageDeviceTest.java
+++ b/hostsidetests/scopedstorage/device/src/android/scopedstorage/cts/device/ScopedStorageDeviceTest.java
@@ -143,6 +143,7 @@
 import androidx.test.filters.SdkSuppress;
 
 import com.android.cts.install.lib.TestApp;
+import com.android.modules.utils.build.SdkLevel;
 
 import com.google.common.io.Files;
 
@@ -1263,12 +1264,18 @@
 
     @Test
     public void testReadStorageInvalidation() throws Exception {
-        testAppOpInvalidation(
+        if (SdkLevel.isAtLeastT()) {
+            testAppOpInvalidation(
                 APP_C,
                 new File(getDcimDir(), "read_storage.jpg"),
                 Manifest.permission.READ_MEDIA_IMAGES,
                 AppOpsManager.OPSTR_READ_MEDIA_IMAGES,
                 /* forWrite */ false);
+        } else {
+            testAppOpInvalidation(APP_C, new File(getDcimDir(), "read_storage.jpg"),
+                Manifest.permission.READ_EXTERNAL_STORAGE,
+                AppOpsManager.OPSTR_READ_EXTERNAL_STORAGE, /* forWrite */ false);
+        }
     }
 
     @Test
diff --git a/hostsidetests/securitybulletin/src/android/security/cts/CVE_2021_39797.java b/hostsidetests/securitybulletin/src/android/security/cts/CVE_2021_39797.java
new file mode 100644
index 0000000..ee835f5
--- /dev/null
+++ b/hostsidetests/securitybulletin/src/android/security/cts/CVE_2021_39797.java
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2022 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 android.security.cts;
+
+import android.platform.test.annotations.AsbSecurityTest;
+
+import com.android.tradefed.device.ITestDevice;
+import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
+import com.android.sts.common.tradefed.testtype.StsExtraBusinessLogicHostTestBase;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+@RunWith(DeviceJUnit4ClassRunner.class)
+public class CVE_2021_39797 extends StsExtraBusinessLogicHostTestBase {
+
+    @AsbSecurityTest(cveBugId = 209607104)
+    @Test
+    public void testPocCVE_2021_39797() throws Exception {
+        ITestDevice device = getDevice();
+        final String testPkg = "android.security.cts.CVE_2021_39797_test";
+        final String targetPkg = "android.security.cts.CVE_2021_39797_target";
+        uninstallPackage(device, testPkg);
+        uninstallPackage(device, targetPkg);
+
+        /* Wake up the screen */
+        AdbUtils.runCommandLine("input keyevent KEYCODE_WAKEUP", device);
+        AdbUtils.runCommandLine("input keyevent KEYCODE_MENU", device);
+        AdbUtils.runCommandLine("input keyevent KEYCODE_HOME", device);
+
+        installPackage("CVE-2021-39797-test.apk");
+        installPackage("CVE-2021-39797-target.apk");
+        String previous = AdbUtils.runCommandLine("settings get global hidden_api_policy", device);
+
+        /* Set the property hidden_api_policy to 1 in order to access the vulnerable function
+           getMainActivityLaunchIntent of class LauncherApps */
+        AdbUtils.runCommandLine("settings put global hidden_api_policy 1", device);
+        runDeviceTests(testPkg, testPkg + ".DeviceTest", "testTaskOverride");
+
+        /* Restore the property hidden_api_policy to its previous value */
+        AdbUtils.runCommandLine("settings put global hidden_api_policy " + previous, device);
+    }
+}
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/Android.bp b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/Android.bp
new file mode 100644
index 0000000..4a58ef3
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/Android.bp
@@ -0,0 +1,30 @@
+/*
+ * Copyright (C) 2022 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 {
+    default_applicable_licenses: ["Android-Apache-2.0"],
+}
+
+android_test_helper_app {
+    name: "CVE-2021-39797-target",
+    defaults: ["cts_support_defaults"],
+    srcs: ["src/**/*.java"],
+    test_suites: [
+        "sts",
+    ],
+    sdk_version: "current",
+}
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/AndroidManifest.xml b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/AndroidManifest.xml
new file mode 100644
index 0000000..514c75a
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/AndroidManifest.xml
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2022 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.
+-->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+          package="android.security.cts.CVE_2021_39797_target">
+    <application android:label="CVE-2021-39797-target">
+        <activity android:name=".TargetActivity"
+            android:exported="true">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="android.intent.category.LAUNCHER" />
+            </intent-filter>
+        </activity>
+    </application>
+</manifest>
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/src/android/security/cts/CVE_2021_39797_target/TargetActivity.java b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/src/android/security/cts/CVE_2021_39797_target/TargetActivity.java
new file mode 100644
index 0000000..b49da17
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/target-app/src/android/security/cts/CVE_2021_39797_target/TargetActivity.java
@@ -0,0 +1,22 @@
+/*
+ * Copyright (C) 2022 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 android.security.cts.CVE_2021_39797_target;
+
+import android.app.Activity;
+
+public class TargetActivity extends Activity {
+}
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/Android.bp b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/Android.bp
new file mode 100644
index 0000000..aa4e813
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/Android.bp
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2022 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 {
+    default_applicable_licenses: ["Android-Apache-2.0"],
+}
+
+android_test_helper_app {
+    name: "CVE-2021-39797-test",
+    defaults: ["cts_support_defaults"],
+    srcs: ["src/**/*.java"],
+    test_suites: [
+        "sts",
+    ],
+    static_libs: [
+        "androidx.test.core",
+        "androidx.test.rules",
+        "androidx.test.uiautomator_uiautomator",
+    ],
+    sdk_version: "current",
+}
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/AndroidManifest.xml b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/AndroidManifest.xml
new file mode 100644
index 0000000..31c61f7b
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/AndroidManifest.xml
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2022 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.
+-->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+          package="android.security.cts.CVE_2021_39797_test">
+    <application android:label="CVE-2021-39797-test">
+        <activity android:name=".PocActivity"
+            android:exported="true">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="android.intent.category.LAUNCHER" />
+            </intent-filter>
+        </activity>
+    </application>
+    <instrumentation
+        android:name="androidx.test.runner.AndroidJUnitRunner"
+        android:targetPackage="android.security.cts.CVE_2021_39797_test" />
+</manifest>
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/res/values/integers.xml b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/res/values/integers.xml
new file mode 100644
index 0000000..363df00
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/res/values/integers.xml
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  Copyright 2022 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.
+  -->
+
+<resources>
+    <integer name="assumptionFailure">-1</integer>
+    <integer name="noAssumptionFailure">0</integer>
+</resources>
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/res/values/strings.xml b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/res/values/strings.xml
new file mode 100644
index 0000000..e61e413
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/res/values/strings.xml
@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2022 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.
+-->
+
+<resources>
+    <string name="activityNotFoundMsg">The activity with intent %1$s was not found</string>
+    <string name="appUiErrorTargetApp">Timed out waiting on UI of CVE_2021_39797_target App</string>
+    <string name="appUiErrorTestApp">Timed out waiting on UI of CVE_2021_39797_test App</string>
+    <string name="attrTaskOverlay">android.activity.taskOverlay</string>
+    <string name="attrLaunchTaskId">android.activity.launchTaskId</string>
+    <string name="attrPIntentLaunchFlags">android.activity.pendingIntentLaunchFlags</string>
+    <string name="defaultSemaphoreMsg">Could not get message key in shared preferences</string>
+    <string name="errorMessage">Device is vulnerable to b/209607104 !!</string>
+    <string name="errorNullCheckPIntent">getMainActivityLaunchIntent returned null, it is expected
+    to return a non-null result</string>
+    <string name="flagTaskSwapped">taskSwapped</string>
+    <string name="invokeExceptionMsg">Got an exception while calling Method.invoke() on
+    LauncherApps method getMainActivityLaunchIntent instance</string>
+    <string name="messageKey">message</string>
+    <string name="noMethodExceptionMsg">Got NoSuchMethodException for LauncherApps method
+    getMainActivityLaunchIntent</string>
+    <string name="resultKey">result</string>
+    <string name="sharedPreferences">prefs</string>
+    <string name="startIntentSenderExceptionMsg">Got an exception while calling startIntentSender
+    </string>
+    <string name="targetPkg">android.security.cts.CVE_2021_39797_target</string>
+    <string name="targetActivityName">android.security.cts.CVE_2021_39797_target.TargetActivity
+    </string>
+    <string name="targetFunction">getMainActivityLaunchIntent</string>
+    <string name="taskId">taskId</string>
+    <string name="timedOutPocActivity">Timed out waiting on a result from PocActivity</string>
+</resources>
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/src/android/security/cts/CVE_2021_39797_test/DeviceTest.java b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/src/android/security/cts/CVE_2021_39797_test/DeviceTest.java
new file mode 100644
index 0000000..d9a2da3
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/src/android/security/cts/CVE_2021_39797_test/DeviceTest.java
@@ -0,0 +1,127 @@
+/**
+ * Copyright (C) 2022 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 android.security.cts.CVE_2021_39797_test;
+
+import static androidx.test.core.app.ApplicationProvider.getApplicationContext;
+import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
+
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assume.assumeNoException;
+import static org.junit.Assume.assumeNotNull;
+import static org.junit.Assume.assumeTrue;
+
+import android.content.ActivityNotFoundException;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
+
+import androidx.test.runner.AndroidJUnit4;
+import androidx.test.uiautomator.By;
+import androidx.test.uiautomator.UiDevice;
+import androidx.test.uiautomator.Until;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+import java.util.concurrent.Semaphore;
+import java.util.concurrent.TimeUnit;
+
+@RunWith(AndroidJUnit4.class)
+public class DeviceTest {
+    static final int TIMEOUT_MS = 10000;
+
+    @Test
+    public void testTaskOverride() {
+        Context context = getApplicationContext();
+        assumeNotNull(context);
+        UiDevice device = UiDevice.getInstance(getInstrumentation());
+        assumeNotNull(device);
+        String targetPkg = context.getString(R.string.targetPkg);
+        String targetActivityName = context.getString(R.string.targetActivityName);
+
+        // Start the TargetActivity to make it a recent task when we start the PocActivity
+        Intent targetIntent = new Intent();
+        targetIntent.setComponent(new ComponentName(targetPkg, targetActivityName));
+        targetIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+        try {
+            context.startActivity(targetIntent);
+        } catch (ActivityNotFoundException e) {
+            assumeNoException(context.getString(R.string.activityNotFoundMsg, targetIntent), e);
+        }
+        assumeTrue(context.getString(R.string.appUiErrorTargetApp),
+                device.wait(Until.hasObject(By.pkg(targetPkg)), TIMEOUT_MS));
+
+        // Start the PocActivity
+        device.pressHome();
+        Intent intent = new Intent(context, PocActivity.class);
+        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+        try {
+            context.startActivity(intent);
+        } catch (ActivityNotFoundException e) {
+            assumeNoException(context.getString(R.string.activityNotFoundMsg, intent), e);
+        }
+
+        // Wait on a result from PocActivity
+        SharedPreferences sharedPrefs = context.getSharedPreferences(
+                context.getString(R.string.sharedPreferences), Context.MODE_APPEND);
+        assumeNotNull(sharedPrefs);
+        final Semaphore preferenceChanged = new Semaphore(0);
+        OnSharedPreferenceChangeListener listener = new OnSharedPreferenceChangeListener() {
+            @Override
+            public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {
+                if (key.equals(context.getString(R.string.resultKey))) {
+                    preferenceChanged.release();
+                }
+            }
+        };
+        sharedPrefs.registerOnSharedPreferenceChangeListener(listener);
+        try {
+            preferenceChanged.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS);
+        } catch (InterruptedException e) {
+            assumeNoException(context.getString(R.string.timedOutPocActivity), e);
+        }
+        int result = sharedPrefs.getInt(context.getString(R.string.resultKey),
+                context.getResources().getInteger(R.integer.assumptionFailure));
+        String message = sharedPrefs.getString(context.getString(R.string.messageKey),
+                context.getString(R.string.defaultSemaphoreMsg));
+        assumeTrue(message,
+                result != context.getResources().getInteger(R.integer.assumptionFailure));
+
+        // Try launching the TargetActivity again. Without fix, it is supposed to be hijacked by
+        // the PocActivity and PocActivity should be started in its place.
+        try {
+            context.startActivity(targetIntent);
+        } catch (ActivityNotFoundException e) {
+            assumeNoException(context.getString(R.string.activityNotFoundMsg, targetIntent), e);
+        }
+
+        // Wait for the UI of TargetActivity
+        boolean targetActivityDisplayed =
+                device.wait(Until.hasObject(By.pkg(targetPkg)), TIMEOUT_MS);
+
+        // Check if the PocActivity task came up on the screen replacing the TargetActivity task
+        boolean taskSwapped =
+                sharedPrefs.getBoolean(context.getString(R.string.flagTaskSwapped), false);
+
+        // Fail the test only if TargetActivity did not appear on the screen and the task of
+        // TargetActivity is hijacked by the PocActivity
+        assertFalse(context.getString(R.string.errorMessage),
+                !targetActivityDisplayed && taskSwapped);
+    }
+}
diff --git a/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/src/android/security/cts/CVE_2021_39797_test/PocActivity.java b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/src/android/security/cts/CVE_2021_39797_test/PocActivity.java
new file mode 100644
index 0000000..42eff75
--- /dev/null
+++ b/hostsidetests/securitybulletin/test-apps/CVE-2021-39797/test-app/src/android/security/cts/CVE_2021_39797_test/PocActivity.java
@@ -0,0 +1,110 @@
+/*
+ * Copyright (C) 2022 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 android.security.cts.CVE_2021_39797_test;
+
+import android.app.Activity;
+import android.app.PendingIntent;
+import android.content.ComponentName;
+import android.content.Intent;
+import android.content.IntentSender.SendIntentException;
+import android.content.SharedPreferences;
+import android.content.pm.LauncherApps;
+import android.os.Bundle;
+import android.os.Process;
+import android.os.UserHandle;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+public class PocActivity extends Activity {
+
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        SharedPreferences prefs =
+                getSharedPreferences(getString(R.string.sharedPreferences), MODE_PRIVATE);
+        if (prefs == null) {
+            return;
+        }
+        int taskIdSaved = prefs.getInt(getString(R.string.taskId), -1);
+        if (taskIdSaved == -1) {
+            SharedPreferences.Editor editor = prefs.edit();
+            editor.putInt(getString(R.string.taskId), getTaskId());
+            editor.apply();
+        } else {
+            if ((taskIdSaved - 1) == getTaskId()) {
+                SharedPreferences.Editor editor = prefs.edit();
+                editor.putBoolean(getString(R.string.flagTaskSwapped), true);
+                editor.apply();
+            }
+            setResult(prefs, getResources().getInteger(R.integer.noAssumptionFailure), "");
+            return;
+        }
+
+        Method method;
+        try {
+            method = LauncherApps.class.getMethod(getString(R.string.targetFunction),
+                    ComponentName.class, Bundle.class, UserHandle.class);
+        } catch (NoSuchMethodException e) {
+            setResult(prefs, getResources().getInteger(R.integer.assumptionFailure),
+                    getString(R.string.noMethodExceptionMsg));
+            return;
+        }
+
+        Bundle options = new Bundle();
+        options.putBoolean(getString(R.string.attrTaskOverlay), true);
+        options.putInt(getString(R.string.attrLaunchTaskId), getTaskId() - 1);
+
+        PendingIntent pi;
+        try {
+            pi = (PendingIntent) method.invoke(getSystemService(LauncherApps.class),
+                    getIntent().getComponent(), options,
+                    UserHandle.getUserHandleForUid(Process.myUid()));
+        } catch (IllegalAccessException | InvocationTargetException e) {
+            setResult(prefs, getResources().getInteger(R.integer.assumptionFailure),
+                    getString(R.string.invokeExceptionMsg));
+            return;
+        }
+        if (pi == null) {
+            setResult(prefs, getResources().getInteger(R.integer.assumptionFailure),
+                    getString(R.string.errorNullCheckPIntent));
+            return;
+        }
+
+        Bundle sendOptions = new Bundle();
+        sendOptions.putInt(getString(R.string.attrPIntentLaunchFlags),
+                Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
+
+        try {
+            startIntentSender(pi.getIntentSender(), null, 0, 0, 0, sendOptions);
+        } catch (SendIntentException e) {
+            setResult(prefs, getResources().getInteger(R.integer.assumptionFailure),
+                    getString(R.string.startIntentSenderExceptionMsg));
+            return;
+        }
+        setResult(prefs, getResources().getInteger(R.integer.noAssumptionFailure), "");
+    }
+
+    private void setResult(SharedPreferences sh, int result, String message) {
+        if (sh != null) {
+            SharedPreferences.Editor edit = sh.edit();
+            edit.putInt(getString(R.string.resultKey), result);
+            edit.putString(getString(R.string.messageKey), message);
+            edit.commit();
+        }
+    }
+}
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v1.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v1.apex
index 791d0dd..c2dc28f 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v1.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v1.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2.apex
index 0a26d23..880ab4a 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_file.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_file.apex
index 5ed2c7e..8c84cd5 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_file.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_file.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_folder.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_folder.apex
index 133f7f7..b519bbe 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_folder.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_additional_folder.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex
index 6ce5397..38e2339 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex
new file mode 100644
index 0000000..3d7bf51
--- /dev/null
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_certificate.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_certificate.apex
index 4228ffe..f4bc7e8 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_certificate.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_certificate.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_package_name.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_package_name.apex
index de090f1..59e9fe1 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_package_name.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_different_package_name.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_no_hashtree.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_no_hashtree.apex
index 162044c..353949b 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_no_hashtree.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_no_hashtree.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_rebootless.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_rebootless.apex
index 9d68887..c39b790 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_rebootless.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_rebootless.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sdk_target_p.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sdk_target_p.apex
index 44f7613..da25328 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sdk_target_p.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sdk_target_p.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex
index 389871d..3eaf372 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob.apex
index f8fa44f..6f38273 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot.apex
index 9658818..1969746 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex
index 3440043..be642bf 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_unsigned_payload.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_unsigned_payload.apex
index d6f7d8f..7bebb77 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_unsigned_payload.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_unsigned_payload.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_post_install_hook.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_post_install_hook.apex
index cc214f8..8006022 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_post_install_hook.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_post_install_hook.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_pre_install_hook.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_pre_install_hook.apex
index dab82a0..3465dbb 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_pre_install_hook.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_with_pre_install_hook.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_without_apk_in_apex.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_without_apk_in_apex.apex
index 9706f2f..67743a9 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_without_apk_in_apex.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_without_apk_in_apex.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_wrong_sha.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_wrong_sha.apex
index f305cff..aa1c10c 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_wrong_sha.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v2_wrong_sha.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3.apex
index 3122c96..b345bca 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_rebootless.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_rebootless.apex
index 0f5134d..c3bab7c 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_rebootless.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_rebootless.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob.apex
index a83bf51..4733bad 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob_rot.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob_rot.apex
index 703b641..6972daa 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob_rot.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim.v3_signed_bob_rot.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim_not_pre_installed.apex b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim_not_pre_installed.apex
index 806ccc7..4cda1c6 100644
--- a/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim_not_pre_installed.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/arm/com.android.apex.cts.shim_not_pre_installed.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v1.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v1.apex
index a94ae75..030c53b 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v1.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v1.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2.apex
index a9c2758..b090a96 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_file.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_file.apex
index 5ed2c7e..c498b32 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_file.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_file.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_folder.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_folder.apex
index 133f7f7..e83ec07 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_folder.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_additional_folder.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex
index 6ce5397..4545b1c 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_sdk_target_p.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex
new file mode 100644
index 0000000..298fd85
--- /dev/null
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_apk_in_apex_upgrades.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_certificate.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_certificate.apex
index 4228ffe..d911fe0 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_certificate.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_certificate.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_package_name.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_package_name.apex
index de090f1..053df91a 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_package_name.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_different_package_name.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_no_hashtree.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_no_hashtree.apex
index 19ec142..65a5473 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_no_hashtree.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_no_hashtree.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_rebootless.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_rebootless.apex
index 9d68887..9f94684 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_rebootless.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_rebootless.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sdk_target_p.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sdk_target_p.apex
index 9929c3d..8fd510c 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sdk_target_p.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sdk_target_p.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex
index 389871d..baae3e3 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_sign_payload_with_different_key.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob.apex
index 3f2fc50..1e80788 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot.apex
index cf628ab..c064928 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex
index ba5af3b..685f347 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_signed_bob_rot_rollback.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_unsigned_payload.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_unsigned_payload.apex
index 38c073f..f2329ae 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_unsigned_payload.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_unsigned_payload.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_post_install_hook.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_post_install_hook.apex
index cc214f8..bb2d96e 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_post_install_hook.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_post_install_hook.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_pre_install_hook.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_pre_install_hook.apex
index dab82a0..fd00bd5 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_pre_install_hook.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_with_pre_install_hook.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_without_apk_in_apex.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_without_apk_in_apex.apex
index 9706f2f..e7da653 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_without_apk_in_apex.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_without_apk_in_apex.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_wrong_sha.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_wrong_sha.apex
index f305cff..32bf141 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_wrong_sha.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v2_wrong_sha.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3.apex
index 7f3e9ec..1bd8b1b 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_rebootless.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_rebootless.apex
index 0f5134d..2f7a2e5 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_rebootless.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_rebootless.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob.apex
index 1aeb0b0..38fe019 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob_rot.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob_rot.apex
index 20f1c85..68505d5 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob_rot.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim.v3_signed_bob_rot.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim_not_pre_installed.apex b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim_not_pre_installed.apex
index 806ccc7..7fd07b5 100644
--- a/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim_not_pre_installed.apex
+++ b/hostsidetests/stagedinstall/testdata/apex/x86/com.android.apex.cts.shim_not_pre_installed.apex
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/arm/CtsShimTargetPSdk.apk b/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/arm/CtsShimTargetPSdk.apk
index 65f2a3b..3d01f0e 100644
--- a/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/arm/CtsShimTargetPSdk.apk
+++ b/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/arm/CtsShimTargetPSdk.apk
Binary files differ
diff --git a/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/x86/CtsShimTargetPSdk.apk b/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/x86/CtsShimTargetPSdk.apk
index 65f2a3b..3d01f0e 100644
--- a/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/x86/CtsShimTargetPSdk.apk
+++ b/hostsidetests/stagedinstall/testdata/apk/CtsShimTargetPSdk/x86/CtsShimTargetPSdk.apk
Binary files differ
diff --git a/hostsidetests/statsdatom/apps/statsdapp/src/com/android/server/cts/device/statsdatom/AtomTests.java b/hostsidetests/statsdatom/apps/statsdapp/src/com/android/server/cts/device/statsdatom/AtomTests.java
index e356ea6..3a45dc0 100644
--- a/hostsidetests/statsdatom/apps/statsdapp/src/com/android/server/cts/device/statsdatom/AtomTests.java
+++ b/hostsidetests/statsdatom/apps/statsdapp/src/com/android/server/cts/device/statsdatom/AtomTests.java
@@ -226,6 +226,7 @@
         APP_OPS_ENUM_MAP.put(AppOpsManager.OPSTR_ESTABLISH_VPN_SERVICE, 117);
         APP_OPS_ENUM_MAP.put(AppOpsManager.OPSTR_ESTABLISH_VPN_MANAGER, 118);
         APP_OPS_ENUM_MAP.put(AppOpsManager.OPSTR_ACCESS_RESTRICTED_SETTINGS, 119);
+        APP_OPS_ENUM_MAP.put(AppOpsManager.OPSTR_RECEIVE_AMBIENT_TRIGGER_AUDIO, 120);
     }
 
     @Test
diff --git a/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmReceiver.java b/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmReceiver.java
index 0e7b8b5..db6207d 100644
--- a/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmReceiver.java
+++ b/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmReceiver.java
@@ -16,6 +16,7 @@
 
 package android.alarmmanager.alarmtestapp.cts;
 
+import android.alarmmanager.alarmtestapp.cts.common.FgsTester;
 import android.content.BroadcastReceiver;
 import android.content.Context;
 import android.content.Intent;
@@ -24,6 +25,8 @@
 public class TestAlarmReceiver extends BroadcastReceiver{
     private static final String TAG = TestAlarmReceiver.class.getSimpleName();
     private static final String PACKAGE_NAME = "android.alarmmanager.alarmtestapp.cts";
+    private static final String INSTRUMENTATION_PACKAGE = "android.alarmmanager.cts";
+
     public static final String ACTION_REPORT_ALARM_EXPIRED = PACKAGE_NAME + ".action.ALARM_EXPIRED";
     public static final String EXTRA_ALARM_COUNT = PACKAGE_NAME + ".extra.ALARM_COUNT";
     public static final String EXTRA_ID = PACKAGE_NAME + ".extra.ID";
@@ -33,10 +36,18 @@
         final int count = intent.getIntExtra(Intent.EXTRA_ALARM_COUNT, 1);
         final long id = intent.getLongExtra(EXTRA_ID, -1);
         Log.d(TAG, "Alarm " + id + " expired " + count + " times");
-        final Intent reportAlarmIntent = new Intent(ACTION_REPORT_ALARM_EXPIRED);
-        reportAlarmIntent.putExtra(EXTRA_ALARM_COUNT, count);
-        reportAlarmIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
-        reportAlarmIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
+
+        final Intent reportAlarmIntent = new Intent(ACTION_REPORT_ALARM_EXPIRED)
+                .putExtra(EXTRA_ALARM_COUNT, count)
+                .setPackage(INSTRUMENTATION_PACKAGE)
+                .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY)
+                .addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
+
+        if (intent.getBooleanExtra(TestAlarmScheduler.EXTRA_TEST_FGS, false)) {
+            final String result = FgsTester.tryStartingFgs(context);
+            Log.d(TAG, "FGS start result: " + result);
+            reportAlarmIntent.putExtra(FgsTester.EXTRA_FGS_START_RESULT, result);
+        }
         context.sendBroadcast(reportAlarmIntent);
     }
 }
diff --git a/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmScheduler.java b/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmScheduler.java
index d9db0b0..78eb875 100644
--- a/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmScheduler.java
+++ b/tests/AlarmManager/app/src/android/alarmmanager/alarmtestapp/cts/TestAlarmScheduler.java
@@ -40,6 +40,7 @@
     public static final String EXTRA_TYPE = PACKAGE_NAME + ".extra.TYPE";
     public static final String ACTION_SET_ALARM_CLOCK = PACKAGE_NAME + ".action.SET_ALARM_CLOCK";
     public static final String EXTRA_ALARM_CLOCK_INFO = PACKAGE_NAME + ".extra.ALARM_CLOCK_INFO";
+    public static final String EXTRA_TEST_FGS = PACKAGE_NAME + ".extra.TEST_FGS";
     public static final String ACTION_CANCEL_ALL_ALARMS = PACKAGE_NAME + ".action.CANCEL_ALARMS";
 
     @Override
@@ -49,6 +50,7 @@
         receiverIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
         final long id = SystemClock.elapsedRealtime();
         receiverIntent.putExtra(TestAlarmReceiver.EXTRA_ID, id);
+        receiverIntent.putExtra(EXTRA_TEST_FGS, intent.getBooleanExtra(EXTRA_TEST_FGS, false));
         final PendingIntent alarmClockSender = PendingIntent.getBroadcast(context, 0,
                 receiverIntent, PendingIntent.FLAG_MUTABLE | PendingIntent.FLAG_UPDATE_CURRENT);
         final PendingIntent alarmSender = PendingIntent.getBroadcast(context, 1, receiverIntent,
diff --git a/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/FgsTester.java b/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/FgsTester.java
new file mode 100644
index 0000000..f3e0be6
--- /dev/null
+++ b/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/FgsTester.java
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2022 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 android.alarmmanager.alarmtestapp.cts.common;
+
+import android.app.ForegroundServiceStartNotAllowedException;
+import android.content.Context;
+import android.content.Intent;
+
+public class FgsTester {
+    public static final String EXTRA_FGS_START_RESULT =
+            "android.alarmmanager.alarmtestapp.cts.common.extra.FGS_START_RESULT";
+
+    private FgsTester() {
+    }
+
+    public static String tryStartingFgs(Context context) {
+        String result;
+        try {
+            // Try starting a foreground service.
+            Intent i = new Intent(context, TestService.class);
+            context.startForegroundService(i);
+
+            result = ""; // Indicates success
+        } catch (ForegroundServiceStartNotAllowedException e) {
+            result = "ForegroundServiceStartNotAllowedException was thrown";
+        } catch (Exception e) {
+            result = "Unexpected exception was thrown: " + e;
+        }
+        return result;
+    }
+}
diff --git a/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/PermissionStateChangedReceiver.java b/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/PermissionStateChangedReceiver.java
index 9adc4a7..573d10c 100644
--- a/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/PermissionStateChangedReceiver.java
+++ b/tests/AlarmManager/app_common/src/android/alarmmanager/alarmtestapp/cts/common/PermissionStateChangedReceiver.java
@@ -17,7 +17,6 @@
 package android.alarmmanager.alarmtestapp.cts.common;
 
 import android.app.AlarmManager;
-import android.app.ForegroundServiceStartNotAllowedException;
 import android.content.BroadcastReceiver;
 import android.content.Context;
 import android.content.Intent;
@@ -30,41 +29,26 @@
 public class PermissionStateChangedReceiver extends BroadcastReceiver {
     private static final String TAG = PermissionStateChangedReceiver.class.getSimpleName();
     private static final String PACKAGE_NAME = "android.alarmmanager.alarmtestapp.cts.common";
-
     private static final String MAIN_CTS_PACKAGE = "android.alarmmanager.cts";
 
-    public static String ACTION_FGS_START_RESULT = PACKAGE_NAME + ".action.FGS_START_RESULT";
-    public static String EXTRA_FGS_START_RESULT = PACKAGE_NAME + ".extra.FGS_START_RESULT";
+    public static final String ACTION_FGS_START_RESULT = PACKAGE_NAME + ".action.FGS_START_RESULT";
 
     @Override
     public void onReceive(Context context, Intent intent) {
         Log.d(TAG, "Broadcast received: " + intent);
         if (AlarmManager.ACTION_SCHEDULE_EXACT_ALARM_PERMISSION_STATE_CHANGED
                 .equals(intent.getAction())) {
-            tryStartingFgs(context);
+
+            final String result = FgsTester.tryStartingFgs(context);
+
+            // Send the result broadcast to the main CTS package.
+            final Intent response = new Intent(ACTION_FGS_START_RESULT);
+            response.setPackage(MAIN_CTS_PACKAGE);
+            response.putExtra(FgsTester.EXTRA_FGS_START_RESULT, result);
+
+            Log.d(TAG, "Sending response: " + result);
+            context.sendBroadcast(response);
         }
     }
 
-    private void tryStartingFgs(Context context) {
-        String result = "Unknown failure";
-        try {
-            // Try starting a foreground service.
-            Intent i = new Intent(context, TestService.class);
-            context.startForegroundService(i);
-
-            result = ""; // Indicates success
-        } catch (ForegroundServiceStartNotAllowedException e) {
-            result = "ForegroundServiceStartNotAllowedException was thrown";
-        } catch (Exception e) {
-            result = "Unexpected exception was thrown: " + e;
-        }
-
-        // Send the result broadcast to the main CTS package.
-        Intent response = new Intent(ACTION_FGS_START_RESULT);
-        response.setPackage(MAIN_CTS_PACKAGE);
-        response.putExtra(EXTRA_FGS_START_RESULT, result);
-
-        Log.d(TAG, "Sending response: " + result);
-        context.sendBroadcast(response);
-    }
 }
diff --git a/tests/AlarmManager/src/android/alarmmanager/cts/ExactAlarmsTest.java b/tests/AlarmManager/src/android/alarmmanager/cts/ExactAlarmsTest.java
index 0cf62ed..44780e7 100644
--- a/tests/AlarmManager/src/android/alarmmanager/cts/ExactAlarmsTest.java
+++ b/tests/AlarmManager/src/android/alarmmanager/cts/ExactAlarmsTest.java
@@ -26,6 +26,9 @@
 import static org.junit.Assert.assertTrue;
 import static org.junit.Assume.assumeFalse;
 
+import android.alarmmanager.alarmtestapp.cts.TestAlarmReceiver;
+import android.alarmmanager.alarmtestapp.cts.TestAlarmScheduler;
+import android.alarmmanager.alarmtestapp.cts.common.FgsTester;
 import android.alarmmanager.alarmtestapp.cts.common.PermissionStateChangedReceiver;
 import android.alarmmanager.alarmtestapp.cts.common.RequestReceiver;
 import android.alarmmanager.util.AlarmManagerDeviceConfigHelper;
@@ -34,6 +37,7 @@
 import android.app.AlarmManager;
 import android.app.AppOpsManager;
 import android.app.PendingIntent;
+import android.app.compat.CompatChanges;
 import android.content.BroadcastReceiver;
 import android.content.ComponentName;
 import android.content.Context;
@@ -142,6 +146,7 @@
                 .with("allow_while_idle_quota", ALLOW_WHILE_IDLE_QUOTA)
                 .with("allow_while_idle_compat_quota", ALLOW_WHILE_IDLE_COMPAT_QUOTA)
                 .with("allow_while_idle_window", ALLOW_WHILE_IDLE_WINDOW)
+                .with("kill_on_schedule_exact_alarm_revoked", false)
                 .commitAndAwaitPropagation();
     }
 
@@ -155,8 +160,6 @@
     public void enableChanges() {
         Utils.enableChangeForSelf(AlarmManager.REQUIRE_EXACT_ALARM_PERMISSION);
         Utils.enableChangeForSelf(AlarmManager.ENABLE_USE_EXACT_ALARM);
-        Utils.enableChange(AlarmManager.SCHEDULE_EXACT_ALARM_DENIED_BY_DEFAULT, TEST_APP_PACKAGE,
-                sContext.getUserId());
     }
 
     @After
@@ -191,14 +194,14 @@
                         PackageManager.DONT_KILL_APP));
     }
 
-    private void resetAppOps() throws IOException {
+    @After
+    public void resetAppOps() throws IOException {
         AppOpsUtils.reset(TEST_APP_PACKAGE);
+        AppOpsUtils.reset(TEST_APP_30);
     }
 
     @After
     public void restoreAlarmManagerConstants() throws IOException {
-        // App ops must be reset while kill_on_schedule_exact_alarm_revoked=false
-        resetAppOps();
         mDeviceConfigHelper.restoreAll();
     }
 
@@ -247,21 +250,25 @@
     }
 
     @Test
+    public void scheduleExactAlarmChangeDisabled() {
+        assertFalse(CompatChanges.isChangeEnabled(
+                AlarmManager.SCHEDULE_EXACT_ALARM_DENIED_BY_DEFAULT));
+    }
+
+    @Test
     public void defaultBehaviorWhenChangeDisabled() throws Exception {
         setAppOp(TEST_APP_PACKAGE, AppOpsManager.MODE_DEFAULT);
-        mDeviceConfigHelper.with("schedule_exact_alarm_denied_by_default", false)
-                .commitAndAwaitPropagation();
         assertTrue(getCanScheduleExactAlarmFromTestApp(TEST_APP_PACKAGE));
 
         mDeviceConfigHelper.with("exact_alarm_deny_list", TEST_APP_PACKAGE)
                 .commitAndAwaitPropagation();
-        // Just to give some time for the app kill to complete.
-        Thread.sleep(1000);
         assertFalse(getCanScheduleExactAlarmFromTestApp(TEST_APP_PACKAGE));
     }
 
     @Test
-    public void noPermissionByDefault() throws Exception {
+    public void defaultBehaviorWhenChangeEnabled() throws Exception {
+        Utils.enableChange(AlarmManager.SCHEDULE_EXACT_ALARM_DENIED_BY_DEFAULT, TEST_APP_PACKAGE,
+                sContext.getUserId());
         setAppOp(TEST_APP_PACKAGE, AppOpsManager.MODE_DEFAULT);
         assertFalse(getCanScheduleExactAlarmFromTestApp(TEST_APP_PACKAGE));
     }
@@ -362,6 +369,61 @@
                 () -> mWhitelistManager.addToWhitelist(sContext.getOpPackageName()));
     }
 
+    private void setAlarmClockForFgs(long triggerRTC, String testAppName) throws Exception {
+        final CountDownLatch resultLatch = new CountDownLatch(1);
+        final AtomicInteger result = new AtomicInteger(-1);
+
+        AlarmManager.AlarmClockInfo alarmInfo = new AlarmManager.AlarmClockInfo(triggerRTC, null);
+
+        final Intent requestToTestApp = new Intent(TestAlarmScheduler.ACTION_SET_ALARM_CLOCK)
+                .setClassName(testAppName, TestAlarmScheduler.class.getName())
+                .putExtra(TestAlarmScheduler.EXTRA_ALARM_CLOCK_INFO, alarmInfo)
+                .putExtra(TestAlarmScheduler.EXTRA_TEST_FGS, true)
+                .addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
+
+        sContext.sendOrderedBroadcast(requestToTestApp, null, new BroadcastReceiver() {
+            @Override
+            public void onReceive(Context context, Intent intent) {
+                result.set(getResultCode());
+                resultLatch.countDown();
+            }
+        }, null, Activity.RESULT_CANCELED, null, null);
+
+        assertTrue("Timed out waiting for response from helper app " + testAppName,
+                resultLatch.await(10, TimeUnit.SECONDS));
+        assertEquals(Activity.RESULT_OK, result.get());
+    }
+
+    @Test
+    public void alarmClockAllowsFGS() throws Exception {
+        setAppOp(TEST_APP_PACKAGE, AppOpsManager.MODE_ALLOWED);
+
+        final long triggerRtc = System.currentTimeMillis() + 5_000;
+        setAlarmClockForFgs(triggerRtc, TEST_APP_PACKAGE);
+
+        final AtomicReference<String> resultHolder = new AtomicReference<>();
+        final CountDownLatch alarmLatch = new CountDownLatch(1);
+
+        final IntentFilter filter = new IntentFilter(TestAlarmReceiver.ACTION_REPORT_ALARM_EXPIRED);
+        final BroadcastReceiver receiver = new BroadcastReceiver() {
+            @Override
+            public void onReceive(Context context, Intent intent) {
+                Log.d(TAG, "Received response intent: " + intent);
+                resultHolder.set(intent.getStringExtra(FgsTester.EXTRA_FGS_START_RESULT));
+                alarmLatch.countDown();
+            }
+        };
+        sContext.registerReceiver(receiver, filter);
+        try {
+            Thread.sleep(5_000);
+            assertTrue("AlarmClock expiration not reported",
+                    alarmLatch.await(30, TimeUnit.SECONDS));
+            assertEquals("FGS result should be empty", "", resultHolder.get());
+        } finally {
+            sContext.unregisterReceiver(receiver);
+        }
+    }
+
     @Test
     public void setAlarmClockWithPermission() throws Exception {
         final long now = System.currentTimeMillis();
@@ -383,7 +445,6 @@
                 TEST_APP_PACKAGE);
     }
 
-
     @Test
     public void setExactAwiWithoutPermissionOrWhitelist() throws Exception {
         revokeAppOp(TEST_APP_PACKAGE);
@@ -577,7 +638,7 @@
             public void onReceive(Context context, Intent intent) {
                 Log.d(TAG, "Received response intent: " + intent);
                 resultHolder.set(intent.getStringExtra(
-                        PermissionStateChangedReceiver.EXTRA_FGS_START_RESULT));
+                        FgsTester.EXTRA_FGS_START_RESULT));
                 latch.countDown();
             }
         };
@@ -618,7 +679,7 @@
             public void onReceive(Context context, Intent intent) {
                 Log.d(TAG, "Received response intent: " + intent);
                 resultHolder.set(intent.getStringExtra(
-                        PermissionStateChangedReceiver.EXTRA_FGS_START_RESULT));
+                        FgsTester.EXTRA_FGS_START_RESULT));
                 latch.countDown();
             }
         };
diff --git a/tests/MediaProviderTranscode/Android.bp b/tests/MediaProviderTranscode/Android.bp
index 54ee715..cbf6fe2 100644
--- a/tests/MediaProviderTranscode/Android.bp
+++ b/tests/MediaProviderTranscode/Android.bp
@@ -32,8 +32,7 @@
     ],
 
     min_sdk_version: "30",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
     certificate: "media",
     java_resources: [":CtsTranscodeTestAppSupportsHevc", ":CtsTranscodeTestAppSupportsSlowMotion"]
 }
diff --git a/tests/app/app/src/android/app/stubs/CommandReceiver.java b/tests/app/app/src/android/app/stubs/CommandReceiver.java
index 5e154f7..26ab62b 100644
--- a/tests/app/app/src/android/app/stubs/CommandReceiver.java
+++ b/tests/app/app/src/android/app/stubs/CommandReceiver.java
@@ -19,15 +19,19 @@
 import android.app.Activity;
 import android.app.ActivityManager;
 import android.app.ForegroundServiceStartNotAllowedException;
+import android.app.IActivityManager;
 import android.app.PendingIntent;
 import android.content.BroadcastReceiver;
 import android.content.ComponentName;
 import android.content.Context;
 import android.content.Intent;
 import android.content.ServiceConnection;
+import android.content.pm.PackageManager;
 import android.os.Bundle;
 import android.os.IBinder;
 import android.os.Parcel;
+import android.os.RemoteException;
+import android.text.TextUtils;
 import android.util.ArrayMap;
 import android.util.Log;
 
@@ -61,6 +65,7 @@
     public static final int COMMAND_START_FOREGROUND_SERVICE_STICKY = 20;
     public static final int COMMAND_STOP_FOREGROUND_SERVICE_STICKY = 21;
     public static final int COMMAND_EMPTY = 22;
+    public static final int COMMAND_START_FOREGROUND_SERVICE_SPOOF_PACKAGE_NAME = 23;
 
     public static final int RESULT_CHILD_PROCESS_STARTED = IBinder.FIRST_CALL_TRANSACTION;
     public static final int RESULT_CHILD_PROCESS_STOPPED = IBinder.FIRST_CALL_TRANSACTION + 1;
@@ -170,6 +175,9 @@
                 break;
             case COMMAND_EMPTY:
                 break;
+            case COMMAND_START_FOREGROUND_SERVICE_SPOOF_PACKAGE_NAME:
+                doStartForegroundServiceSpoofPackageName(context, intent);
+                break;
         }
     }
 
@@ -371,6 +379,56 @@
         }).start();
     }
 
+    /**
+     * Directly call IActivityManager.startService() using a spoofed packageName which is known to
+     * be allowlisted by Android framework to be able to start foreground service
+     * from the background. Framework will disallow the foreground service to start from the
+     * background and a ForegroundServiceStartNotAllowedException will be caught.
+     * @param context
+     * @param commandIntent
+     */
+    private void doStartForegroundServiceSpoofPackageName(Context context, Intent commandIntent) {
+        String targetPackage = getTargetPackage(commandIntent);
+        Intent fgsIntent = new Intent();
+        fgsIntent.putExtras(commandIntent);
+        fgsIntent.setComponent(new ComponentName(targetPackage, FG_SERVICE_NAME));
+        int command = LocalForegroundService.COMMAND_START_FOREGROUND;
+        fgsIntent.putExtras(LocalForegroundService.newCommand(command));
+        try {
+            final PackageManager pm = context.getPackageManager();
+            String spoofPackageName = pm.getAttentionServicePackageName();
+            if (TextUtils.isEmpty(spoofPackageName)) {
+                Log.d(TAG, "getAttentionServicePackageName() returns empty");
+                spoofPackageName = pm.getSystemCaptionsServicePackageName();
+            }
+            if (TextUtils.isEmpty(spoofPackageName)) {
+                Log.d(TAG, "getSystemCaptionsServicePackageName() returns empty");
+                spoofPackageName = "android";
+            }
+            Log.d(TAG, "spoofPackageName: " + spoofPackageName);
+            final IBinder activityProxy = android.os.ServiceManager.getService("activity");
+            // Call IActivityManager.startService() directly using a spoofed packageName.
+            IActivityManager.Stub.asInterface(activityProxy).startService(
+                    context.getIApplicationThread(),
+                    fgsIntent,
+                    null,
+                    true,
+                    spoofPackageName,
+                    null,
+                    android.os.Process.myUserHandle().getIdentifier()
+            );
+        } catch (ForegroundServiceStartNotAllowedException e) {
+            Log.d(TAG, "startForegroundService gets an "
+                    + " ForegroundServiceStartNotAllowedException", e);
+        } catch (LinkageError e) {
+            // IActivityManager.startService() is a hidden API, access hidden API could get
+            // LinkageError, consider the test as pass if we get LinkageError.
+            Log.d(TAG, "startForegroundService gets an LinkageError", e);
+        } catch (RemoteException e) {
+            Log.d(TAG, "startForegroundService gets an RemoteException", e);
+        }
+    }
+
     private String getTargetPackage(Intent intent) {
         return intent.getStringExtra(EXTRA_TARGET_PACKAGE);
     }
diff --git a/tests/app/src/android/app/cts/ActivityManagerFgsBgStartTest.java b/tests/app/src/android/app/cts/ActivityManagerFgsBgStartTest.java
index 0f98cdf..ff40aff 100644
--- a/tests/app/src/android/app/cts/ActivityManagerFgsBgStartTest.java
+++ b/tests/app/src/android/app/cts/ActivityManagerFgsBgStartTest.java
@@ -60,6 +60,7 @@
 import android.platform.test.annotations.AsbSecurityTest;
 import android.provider.DeviceConfig;
 import android.provider.Settings;
+import android.server.wm.settings.SettingsSession;
 import android.support.test.uiautomator.UiDevice;
 import android.util.Log;
 
@@ -2015,6 +2016,52 @@
     }
 
     /**
+     * IActivityManager.startService() is called directly (does not go through
+     * {@link Context#startForegroundService(Intent)}, a spoofed packageName "com.google.android.as"
+     * is used as callingPackage. Although "com.google.android.as" is allowlisted to start
+     * foreground service from the background, but framework will detect this is a spoofed
+     * packageName and disallow foreground service start from the background.
+     * @throws Exception
+     */
+    @Test
+    public void testSpoofPackageName() throws Exception {
+        ApplicationInfo app1Info = mContext.getPackageManager().getApplicationInfo(
+                PACKAGE_NAME_APP1, 0);
+        WatchUidRunner uid1Watcher = new WatchUidRunner(mInstrumentation, app1Info.uid,
+                WAITFOR_MSEC);
+        // CommandReceiver.COMMAND_START_FOREGROUND_SERVICE_SPOOF_PACKAGE_NAME needs access
+        // to hidden API PackageManager.getAttentionServicePackageName() and
+        // PackageManager.getSystemCaptionsServicePackageName(), so we need to call
+        // hddenApiSettings.set("*") to exempt the hidden APIs.
+        SettingsSession<String> hiddenApiSettings = new SettingsSession<>(
+                Settings.Global.getUriFor(
+                        Settings.Global.HIDDEN_API_BLACKLIST_EXEMPTIONS),
+                Settings.Global::getString, Settings.Global::putString);
+        hiddenApiSettings.set("*");
+        try {
+            // Enable the FGS background startForeground() restriction.
+            enableFgsRestriction(true, true, null);
+            // Start FGS in BG state.
+            WaitForBroadcast waiter = new WaitForBroadcast(mInstrumentation.getTargetContext());
+            waiter.prepare(ACTION_START_FGS_RESULT);
+            CommandReceiver.sendCommand(mContext,
+                    CommandReceiver.COMMAND_START_FOREGROUND_SERVICE_SPOOF_PACKAGE_NAME,
+                    PACKAGE_NAME_APP1, PACKAGE_NAME_APP1, 0, null);
+            // APP1 does not enter FGS state
+            try {
+                waiter.doWait(WAITFOR_MSEC);
+                fail("Service should not enter foreground service state");
+            } catch (Exception e) {
+            }
+        } finally {
+            uid1Watcher.finish();
+            if (hiddenApiSettings != null) {
+                hiddenApiSettings.close();
+            }
+        }
+    }
+
+    /**
      * Turn on the FGS BG-launch restriction. DeviceConfig can turn on restriction on the whole
      * device (across all apps). AppCompat can turn on restriction on a single app package.
      * @param enable true to turn on restriction, false to turn off.
diff --git a/tests/app/src/android/app/cts/WallpaperManagerTest.java b/tests/app/src/android/app/cts/WallpaperManagerTest.java
index fc640a5..7fbd297 100644
--- a/tests/app/src/android/app/cts/WallpaperManagerTest.java
+++ b/tests/app/src/android/app/cts/WallpaperManagerTest.java
@@ -29,7 +29,6 @@
 import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.verify;
 
-import android.Manifest;
 import android.app.WallpaperColors;
 import android.app.WallpaperManager;
 import android.app.stubs.R;
@@ -52,8 +51,6 @@
 import androidx.test.InstrumentationRegistry;
 import androidx.test.runner.AndroidJUnit4;
 
-import com.android.compatibility.common.util.CddTest;
-
 import org.junit.After;
 import org.junit.Assert;
 import org.junit.Before;
@@ -71,9 +68,6 @@
 
     private static final boolean DEBUG = false;
     private static final String TAG = "WallpaperManagerTest";
-    private static final long MAX_WAIT_TIME_SECS = 2;
-    private static final long MAX_WAIT_TIME_MS = MAX_WAIT_TIME_SECS * 1000;
-    private static final long WAIT_TIME_INCR_MS = 100;
 
     private WallpaperManager mWallpaperManager;
     private Context mContext;
@@ -81,7 +75,6 @@
     private BroadcastReceiver mBroadcastReceiver;
     private CountDownLatch mCountDownLatch;
     private boolean mEnableWcg;
-    private boolean mAcquiredWallpaperDimmingPermission = false;
 
     @Before
     public void setUp() throws Exception {
@@ -113,24 +106,6 @@
         if (mBroadcastReceiver != null) {
             mContext.unregisterReceiver(mBroadcastReceiver);
         }
-        if (mAcquiredWallpaperDimmingPermission) {
-            try {
-                mWallpaperManager.setWallpaperDimAmount(0f);
-                assertDimAmountEqualsTo(0f);
-            } finally {
-                InstrumentationRegistry.getInstrumentation().getUiAutomation()
-                        .dropShellPermissionIdentity();
-                mAcquiredWallpaperDimmingPermission = false;
-            }
-        }
-    }
-
-    private void ensureSetWallpaperDimAmountPermissionIsGranted() {
-        if (!mAcquiredWallpaperDimmingPermission) {
-            InstrumentationRegistry.getInstrumentation().getUiAutomation()
-                .adoptShellPermissionIdentity(Manifest.permission.SET_WALLPAPER_DIM_AMOUNT);
-            mAcquiredWallpaperDimmingPermission = true;
-        }
     }
 
     @Test
@@ -428,96 +403,6 @@
         }
     }
 
-    @Test
-    public void testGetWallpaperDimAmountWithNoPermission_shouldThrowException() {
-        Assert.assertThrows(SecurityException.class,
-                () -> mWallpaperManager.getWallpaperDimAmount());
-    }
-
-    @Test
-    public void testSetWallpaperDimAmountWithNoPermission_shouldThrowException() {
-        Assert.assertThrows(SecurityException.class,
-                () -> {
-                    float dimAmount = 0.5f;
-                    mWallpaperManager.setWallpaperDimAmount(dimAmount);
-                    assertDimAmountEqualsTo(dimAmount);
-                });
-    }
-
-    @Test
-    public void setWallpaperDimAmount_withinBound_shouldSetDimAmount() {
-        ensureSetWallpaperDimAmountPermissionIsGranted();
-
-        float dimAmount = 0.6f;
-        mWallpaperManager.setWallpaperDimAmount(dimAmount);
-        assertDimAmountEqualsTo(dimAmount);
-
-        // Remove additional dimming and verify that the dim amount is set to 0 again
-        mWallpaperManager.setWallpaperDimAmount(0f);
-        assertDimAmountEqualsTo(0f);
-    }
-
-    @Test
-    public void setWallpaperDimAmountBeyondRange_shouldBeBounded() {
-        ensureSetWallpaperDimAmountPermissionIsGranted();
-
-        // Setting dim amount < 0 should be bounded to lower limit 0.0
-        mWallpaperManager.setWallpaperDimAmount(-1f);
-        assertDimAmountEqualsTo(0f);
-
-        // Setting dim amount > 1 should be bounded to upper limit 1.0
-        mWallpaperManager.setWallpaperDimAmount(1.5f);
-        assertDimAmountEqualsTo(1f);
-    }
-
-    @CddTest(requirement = "3.8.7.1/H-1-2")
-    @Test
-    public void setWallpaperDimAmount_changingWallpaperShouldRemainDimmed() throws IOException {
-        ensureSetWallpaperDimAmountPermissionIsGranted();
-
-        float dimAmount = 0.65f;
-        mWallpaperManager.setWallpaperDimAmount(dimAmount);
-        mWallpaperManager.setResource(R.drawable.robot);
-
-        assertDimAmountEqualsTo(dimAmount);
-    }
-
-    @Test
-    public void colorHintsOnDimTest() throws IOException {
-        ensureSetWallpaperDimAmountPermissionIsGranted();
-
-        Bitmap tmpWallpaper = Bitmap.createBitmap(100, 100, Bitmap.Config.ARGB_8888);
-        Canvas canvas = new Canvas(tmpWallpaper);
-        canvas.drawColor(Color.WHITE);
-
-        mWallpaperManager.setBitmap(tmpWallpaper);
-
-        WallpaperColors colors = mWallpaperManager
-                .getWallpaperColors(WallpaperManager.FLAG_SYSTEM);
-        int colorHints = colors.getColorHints();
-        // Color hints support dark text on white wallpaper
-        Assert.assertEquals(WallpaperColors.HINT_SUPPORTS_DARK_TEXT,
-                colorHints & WallpaperColors.HINT_SUPPORTS_DARK_TEXT);
-
-        float lowDimAmount = 0.1f;
-        mWallpaperManager.setWallpaperDimAmount(lowDimAmount);
-        assertDimAmountEqualsTo(lowDimAmount);
-        colors = mWallpaperManager.getWallpaperColors(WallpaperManager.FLAG_SYSTEM);
-        colorHints = colors.getColorHints();
-        // Color hints still support dark text on white wallpaper that is not dimmed enough
-        Assert.assertEquals(WallpaperColors.HINT_SUPPORTS_DARK_TEXT,
-                colorHints & WallpaperColors.HINT_SUPPORTS_DARK_TEXT);
-
-        float higherDimAmount = 0.7f;
-        mWallpaperManager.setWallpaperDimAmount(higherDimAmount);
-        assertDimAmountEqualsTo(higherDimAmount);
-        colors = mWallpaperManager.getWallpaperColors(WallpaperManager.FLAG_SYSTEM);
-        colorHints = colors.getColorHints();
-        // Dimmed white wallpaper does not support dark text
-        Assert.assertNotEquals(WallpaperColors.HINT_SUPPORTS_DARK_TEXT,
-                colorHints & WallpaperColors.HINT_SUPPORTS_DARK_TEXT);
-    }
-
     private void assertBitmapDimensions(Bitmap bitmap) {
         int maxSize = getMaxTextureSize();
         boolean safe = false;
@@ -686,20 +571,6 @@
         return spy(new TestableColorListener());
     }
 
-    private void assertDimAmountEqualsTo(float dimAmount) {
-        float storedDimAmount = -1f;
-        for (int i = 0; i < MAX_WAIT_TIME_MS; i += WAIT_TIME_INCR_MS) {
-            storedDimAmount = mWallpaperManager.getWallpaperDimAmount();
-            if (dimAmount == storedDimAmount) break;
-            try {
-                Thread.sleep(WAIT_TIME_INCR_MS);
-            } catch (InterruptedException e) {
-                e.printStackTrace();
-            }
-        }
-        Assert.assertEquals(dimAmount, storedDimAmount, /* delta */ 0f);
-    }
-
     public class TestableColorListener implements WallpaperManager.OnColorsChangedListener {
         @Override
         public void onColorsChanged(WallpaperColors colors, int which) {
diff --git a/tests/autofillservice/src/android/autofillservice/cts/commontests/AbstractWebViewTestCase.java b/tests/autofillservice/src/android/autofillservice/cts/commontests/AbstractWebViewTestCase.java
index 7720bc8..d2bd91a 100644
--- a/tests/autofillservice/src/android/autofillservice/cts/commontests/AbstractWebViewTestCase.java
+++ b/tests/autofillservice/src/android/autofillservice/cts/commontests/AbstractWebViewTestCase.java
@@ -18,6 +18,10 @@
 import android.autofillservice.cts.activities.AbstractWebViewActivity;
 import android.autofillservice.cts.testcore.IdMode;
 import android.autofillservice.cts.testcore.UiBot;
+import android.content.Context;
+import android.content.res.Resources;
+
+import androidx.test.InstrumentationRegistry;
 
 import org.junit.AfterClass;
 import org.junit.BeforeClass;
@@ -45,4 +49,20 @@
     public static void resetReplierMode() {
         sReplier.setIdMode(IdMode.RESOURCE_ID);
     }
+
+    /**
+     * @return whether the preventable IME feature as specified by {@code
+     * config_preventImeStartupUnlessTextEditor} is enabled.
+     */
+    protected static boolean isPreventImeStartup() {
+        final Context context = InstrumentationRegistry.getInstrumentation().getContext();
+        try {
+            return context.getResources().getBoolean(
+                    Resources.getSystem().getIdentifier(
+                            "config_preventImeStartupUnlessTextEditor", "bool", "android"));
+        } catch (Resources.NotFoundException e) {
+            // Assume this is not enabled.
+            return false;
+        }
+    }
 }
diff --git a/tests/autofillservice/src/android/autofillservice/cts/commontests/FillEventHistoryCommonTestCase.java b/tests/autofillservice/src/android/autofillservice/cts/commontests/FillEventHistoryCommonTestCase.java
index 416c79a..9ab86ce 100644
--- a/tests/autofillservice/src/android/autofillservice/cts/commontests/FillEventHistoryCommonTestCase.java
+++ b/tests/autofillservice/src/android/autofillservice/cts/commontests/FillEventHistoryCommonTestCase.java
@@ -574,12 +574,12 @@
         enableService();
 
         // Set expectations.
-        final CannedFillResponse.Builder builder = createTestResponseBuilder();
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ true);
         sReplier.addResponse(builder.build());
 
         // Trigger autofill and set the save UI not show reason with
         // NO_SAVE_UI_REASON_NO_SAVE_INFO.
-        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_NO_SAVE_INFO);
+        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_NO_SAVE_INFO, /* withDataSet= */ true);
 
         // Finish the context by login in and it will trigger to check if the save UI should be
         // shown.
@@ -603,17 +603,8 @@
         enableService();
 
         // Set expectations.
-        final CannedFillResponse.Builder builder = createTestResponseBuilder();
-        builder.setSaveInfoFlags(SaveInfo.FLAG_DELAY_SAVE);
-        sReplier.addResponse(builder.build());
-
-        // Trigger autofill and set the save UI not show reason with
-        // NO_SAVE_UI_REASON_WITH_DELAY_SAVE_FLAG.
-        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_WITH_DELAY_SAVE_FLAG);
-
-        // Finish the context by login in and it will trigger to check if the save UI should be
-        // shown.
-        tapLogin();
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ true);
+        contextCommitted_whileDelaySave(builder, /* withDataSet= */ true);
 
         // Verify that the save UI should not be shown and the history should include the reason.
         mUiBot.assertSaveNotShowing(SAVE_DATA_TYPE_PASSWORD);
@@ -624,6 +615,38 @@
         assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_WITH_DELAY_SAVE_FLAG);
     }
 
+    @Test
+    public void testContextCommitted_noSaveUi_whileDelaySave_noDataset() throws Exception {
+        enableService();
+
+        // Set expectations.
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ false);
+        contextCommitted_whileDelaySave(builder, /* withDataSet= */ false);
+
+        // Verify that the save UI should not be shown and the history should include the reason.
+        mUiBot.assertSaveNotShowing(SAVE_DATA_TYPE_PASSWORD);
+
+        final List<Event> verifyEvents = InstrumentedAutoFillService.getFillEvents(1);
+        final Event event = verifyEvents.get(0);
+
+        assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_WITH_DELAY_SAVE_FLAG);
+    }
+
+    // TODO: refine the helper function
+    private void contextCommitted_whileDelaySave(CannedFillResponse.Builder builder,
+            boolean withDataSet) throws Exception {
+        builder.setSaveInfoFlags(SaveInfo.FLAG_DELAY_SAVE);
+        sReplier.addResponse(builder.build());
+
+        // Trigger autofill and set the save UI not show reason with
+        // NO_SAVE_UI_REASON_WITH_DELAY_SAVE_FLAG.
+        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_WITH_DELAY_SAVE_FLAG, withDataSet);
+
+        // Finish the context by login in and it will trigger to check if the save UI should be
+        // shown.
+        tapLogin();
+    }
+
     /**
      * Tests scenario where the context was committed, the save dialog was not shown because there
      * was empty value for required ids.
@@ -633,17 +656,8 @@
         enableService();
 
         // Set expectations.
-        final CannedFillResponse.Builder builder = createTestResponseBuilder();
-        builder.setRequiredSavableIds(SAVE_DATA_TYPE_PASSWORD, ID_USERNAME, ID_PASSWORD);
-        sReplier.addResponse(builder.build());
-
-        // Trigger autofill and set the save UI not show reason with
-        // NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED.
-        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED);
-
-        // Finish the context by login in and it will trigger to check if the save UI should be
-        // shown.
-        tapLogin();
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ true);
+        contextCommitted_whileEmptyValueForRequiredIds(builder, /* withDataSet= */ true);
 
         // Verify that the save UI should not be shown and the history should include the reason.
         mUiBot.assertSaveNotShowing(SAVE_DATA_TYPE_PASSWORD);
@@ -654,6 +668,38 @@
         assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED);
     }
 
+    @Test
+    public void testContextCommitted_noSaveUi_whileEmptyValueForRequiredIds_noDataset()
+            throws Exception {
+        enableService();
+
+        // Set expectations.
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ false);
+        contextCommitted_whileEmptyValueForRequiredIds(builder, /* withDataSet= */ false);
+
+        // Verify that the save UI should not be shown and the history should include the reason.
+        mUiBot.assertSaveNotShowing(SAVE_DATA_TYPE_PASSWORD);
+
+        final List<Event> verifyEvents = InstrumentedAutoFillService.getFillEvents(1);
+        final Event event = verifyEvents.get(0);
+
+        assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED);
+    }
+
+    private void contextCommitted_whileEmptyValueForRequiredIds(CannedFillResponse.Builder builder,
+                boolean withDataSet) throws Exception {
+        builder.setRequiredSavableIds(SAVE_DATA_TYPE_PASSWORD, ID_USERNAME, ID_PASSWORD);
+        sReplier.addResponse(builder.build());
+
+        // Trigger autofill and set the save UI not show reason with
+        // NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED.
+        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED, withDataSet);
+
+        // Finish the context by login in and it will trigger to check if the save UI should be
+        // shown.
+        tapLogin();
+    }
+
     /**
      * Tests scenario where the context was committed, the save dialog was not shown because no
      * value has been changed.
@@ -663,13 +709,16 @@
         enableService();
 
         // Set expectations.
-        final CannedFillResponse.Builder builder = createTestResponseBuilder();
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ true);
         builder.setRequiredSavableIds(SAVE_DATA_TYPE_PASSWORD, ID_USERNAME, ID_PASSWORD);
         sReplier.addResponse(builder.build());
 
         // Trigger autofill and set the save UI not show reason with
         // NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED.
-        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_NO_VALUE_CHANGED);
+        // This test will compare the autofilled value and the ViewState value so the dataset
+        // is needed in this case.
+        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_NO_VALUE_CHANGED,
+                /* withDataSet= */ true);
 
         // Finish the context by login in and it will trigger to check if the save UI should be
         // shown.
@@ -693,7 +742,33 @@
         enableService();
 
         // Set expectations.
-        final CannedFillResponse.Builder builder = createTestResponseBuilder();
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ true);
+        contextCommitted_whileFieldsFailedValidation(builder, /* withDataSet= */ true);
+
+
+        final List<Event> verifyEvents = InstrumentedAutoFillService.getFillEvents(2);
+        final Event event = verifyEvents.get(1);
+
+        assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_FIELD_VALIDATION_FAILED);
+    }
+
+    @Test
+    public void testContextCommitted_noSaveUi_whileFieldsFailedValidation_noDataSet()
+            throws Exception {
+        enableService();
+
+        // Set expectations.
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ false);
+        contextCommitted_whileFieldsFailedValidation(builder, /* withDataSet= */ false);
+
+        final List<Event> verifyEvents = InstrumentedAutoFillService.getFillEvents(1);
+        final Event event = verifyEvents.get(0);
+
+        assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_FIELD_VALIDATION_FAILED);
+    }
+
+    private void contextCommitted_whileFieldsFailedValidation(CannedFillResponse.Builder builder,
+            boolean withDataSet) throws Exception {
         builder.setRequiredSavableIds(SAVE_DATA_TYPE_PASSWORD, ID_USERNAME, ID_PASSWORD)
                 .setSaveInfoVisitor((contexts, saveInfoBuilder) -> {
                     final Validator validator =
@@ -704,7 +779,7 @@
 
         // Trigger autofill and set the save UI not show reason with
         // NO_SAVE_UI_REASON_FIELD_VALIDATION_FAILED.
-        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_FIELD_VALIDATION_FAILED);
+        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_FIELD_VALIDATION_FAILED, withDataSet);
 
         // Finish the context by login in and it will trigger to check if the save UI should be
         // shown.
@@ -712,11 +787,6 @@
 
         // Verify that the save UI should not be shown and the history should include the reason.
         mUiBot.assertSaveNotShowing(SAVE_DATA_TYPE_PASSWORD);
-
-        final List<Event> verifyEvents = InstrumentedAutoFillService.getFillEvents(2);
-        final Event event = verifyEvents.get(1);
-
-        assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_FIELD_VALIDATION_FAILED);
     }
 
     /**
@@ -728,13 +798,13 @@
         enableService();
 
         // Set expectations.
-        final CannedFillResponse.Builder builder = createTestResponseBuilder();
+        CannedFillResponse.Builder builder = createTestResponseBuilder(/* withDataSet= */ true);
         builder.setRequiredSavableIds(SAVE_DATA_TYPE_PASSWORD, ID_USERNAME, ID_PASSWORD);
         sReplier.addResponse(builder.build());
 
         // Trigger autofill and set the save UI not show reason with
         // NO_SAVE_UI_REASON_DATASET_MATCH.
-        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_DATASET_MATCH);
+        triggerAutofillForSaveUiCondition(NO_SAVE_UI_REASON_DATASET_MATCH, /* withDataSet= */ true);
 
         // Finish the context by login in and it will trigger to check if the save UI should be
         // shown.
@@ -749,28 +819,33 @@
         assertThat(event.getNoSaveUiReason()).isEqualTo(NO_SAVE_UI_REASON_DATASET_MATCH);
     }
 
-    private CannedFillResponse.Builder createTestResponseBuilder() {
-        return new CannedFillResponse.Builder()
-                .addDataset(new CannedDataset.Builder()
-                        .setId("id1")
-                        .setField(ID_USERNAME, BACKDOOR_USERNAME)
-                        .setField(ID_PASSWORD, "whatever")
-                        .setPresentation("dataset1", isInlineMode())
-                        .build())
-                .setFillResponseFlags(FillResponse.FLAG_TRACK_CONTEXT_COMMITED);
+    private CannedFillResponse.Builder createTestResponseBuilder(boolean withDataSet) {
+        CannedFillResponse.Builder builder = new CannedFillResponse.Builder();
+        if (withDataSet) {
+            builder.addDataset(new CannedDataset.Builder()
+                    .setId("id1")
+                    .setField(ID_USERNAME, BACKDOOR_USERNAME)
+                    .setField(ID_PASSWORD, "whatever")
+                    .setPresentation("dataset1", isInlineMode())
+                    .build());
+        }
+        return builder.setFillResponseFlags(FillResponse.FLAG_TRACK_CONTEXT_COMMITED);
     }
 
     /**
      * Triggers autofill on username first and set the behavior of the different conditions so that
      * the save UI should not be shown.
      */
-    private void triggerAutofillForSaveUiCondition(int reason) throws Exception {
+    private void triggerAutofillForSaveUiCondition(int reason, boolean withDataSet)
+            throws Exception {
         // Trigger autofill on username and check the suggestion is shown.
         mUiBot.focusByRelativeId(ID_USERNAME);
         mUiBot.waitForIdle();
         sReplier.getNextFillRequest();
 
-        mUiBot.assertDatasets("dataset1");
+        if (withDataSet) {
+            mUiBot.assertDatasets("dataset1");
+        }
 
         if (reason == NO_SAVE_UI_REASON_HAS_EMPTY_REQUIRED) {
             // Set empty value on password to meet that there was empty value for required ids.
diff --git a/tests/autofillservice/src/android/autofillservice/cts/dropdown/CheckoutActivityTest.java b/tests/autofillservice/src/android/autofillservice/cts/dropdown/CheckoutActivityTest.java
index 1e3535e..94fe54d 100644
--- a/tests/autofillservice/src/android/autofillservice/cts/dropdown/CheckoutActivityTest.java
+++ b/tests/autofillservice/src/android/autofillservice/cts/dropdown/CheckoutActivityTest.java
@@ -76,6 +76,7 @@
 import android.widget.Spinner;
 import android.widget.TimePicker;
 
+import org.junit.Ignore;
 import org.junit.Test;
 
 import java.util.Arrays;
@@ -573,6 +574,7 @@
     }
 
     @Test
+    @Ignore("b/232198065 Fix touch mode problem in ActivityTestRule")
     public void autofillOneListValueToSpinner() throws Exception {
         autofillListValue(AutofillValue.forList(1), 1, true);
     }
diff --git a/tests/autofillservice/src/android/autofillservice/cts/dropdown/FillEventHistoryTest.java b/tests/autofillservice/src/android/autofillservice/cts/dropdown/FillEventHistoryTest.java
index 9cf27f1..bbb30dc 100644
--- a/tests/autofillservice/src/android/autofillservice/cts/dropdown/FillEventHistoryTest.java
+++ b/tests/autofillservice/src/android/autofillservice/cts/dropdown/FillEventHistoryTest.java
@@ -109,8 +109,10 @@
         sReplier.getNextSaveRequest();
 
         // Assert it
-        final List<Event> events = InstrumentedAutoFillService.getFillEvents(1);
-        assertFillEventForSaveShown(events.get(0), NULL_DATASET_ID);
+        final List<Event> events = InstrumentedAutoFillService.getFillEvents(2);
+        FillEventHistory.Event event = events.get(0);
+        assertThat(event.getType()).isEqualTo(TYPE_CONTEXT_COMMITTED);
+        assertFillEventForSaveShown(events.get(1), NULL_DATASET_ID);
     }
 
 
@@ -159,10 +161,12 @@
 
         // ...and check again
         {
-            final List<Event> events = InstrumentedAutoFillService.getFillEvents(3);
+            final List<Event> events = InstrumentedAutoFillService.getFillEvents(4);
             assertFillEventForDatasetShown(events.get(0), UI_TYPE_MENU);
             assertFillEventForDatasetSelected(events.get(1), NULL_DATASET_ID, UI_TYPE_MENU);
             assertFillEventForDatasetShown(events.get(2), UI_TYPE_MENU);
+            FillEventHistory.Event event = events.get(3);
+            assertThat(event.getType()).isEqualTo(TYPE_CONTEXT_COMMITTED);
         }
     }
 
diff --git a/tests/autofillservice/src/android/autofillservice/cts/dropdown/WebViewActivityTest.java b/tests/autofillservice/src/android/autofillservice/cts/dropdown/WebViewActivityTest.java
index 698ba48..0be57ea 100644
--- a/tests/autofillservice/src/android/autofillservice/cts/dropdown/WebViewActivityTest.java
+++ b/tests/autofillservice/src/android/autofillservice/cts/dropdown/WebViewActivityTest.java
@@ -42,6 +42,7 @@
 import android.view.KeyEvent;
 import android.view.ViewStructure.HtmlInfo;
 
+import org.junit.Assume;
 import org.junit.Ignore;
 import org.junit.Test;
 
@@ -107,6 +108,9 @@
     }
 
     private void autofillOneDatasetTest(boolean usesAppContext) throws Exception {
+        // TODO(b/226240255) WebView does not inform the autofill service about editText (re-)entry
+        Assume.assumeFalse(isPreventImeStartup());
+
         // Set service.
         enableService();
 
diff --git a/tests/devicepolicy/src/android/devicepolicy/cts/DevicePolicyManagerTest.java b/tests/devicepolicy/src/android/devicepolicy/cts/DevicePolicyManagerTest.java
index bbf4325..f0e7e83 100644
--- a/tests/devicepolicy/src/android/devicepolicy/cts/DevicePolicyManagerTest.java
+++ b/tests/devicepolicy/src/android/devicepolicy/cts/DevicePolicyManagerTest.java
@@ -22,14 +22,18 @@
 import static android.app.AppOpsManager.MODE_ALLOWED;
 import static android.app.admin.DevicePolicyManager.ACTION_MANAGED_PROFILE_PROVISIONED;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE;
+import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_LOCALE;
+import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ROLE_HOLDER_EXTRAS_BUNDLE;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_TIME_ZONE;
+import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_TRIGGER;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_WIFI_PASSWORD;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_WIFI_SECURITY_TYPE;
 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_WIFI_SSID;
 import static android.app.admin.DevicePolicyManager.MIME_TYPE_PROVISIONING_NFC;
+import static android.app.admin.DevicePolicyManager.PROVISIONING_TRIGGER_NFC;
 import static android.app.admin.ProvisioningException.ERROR_PRE_CONDITION_FAILED;
 import static android.content.Intent.EXTRA_USER;
 import static android.content.pm.PackageManager.FEATURE_DEVICE_ADMIN;
@@ -186,11 +190,15 @@
     private static final String NFC_INTENT_PROVISIONING_SAMPLE = "NFC provisioning sample";
     private static final Intent NFC_INTENT_NO_NDEF_RECORD = new Intent(ACTION_NDEF_DISCOVERED);
     private static final HashMap<String, String> NFC_DATA_VALID = createNfcIntentData();
-    private static final HashMap<String, String> NFC_DATA_EMPTY = new HashMap();
+    private static final HashMap<String, String> NFC_DATA_EMPTY = new HashMap<>();
     private static final Map<String, String> NFC_DATA_WITH_COMPONENT_NAME =
             Map.of(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME, NFC_INTENT_COMPONENT_NAME);
+    private static final Bundle EXPECTED_BUNDLE_WITH_COMPONENT_NAME =
+            createExpectedBundleWithComponentName();
     private static final Map<String, String> NFC_DATA_WITH_ADMIN_PACKAGE_NAME =
             Map.of(EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME, NFC_INTENT_PACKAGE_NAME);
+    private static final Bundle EXPECTED_BUNDLE_WITH_PACKAGE_NAME =
+            createExpectedBundleWithPackageName();
 
     private static final TestAppProvider sTestAppProvider = new TestAppProvider();
     private static final TestApp sDpcApp = sTestAppProvider.query()
@@ -199,6 +207,11 @@
             .get();
 
     private static final PersistableBundle ADMIN_EXTRAS_BUNDLE = createAdminExtrasBundle();
+    private static final PersistableBundle ROLE_HOLDER_EXTRAS_BUNDLE =
+            createRoleHolderExtrasBundle();
+    private static final String ADMIN_EXTRAS_PROPERTIES = createAdminExtrasProperties();
+    private static final String ROLE_HOLDER_EXTRAS_PROPERTIES =
+            createRoleHolderExtrasProperties();
     private static final String TEST_KEY = "test_key";
     private static final String TEST_VALUE = "test_value";
     private static final UserType MANAGED_PROFILE_USER_TYPE =
@@ -933,8 +946,9 @@
                 sDevicePolicyManager.createProvisioningIntentFromNfcIntent(nfcIntent);
 
         assertThat(provisioningIntent).isNotNull();
-        assertThat(provisioningBundleToMap(provisioningIntent.getExtras()))
-                .containsAtLeastEntriesIn(NFC_DATA_VALID);
+        assertThat(provisioningIntent.getAction())
+                .isEqualTo(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE_FROM_TRUSTED_SOURCE);
+        assertBundlesEqual(provisioningIntent.getExtras(), createExpectedValidBundle());
     }
 
     @Test
@@ -957,8 +971,9 @@
                 sDevicePolicyManager.createProvisioningIntentFromNfcIntent(nfcIntent);
 
         assertThat(provisioningIntent).isNotNull();
-        assertThat(provisioningBundleToMap(provisioningIntent.getExtras()))
-                .containsAtLeastEntriesIn(NFC_DATA_WITH_COMPONENT_NAME);
+        assertThat(provisioningIntent.getAction())
+                .isEqualTo(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE_FROM_TRUSTED_SOURCE);
+        assertBundlesEqual(provisioningIntent.getExtras(), EXPECTED_BUNDLE_WITH_COMPONENT_NAME);
     }
 
     @Test
@@ -970,8 +985,9 @@
                 sDevicePolicyManager.createProvisioningIntentFromNfcIntent(nfcIntent);
 
         assertThat(provisioningIntent).isNotNull();
-        assertThat(provisioningBundleToMap(provisioningIntent.getExtras()))
-                .containsAtLeastEntriesIn(NFC_DATA_WITH_ADMIN_PACKAGE_NAME);
+        assertThat(provisioningIntent.getAction())
+                .isEqualTo(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE_FROM_TRUSTED_SOURCE);
+        assertBundlesEqual(provisioningIntent.getExtras(), EXPECTED_BUNDLE_WITH_PACKAGE_NAME);
     }
 
     @Test
@@ -1036,7 +1052,7 @@
     }
 
     private static HashMap<String, String> createNfcIntentData() {
-        HashMap<String, String> nfcIntentInput = new HashMap<String, String>();
+        HashMap<String, String> nfcIntentInput = new HashMap<>();
         nfcIntentInput.putAll(
                 Map.of(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME, NFC_INTENT_COMPONENT_NAME,
                 EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME, NFC_INTENT_PACKAGE_NAME,
@@ -1044,9 +1060,10 @@
                 EXTRA_PROVISIONING_TIME_ZONE, NFC_INTENT_TIMEZONE,
                 EXTRA_PROVISIONING_WIFI_SSID, NFC_INTENT_WIFI_SSID,
                 EXTRA_PROVISIONING_WIFI_SECURITY_TYPE, NFC_INTENT_WIFI_SECURITY_TYPE,
-                EXTRA_PROVISIONING_WIFI_PASSWORD, NFC_INTENT_WIFI_PASSWORD)
+                EXTRA_PROVISIONING_WIFI_PASSWORD, NFC_INTENT_WIFI_PASSWORD,
+                EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE, createAdminExtrasProperties(),
+                EXTRA_PROVISIONING_ROLE_HOLDER_EXTRAS_BUNDLE, createRoleHolderExtrasProperties())
         );
-
         return nfcIntentInput;
     }
 
@@ -1075,22 +1092,6 @@
         return nfcIntent;
     }
 
-    private Map<String, String> provisioningBundleToMap(Bundle bundle) {
-        Map<String, String> map = new HashMap();
-
-        for (String key : bundle.keySet()) {
-            if(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME.equals(key)) {
-                ComponentName componentName = bundle.getParcelable(key);
-                map.put(key, componentName.getPackageName() + "/" + componentName.getClassName());
-            }
-            else {
-                map.put(key, bundle.getString(key));
-            }
-        }
-
-        return map;
-    }
-
     private NdefMessage createNdefMessage(Map<String, String> provisioningValues, String mime)
             throws IOException {
         ByteArrayOutputStream stream = new ByteArrayOutputStream();
@@ -1106,6 +1107,58 @@
         return new NdefMessage(new NdefRecord[]{record});
     }
 
+    private static PersistableBundle createAdminExtrasBundle() {
+        PersistableBundle result = new PersistableBundle();
+        result.putString("admin-extras-key", "admin extras value");
+        return result;
+    }
+
+    private static String createAdminExtrasProperties() {
+        return "admin-extras-key=admin extras value\n";
+    }
+
+    private static PersistableBundle createRoleHolderExtrasBundle() {
+        PersistableBundle result = new PersistableBundle();
+        result.putString("role-holder-extras-key", "role holder extras value");
+        return result;
+    }
+
+    private static String createRoleHolderExtrasProperties() {
+        return "role-holder-extras-key=role holder extras value\n";
+    }
+
+    private static Bundle createExpectedBundleWithComponentName() {
+        Bundle bundle = new Bundle();
+        bundle.putParcelable(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME,
+                ComponentName.unflattenFromString(NFC_INTENT_COMPONENT_NAME));
+        bundle.putInt(EXTRA_PROVISIONING_TRIGGER, PROVISIONING_TRIGGER_NFC);
+        return bundle;
+    }
+
+    private static Bundle createExpectedBundleWithPackageName() {
+        Bundle bundle = new Bundle();
+        bundle.putString(EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME, NFC_INTENT_PACKAGE_NAME);
+        bundle.putInt(EXTRA_PROVISIONING_TRIGGER, PROVISIONING_TRIGGER_NFC);
+        return bundle;
+    }
+
+    private static Bundle createExpectedValidBundle() {
+        Bundle bundle = new Bundle();
+        bundle.putParcelable(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME,
+                ComponentName.unflattenFromString(NFC_INTENT_COMPONENT_NAME));
+        bundle.putString(EXTRA_PROVISIONING_DEVICE_ADMIN_PACKAGE_NAME, NFC_INTENT_PACKAGE_NAME);
+        bundle.putString(EXTRA_PROVISIONING_LOCALE, NFC_INTENT_LOCALE);
+        bundle.putString(EXTRA_PROVISIONING_TIME_ZONE, NFC_INTENT_TIMEZONE);
+        bundle.putString(EXTRA_PROVISIONING_WIFI_SSID, NFC_INTENT_WIFI_SSID);
+        bundle.putString(EXTRA_PROVISIONING_WIFI_SECURITY_TYPE, NFC_INTENT_WIFI_SECURITY_TYPE);
+        bundle.putString(EXTRA_PROVISIONING_WIFI_PASSWORD, NFC_INTENT_WIFI_PASSWORD);
+        bundle.putParcelable(EXTRA_PROVISIONING_ADMIN_EXTRAS_BUNDLE, ADMIN_EXTRAS_BUNDLE);
+        bundle.putParcelable(EXTRA_PROVISIONING_ROLE_HOLDER_EXTRAS_BUNDLE,
+                ROLE_HOLDER_EXTRAS_BUNDLE);
+        bundle.putInt(EXTRA_PROVISIONING_TRIGGER, PROVISIONING_TRIGGER_NFC);
+        return bundle;
+    }
+
     @Postsubmit(reason = "New test")
     @Test
     @EnsureDoesNotHavePermission(MANAGE_PROFILE_AND_DEVICE_OWNERS)
@@ -1559,14 +1612,6 @@
         sDevicePolicyManager.getDevicePolicyManagementRoleHolderPackage();
     }
 
-    private static PersistableBundle createAdminExtrasBundle() {
-        PersistableBundle result = new PersistableBundle();
-        result.putString("key1", "value1");
-        result.putInt("key2", 2);
-        result.putBoolean("key3", true);
-        return result;
-    }
-
     private static void assertBundlesEqual(BaseBundle bundle1, BaseBundle bundle2) {
         if (bundle1 != null) {
             assertWithMessage("Intent bundles are not equal")
@@ -1574,9 +1619,19 @@
             assertWithMessage("Intent bundles are not equal")
                     .that(bundle1.keySet().size()).isEqualTo(bundle2.keySet().size());
             for (String key : bundle1.keySet()) {
-                assertWithMessage("Intent bundles are not equal")
-                        .that(bundle1.get(key))
-                        .isEqualTo(bundle2.get(key));
+                if (bundle1.get(key) != null && bundle1.get(key) instanceof PersistableBundle) {
+                    assertWithMessage("Intent bundles are not equal")
+                            .that(bundle2.containsKey(key)).isTrue();
+                    assertWithMessage("Intent bundles are not equal")
+                            .that(bundle2.get(key)).isInstanceOf(PersistableBundle.class);
+                    assertBundlesEqual(
+                            (PersistableBundle) bundle1.get(key),
+                            (PersistableBundle) bundle2.get(key));
+                } else {
+                    assertWithMessage("Intent bundles are not equal")
+                            .that(bundle1.get(key))
+                            .isEqualTo(bundle2.get(key));
+                }
             }
         } else {
             assertWithMessage("Intent bundles are not equal").that(bundle2).isNull();
diff --git a/tests/devicepolicy/src/android/devicepolicy/cts/UserControlDisabledPackagesTest.java b/tests/devicepolicy/src/android/devicepolicy/cts/UserControlDisabledPackagesTest.java
index 82195db..fcf71d0 100644
--- a/tests/devicepolicy/src/android/devicepolicy/cts/UserControlDisabledPackagesTest.java
+++ b/tests/devicepolicy/src/android/devicepolicy/cts/UserControlDisabledPackagesTest.java
@@ -40,6 +40,7 @@
 import com.android.bedstead.harrier.annotations.enterprise.CanSetPolicyTest;
 import com.android.bedstead.harrier.annotations.enterprise.CannotSetPolicyTest;
 import com.android.bedstead.harrier.annotations.enterprise.PolicyAppliesTest;
+import com.android.bedstead.harrier.annotations.enterprise.PolicyDoesNotApplyTest;
 import com.android.bedstead.harrier.policies.UserControlDisabledPackages;
 import com.android.bedstead.metricsrecorder.EnterpriseMetricsRecorder;
 import com.android.bedstead.nene.TestApis;
@@ -175,9 +176,10 @@
                         DPC_COMPONENT_NAME);
         String testAppPackageName = sTestApp.packageName();
 
-        sDeviceState.dpc().devicePolicyManager().setUserControlDisabledPackages(DPC_COMPONENT_NAME,
-                Arrays.asList(testAppPackageName));
         try (TestAppInstance instance = sTestApp.install()) {
+            sDeviceState.dpc().devicePolicyManager().setUserControlDisabledPackages(
+                    DPC_COMPONENT_NAME, Arrays.asList(testAppPackageName));
+
             instance.activities().any().start();
 
             sActivityManager.forceStopPackage(testAppPackageName);
@@ -194,6 +196,36 @@
         }
     }
 
+    @EnsureHasPermission(value = permission.FORCE_STOP_PACKAGES)
+    @PolicyDoesNotApplyTest(policy = UserControlDisabledPackages.class)
+    @Postsubmit(reason = "new test")
+    public void setUserControlDisabledPackages_launchActivity_verifyPackageStopped()
+            throws Exception {
+        List<String> originalDisabledPackages =
+                sDeviceState.dpc().devicePolicyManager().getUserControlDisabledPackages(
+                        DPC_COMPONENT_NAME);
+        String testAppPackageName = sTestApp.packageName();
+
+        try (TestAppInstance instance = sTestApp.install()) {
+            sDeviceState.dpc().devicePolicyManager().setUserControlDisabledPackages(
+                    DPC_COMPONENT_NAME, Arrays.asList(testAppPackageName));
+
+            instance.activities().any().start();
+
+            sActivityManager.forceStopPackage(testAppPackageName);
+
+            try {
+                assertPackageStopped(testAppPackageName);
+            } finally {
+                stopPackage(sTestApp.pkg());
+            }
+        } finally {
+            sDeviceState.dpc().devicePolicyManager().setUserControlDisabledPackages(
+                    DPC_COMPONENT_NAME,
+                    originalDisabledPackages);
+        }
+    }
+
     private void stopPackage(Package pkg) throws Exception {
         sDeviceState.dpc().devicePolicyManager().setUserControlDisabledPackages(DPC_COMPONENT_NAME,
                 Collections.emptyList());
@@ -201,9 +233,15 @@
         pkg.forceStop();
     }
 
+    private void assertPackageStopped(String packageName)
+            throws Exception {
+        assertWithMessage("Package %s not stopped", packageName)
+                .that(isPackageStopped(packageName)).isTrue();
+    }
+
     private void assertPackageNotStopped(String packageName)
             throws Exception {
-        assertWithMessage("Package %s not stopped for", packageName)
+        assertWithMessage("Package %s stopped", packageName)
                 .that(isPackageStopped(packageName)).isFalse();
     }
 
diff --git a/tests/framework/base/windowmanager/AndroidManifest.xml b/tests/framework/base/windowmanager/AndroidManifest.xml
index f714f77..b49a5cd 100644
--- a/tests/framework/base/windowmanager/AndroidManifest.xml
+++ b/tests/framework/base/windowmanager/AndroidManifest.xml
@@ -73,7 +73,7 @@
              android:process=":SecondProcess"
              android:exported="true"/>
 
-        <provider android:name="android.server.wm.lifecycle.LifecycleLog"
+        <provider android:name="android.server.wm.lifecycle.EventLog"
              android:authorities="android.server.wm.lifecycle.logprovider"
              android:exported="true"/>
 
diff --git a/tests/framework/base/windowmanager/jetpack/AndroidManifest.xml b/tests/framework/base/windowmanager/jetpack/AndroidManifest.xml
index 27f2870..70c0190 100644
--- a/tests/framework/base/windowmanager/jetpack/AndroidManifest.xml
+++ b/tests/framework/base/windowmanager/jetpack/AndroidManifest.xml
@@ -45,7 +45,7 @@
         />
 
         <!-- The provider properties must match the shared one defined in the util module. -->
-        <provider android:name="android.server.wm.lifecycle.LifecycleLog"
+        <provider android:name="android.server.wm.lifecycle.EventLog"
                   android:authorities="android.server.wm.lifecycle.logprovider"
                   android:exported="true"/>
     </application>
diff --git a/tests/framework/base/windowmanager/jetpack/SignedApp/src/android/server/wm/jetpack/signed/SignedEmbeddingActivity.java b/tests/framework/base/windowmanager/jetpack/SignedApp/src/android/server/wm/jetpack/signed/SignedEmbeddingActivity.java
index d2f6f2b..b332543 100644
--- a/tests/framework/base/windowmanager/jetpack/SignedApp/src/android/server/wm/jetpack/signed/SignedEmbeddingActivity.java
+++ b/tests/framework/base/windowmanager/jetpack/SignedApp/src/android/server/wm/jetpack/signed/SignedEmbeddingActivity.java
@@ -22,11 +22,13 @@
 import static android.server.wm.jetpack.utils.ActivityEmbeddingUtil.startActivityCrossUidInSplit;
 import static android.server.wm.jetpack.utils.ExtensionUtil.assumeExtensionSupportedDevice;
 import static android.server.wm.jetpack.utils.ExtensionUtil.getWindowExtensions;
+import static android.server.wm.jetpack.utils.WindowManagerJetpackTestBase.EXTRA_EMBED_ACTIVITY;
 
 import static org.junit.Assume.assumeNotNull;
 
 import android.app.Activity;
 import android.content.ComponentName;
+import android.content.Intent;
 import android.os.Bundle;
 import android.server.wm.jetpack.utils.TestActivityKnownEmbeddingCerts;
 import android.server.wm.jetpack.utils.TestValueCountConsumer;
@@ -52,6 +54,21 @@
     protected void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
 
+        if (getIntent().getBooleanExtra(EXTRA_EMBED_ACTIVITY, false)) {
+            startActivityInSplit();
+        }
+    }
+
+    @Override
+    protected void onNewIntent(Intent intent) {
+        super.onNewIntent(intent);
+
+        if (intent.getBooleanExtra(EXTRA_EMBED_ACTIVITY, false)) {
+            startActivityInSplit();
+        }
+    }
+
+    void startActivityInSplit() {
         ActivityEmbeddingComponent embeddingComponent;
         try {
             assumeExtensionSupportedDevice();
diff --git a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingCrossUidTests.java b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingCrossUidTests.java
index 0092ed2..aa79a5d 100644
--- a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingCrossUidTests.java
+++ b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingCrossUidTests.java
@@ -120,12 +120,14 @@
 
     /**
      * Tests that embedding an activity across UIDs is allowed if an activity requires a
-     * permission that the host has.
+     * certificate that the host has.
      */
     @Test
     public void testCrossUidActivityEmbeddingIsAllowedWithPermission() {
         // Start an activity that will attempt to embed TestActivityKnownEmbeddingCerts
-        startActivityNewTask(SIGNED_EMBEDDING_ACTIVITY);
+        Bundle extras = new Bundle();
+        extras.putBoolean(EXTRA_EMBED_ACTIVITY, true);
+        startActivityNoWait(mContext, SIGNED_EMBEDDING_ACTIVITY, extras);
 
         waitAndAssertResumed(EMBEDDED_ACTIVITY_ID);
         TestActivityWithId embeddedActivity = getResumedActivityById(EMBEDDED_ACTIVITY_ID);
diff --git a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingLifecycleTests.java b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingLifecycleTests.java
index 2ad5b78..98cfb2b 100644
--- a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingLifecycleTests.java
+++ b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingLifecycleTests.java
@@ -28,9 +28,9 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_RESUME;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_START;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_STOP;
-import static android.server.wm.lifecycle.LifecycleVerifier.assertOrder;
-import static android.server.wm.lifecycle.LifecycleVerifier.checkOrder;
-import static android.server.wm.lifecycle.LifecycleVerifier.transition;
+import static android.server.wm.lifecycle.TransitionVerifier.assertOrder;
+import static android.server.wm.lifecycle.TransitionVerifier.checkOrder;
+import static android.server.wm.lifecycle.TransitionVerifier.transition;
 
 import static androidx.window.extensions.embedding.SplitRule.FINISH_ALWAYS;
 import static androidx.window.extensions.embedding.SplitRule.FINISH_NEVER;
@@ -44,9 +44,9 @@
 import android.server.wm.jetpack.utils.TestActivityWithId2;
 import android.server.wm.jetpack.utils.TestConfigChangeHandlingActivity;
 import android.server.wm.jetpack.utils.TestValueCountConsumer;
-import android.server.wm.lifecycle.LifecycleLog;
-import android.server.wm.lifecycle.LifecycleLog.LifecycleLogClient;
-import android.server.wm.lifecycle.LifecycleTracker;
+import android.server.wm.lifecycle.EventLog;
+import android.server.wm.lifecycle.EventLog.EventLogClient;
+import android.server.wm.lifecycle.EventTracker;
 import android.util.Pair;
 
 import androidx.test.ext.junit.runners.AndroidJUnit4;
@@ -71,9 +71,9 @@
     private static final String TEST_OWNER = "TEST_OWNER";
     private static final String ON_SPLIT_STATES_UPDATED = "ON_SPLIT_STATES_UPDATED";
 
-    private LifecycleLogClient mLifecycleLogClient;
-    private LifecycleLog mLifecycleLog;
-    private LifecycleTracker mLifecycleTracker;
+    private EventLogClient mEventLogClient;
+    private EventLog mEventLog;
+    private EventTracker mLifecycleTracker;
     private LifecycleCallbacks mLifecycleCallbacks;
 
     @Override
@@ -82,26 +82,26 @@
         mSplitInfoConsumer = new SplitInfoLifecycleConsumer<>();
         mActivityEmbeddingComponent.setSplitInfoCallback(mSplitInfoConsumer);
 
-        mLifecycleLogClient = LifecycleLogClient.create(TEST_OWNER,
+        mEventLogClient = EventLogClient.create(TEST_OWNER,
                 mInstrumentation.getTargetContext());
 
         // Log transitions for all activities that belong to this app.
-        mLifecycleLog = new LifecycleLog();
-        mLifecycleLog.clear();
+        mEventLog = new EventLog();
+        mEventLog.clear();
 
         // Track transitions and allow waiting for pending activity states.
-        mLifecycleTracker = new LifecycleTracker(mLifecycleLog);
+        mLifecycleTracker = new EventTracker(mEventLog);
         mLifecycleCallbacks = new LifecycleCallbacks();
-        ((Application) mInstrumentation.getContext().getApplicationContext())
-                .registerActivityLifecycleCallbacks(mLifecycleCallbacks);
+        mApplication.registerActivityLifecycleCallbacks(mLifecycleCallbacks);
     }
 
     @Override
     public void tearDown() {
         super.tearDown();
-        ((Application) mInstrumentation.getContext().getApplicationContext())
-                .unregisterActivityLifecycleCallbacks(mLifecycleCallbacks);
-        mLifecycleLogClient.close();
+        mApplication.unregisterActivityLifecycleCallbacks(mLifecycleCallbacks);
+        if (mEventLogClient != null) {
+            mEventLogClient.close();
+        }
     }
 
     /**
@@ -110,7 +110,6 @@
      */
     @Test
     public void testSecondaryActivityLaunch_replacing() {
-        mLifecycleLog.clear();
         Activity primaryActivity = startActivityNewTask(TestConfigChangeHandlingActivity.class);
 
         SplitPairRule splitPairRule = createWildcardSplitPairRuleWithPrimaryActivityClass(
@@ -124,9 +123,9 @@
                 transition(TestConfigChangeHandlingActivity.class, ON_CREATE),
                 transition(TestActivityWithId.class, ON_CREATE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Init split states");
-        mLifecycleLog.clear();
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Init split states");
+        mEventLog.clear();
 
         // Launch a replacing secondary activity
         Activity secondaryActivity2 = startActivityAndVerifySplit(primaryActivity,
@@ -136,8 +135,8 @@
                 transition(TestActivityWithId.class, ON_DESTROY),
                 transition(TestActivityWithId2.class, ON_CREATE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected2));
-        assertOrder(mLifecycleLog, expected2, "Replace secondary container activity");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected2));
+        assertOrder(mEventLog, expected2, "Replace secondary container activity");
         waitAndAssertResumed(primaryActivity);
         waitAndAssertResumed(secondaryActivity2);
     }
@@ -148,7 +147,6 @@
      */
     @Test
     public void testSecondaryActivityLaunch_nonReplacing() {
-        mLifecycleLog.clear();
         Activity primaryActivity = startActivityNewTask(TestConfigChangeHandlingActivity.class);
 
         SplitPairRule splitPairRule = createWildcardSplitPairRuleWithPrimaryActivityClass(
@@ -163,9 +161,9 @@
                 transition(TestConfigChangeHandlingActivity.class, ON_CREATE),
                 transition(TestActivityWithId.class, ON_CREATE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Init split states");
-        mLifecycleLog.clear();
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Init split states");
+        mEventLog.clear();
 
         // Launch a secondary activity on top
         Activity secondaryActivity2 = startActivityAndVerifySplit(primaryActivity,
@@ -175,8 +173,8 @@
                 transition(TestActivityWithId.class, ON_PAUSE),
                 transition(TestActivityWithId2.class, ON_CREATE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected2));
-        assertOrder(mLifecycleLog, expected2, "Launch second secondary activity");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected2));
+        assertOrder(mEventLog, expected2, "Launch second secondary activity");
         waitAndAssertResumed(primaryActivity);
         waitAndAssertResumed(secondaryActivity2);
         waitAndAssertNotVisible(secondaryActivity1);
@@ -187,7 +185,6 @@
      */
     @Test
     public void testSecondaryActivityLaunch_multiSplit() {
-        mLifecycleLog.clear();
         Activity primaryActivity = startActivityNewTask(TestConfigChangeHandlingActivity.class);
 
         SplitPairRule splitPairRule = createWildcardSplitPairRuleWithPrimaryActivityClass(
@@ -202,9 +199,9 @@
                 transition(TestConfigChangeHandlingActivity.class, ON_CREATE),
                 transition(TestActivityWithId.class, ON_CREATE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Init split states");
-        mLifecycleLog.clear();
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Init split states");
+        mEventLog.clear();
 
         // Launch another secondary activity to side
         splitPairRule = createWildcardSplitPairRuleWithPrimaryActivityClass(
@@ -217,8 +214,8 @@
                 transition(TestConfigChangeHandlingActivity.class, ON_PAUSE),
                 transition(TestActivityWithId2.class, ON_CREATE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected2));
-        assertOrder(mLifecycleLog, expected2, "Launch second secondary activity to side");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected2));
+        assertOrder(mEventLog, expected2, "Launch second secondary activity to side");
         waitAndAssertNotVisible(primaryActivity);
         waitAndAssertResumed(secondaryActivity);
         waitAndAssertResumed(secondaryActivity2);
@@ -239,7 +236,7 @@
         Activity secondaryActivity = startActivityAndVerifySplit(primaryActivity,
                 TestActivityWithId.class, splitPairRule,
                 "secondaryActivity1", mSplitInfoConsumer);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish secondary activity
         secondaryActivity.finish();
@@ -247,8 +244,8 @@
                 transition(TestActivityWithId.class, ON_PAUSE),
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED),
                 transition(TestActivityWithId.class, ON_DESTROY));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish secondary activity");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish secondary activity");
         waitAndAssertResumed(primaryActivity);
     }
 
@@ -271,7 +268,7 @@
         Activity secondaryActivity = startActivityAndVerifySplit(primaryActivity,
                 TestActivityWithId.class, splitPairRule,
                 "secondaryActivity1", mSplitInfoConsumer);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish secondary activity, should trigger finishing of the primary as well
         secondaryActivity.finish();
@@ -279,8 +276,8 @@
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED),
                 transition(TestActivityWithId.class, ON_DESTROY),
                 transition(TestConfigChangeHandlingActivity.class, ON_DESTROY));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish secondary activity with dependents");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish secondary activity with dependents");
     }
 
     /**
@@ -302,15 +299,15 @@
         Activity secondaryActivity = startActivityAndVerifySplit(primaryActivity,
                 TestActivityWithId.class, splitPairRule,
                 "secondaryActivity1", mSplitInfoConsumer);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish primary activity
         primaryActivity.finish();
         List<Pair<String, String>> expected = List.of(
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED),
                 transition(TestConfigChangeHandlingActivity.class, ON_DESTROY));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish primary activity only");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish primary activity only");
         waitAndAssertResumed(secondaryActivity);
     }
 
@@ -332,7 +329,7 @@
         // Launch a secondary activity to side
         startActivityAndVerifySplit(primaryActivity, TestActivityWithId.class, splitPairRule,
                 "secondaryActivity1", mSplitInfoConsumer);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish primary activity should trigger finishing of the secondary as well.
         primaryActivity.finish();
@@ -340,8 +337,8 @@
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED),
                 transition(TestActivityWithId.class, ON_DESTROY),
                 transition(TestConfigChangeHandlingActivity.class, ON_DESTROY));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish primary activity with dependents");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish primary activity with dependents");
     }
 
     /**
@@ -370,7 +367,7 @@
                 "secondaryActivity2", mSplitInfoConsumer);
         waitAndAssertResumed(secondaryActivity);
         waitAndAssertResumed(secondaryActivity2);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish the last activity
         secondaryActivity2.finish();
@@ -378,8 +375,8 @@
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED),
                 transition(TestActivityWithId2.class, ON_DESTROY),
                 transition(TestConfigChangeHandlingActivity.class, ON_RESUME));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish last activity in multi-split");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish last activity in multi-split");
     }
 
     /**
@@ -409,7 +406,7 @@
                 "secondaryActivity2", mSplitInfoConsumer);
         waitAndAssertResumed(secondaryActivity);
         waitAndAssertResumed(secondaryActivity2);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish the middle activity
         secondaryActivity.finish();
@@ -419,8 +416,8 @@
                 transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED),
                 transition(TestActivityWithId.class, ON_DESTROY),
                 transition(TestConfigChangeHandlingActivity.class, ON_STOP));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish middle activity in multi-split");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish middle activity in multi-split");
     }
 
     /**
@@ -447,7 +444,7 @@
                 "secondaryActivity2", mSplitInfoConsumer);
         waitAndAssertResumed(secondaryActivity);
         waitAndAssertResumed(secondaryActivity2);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish the middle activity
         secondaryActivity.finish();
@@ -458,8 +455,8 @@
                 transition(TestActivityWithId.class, ON_DESTROY),
                 transition(TestConfigChangeHandlingActivity.class, ON_STOP));
 
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected, "Finish middle activity in multi-split");
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected, "Finish middle activity in multi-split");
     }
 
     /**
@@ -489,7 +486,7 @@
                 "secondaryActivity2", mSplitInfoConsumer);
         waitAndAssertResumed(secondaryActivity);
         waitAndAssertResumed(secondaryActivity2);
-        mLifecycleLog.clear();
+        mEventLog.clear();
 
         // Finish the middle activity
         secondaryActivity.finish();
@@ -497,45 +494,45 @@
         List<Pair<String, String>> expected = List.of(
                 transition(TestActivityWithId2.class, ON_DESTROY),
                 transition(TestActivityWithId.class, ON_DESTROY));
-        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mLifecycleLog, expected));
-        assertOrder(mLifecycleLog, expected,
+        mLifecycleTracker.waitForConditionWithTimeout(() -> checkOrder(mEventLog, expected));
+        assertOrder(mEventLog, expected,
                 "Finish middle activity in multi-split with dependents");
         mLifecycleTracker.waitForConditionWithTimeout(() ->
-                mLifecycleLog.getLog().contains(transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED)));
+                mEventLog.getLog().contains(transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED)));
         assertTrue("Split state change must be observed",
-                mLifecycleLog.getLog().contains(transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED)));
+                mEventLog.getLog().contains(transition(TEST_OWNER, ON_SPLIT_STATES_UPDATED)));
     }
 
     private final class LifecycleCallbacks implements
             Application.ActivityLifecycleCallbacks {
         @Override
         public void onActivityCreated(Activity activity, Bundle savedInstanceState) {
-            mLifecycleLogClient.onActivityCallback(ON_CREATE, activity);
+            mEventLogClient.onCallback(ON_CREATE, activity);
         }
 
         @Override
         public void onActivityStarted(Activity activity) {
-            mLifecycleLogClient.onActivityCallback(ON_START, activity);
+            mEventLogClient.onCallback(ON_START, activity);
         }
 
         @Override
         public void onActivityResumed(Activity activity) {
-            mLifecycleLogClient.onActivityCallback(ON_RESUME, activity);
+            mEventLogClient.onCallback(ON_RESUME, activity);
         }
 
         @Override
         public void onActivityPaused(Activity activity) {
-            mLifecycleLogClient.onActivityCallback(ON_PAUSE, activity);
+            mEventLogClient.onCallback(ON_PAUSE, activity);
         }
 
         @Override
         public void onActivityStopped(Activity activity) {
-            mLifecycleLogClient.onActivityCallback(ON_STOP, activity);
+            mEventLogClient.onCallback(ON_STOP, activity);
         }
 
         @Override
         public void onActivityDestroyed(Activity activity) {
-            mLifecycleLogClient.onActivityCallback(ON_DESTROY, activity);
+            mEventLogClient.onCallback(ON_DESTROY, activity);
         }
 
         @Override
@@ -547,7 +544,7 @@
         @Override
         public void accept(T value) {
             super.accept(value);
-            mLifecycleLogClient.onActivityCallback(ON_SPLIT_STATES_UPDATED, TEST_OWNER);
+            mEventLogClient.onCallback(ON_SPLIT_STATES_UPDATED, TEST_OWNER);
         }
     }
 }
diff --git a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingPolicyTests.java b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingPolicyTests.java
new file mode 100644
index 0000000..a929e86
--- /dev/null
+++ b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/ActivityEmbeddingPolicyTests.java
@@ -0,0 +1,190 @@
+/*
+ * Copyright (C) 2022 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 android.server.wm.jetpack;
+
+import static android.server.wm.jetpack.second.Components.SECOND_UNTRUSTED_EMBEDDING_ACTIVITY;
+import static android.server.wm.jetpack.signed.Components.SIGNED_EMBEDDING_ACTIVITY;
+import static android.server.wm.jetpack.utils.ActivityEmbeddingUtil.createWildcardSplitPairRule;
+import static android.server.wm.jetpack.utils.ExtensionUtil.assumeExtensionSupportedDevice;
+import static android.server.wm.jetpack.utils.ExtensionUtil.getWindowExtensions;
+import static android.server.wm.jetpack.utils.WindowManagerJetpackTestBase.EXTRA_EMBED_ACTIVITY;
+import static android.server.wm.jetpack.utils.WindowManagerJetpackTestBase.startActivityFromActivity;
+import static android.server.wm.jetpack.utils.WindowManagerJetpackTestBase.startActivityNewTask;
+import static android.server.wm.jetpack.utils.WindowManagerJetpackTestBase.startActivityOnDisplaySingleTop;
+import static android.view.Display.DEFAULT_DISPLAY;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.fail;
+import static org.junit.Assume.assumeFalse;
+import static org.junit.Assume.assumeNotNull;
+
+import android.app.Activity;
+import android.app.ActivityManager;
+import android.app.UiAutomation;
+import android.content.ComponentName;
+import android.os.Bundle;
+import android.server.wm.ActivityManagerTestBase;
+import android.server.wm.Condition;
+import android.server.wm.NestedShellPermission;
+import android.server.wm.WindowManagerState;
+import android.server.wm.jetpack.utils.TestActivityKnownEmbeddingCerts;
+import android.server.wm.jetpack.utils.TestConfigChangeHandlingActivity;
+
+import androidx.annotation.NonNull;
+import androidx.test.ext.junit.runners.AndroidJUnit4;
+import androidx.window.extensions.WindowExtensions;
+import androidx.window.extensions.embedding.ActivityEmbeddingComponent;
+import androidx.window.extensions.embedding.SplitPairRule;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+import java.util.Collections;
+import java.util.function.BooleanSupplier;
+
+/**
+ * Tests for the {@link androidx.window.extensions} implementation provided on the device (and only
+ * if one is available) for the Activity Embedding functionality. Specifically tests security
+ * policies that should be applied by the system.
+ *
+ * Build/Install/Run:
+ *     atest CtsWindowManagerJetpackTestCases:ActivityEmbeddingPolicyTests
+ */
+@RunWith(AndroidJUnit4.class)
+public class ActivityEmbeddingPolicyTests extends ActivityManagerTestBase {
+    protected ActivityEmbeddingComponent mActivityEmbeddingComponent;
+
+    @Override
+    @Before
+    public void setUp() throws Exception {
+        super.setUp();
+        // TODO(b/207070762): remove the assumption after shell transition enabled.
+        assumeFalse(ENABLE_SHELL_TRANSITIONS);
+        assumeExtensionSupportedDevice();
+        WindowExtensions windowExtensions = getWindowExtensions();
+        assumeNotNull(windowExtensions);
+        mActivityEmbeddingComponent = windowExtensions.getActivityEmbeddingComponent();
+        assumeNotNull(mActivityEmbeddingComponent);
+    }
+
+    @After
+    public void tearDown() {
+        ActivityManager am = mContext.getSystemService(ActivityManager.class);
+        NestedShellPermission.run(() -> am.forceStopPackage("android.server.wm.jetpack.second"));
+        NestedShellPermission.run(() -> am.forceStopPackage("android.server.wm.jetpack.signed"));
+    }
+
+    /**
+     * Verifies that all input is dropped for activities that are embedded and being animated with
+     * untrusted embedding.
+     */
+    @Test
+    public void testInputDuringAnimationIsNotAllowed_untrustedEmbedding() {
+        Activity primaryActivity = startActivityNewTask(mContext, mInstrumentation,
+                TestConfigChangeHandlingActivity.class, null /* activityId */);
+
+        SplitPairRule splitPairRule = createWildcardSplitPairRule(true /* shouldClearTop */);
+        mActivityEmbeddingComponent.setEmbeddingRules(Collections.singleton(splitPairRule));
+
+        // Extend the animation scale, so that the test has enough time to catch the state during
+        // transition.
+        UiAutomation automation = mInstrumentation.getUiAutomation();
+        automation.setAnimationScale(2f);
+
+        try {
+            startActivityFromActivity(primaryActivity, SECOND_UNTRUSTED_EMBEDDING_ACTIVITY,
+                    "initialSecondaryActivity", Bundle.EMPTY);
+
+            // Verify that the embedded activity drops input during animation
+            mWmState.waitForAppTransitionRunningOnDisplay(primaryActivity.getDisplayId());
+            waitForOrFailWithRapidRetry(
+                    "Embedded activity must drop all input for the duration of animation",
+                    () -> {
+                        mWmState.computeState();
+                        return mWmState.getActivity(SECOND_UNTRUSTED_EMBEDDING_ACTIVITY)
+                                .getLastDropInputMode() == 1 /* DropInputMode.ALL */;
+                    });
+
+            // Verify that the embedded activity drops input if obscured after animation
+            mWmState.waitForAppTransitionIdleOnDisplay(primaryActivity.getDisplayId());
+            assertEquals(
+                    "Embedded activity must drop input if obscured in untrusted embedding",
+                    2 /* DropInputMode.OBSCURED */,
+                    mWmState.getActivity(
+                            SECOND_UNTRUSTED_EMBEDDING_ACTIVITY).getLastDropInputMode());
+        } finally {
+            automation.setAnimationScale(1f);
+        }
+    }
+
+    /**
+     * Verifies that all input is dropped for activities that are embedded and being animated with
+     * trusted embedding.
+     */
+    @Test
+    public void testInputDuringAnimationIsNotAllowed_trustedEmbedding() {
+        // Extend the animation scale, so that the test has enough time to catch the state during
+        // transition.
+        UiAutomation automation = mInstrumentation.getUiAutomation();
+        automation.setAnimationScale(2f);
+
+        try {
+            // Start an activity that will attempt to embed TestActivityKnownEmbeddingCerts
+            startActivityOnDisplaySingleTop(mContext, DEFAULT_DISPLAY, SIGNED_EMBEDDING_ACTIVITY,
+                    Bundle.EMPTY);
+            mWmState.waitForActivityState(SIGNED_EMBEDDING_ACTIVITY,
+                    WindowManagerState.STATE_RESUMED);
+            mWmState.waitForAppTransitionIdleOnDisplay(DEFAULT_DISPLAY);
+
+            Bundle embedExtra = new Bundle();
+            embedExtra.putBoolean(EXTRA_EMBED_ACTIVITY, true);
+            startActivityOnDisplaySingleTop(mContext, DEFAULT_DISPLAY, SIGNED_EMBEDDING_ACTIVITY,
+                    embedExtra);
+
+            // Verify that the embedded activity drops input during animation
+            final ComponentName embeddedActivityComponent = new ComponentName(mContext,
+                    TestActivityKnownEmbeddingCerts.class);
+            mWmState.waitForAppTransitionRunningOnDisplay(DEFAULT_DISPLAY);
+            waitForOrFailWithRapidRetry(
+                    "Embedded activity must drop all input for the duration of animation",
+                    () -> {
+                        mWmState.computeState();
+                        return mWmState.getActivity(embeddedActivityComponent)
+                                .getLastDropInputMode() == 1 /* DropInputMode.ALL */;
+                    });
+
+            // Verify that the embedded activity drops input if obscured after animation
+            mWmState.waitForAppTransitionIdleOnDisplay(DEFAULT_DISPLAY);
+            assertEquals(
+                    "Embedded activity must not drop input if obscured in trusted embedding",
+                    0 /* DropInputMode.NONE */,
+                    mWmState.getActivity(embeddedActivityComponent).getLastDropInputMode());
+        } finally {
+            automation.setAnimationScale(1f);
+        }
+    }
+
+    static void waitForOrFailWithRapidRetry(@NonNull String message,
+            @NonNull BooleanSupplier condition) {
+        Condition.waitFor(new Condition<>(message, condition)
+                .setRetryIntervalMs(50)
+                .setRetryLimit(100)
+                .setOnFailure(unusedResult -> fail("FAILED because unsatisfied: " + message)));
+    }
+}
diff --git a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/utils/WindowManagerJetpackTestBase.java b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/utils/WindowManagerJetpackTestBase.java
index 4e5cdc0..fb9f5e8 100644
--- a/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/utils/WindowManagerJetpackTestBase.java
+++ b/tests/framework/base/windowmanager/jetpack/src/android/server/wm/jetpack/utils/WindowManagerJetpackTestBase.java
@@ -17,6 +17,7 @@
 package android.server.wm.jetpack.utils;
 
 import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
+import static android.content.Intent.FLAG_ACTIVITY_SINGLE_TOP;
 import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
 import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
 import static android.content.res.Configuration.ORIENTATION_LANDSCAPE;
@@ -31,6 +32,7 @@
 import static org.junit.Assert.assertTrue;
 
 import android.app.Activity;
+import android.app.ActivityOptions;
 import android.app.Application;
 import android.app.Instrumentation;
 import android.content.ComponentName;
@@ -56,6 +58,7 @@
 public class WindowManagerJetpackTestBase {
 
     public static final String ACTIVITY_ID_LABEL = "ActivityID";
+    public static final String EXTRA_EMBED_ACTIVITY = "EmbedActivity";
 
     public Instrumentation mInstrumentation;
     public Context mContext;
@@ -88,23 +91,46 @@
 
     public Activity startActivityNewTask(@NonNull Class activityClass,
             @Nullable String activityId) {
-        final Intent intent = new Intent(mContext, activityClass);
+        return startActivityNewTask(mContext, mInstrumentation, activityClass, activityId);
+    }
+
+    public static Activity startActivityNewTask(@NonNull Context context,
+            @NonNull Instrumentation instrumentation, @NonNull Class activityClass,
+            @Nullable String activityId) {
+        final Intent intent = new Intent(context, activityClass);
         intent.addFlags(FLAG_ACTIVITY_NEW_TASK);
         if (activityId != null) {
             intent.putExtra(ACTIVITY_ID_LABEL, activityId);
         }
-        final Activity activity = mInstrumentation.startActivitySync(intent);
-        return activity;
+        return instrumentation.startActivitySync(intent);
     }
 
     /**
      * Start an activity using a component name. Can be used for activities from a different UIDs.
      */
-    public void startActivityNewTask(@NonNull ComponentName activityComponent) {
-        final Intent intent = new Intent();
-        intent.setClassName(activityComponent.getPackageName(), activityComponent.getClassName());
-        intent.addFlags(FLAG_ACTIVITY_NEW_TASK);
-        mContext.startActivity(intent);
+    public static void startActivityNoWait(@NonNull Context context,
+            @NonNull ComponentName activityComponent, @NonNull Bundle extras) {
+        final Intent intent = new Intent()
+                .setClassName(activityComponent.getPackageName(), activityComponent.getClassName())
+                .addFlags(FLAG_ACTIVITY_NEW_TASK)
+                .putExtras(extras);
+        context.startActivity(intent);
+    }
+
+    /**
+     * Start an activity using a component name on the specified display with
+     * {@link FLAG_ACTIVITY_SINGLE_TOP}. Can be used for activities from a different UIDs.
+     */
+    public static void startActivityOnDisplaySingleTop(@NonNull Context context,
+            int displayId, @NonNull ComponentName activityComponent, @NonNull Bundle extras) {
+        final ActivityOptions options = ActivityOptions.makeBasic();
+        options.setLaunchDisplayId(displayId);
+
+        Intent intent = new Intent()
+                .addFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_SINGLE_TOP)
+                .setComponent(activityComponent)
+                .putExtras(extras);
+        context.startActivity(intent, options.toBundle());
     }
 
     /**
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/KeepClearRectsTests.java b/tests/framework/base/windowmanager/src/android/server/wm/KeepClearRectsTests.java
index 5e7ea21..92d738c 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/KeepClearRectsTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/KeepClearRectsTests.java
@@ -21,7 +21,6 @@
 import static android.server.wm.app.Components.KeepClearRectsActivity.EXTRA_KEEP_CLEAR_RECTS;
 import static android.view.Display.DEFAULT_DISPLAY;
 
-import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
 import static org.junit.Assume.assumeTrue;
@@ -55,11 +54,12 @@
 import java.util.Arrays;
 import java.util.Collections;
 import java.util.List;
+import java.util.concurrent.Callable;
 
 @Presubmit
 @FlakyTest(detail = "Promote once confirmed non-flaky")
 public class KeepClearRectsTests extends WindowManagerTestBase {
-    private static final long FOCUS_VIEW_CHECK_TIMEOUT = 3000;
+    private static final long SAME_ELEMENT_ASSERTION_TIMEOUT = 3000;
     private static final List<Rect> TEST_KEEP_CLEAR_RECTS =
             Arrays.asList(new Rect(0, 0, 25, 25),
                           new Rect(30, 0, 50, 25),
@@ -82,7 +82,7 @@
     }
 
     @Test
-    public void testSetPreferKeepClearAttr() {
+    public void testSetPreferKeepClearAttr() throws Exception {
         final Intent intent = new Intent(mContext, TestActivity.class);
         intent.putExtra(USE_KEEP_CLEAR_ATTR_LAYOUT, true);
         mTestSession.launchTestActivityOnDisplaySync(null, intent, DEFAULT_DISPLAY);
@@ -90,11 +90,12 @@
 
         // To be kept in sync with res/layout/keep_clear_attr_activity
         final Rect keepClearRect = new Rect(0, 0, 25, 25);
-        assertSameElements(Arrays.asList(keepClearRect), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(keepClearRect),
+                () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testSetPreferKeepClearSingleView() {
+    public void testSetPreferKeepClearSingleView() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
@@ -102,11 +103,12 @@
         final View v = createTestViewInActivity(activity, keepClearRect);
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(true));
 
-        assertSameElements(Arrays.asList(keepClearRect), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(keepClearRect),
+                () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testSetPreferKeepClearTwoViews() {
+    public void testSetPreferKeepClearTwoViews() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
@@ -115,29 +117,30 @@
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(true));
 
         final List<Rect> expected = new ArrayList(Arrays.asList(keepClearRect));
-        assertSameElements(expected, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(expected, () -> getKeepClearRectsForActivity(activity));
 
         final Rect keepClearRect2 = new Rect(25, 25, 50, 50);
         final View v2 = createTestViewInActivity(activity, keepClearRect2);
         mTestSession.runOnMainSyncAndWait(() -> v2.setPreferKeepClear(true));
 
         expected.addAll(Arrays.asList(keepClearRect2));
-        assertSameElements(expected, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(expected, () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testSetMultipleKeepClearRectsSingleView() {
+    public void testSetMultipleKeepClearRectsSingleView() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final View v = createTestViewInActivity(activity);
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS));
 
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testSetMultipleKeepClearRectsTwoViews() {
+    public void testSetMultipleKeepClearRectsTwoViews() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
@@ -150,7 +153,7 @@
 
         final List<Rect> expected = new ArrayList(TEST_KEEP_CLEAR_RECTS);
         expected.addAll(TEST_KEEP_CLEAR_RECTS_2);
-        assertSameElements(expected, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(expected, () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
@@ -169,25 +172,25 @@
     }
 
     @Test
-    public void testGetPreferKeepClearRectsSingleView() {
+    public void testGetPreferKeepClearRectsSingleView() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final Rect viewBounds = new Rect(0, 0, 60, 60);
         final View v = createTestViewInActivity(activity, viewBounds);
-        assertSameElements(EMPTY_LIST, v.getPreferKeepClearRects());
+        assertSameElementsEventually(EMPTY_LIST, () -> v.getPreferKeepClearRects());
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, v.getPreferKeepClearRects());
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS, () -> v.getPreferKeepClearRects());
 
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS_2));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS_2, v.getPreferKeepClearRects());
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS_2, () -> v.getPreferKeepClearRects());
 
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClearRects(EMPTY_LIST));
-        assertSameElements(EMPTY_LIST, v.getPreferKeepClearRects());
+        assertSameElementsEventually(EMPTY_LIST, () -> v.getPreferKeepClearRects());
     }
 
     @Test
-    public void testGettersPreferKeepClearRectsTwoViews() {
+    public void testGettersPreferKeepClearRectsTwoViews() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
@@ -201,66 +204,72 @@
         });
 
         assertTrue(v1.isPreferKeepClear());
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, v2.getPreferKeepClearRects());
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS, () -> v2.getPreferKeepClearRects());
 
         mTestSession.runOnMainSyncAndWait(() -> v1.setPreferKeepClear(false));
         assertFalse(v1.isPreferKeepClear());
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, v2.getPreferKeepClearRects());
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS, () -> v2.getPreferKeepClearRects());
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v1.setPreferKeepClear(true);
             v2.setPreferKeepClearRects(EMPTY_LIST);
         });
         assertTrue(v1.isPreferKeepClear());
-        assertSameElements(EMPTY_LIST, v2.getPreferKeepClearRects());
+        assertSameElementsEventually(EMPTY_LIST, () -> v2.getPreferKeepClearRects());
     }
 
     @Test
-    public void testSetPreferKeepClearCombinesWithMultipleRects() {
+    public void testSetPreferKeepClearCombinesWithMultipleRects() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final Rect viewBounds = new Rect(0, 0, 60, 60);
         final View v = createTestViewInActivity(activity, viewBounds);
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(true));
         final List<Rect> combinedRects = new ArrayList<>(TEST_KEEP_CLEAR_RECTS);
         combinedRects.add(viewBounds);
-        assertSameElements(combinedRects, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(combinedRects, () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(false));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testIgnoreKeepClearRectsFromGoneViews() {
+    public void testIgnoreKeepClearRectsFromGoneViews() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final Rect viewBounds = new Rect(0, 0, 60, 60);
         final View v = createTestViewInActivity(activity, viewBounds);
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(true));
-        assertSameElements(Arrays.asList(viewBounds), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setVisibility(View.GONE));
-        assertSameElements(EMPTY_LIST, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST, () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setVisibility(View.VISIBLE));
-        assertSameElements(Arrays.asList(viewBounds), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v.setPreferKeepClear(false);
             v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS);
         });
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setVisibility(View.GONE));
-        assertSameElements(EMPTY_LIST, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST, () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setVisibility(View.VISIBLE));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
 
         final Rect viewBounds2 = new Rect(60, 60, 90, 90);
         final View v2 = createTestViewInActivity(activity, viewBounds2);
@@ -268,36 +277,39 @@
 
         final List<Rect> expected = new ArrayList(TEST_KEEP_CLEAR_RECTS);
         expected.add(viewBounds2);
-        assertSameElements(expected, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(expected, () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setVisibility(View.GONE));
-        assertSameElements(Arrays.asList(viewBounds2), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(viewBounds2),
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v.setVisibility(View.VISIBLE);
             v2.setVisibility(View.GONE);
         });
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v.setVisibility(View.VISIBLE);
             v2.setVisibility(View.VISIBLE);
         });
-        assertSameElements(expected, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(expected, () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testIgnoreKeepClearRectsFromDetachedViews() {
+    public void testIgnoreKeepClearRectsFromDetachedViews() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final Rect viewBounds = new Rect(0, 0, 60, 60);
         final View v = createTestViewInActivity(activity, viewBounds);
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(true));
-        assertSameElements(Arrays.asList(viewBounds), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> ((ViewGroup) v.getParent()).removeView(v));
-        assertSameElements(EMPTY_LIST, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST, () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
@@ -312,26 +324,22 @@
 
         final Rect viewBounds = new Rect(0, 0, 60, 60);
         final View v = createTestViewInActivity(activity, viewBounds);
-        assertSameElements(EMPTY_LIST, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST, () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v.setFocusable(true);
             v.requestFocus();
         });
 
-        PollingCheck.check("Expected focused view bounds as keep clear area",
-                preferKeepClearForFocusDelay + FOCUS_VIEW_CHECK_TIMEOUT,
-                () -> hasSameElements(Arrays.asList(viewBounds),
-                        getKeepClearRectsForActivity(activity)));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> v.setFocusable(false));
-        PollingCheck.check("Expected no keep clear areas after clearing focus, but found some",
-                preferKeepClearForFocusDelay + FOCUS_VIEW_CHECK_TIMEOUT,
-                () -> hasSameElements(EMPTY_LIST, getKeepClearRectsForActivity(activity)));
+        assertSameElementsEventually(EMPTY_LIST, () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testKeepClearRectsGetTranslatedToWindowSpace() {
+    public void testKeepClearRectsGetTranslatedToWindowSpace() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
@@ -345,28 +353,31 @@
             expected.add(newRect);
         }
 
-        assertSameElements(expected, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(expected, () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testSetKeepClearRectsOnDisplaySingleWindow() {
+    public void testSetKeepClearRectsOnDisplaySingleWindow() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final Rect keepClearRect = new Rect(0, 0, 25, 25);
         final View v = createTestViewInActivity(activity, keepClearRect);
         mTestSession.runOnMainSyncAndWait(() -> v.setPreferKeepClear(true));
-        assertSameElements(Arrays.asList(keepClearRect), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(keepClearRect),
+                () -> getKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v.setPreferKeepClear(false);
             v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS);
         });
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
 
         final List<Rect> expectedRectsInScreenSpace =
                 getRectsInScreenSpace(TEST_KEEP_CLEAR_RECTS, activity.getComponentName());
-        assertSameElements(expectedRectsInScreenSpace, getKeepClearRectsOnDefaultDisplay());
+        assertSameElementsEventually(expectedRectsInScreenSpace,
+                () -> getKeepClearRectsOnDefaultDisplay());
 
         activity.finishAndRemoveTask();
         assertTrue(Collections.disjoint(
@@ -375,14 +386,15 @@
     }
 
     @Test
-    public void testKeepClearRectsOnDisplayTwoWindows() {
+    public void testKeepClearRectsOnDisplayTwoWindows() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
         final Rect viewBounds = new Rect(0, 0, 25, 25);
         final View v1 = createTestViewInActivity(activity, viewBounds);
         mTestSession.runOnMainSyncAndWait(() -> v1.setPreferKeepClear(true));
-        assertSameElements(Arrays.asList(viewBounds), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity));
 
         final String title = "KeepClearRectsTestWindow";
         mTestSession.runOnMainSyncAndWait(() -> {
@@ -398,18 +410,20 @@
         });
         mWmState.waitAndAssertWindowSurfaceShown(title, true);
 
-        assertSameElements(Arrays.asList(viewBounds), getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity));
     }
 
     @Test
-    public void testKeepClearRectsOnDisplayTwoFullscreenActivities() {
+    public void testKeepClearRectsOnDisplayTwoFullscreenActivities() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity1 = mTestSession.getActivity();
 
         final Rect viewBounds = new Rect(0, 0, 25, 25);
         final View v1 = createTestViewInActivity(activity1, viewBounds);
         mTestSession.runOnMainSyncAndWait(() -> v1.setPreferKeepClear(true));
-        assertSameElements(Arrays.asList(viewBounds), getKeepClearRectsForActivity(activity1));
+        assertSameElementsEventually(Arrays.asList(viewBounds),
+                () -> getKeepClearRectsForActivity(activity1));
 
         final TestActivitySession<TranslucentTestActivity> translucentTestSession =
                 createManagedTestActivitySession();
@@ -419,18 +433,19 @@
 
         final View v2 = createTestViewInActivity(activity2);
         mTestSession.runOnMainSyncAndWait(() -> v2.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity2));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity2));
 
         mWmState.assertVisibility(activity1.getComponentName(), true);
         mWmState.assertVisibility(activity2.getComponentName(), true);
 
         // Since both activities are fullscreen, WM only takes the keep clear areas from the top one
-        assertSameElements(getRectsInScreenSpace(TEST_KEEP_CLEAR_RECTS,
-                    activity2.getComponentName()), getKeepClearRectsOnDefaultDisplay());
+        assertSameElementsEventually(getRectsInScreenSpace(TEST_KEEP_CLEAR_RECTS,
+                activity2.getComponentName()), () -> getKeepClearRectsOnDefaultDisplay());
     }
 
     @Test
-    public void testDisplayHasKeepClearRectsOnlyFromVisibleWindows() {
+    public void testDisplayHasKeepClearRectsOnlyFromVisibleWindows() throws Exception {
         final TestActivitySession<TranslucentTestActivity> translucentTestSession =
                 createManagedTestActivitySession();
         translucentTestSession.launchTestActivityOnDisplaySync(
@@ -440,24 +455,25 @@
         final Rect viewBounds = new Rect(0, 0, 25, 25);
         final View v1 = createTestViewInActivity(activity1, viewBounds);
         translucentTestSession.runOnMainSyncAndWait(() -> v1.setPreferKeepClear(true));
-        assertSameElements(getRectsInScreenSpace(Arrays.asList(viewBounds),
-                                                 activity1.getComponentName()),
-                           getKeepClearRectsOnDefaultDisplay());
+        assertSameElementsEventually(getRectsInScreenSpace(Arrays.asList(viewBounds),
+                activity1.getComponentName()), () -> getKeepClearRectsOnDefaultDisplay());
 
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity2 = mTestSession.getActivity();
         final View v2 = createTestViewInActivity(activity2);
         mTestSession.runOnMainSyncAndWait(() -> v2.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity2));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity2));
 
         mWmState.waitAndAssertVisibilityGone(activity1.getComponentName());
         mWmState.assertVisibility(activity2.getComponentName(), true);
 
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity2));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity2));
     }
 
     @Test
-    public void testDisplayHasKeepClearAreasFromTwoActivitiesInSplitscreen() {
+    public void testDisplayHasKeepClearAreasFromTwoActivitiesInSplitscreen() throws Exception {
         assumeTrue("Skipping test: no split multi-window support",
                 supportsSplitScreenMultiWindow());
 
@@ -486,19 +502,19 @@
         mWmState.assertVisibility(KEEP_CLEAR_RECTS_ACTIVITY, true);
         mWmState.assertVisibility(KEEP_CLEAR_RECTS_ACTIVITY2, true);
 
-        assertSameElements(TEST_KEEP_CLEAR_RECTS,
-                           getKeepClearRectsForActivity(KEEP_CLEAR_RECTS_ACTIVITY));
-        assertSameElements(TEST_KEEP_CLEAR_RECTS_2,
-                           getKeepClearRectsForActivity(KEEP_CLEAR_RECTS_ACTIVITY2));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(KEEP_CLEAR_RECTS_ACTIVITY));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS_2,
+                () -> getKeepClearRectsForActivity(KEEP_CLEAR_RECTS_ACTIVITY2));
 
         final List<Rect> expected = new ArrayList();
         expected.addAll(getRectsInScreenSpace(TEST_KEEP_CLEAR_RECTS, KEEP_CLEAR_RECTS_ACTIVITY));
         expected.addAll(getRectsInScreenSpace(TEST_KEEP_CLEAR_RECTS_2, KEEP_CLEAR_RECTS_ACTIVITY2));
-        assertSameElements(expected, getKeepClearRectsOnDefaultDisplay());
+        assertSameElementsEventually(expected, () -> getKeepClearRectsOnDefaultDisplay());
     }
 
     @Test
-    public void testUnrestrictedKeepClearRects() {
+    public void testUnrestrictedKeepClearRects() throws Exception {
         mTestSession.launchTestActivityOnDisplaySync(TestActivity.class, DEFAULT_DISPLAY);
         final TestActivity activity = mTestSession.getActivity();
 
@@ -507,15 +523,18 @@
             v.setUnrestrictedPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS);
         });
 
-        assertSameElements(EMPTY_LIST, getKeepClearRectsForActivity(activity));
-        assertSameElements(EMPTY_LIST, getUnrestrictedKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST, () -> getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST,
+                () -> getUnrestrictedKeepClearRectsForActivity(activity));
 
         mTestSession.runOnMainSyncAndWait(() -> {
             v.setPreferKeepClearRects(TEST_KEEP_CLEAR_RECTS);
         });
 
-        assertSameElements(TEST_KEEP_CLEAR_RECTS, getKeepClearRectsForActivity(activity));
-        assertSameElements(EMPTY_LIST, getUnrestrictedKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(TEST_KEEP_CLEAR_RECTS,
+                () -> getKeepClearRectsForActivity(activity));
+        assertSameElementsEventually(EMPTY_LIST,
+                () -> getUnrestrictedKeepClearRectsForActivity(activity));
     }
 
     private View createTestViewInActivity(TestActivity activity) {
@@ -588,10 +607,11 @@
         return result;
     }
 
-    private static <T> void assertSameElements(List<T> expected, List<T> actual) {
-        if (!hasSameElements(expected, actual)) {
-            assertEquals(expected, actual);
-        }
+    private static <T> void assertSameElementsEventually(List<T> expected, Callable<List<T>> actual)
+            throws Exception {
+        PollingCheck.check("Lists do not have the same elements.",
+                SAME_ELEMENT_ASSERTION_TIMEOUT,
+                () -> hasSameElements(expected, actual.call()));
     }
 
     private static <T> boolean hasSameElements(List<T> fst, List<T> snd) {
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/SplitActivityLifecycleTest.java b/tests/framework/base/windowmanager/src/android/server/wm/SplitActivityLifecycleTest.java
index ace9d8f..4b7242e 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/SplitActivityLifecycleTest.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/SplitActivityLifecycleTest.java
@@ -23,6 +23,7 @@
 import static android.server.wm.SplitActivityLifecycleTest.ActivityB.EXTRA_SHOW_WHEN_LOCKED;
 import static android.server.wm.WindowManagerState.STATE_STARTED;
 import static android.server.wm.WindowManagerState.STATE_STOPPED;
+import static android.view.Display.DEFAULT_DISPLAY;
 
 import static com.google.common.truth.Truth.assertThat;
 import static com.google.common.truth.Truth.assertWithMessage;
@@ -497,8 +498,11 @@
      */
     @Test
     public void testTranslucentAdjacentTaskFragment() {
-        // Create ActivityB on top of ActivityA
-        Activity activityB = startActivityInWindowingModeFullScreen(ActivityB.class);
+        // Create ActivityB on top of ActivityA.
+        // Make sure ActivityB is launched into the same task as ActivityA so that we can reparent
+        // it to TaskFragment in the same task later.
+        Activity activityB = startActivity(ActivityB.class, DEFAULT_DISPLAY, true /* hasFocus */,
+                WINDOWING_MODE_FULLSCREEN, mOwnerActivity.getTaskId());
         waitAndAssertResumedActivity(mActivityB, "Activity B must be resumed.");
         waitAndAssertActivityState(mActivityA, STATE_STOPPED,
                 "Activity A is occluded by Activity B, so it must be stopped.");
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/WindowFocusTests.java b/tests/framework/base/windowmanager/src/android/server/wm/WindowFocusTests.java
index 024ea17..283a1f0 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/WindowFocusTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/WindowFocusTests.java
@@ -61,8 +61,6 @@
 
 import androidx.annotation.NonNull;
 
-import com.android.compatibility.common.util.SystemUtil;
-
 import org.junit.Test;
 
 import java.util.ArrayList;
@@ -81,9 +79,7 @@
     private static void sendKey(int action, int keyCode, int displayId) {
         final KeyEvent keyEvent = new KeyEvent(action, keyCode);
         keyEvent.setDisplayId(displayId);
-        SystemUtil.runWithShellPermissionIdentity(() -> {
-            getInstrumentation().sendKeySync(keyEvent);
-        });
+        getInstrumentation().sendKeySync(keyEvent);
     }
 
     private static void sendAndAssertTargetConsumedKey(InputTargetActivity target, int keyCode,
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/WindowInputTests.java b/tests/framework/base/windowmanager/src/android/server/wm/WindowInputTests.java
index 322355f..2e29a74 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/WindowInputTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/WindowInputTests.java
@@ -73,12 +73,11 @@
 import java.util.ArrayList;
 import java.util.Random;
 import java.util.Set;
+import java.util.concurrent.CompletableFuture;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Executors;
 import java.util.concurrent.TimeUnit;
 import java.util.concurrent.atomic.AtomicBoolean;
-import java.util.concurrent.CompletableFuture;
-import java.util.concurrent.TimeoutException;
 
 /**
  * Ensure moving windows and tapping is done synchronously.
@@ -728,9 +727,10 @@
         eventHover.setSource(InputDevice.SOURCE_MOUSE);
         try {
             mInstrumentation.sendPointerSync(eventHover);
-            fail("Not allowed to inject event to the window from another process.");
-        } catch (SecurityException e) {
-            // Should not be allowed to inject event to the window from another process.
+            fail("Not allowed to inject to windows owned by another uid from Instrumentation.");
+        } catch (RuntimeException e) {
+            // Should not be allowed to inject event to a window owned by another uid from the
+            // Instrumentation class.
         }
     }
 
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsAnimationSynchronicityTests.java b/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsAnimationSynchronicityTests.java
index 20bce66..229104c 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsAnimationSynchronicityTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsAnimationSynchronicityTests.java
@@ -64,6 +64,7 @@
 import com.android.compatibility.common.util.SystemUtil;
 import com.android.compatibility.common.util.WindowUtil;
 
+import org.junit.Ignore;
 import org.junit.Rule;
 import org.junit.Test;
 
@@ -83,11 +84,13 @@
 
     private final Context mContext = InstrumentationRegistry.getInstrumentation().getContext();
 
+    @Ignore("b/168446060")
     @Test
     public void testShowAndHide_renderSynchronouslyBetweenImeWindowAndAppContent() throws Throwable {
         runTest(false /* useControlApi */);
     }
 
+    @Ignore("b/168446060")
     @Test
     public void testControl_rendersSynchronouslyBetweenImeWindowAndAppContent() throws Throwable {
         runTest(true /* useControlApi */);
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsControllerTests.java b/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsControllerTests.java
index aa19b08..65465b2 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsControllerTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/WindowInsetsControllerTests.java
@@ -62,6 +62,7 @@
 import android.os.Bundle;
 import android.os.SystemClock;
 import android.platform.test.annotations.Presubmit;
+import android.view.InputDevice;
 import android.view.MotionEvent;
 import android.view.View;
 import android.view.ViewGroup;
@@ -77,7 +78,6 @@
 import androidx.annotation.Nullable;
 
 import com.android.compatibility.common.util.PollingCheck;
-import com.android.compatibility.common.util.SystemUtil;
 import com.android.cts.mockime.ImeEventStream;
 import com.android.cts.mockime.ImeSettings;
 import com.android.cts.mockime.MockImeSession;
@@ -844,8 +844,10 @@
     }
 
     private void sendPointerSync(MotionEvent event) {
-        SystemUtil.runWithShellPermissionIdentity(
-                () -> getInstrumentation().sendPointerSync(event));
+        event.setSource(event.getSource() | InputDevice.SOURCE_CLASS_POINTER);
+        // Use UiAutomation to inject into TestActivity because it is started and owned by the
+        // Shell, which has a different uid than this instrumentation.
+        getInstrumentation().getUiAutomation().injectInputEvent(event, true);
     }
 
     private static class AnimationCallback extends WindowInsetsAnimation.Callback {
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/WindowManagerTestBase.java b/tests/framework/base/windowmanager/src/android/server/wm/WindowManagerTestBase.java
index df3f9e3..7977030 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/WindowManagerTestBase.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/WindowManagerTestBase.java
@@ -16,6 +16,7 @@
 
 package android.server.wm;
 
+import static android.app.ActivityTaskManager.INVALID_STACK_ID;
 import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
 import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED;
 import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
@@ -64,13 +65,20 @@
 
     static <T extends FocusableActivity> T startActivity(Class<T> cls, int displayId,
             boolean hasFocus, int windowingMode) {
+        return startActivity(cls, displayId, hasFocus, windowingMode, INVALID_STACK_ID);
+    }
+
+    static <T extends FocusableActivity> T startActivity(Class<T> cls, int displayId,
+            boolean hasFocus, int windowingMode, int taskId) {
         final Bundle options;
-        if (displayId == DEFAULT_DISPLAY && windowingMode == WINDOWING_MODE_UNDEFINED) {
+        if (displayId == DEFAULT_DISPLAY && windowingMode == WINDOWING_MODE_UNDEFINED
+                && taskId == INVALID_STACK_ID) {
             options = null;
         } else {
             final ActivityOptions ap= ActivityOptions.makeBasic();
             if (displayId != DEFAULT_DISPLAY) ap.setLaunchDisplayId(displayId);
             if (windowingMode != WINDOWING_MODE_UNDEFINED) ap.setLaunchWindowingMode(windowingMode);
+            if (taskId != INVALID_STACK_ID) ap.setLaunchTaskId(taskId);
             options = ap.toBundle();
         }
         final T[] activity = (T[]) Array.newInstance(FocusableActivity.class, 1);
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleClientTestBase.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleClientTestBase.java
index df015a6..b6eea5a 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleClientTestBase.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleClientTestBase.java
@@ -71,10 +71,10 @@
     final ActivityTestRule mSlowActivityTestRule = new ActivityTestRule<>(
             SlowActivity.class, true /* initialTouchMode */, false /* launchActivity */);
 
-    private static LifecycleLog mLifecycleLog;
+    private static EventLog sEventLog;
 
     protected Context mTargetContext;
-    private LifecycleTracker mLifecycleTracker;
+    private EventTracker mTransitionTracker;
 
     @Before
     @Override
@@ -83,11 +83,11 @@
 
         mTargetContext = getInstrumentation().getTargetContext();
         // Log transitions for all activities that belong to this app.
-        mLifecycleLog = new LifecycleLog();
-        mLifecycleLog.clear();
+        sEventLog = new EventLog();
+        sEventLog.clear();
 
         // Track transitions and allow waiting for pending activity states.
-        mLifecycleTracker = new LifecycleTracker(mLifecycleLog);
+        mTransitionTracker = new EventTracker(sEventLog);
 
         // Some lifecycle tracking activities that have not been destroyed may affect the
         // verification of next test because of the lifecycle log. We need to wait them to be
@@ -252,7 +252,7 @@
     final void waitAndAssertActivityStates(
             Pair<Class<? extends Activity>, String>... activityCallbacks) {
         log("Start waitAndAssertActivityCallbacks");
-        mLifecycleTracker.waitAndAssertActivityStates(activityCallbacks);
+        mTransitionTracker.waitAndAssertActivityStates(activityCallbacks);
     }
 
     /**
@@ -262,35 +262,35 @@
     final void waitAndAssertActivityCurrentState(
             Class<? extends Activity> activityClass, String expectedState) {
         log("Start waitAndAssertActivityCurrentState");
-        mLifecycleTracker.waitAndAssertActivityCurrentState(activityClass, expectedState);
+        mTransitionTracker.waitAndAssertActivityCurrentState(activityClass, expectedState);
     }
 
     /**
      * Blocking call that will wait for activities to perform the expected sequence of transitions.
-     * @see LifecycleTracker#waitForActivityTransitions(Class, List)
+     * @see EventTracker#waitForActivityTransitions(Class, List)
      */
     final void waitForActivityTransitions(Class<? extends Activity> activityClass,
             List<String> expectedTransitions) {
         log("Start waitForActivityTransitions");
-        mLifecycleTracker.waitForActivityTransitions(activityClass, expectedTransitions);
+        mTransitionTracker.waitForActivityTransitions(activityClass, expectedTransitions);
     }
 
     /**
      * Blocking call that will wait for activities to perform the expected sequence of transitions.
      * After waiting it asserts that the sequence matches the expected.
-     * @see LifecycleTracker#waitForActivityTransitions(Class, List)
+     * @see EventTracker#waitForActivityTransitions(Class, List)
      */
     final void waitAndAssertActivityTransitions(Class<? extends Activity> activityClass,
             List<String> expectedTransitions, String message) {
         log("Start waitAndAssertActivityTransition");
-        mLifecycleTracker.waitForActivityTransitions(activityClass, expectedTransitions);
+        mTransitionTracker.waitForActivityTransitions(activityClass, expectedTransitions);
 
-        LifecycleVerifier.assertSequence(activityClass, getLifecycleLog(), expectedTransitions,
+        TransitionVerifier.assertSequence(activityClass, getTransitionLog(), expectedTransitions,
                 message);
     }
 
-    LifecycleLog getLifecycleLog() {
-        return mLifecycleLog;
+    EventLog getTransitionLog() {
+        return sEventLog;
     }
 
     static Pair<Class<? extends Activity>, String> state(Activity activity,
@@ -620,7 +620,7 @@
 
     void moveTaskToPrimarySplitScreenAndVerify(Activity primaryActivity,
             Activity secondaryActivity) throws Exception {
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         mWmState.computeState(secondaryActivity.getComponentName());
         moveActivitiesToSplitScreen(primaryActivity.getComponentName(),
@@ -629,9 +629,9 @@
         final Class<? extends Activity> activityClass = primaryActivity.getClass();
 
         final List<String> expectedTransitions =
-                new ArrayList<>(LifecycleVerifier.getSplitScreenTransitionSequence(activityClass));
+                new ArrayList<>(TransitionVerifier.getSplitScreenTransitionSequence(activityClass));
         final List<String> expectedTransitionForMinimizedDock =
-                LifecycleVerifier.appendMinimizedDockTransitionTrail(expectedTransitions);
+                TransitionVerifier.appendMinimizedDockTransitionTrail(expectedTransitions);
 
         final int displayWindowingMode =
                 getDisplayWindowingModeByActivity(getComponentName(activityClass));
@@ -642,10 +642,10 @@
                     Collections.singleton(ON_MULTI_WINDOW_MODE_CHANGED));
         }
 
-        mLifecycleTracker.waitForActivityTransitions(activityClass, expectedTransitions);
-        LifecycleVerifier.assertSequenceMatchesOneOf(
+        mTransitionTracker.waitForActivityTransitions(activityClass, expectedTransitions);
+        TransitionVerifier.assertSequenceMatchesOneOf(
                 activityClass,
-                getLifecycleLog(),
+                getTransitionLog(),
                 Arrays.asList(expectedTransitions, expectedTransitionForMinimizedDock),
                 "enterSplitScreen");
     }
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleFreeformTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleFreeformTests.java
index 9dded99..07e4ac0 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleFreeformTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleFreeformTests.java
@@ -29,6 +29,12 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_RESUME;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_LOST;
 import static android.server.wm.lifecycle.LifecycleConstants.getComponentName;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEmptySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchAndPauseSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartAndResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
 
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assume.assumeTrue;
@@ -44,7 +50,7 @@
 import org.junit.Before;
 import org.junit.Test;
 
-import java.util.Arrays;
+import java.util.Collections;
 
 /**
  * Build/Install/Run:
@@ -77,8 +83,8 @@
         // Wait and assert resume
         waitAndAssertActivityState(getComponentName(FirstActivity.class), STATE_RESUMED,
                 "Activity should be resumed after launch");
-        LifecycleVerifier.assertLaunchSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertLaunchSequence(FirstActivity.class, getTransitionLog());
+        assertLaunchSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 ON_TOP_POSITION_LOST);
     }
 
@@ -113,10 +119,10 @@
         waitAndAssertActivityState(getComponentName(ThirdActivity.class), STATE_RESUMED, message);
 
         // Assert lifecycle
-        LifecycleVerifier.assertLaunchSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(SecondActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(ThirdActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertLaunchSequence(FirstActivity.class, getTransitionLog());
+        assertLaunchSequence(SecondActivity.class, getTransitionLog());
+        assertLaunchSequence(ThirdActivity.class, getTransitionLog());
+        assertLaunchSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 ON_TOP_POSITION_LOST);
     }
 
@@ -150,14 +156,14 @@
         waitAndAssertActivityState(getComponentName(ThirdActivity.class), STATE_RESUMED, message);
 
         // Assert lifecycle
-        LifecycleVerifier.assertLaunchAndStopSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(SecondActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(ThirdActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        TransitionVerifier.assertLaunchAndStopSequence(FirstActivity.class, getTransitionLog());
+        assertLaunchSequence(SecondActivity.class, getTransitionLog());
+        assertLaunchSequence(ThirdActivity.class, getTransitionLog());
+        assertLaunchSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 ON_TOP_POSITION_LOST);
 
         // Finish the activity that was occluding the first one
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondActivity.finish();
 
         // Wait and assert the lifecycle
@@ -170,11 +176,10 @@
         assertFalse("Activity must be destroyed",
                 mWmState.containsWindow(
                         getWindowName(getComponentName(SecondActivity.class))));
-        LifecycleVerifier.assertRestartAndResumeSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertResumeToDestroySequence(SecondActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertEmptySequence(ThirdActivity.class, getLifecycleLog(),
-                "finishInOtherStack");
-        LifecycleVerifier.assertEmptySequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertRestartAndResumeSequence(FirstActivity.class, getTransitionLog());
+        assertResumeToDestroySequence(SecondActivity.class, getTransitionLog());
+        assertEmptySequence(ThirdActivity.class, getTransitionLog(), "finishInOtherStack");
+        assertEmptySequence(CallbackTrackingActivity.class, getTransitionLog(),
                 "finishInOtherStack");
     }
 
@@ -209,14 +214,14 @@
         waitAndAssertActivityState(getComponentName(ThirdActivity.class), STATE_RESUMED, message);
 
         // Assert lifecycle
-        LifecycleVerifier.assertLaunchAndPauseSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(TranslucentActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(ThirdActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertLaunchSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertLaunchAndPauseSequence(FirstActivity.class, getTransitionLog());
+        assertLaunchSequence(TranslucentActivity.class, getTransitionLog());
+        assertLaunchSequence(ThirdActivity.class, getTransitionLog());
+        assertLaunchSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 ON_TOP_POSITION_LOST);
 
         // Finish the activity that was occluding the first one
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         transparentActivity.finish();
 
         // Wait and assert the lifecycle
@@ -231,13 +236,13 @@
         assertFalse("Activity must be destroyed",
                 mWmState.containsWindow(
                         getWindowName(getComponentName(TranslucentActivity.class))));
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_RESUME), "finishTranslucentOnTop");
-        LifecycleVerifier.assertResumeToDestroySequence(TranslucentActivity.class,
-                getLifecycleLog());
-        LifecycleVerifier.assertEmptySequence(ThirdActivity.class, getLifecycleLog(),
+        assertSequence(FirstActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_RESUME), "finishTranslucentOnTop");
+        assertResumeToDestroySequence(TranslucentActivity.class,
+                getTransitionLog());
+        assertEmptySequence(ThirdActivity.class, getTransitionLog(),
                 "finishInOtherStack");
-        LifecycleVerifier.assertEmptySequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertEmptySequence(CallbackTrackingActivity.class, getTransitionLog(),
                 "finishInOtherStack");
     }
 
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleKeyguardTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleKeyguardTests.java
index 2465c15..b958cd8 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleKeyguardTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleKeyguardTests.java
@@ -22,6 +22,11 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_RESUME;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_START;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_STOP;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchAndStopSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartAndResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartAndResumeSubSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToStopSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
 
 import static org.junit.Assume.assumeTrue;
 
@@ -33,6 +38,7 @@
 import org.junit.Test;
 
 import java.util.Arrays;
+import java.util.Collections;
 
 /**
  * Build/Install/Run:
@@ -53,7 +59,7 @@
                     .setExpectedState(ON_STOP)
                     .setNoInstance()
                     .launch();
-            LifecycleVerifier.assertLaunchAndStopSequence(FirstActivity.class, getLifecycleLog());
+            assertLaunchAndStopSequence(FirstActivity.class, getTransitionLog());
         }
     }
 
@@ -69,19 +75,17 @@
             lockScreenSession.setLockCredential().gotoKeyguard();
             waitAndAssertActivityStates(state(activity, ON_STOP));
 
-            LifecycleVerifier.assertLaunchAndStopSequence(FirstActivity.class, getLifecycleLog());
-            getLifecycleLog().clear();
+            assertLaunchAndStopSequence(FirstActivity.class, getTransitionLog());
+            getTransitionLog().clear();
         } // keyguard hidden
 
         // Verify that activity was resumed
         if (isCar()) {
-            LifecycleVerifier.assertRestartAndResumeSubSequence(FirstActivity.class,
-                    getLifecycleLog());
+            assertRestartAndResumeSubSequence(FirstActivity.class, getTransitionLog());
             waitAndAssertActivityCurrentState(activity.getClass(), ON_RESUME);
         } else {
             waitAndAssertActivityStates(state(activity, ON_RESUME));
-            LifecycleVerifier.assertRestartAndResumeSequence(FirstActivity.class,
-                    getLifecycleLog());
+            assertRestartAndResumeSequence(FirstActivity.class, getTransitionLog());
         }
     }
 
@@ -97,21 +101,21 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, secondaryActivity);
 
         // Show and hide lock screen
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         try (final LockScreenSession lockScreenSession = new LockScreenSession()) {
             lockScreenSession.setLockCredential().gotoKeyguard();
             waitAndAssertActivityStates(state(firstActivity, ON_STOP));
             waitAndAssertActivityStates(state(secondaryActivity, ON_STOP));
 
-            LifecycleVerifier.assertResumeToStopSequence(FirstActivity.class, getLifecycleLog());
-            LifecycleVerifier.assertResumeToStopSequence(SideActivity.class, getLifecycleLog());
-            getLifecycleLog().clear();
+            assertResumeToStopSequence(FirstActivity.class, getTransitionLog());
+            assertResumeToStopSequence(SideActivity.class, getTransitionLog());
+            getTransitionLog().clear();
         } // keyguard hidden
 
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME),
                 state(secondaryActivity, ON_RESUME));
-        LifecycleVerifier.assertRestartAndResumeSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertRestartAndResumeSequence(SideActivity.class, getLifecycleLog());
+        assertRestartAndResumeSequence(FirstActivity.class, getTransitionLog());
+        assertRestartAndResumeSequence(SideActivity.class, getTransitionLog());
     }
 
     @Test
@@ -126,7 +130,7 @@
         final Activity firstActivity = launchActivityAndWait(FirstActivity.class);
 
         // Clear the log before launching to Pip
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Launch Pip-capable activity and enter Pip immediately
         new Launcher(PipActivity.class)
@@ -138,23 +142,23 @@
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME));
 
         // Show and hide lock screen
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         try (final LockScreenSession lockScreenSession = new LockScreenSession()) {
             lockScreenSession.setLockCredential().gotoKeyguard();
             waitAndAssertActivityStates(state(firstActivity, ON_STOP));
             waitAndAssertActivityStates(state(PipActivity.class, ON_STOP));
 
-            LifecycleVerifier.assertResumeToStopSequence(FirstActivity.class, getLifecycleLog());
-            LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
-                    Arrays.asList(ON_STOP), "keyguardShown");
-            getLifecycleLog().clear();
+            assertResumeToStopSequence(FirstActivity.class, getTransitionLog());
+            assertSequence(PipActivity.class, getTransitionLog(),
+                    Collections.singletonList(ON_STOP), "keyguardShown");
+            getTransitionLog().clear();
         } // keyguard hidden
 
         // Wait and assert lifecycle
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME),
                 state(PipActivity.class, ON_PAUSE));
-        LifecycleVerifier.assertRestartAndResumeSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
+        assertRestartAndResumeSequence(FirstActivity.class, getTransitionLog());
+        assertSequence(PipActivity.class, getTransitionLog(),
                 Arrays.asList(ON_RESTART, ON_START, ON_RESUME, ON_PAUSE), "keyguardGone");
     }
 }
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleLegacySplitScreenTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleLegacySplitScreenTests.java
index 85bc07e..a1e4a5c 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleLegacySplitScreenTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleLegacySplitScreenTests.java
@@ -33,7 +33,14 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_LOST;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_USER_LEAVE_HINT;
 import static android.server.wm.lifecycle.LifecycleConstants.getComponentName;
-import static android.server.wm.lifecycle.LifecycleVerifier.transition;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertOrder;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRecreateAndResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartAndResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertTransitionObserved;
+import static android.server.wm.lifecycle.TransitionVerifier.transition;
 
 import static androidx.test.InstrumentationRegistry.getInstrumentation;
 
@@ -86,7 +93,7 @@
         moveTaskToPrimarySplitScreenAndVerify(secondActivity, sideActivity);
 
         // CLear logs so we can capture just the destroy sequence
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Start an activity in separate task (will be placed in secondary stack)
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
@@ -102,10 +109,10 @@
 
         // Verify that the first activity was recreated to resume as it was created before
         // windowing mode was switched
-        LifecycleVerifier.assertRecreateAndResumeSequence(FirstActivity.class, getLifecycleLog());
+        assertRecreateAndResumeSequence(FirstActivity.class, getTransitionLog());
 
         // Verify that the lifecycle state did not change for activity in non-focused stack
-        LifecycleVerifier.assertLaunchSequence(ThirdActivity.class, getLifecycleLog());
+        assertLaunchSequence(ThirdActivity.class, getTransitionLog());
     }
 
     @Test
@@ -120,7 +127,7 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Launch third activity on top of second
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         new Launcher(ThirdActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
@@ -142,7 +149,7 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Launch translucent activity on top of second
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         new Launcher(TranslucentActivity.class)
@@ -184,13 +191,13 @@
         moveTaskToPrimarySplitScreenAndVerify(secondActivity, sideActivity);
 
         // Finish top activity and verify that activity below became focused.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondActivity.setResult(Activity.RESULT_OK);
         secondActivity.finish();
 
         // Check that activity was restarted and result was delivered
         waitAndAssertActivityStates(state(callbackTrackingActivity, ON_RESUME));
-        LifecycleVerifier.assertSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 Arrays.asList(ON_DESTROY, ON_CREATE, ON_START, ON_POST_CREATE,
                         ON_ACTIVITY_RESULT, ON_RESUME), "restart");
     }
@@ -213,14 +220,14 @@
                 .launch();
 
         // Launch second activity, first become stopped
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Activity secondActivity = launchActivityAndWait(SecondActivity.class);
 
         // Wait for second activity to resume and first to stop
         waitAndAssertActivityStates(state(newTaskActivity, ON_STOP));
 
         // Finish top activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondActivity.finish();
 
         waitAndAssertActivityStates(state(newTaskActivity, ON_RESUME));
@@ -228,8 +235,8 @@
 
         // Verify that the first activity was restarted to resumed state as it was brought back
         // after windowing mode was switched
-        LifecycleVerifier.assertRestartAndResumeSequence(ThirdActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertResumeToDestroySequence(SecondActivity.class, getLifecycleLog());
+        assertRestartAndResumeSequence(ThirdActivity.class, getTransitionLog());
+        assertResumeToDestroySequence(SecondActivity.class, getTransitionLog());
     }
 
     @Test
@@ -252,17 +259,17 @@
                 sideActivity.getComponentName());
 
         // Finish top activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         translucentActivity.finish();
 
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME));
         waitAndAssertActivityStates(state(translucentActivity, ON_DESTROY));
 
         // Verify that the first activity was resumed
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
+        assertSequence(FirstActivity.class, getTransitionLog(),
                 Arrays.asList(ON_RESUME), "resume");
-        LifecycleVerifier.assertResumeToDestroySequence(TranslucentActivity.class,
-                getLifecycleLog());
+        assertResumeToDestroySequence(TranslucentActivity.class,
+                getTransitionLog());
     }
 
     @Test
@@ -276,10 +283,10 @@
                 .launch();
 
         // Wait for the activity to resume
-        LifecycleVerifier.assertLaunchSequence(CallbackTrackingActivity.class, getLifecycleLog());
+        assertLaunchSequence(CallbackTrackingActivity.class, getTransitionLog());
 
         // Enter split screen
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Wait for the activity to relaunch and receive multi-window mode change
@@ -288,12 +295,12 @@
                         ON_CREATE, ON_START, ON_POST_CREATE, ON_RESUME, ON_TOP_POSITION_GAINED,
                         ON_TOP_POSITION_LOST, ON_PAUSE);
         waitForActivityTransitions(CallbackTrackingActivity.class, expectedEnterSequence);
-        LifecycleVerifier.assertOrder(getLifecycleLog(), CallbackTrackingActivity.class,
+        assertOrder(getTransitionLog(), CallbackTrackingActivity.class,
                 Arrays.asList(ON_TOP_POSITION_LOST, ON_PAUSE, ON_STOP, ON_DESTROY, ON_CREATE,
                         ON_RESUME), "moveToSplitScreen");
 
         // Exit split-screen
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         dismissSplitScreen(true /* primaryOnTop */);
 
         // Wait for the activity to relaunch and receive multi-window mode change
@@ -301,7 +308,7 @@
                 Arrays.asList(ON_STOP, ON_DESTROY, ON_CREATE, ON_START,
                         ON_POST_CREATE, ON_RESUME, ON_PAUSE, ON_RESUME, ON_TOP_POSITION_GAINED);
         waitForActivityTransitions(CallbackTrackingActivity.class, expectedExitSequence);
-        LifecycleVerifier.assertOrder(getLifecycleLog(), CallbackTrackingActivity.class,
+        assertOrder(getTransitionLog(), CallbackTrackingActivity.class,
                 Arrays.asList(ON_DESTROY, ON_CREATE, ON_RESUME, ON_TOP_POSITION_GAINED),
                 "moveFromSplitScreen");
     }
@@ -325,7 +332,7 @@
             // Wait for the activity to receive the change.
             waitForActivityTransitions(LifecycleConfigChangeHandlingActivity.class,
                     Arrays.asList(ON_TOP_POSITION_LOST, ON_MULTI_WINDOW_MODE_CHANGED));
-            LifecycleVerifier.assertOrder(getLifecycleLog(),
+            assertOrder(getTransitionLog(),
                     LifecycleConfigChangeHandlingActivity.class,
                     Arrays.asList(ON_MULTI_WINDOW_MODE_CHANGED, ON_TOP_POSITION_LOST),
                     "moveToSplitScreen");
@@ -333,13 +340,13 @@
             // For non-fullscreen display mode, there won't be a multi-window callback.
             waitForActivityTransitions(LifecycleConfigChangeHandlingActivity.class,
                     Arrays.asList(ON_TOP_POSITION_LOST));
-            LifecycleVerifier.assertTransitionObserved(getLifecycleLog(),
+            assertTransitionObserved(getTransitionLog(),
                     transition(LifecycleConfigChangeHandlingActivity.class, ON_TOP_POSITION_LOST),
                     "moveToSplitScreen");
         }
 
         // Exit split-screen
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         dismissSplitScreen(true /* primaryOnTop */);
 
         // Wait for the activity to receive the change
@@ -348,11 +355,11 @@
         waitForActivityTransitions(LifecycleConfigChangeHandlingActivity.class, expectedSequence);
 
         if (displayWindowingMode == WINDOWING_MODE_FULLSCREEN) {
-                LifecycleVerifier.assertTransitionObserved(getLifecycleLog(),
-                        transition(LifecycleConfigChangeHandlingActivity.class,
-                        ON_MULTI_WINDOW_MODE_CHANGED), "exitSplitScreen");
+            assertTransitionObserved(getTransitionLog(),
+                    transition(LifecycleConfigChangeHandlingActivity.class,
+                            ON_MULTI_WINDOW_MODE_CHANGED), "exitSplitScreen");
         }
-        LifecycleVerifier.assertTransitionObserved(getLifecycleLog(),
+        assertTransitionObserved(getTransitionLog(),
                 transition(LifecycleConfigChangeHandlingActivity.class, ON_TOP_POSITION_GAINED),
                 "exitSplitScreen");
     }
@@ -368,12 +375,12 @@
                                 extra -> extra.putBoolean(EXTRA_ACTIVITY_ON_USER_LEAVE_HINT, true))
                         .setTargetActivity(getComponentName(FirstActivity.class)));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         launchActivityAndWait(SecondActivity.class);
 
         waitForIdle();
 
-        LifecycleVerifier.assertOrder(getLifecycleLog(), FirstActivity.class,
+        assertOrder(getTransitionLog(), FirstActivity.class,
                 Arrays.asList(ON_USER_LEAVE_HINT, ON_PAUSE, ON_STOP),
                 "moveFromSplitScreen");
     }
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecyclePipTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecyclePipTests.java
index f0dd905..f895e4f 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecyclePipTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecyclePipTests.java
@@ -26,6 +26,12 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_RESUME;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_START;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_STOP;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEmptySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartAndResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequenceMatchesOneOf;
 
 import static org.junit.Assume.assumeTrue;
 
@@ -38,6 +44,7 @@
 import org.junit.Test;
 
 import java.util.Arrays;
+import java.util.Collections;
 import java.util.List;
 
 /**
@@ -66,14 +73,14 @@
         waitAndAssertActivityStates(state(firstActivity, ON_STOP));
 
         // Move activity to Picture-In-Picture
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         pipActivity.enterPip();
 
         // Wait and assert lifecycle
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME), state(pipActivity, ON_PAUSE));
-        LifecycleVerifier.assertRestartAndResumeSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_PAUSE), "enterPip");
+        assertRestartAndResumeSequence(FirstActivity.class, getTransitionLog());
+        assertSequence(PipActivity.class, getTransitionLog(), Collections.singletonList(ON_PAUSE),
+                "enterPip");
     }
 
     @Test
@@ -82,7 +89,7 @@
         final Activity firstActivity = launchActivityAndWait(FirstActivity.class);
 
         // Clear the log before launching to Pip
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Launch Pip-capable activity and enter Pip immediately
         new Launcher(PipActivity.class)
@@ -97,10 +104,9 @@
                 Arrays.asList(ON_PAUSE, ON_RESUME);
         final List<String> extraCycleSequence =
                 Arrays.asList(ON_PAUSE, ON_STOP, ON_RESTART, ON_START, ON_RESUME);
-        LifecycleVerifier.assertSequenceMatchesOneOf(FirstActivity.class,
-                getLifecycleLog(), Arrays.asList(expectedSequence, extraCycleSequence),
-                "activityEnteringPipOnTop");
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
+        assertSequenceMatchesOneOf(FirstActivity.class, getTransitionLog(),
+                Arrays.asList(expectedSequence, extraCycleSequence), "activityEnteringPipOnTop");
+        assertSequence(PipActivity.class, getTransitionLog(),
                 Arrays.asList(ON_CREATE, ON_START, ON_RESUME, ON_PAUSE), "launchAndEnterPip");
     }
 
@@ -110,7 +116,7 @@
         final Activity firstActivity = launchActivityAndWait(FirstActivity.class);
 
         // Clear the log before launching to Pip
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Launch Pip-capable activity and enter Pip immediately
         final Activity pipActivity = new Launcher(PipActivity.class)
@@ -122,12 +128,12 @@
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME));
 
         // Exit PiP
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         pipActivity.finish();
 
         waitAndAssertActivityStates(state(pipActivity, ON_DESTROY));
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(), "finishPip");
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
+        assertEmptySequence(FirstActivity.class, getTransitionLog(), "finishPip");
+        assertSequence(PipActivity.class, getTransitionLog(),
                 Arrays.asList(ON_STOP, ON_DESTROY), "finishPip");
     }
 
@@ -140,14 +146,14 @@
                 .launch();
 
         // Launch a regular activity below
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(FirstActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
                 .launch();
 
         // Wait and verify the sequence
-        LifecycleVerifier.assertLaunchSequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertEmptySequence(PipActivity.class, getLifecycleLog(),
+        assertLaunchSequence(FirstActivity.class, getTransitionLog());
+        assertEmptySequence(PipActivity.class, getTransitionLog(),
                 "launchBelowPip");
     }
 
@@ -160,7 +166,7 @@
                 .launch();
 
         // Launch a regular activity into same task
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(FirstActivity.class)
                 .setExpectedState(ON_PAUSE)
                 // Skip launch time verification - it can be affected by PiP menu activity
@@ -177,11 +183,11 @@
         //waitForActivityTransitions(FirstActivity.class, extraDestroySequence);
         //final List<String> expectedSequence =
         //        Arrays.asList(PRE_ON_CREATE, ON_CREATE, ON_START, ON_RESUME, ON_PAUSE);
-        //LifecycleVerifier.assertSequenceMatchesOneOf(FirstActivity.class, getLifecycleLog(),
+        //TransitionVerifier.assertSequenceMatchesOneOf(FirstActivity.class, getLifecycleLog(),
         //        Arrays.asList(extraDestroySequence, expectedSequence),
         //        "launchIntoPip");
 
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
+        assertSequence(PipActivity.class, getTransitionLog(),
                 Arrays.asList(ON_STOP), "launchIntoPip");
     }
 
@@ -199,11 +205,11 @@
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME));
 
         // Destroy the activity below
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         firstActivity.finish();
         waitAndAssertActivityStates(state(firstActivity, ON_DESTROY));
-        LifecycleVerifier.assertResumeToDestroySequence(FirstActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertEmptySequence(PipActivity.class, getLifecycleLog(),
+        assertResumeToDestroySequence(FirstActivity.class, getTransitionLog());
+        assertEmptySequence(PipActivity.class, getTransitionLog(),
                 "destroyBelowPip");
     }
 
@@ -223,25 +229,25 @@
                 .launch();
 
         // Launch first activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Activity firstActivity = new Launcher(FirstActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
                 .launch();
-        LifecycleVerifier.assertLaunchSequence(FirstActivity.class, getLifecycleLog());
+        assertLaunchSequence(FirstActivity.class, getTransitionLog());
 
         // Enter split screen
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
-        LifecycleVerifier.assertEmptySequence(PipActivity.class, getLifecycleLog(),
+        assertEmptySequence(PipActivity.class, getTransitionLog(),
                 "launchBelow");
 
         // Launch second activity to side
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SecondActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
                 .launch();
 
-        LifecycleVerifier.assertLaunchSequence(SecondActivity.class, getLifecycleLog());
-        LifecycleVerifier.assertEmptySequence(PipActivity.class, getLifecycleLog(),
+        assertLaunchSequence(SecondActivity.class, getTransitionLog());
+        assertEmptySequence(PipActivity.class, getTransitionLog(),
                 "launchBelow");
     }
 
@@ -264,7 +270,7 @@
                 .launch();
 
         // Launch Pip-capable activity and enter Pip immediately
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(PipActivity.class)
                 .setExpectedState(ON_PAUSE)
                 .setExtraFlags(EXTRA_ENTER_PIP)
@@ -272,18 +278,18 @@
 
         // Wait for it to launch and pause. Other activities should not be affected.
         waitAndAssertActivityStates(state(secondActivity, ON_RESUME));
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
+        assertSequence(PipActivity.class, getTransitionLog(),
                 Arrays.asList(ON_CREATE, ON_START, ON_RESUME, ON_PAUSE),
                 "launchAndEnterPip");
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(),
+        assertEmptySequence(FirstActivity.class, getTransitionLog(),
                 "launchPipOnTop");
         final List<String> expectedSequence =
                 Arrays.asList(ON_PAUSE, ON_RESUME);
         final List<String> extraCycleSequence =
                 Arrays.asList(ON_PAUSE, ON_STOP, ON_RESTART, ON_START, ON_RESUME);
         // TODO(b/123013403): sometimes extra destroy is observed
-        LifecycleVerifier.assertSequenceMatchesOneOf(SecondActivity.class,
-                getLifecycleLog(), Arrays.asList(expectedSequence, extraCycleSequence),
+        assertSequenceMatchesOneOf(SecondActivity.class,
+                getTransitionLog(), Arrays.asList(expectedSequence, extraCycleSequence),
                 "activityEnteringPipOnTop");
     }
 }
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTests.java
index 0cf0dc3..e7b2909 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTests.java
@@ -53,7 +53,21 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_LOST;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_USER_LEAVE_HINT;
 import static android.server.wm.lifecycle.LifecycleConstants.getComponentName;
-import static android.server.wm.lifecycle.LifecycleVerifier.transition;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEmptySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEntireSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchAndDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertOrder;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRelaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartAndResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRestartSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequenceMatchesOneOf;
+import static android.server.wm.lifecycle.TransitionVerifier.assertTransitionNotObserved;
+import static android.server.wm.lifecycle.TransitionVerifier.assertTransitionObserved;
+import static android.server.wm.lifecycle.TransitionVerifier.getLaunchAndDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.transition;
 import static android.view.Surface.ROTATION_0;
 import static android.view.Surface.ROTATION_180;
 import static android.view.Surface.ROTATION_270;
@@ -77,6 +91,7 @@
 import org.junit.Test;
 
 import java.util.Arrays;
+import java.util.Collections;
 import java.util.List;
 
 /**
@@ -92,19 +107,19 @@
     public void testSingleLaunch() throws Exception {
         launchActivityAndWait(FirstActivity.class);
 
-        LifecycleVerifier.assertLaunchSequence(FirstActivity.class, getLifecycleLog());
+        assertLaunchSequence(FirstActivity.class, getTransitionLog());
     }
 
     @Test
     public void testLaunchOnTop() throws Exception {
         final Activity firstActivity = launchActivityAndWait(FirstActivity.class);
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         launchActivityAndWait(SecondActivity.class);
         waitAndAssertActivityStates(state(firstActivity, ON_STOP));
 
-        LifecycleVerifier.assertLaunchSequence(SecondActivity.class, FirstActivity.class,
-                getLifecycleLog(), false /* launchIsTranslucent */);
+        assertLaunchSequence(SecondActivity.class, FirstActivity.class,
+                getTransitionLog(), false /* launchIsTranslucent */);
     }
 
     @Test
@@ -113,12 +128,12 @@
         final Activity firstActivity = launchActivityAndWait(FirstActivity.class);
 
         // Launch translucent activity on top
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Activity translucentActivity = launchActivityAndWait(TranslucentActivity.class);
         waitAndAssertActivityStates(occludedActivityState(firstActivity, translucentActivity));
 
-        LifecycleVerifier.assertLaunchSequence(TranslucentActivity.class, FirstActivity.class,
-                getLifecycleLog(), true /* launchIsTranslucent */);
+        assertLaunchSequence(TranslucentActivity.class, FirstActivity.class,
+                getTransitionLog(), true /* launchIsTranslucent */);
     }
 
     @Test
@@ -126,34 +141,33 @@
         final Activity firstActivity = launchActivityAndWait(FirstActivity.class);
 
         // Launch translucent activity on top
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Activity translucentActivity = launchActivityAndWait(TranslucentActivity.class);
         waitAndAssertActivityStates(occludedActivityState(firstActivity, translucentActivity));
 
-        LifecycleVerifier.assertLaunchSequence(TranslucentActivity.class, FirstActivity.class,
-                getLifecycleLog(), true /* launchIsTranslucent */);
+        assertLaunchSequence(TranslucentActivity.class, FirstActivity.class,
+                getTransitionLog(), true /* launchIsTranslucent */);
 
         // Launch another translucent activity on top
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Activity secondTranslucentActivity =
                 launchActivityAndWait(SecondTranslucentActivity.class);
         waitAndAssertActivityStates(
                 occludedActivityState(translucentActivity, secondTranslucentActivity));
-        LifecycleVerifier.assertSequence(TranslucentActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_PAUSE), "launch");
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(), "launch");
+        assertSequence(TranslucentActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_PAUSE), "launch");
+        assertEmptySequence(FirstActivity.class, getTransitionLog(), "launch");
 
         // Finish top translucent activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondTranslucentActivity.finish();
 
         waitAndAssertActivityStates(state(translucentActivity, ON_RESUME));
         waitAndAssertActivityStates(state(secondTranslucentActivity, ON_DESTROY));
-        LifecycleVerifier.assertResumeToDestroySequence(SecondTranslucentActivity.class,
-                getLifecycleLog());
-        LifecycleVerifier.assertSequence(TranslucentActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_RESUME), "launch");
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(), "launch");
+        assertResumeToDestroySequence(SecondTranslucentActivity.class, getTransitionLog());
+        assertSequence(TranslucentActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_RESUME), "launch");
+        assertEmptySequence(FirstActivity.class, getTransitionLog(), "launch");
     }
 
     @Test
@@ -173,16 +187,15 @@
         int firstActivityStack = mWmState.getRootTaskIdByActivity(firstActivityName);
 
         // Move translucent activity into the stack with the first activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         moveActivityToRootTaskOrOnTop(getComponentName(TranslucentActivity.class), firstActivityStack);
 
         // Wait for translucent activity to resume and first activity to pause
         waitAndAssertActivityStates(state(translucentActivity, ON_RESUME),
                 state(firstActivity, ON_PAUSE));
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_PAUSE), "launchOnTop");
-        LifecycleVerifier.assertRestartAndResumeSequence(TranslucentActivity.class,
-                getLifecycleLog());
+        assertSequence(FirstActivity.class, getTransitionLog(), Collections.singletonList(ON_PAUSE),
+                "launchOnTop");
+        assertRestartAndResumeSequence(TranslucentActivity.class, getTransitionLog());
     }
 
     @Test
@@ -193,16 +206,16 @@
         waitAndAssertActivityStates(occludedActivityState(firstActivity, translucentActivity));
 
         // Finish translucent activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         translucentActivity.finish();
 
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME),
                 state(translucentActivity, ON_DESTROY));
 
         // Verify destruction lifecycle
-        LifecycleVerifier.assertResumeToDestroySequence(TranslucentActivity.class,
-                getLifecycleLog());
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
+        assertResumeToDestroySequence(TranslucentActivity.class,
+                getTransitionLog());
+        assertSequence(FirstActivity.class, getTransitionLog(),
                 Arrays.asList(ON_RESUME), "resumeAfterTopDestroyed");
     }
 
@@ -219,7 +232,7 @@
         waitAndAssertActivityStates(state(translucentActivity, ON_STOP),
                 state(firstActivity, ON_STOP));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         final boolean secondActivityIsTranslucent = ActivityInfo.isTranslucentOrFloating(
                 secondActivity.getWindow().getWindowStyle());
@@ -228,7 +241,7 @@
         secondActivity.finish();
 
         waitAndAssertActivityStates(state(secondActivity, ON_DESTROY));
-        LifecycleVerifier.assertResumeToDestroySequence(SecondActivity.class, getLifecycleLog());
+        assertResumeToDestroySequence(SecondActivity.class, getTransitionLog());
         if (secondActivityIsTranslucent) {
             // In this case we don't expect the state of the firstActivity to change since it is
             // already in the visible paused state. So, we just verify that translucentActivity
@@ -240,7 +253,7 @@
                     state(firstActivity, ON_START));
 
             // Verify that the first activity was restarted
-            LifecycleVerifier.assertRestartSequence(FirstActivity.class, getLifecycleLog());
+            assertRestartSequence(FirstActivity.class, getTransitionLog());
         }
     }
 
@@ -254,27 +267,26 @@
                 occludedActivityState(translucentActivity, secondTranslucentActivity));
 
         // Finish top translucent activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondTranslucentActivity.finish();
 
         waitAndAssertActivityStates(state(translucentActivity, ON_RESUME));
         waitAndAssertActivityStates(state(secondTranslucentActivity, ON_DESTROY));
-        LifecycleVerifier.assertResumeToDestroySequence(SecondTranslucentActivity.class,
-                getLifecycleLog());
-        LifecycleVerifier.assertSequence(TranslucentActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_RESUME), "destroy");
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(), "destroy");
+        assertResumeToDestroySequence(SecondTranslucentActivity.class,
+                getTransitionLog());
+        assertSequence(TranslucentActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_RESUME), "destroy");
+        assertEmptySequence(FirstActivity.class, getTransitionLog(), "destroy");
 
         // Finish first translucent activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         translucentActivity.finish();
 
         waitAndAssertActivityStates(state(firstActivity, ON_RESUME));
         waitAndAssertActivityStates(state(translucentActivity, ON_DESTROY));
-        LifecycleVerifier.assertResumeToDestroySequence(TranslucentActivity.class,
-                getLifecycleLog());
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_RESUME), "secondDestroy");
+        assertResumeToDestroySequence(TranslucentActivity.class, getTransitionLog());
+        assertSequence(FirstActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_RESUME), "secondDestroy");
     }
 
     @Test
@@ -284,15 +296,15 @@
         waitAndAssertActivityStates(state(bottomActivity, ON_STOP));
 
         // Finish the activity on the bottom
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         bottomActivity.finish();
 
         // Assert that activity on the bottom went directly to destroyed state, and activity on top
         // did not get any lifecycle changes.
         waitAndAssertActivityStates(state(bottomActivity, ON_DESTROY));
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_DESTROY), "destroyOnBottom");
-        LifecycleVerifier.assertEmptySequence(SecondActivity.class, getLifecycleLog(),
+        assertSequence(FirstActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_DESTROY), "destroyOnBottom");
+        assertEmptySequence(SecondActivity.class, getTransitionLog(),
                 "destroyOnBottom");
     }
 
@@ -321,7 +333,7 @@
 
         waitAndAssertActivityStates(state(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED),
                 state(ResultActivity.class, ON_DESTROY));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 // Base launching activity starting.
                 transition(LaunchForResultActivity.class, ON_CREATE),
                 transition(LaunchForResultActivity.class, ON_START),
@@ -352,7 +364,7 @@
         activity.finish();
         waitAndAssertActivityStates(state(activity, ON_DESTROY));
 
-        LifecycleVerifier.assertLaunchAndDestroySequence(FirstActivity.class, getLifecycleLog());
+        assertLaunchAndDestroySequence(FirstActivity.class, getTransitionLog());
     }
 
     @Test
@@ -385,7 +397,7 @@
         launcher.launch();
         waitAndAssertActivityStates(state(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED));
 
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(NoDisplayActivity.class, ON_CREATE),
                 transition(CallbackTrackingActivity.class, ON_CREATE),
                 transition(CallbackTrackingActivity.class, ON_START),
@@ -393,7 +405,7 @@
                 transition(CallbackTrackingActivity.class, ON_RESUME),
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED),
                 transition(NoDisplayActivity.class, ON_DESTROY)),
-                getLifecycleLog(), "trampolineLaunch");
+                getTransitionLog(), "trampolineLaunch");
     }
 
     /** @see #testTrampolineWithAnotherProcess */
@@ -413,7 +425,7 @@
                 .setFlags(Intent.FLAG_ACTIVITY_NEW_TASK));
         waitAndAssertActivityStates(
                 state(SecondProcessCallbackTrackingActivity.class, ON_TOP_POSITION_GAINED));
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         testTrampolineWithAnotherProcess();
     }
@@ -444,11 +456,11 @@
     public void testRelaunchResumed() throws Exception {
         final Activity activity = launchActivityAndWait(FirstActivity.class);
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(activity::recreate);
         waitAndAssertActivityStates(state(activity, ON_RESUME));
 
-        LifecycleVerifier.assertRelaunchSequence(FirstActivity.class, getLifecycleLog(), ON_RESUME);
+        assertRelaunchSequence(FirstActivity.class, getTransitionLog(), ON_RESUME);
     }
 
     @Test
@@ -458,11 +470,11 @@
 
         waitAndAssertActivityStates(occludedActivityState(pausedActivity, translucentActivity));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(pausedActivity::recreate);
         waitAndAssertActivityStates(state(pausedActivity, ON_PAUSE));
 
-        LifecycleVerifier.assertRelaunchSequence(FirstActivity.class, getLifecycleLog(), ON_PAUSE);
+        assertRelaunchSequence(FirstActivity.class, getTransitionLog(), ON_PAUSE);
     }
 
     @Test
@@ -472,12 +484,11 @@
 
         waitAndAssertActivityStates(state(stoppedActivity, ON_STOP));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(stoppedActivity::recreate);
         waitAndAssertActivityStates(state(stoppedActivity, ON_STOP));
 
-        LifecycleVerifier.assertRelaunchSequence(FirstActivity.class, getLifecycleLog(),
-                ON_STOP);
+        assertRelaunchSequence(FirstActivity.class, getTransitionLog(), ON_STOP);
     }
 
     @Test
@@ -507,7 +518,7 @@
             return;
         }
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         final int current = rotationSession.get();
         // Set new rotation to cause a configuration change.
@@ -526,11 +537,10 @@
 
         // Assert that the top activity was relaunched.
         waitAndAssertActivityStates(state(topOpaqueActivity, ON_RESUME));
-        LifecycleVerifier.assertRelaunchSequence(
-                SecondActivity.class, getLifecycleLog(), ON_RESUME);
+        assertRelaunchSequence(SecondActivity.class, getTransitionLog(), ON_RESUME);
 
         // Finish the top activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         topOpaqueActivity.finish();
 
         // Assert that the translucent activity and the activity visible behind it were
@@ -538,13 +548,13 @@
         waitAndAssertActivityStates(state(becomingVisibleActivity, ON_PAUSE),
                 state(translucentActivity, ON_RESUME));
 
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_DESTROY, ON_CREATE, ON_START, ON_RESUME,
-                        ON_PAUSE), "becomingVisiblePaused");
+        assertSequence(FirstActivity.class, getTransitionLog(),
+                Arrays.asList(ON_DESTROY, ON_CREATE, ON_START, ON_RESUME, ON_PAUSE),
+                "becomingVisiblePaused");
         final List<String> expectedSequence =
                 Arrays.asList(ON_DESTROY, ON_CREATE, ON_START, ON_RESUME);
-        LifecycleVerifier.assertSequence(TranslucentActivity.class, getLifecycleLog(),
-                expectedSequence, "becomingVisibleResumed");
+        assertSequence(TranslucentActivity.class, getTransitionLog(), expectedSequence,
+                "becomingVisibleResumed");
     }
 
     @Test
@@ -569,7 +579,7 @@
                         ON_TOP_POSITION_GAINED, ON_TOP_POSITION_LOST, ON_PAUSE, ON_STOP,
                         ON_RESTART, ON_START, ON_ACTIVITY_RESULT, ON_RESUME,
                         ON_TOP_POSITION_GAINED);
-        LifecycleVerifier.assertSequence(LaunchForwardResultActivity.class, getLifecycleLog(),
+        assertSequence(LaunchForwardResultActivity.class, getTransitionLog(),
                 expectedSequence, "becomingVisibleResumed");
     }
 
@@ -591,8 +601,7 @@
         final List<String> sequenceWithStop =
                 Arrays.asList(ON_CREATE, ON_START, ON_POST_CREATE, ON_RESUME,
                         ON_PAUSE, ON_STOP, ON_RESTART, ON_START, ON_ACTIVITY_RESULT, ON_RESUME);
-        LifecycleVerifier.assertSequenceMatchesOneOf(LaunchForResultActivity.class,
-                getLifecycleLog(),
+        assertSequenceMatchesOneOf(LaunchForResultActivity.class, getTransitionLog(),
                 Arrays.asList(expectedSequence, sequenceWithStop), "activityResult");
     }
 
@@ -629,8 +638,8 @@
         }
         waitForActivityTransitions(LaunchForResultActivity.class, expectedSequences);
 
-        LifecycleVerifier.assertSequence(LaunchForResultActivity.class,
-                getLifecycleLog(), expectedSequences, "activityResult");
+        assertSequence(LaunchForResultActivity.class, getTransitionLog(), expectedSequences,
+                "activityResult");
     }
 
     @Test
@@ -638,12 +647,11 @@
         final Activity trackingActivity = launchActivityAndWait(CallbackTrackingActivity.class);
 
         // Call "recreate" and assert sequence
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(trackingActivity::recreate);
         waitAndAssertActivityStates(state(trackingActivity, ON_TOP_POSITION_GAINED));
 
-        LifecycleVerifier.assertSequence(CallbackTrackingActivity.class,
-                getLifecycleLog(),
+        assertSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 Arrays.asList(ON_TOP_POSITION_LOST, ON_PAUSE, ON_STOP, ON_DESTROY,
                         ON_CREATE, ON_START, ON_POST_CREATE, ON_RESUME, ON_TOP_POSITION_GAINED),
                 "recreate");
@@ -660,12 +668,11 @@
         waitAndAssertActivityStates(occludedActivityState(trackingActivity, translucentActivity));
 
         // Call "recreate" and assert sequence
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(trackingActivity::recreate);
         waitAndAssertActivityStates(occludedActivityState(trackingActivity, translucentActivity));
 
-        LifecycleVerifier.assertSequence(CallbackTrackingActivity.class,
-                getLifecycleLog(),
+        assertSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 Arrays.asList(ON_STOP, ON_DESTROY, ON_CREATE, ON_START,
                         ON_POST_CREATE, ON_RESUME, ON_PAUSE),
                 "recreate");
@@ -681,7 +688,7 @@
         waitAndAssertActivityStates(state(trackingActivity, ON_STOP));
 
         // Call "recreate" and assert sequence
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(trackingActivity::recreate);
         waitAndAssertActivityStates(state(trackingActivity, ON_STOP));
 
@@ -694,8 +701,8 @@
                     ON_POST_CREATE, ON_RESUME, ON_PAUSE, ON_STOP);
         }
 
-        LifecycleVerifier.assertSequence(
-                CallbackTrackingActivity.class, getLifecycleLog(), callbacks, "recreate");
+        assertSequence(
+                CallbackTrackingActivity.class, getTransitionLog(), callbacks, "recreate");
     }
 
     /**
@@ -754,7 +761,7 @@
         waitAndAssertActivityStates(state(recreatingActivity, ON_STOP));
 
         // Launch the activity again to recreate
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
                 .setExtraFlags(EXTRA_RECREATE)
@@ -774,8 +781,8 @@
         }
 
         waitForActivityTransitions(SingleTopActivity.class, expectedRelaunchSequence);
-        LifecycleVerifier.assertSequence(SingleTopActivity.class, getLifecycleLog(),
-                expectedRelaunchSequence, "recreate");
+        assertSequence(SingleTopActivity.class, getTransitionLog(), expectedRelaunchSequence,
+                "recreate");
     }
 
     @Test
@@ -783,17 +790,17 @@
         // Launch a singleTop activity
         launchActivityAndWait(SingleTopActivity.class);
 
-        LifecycleVerifier.assertLaunchSequence(SingleTopActivity.class, getLifecycleLog());
+        assertLaunchSequence(SingleTopActivity.class, getTransitionLog());
 
         // Try to launch again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
                 .setNoInstance()
                 .launch();
 
         // Verify that the first activity was paused, new intent was delivered and resumed again
-        LifecycleVerifier.assertSequence(SingleTopActivity.class, getLifecycleLog(),
+        assertSequence(SingleTopActivity.class, getTransitionLog(),
                 Arrays.asList(ON_TOP_POSITION_LOST, ON_PAUSE, ON_NEW_INTENT, ON_RESUME,
                         ON_TOP_POSITION_GAINED), "newIntent");
     }
@@ -802,7 +809,7 @@
     public void testOnNewIntentFromHidden() throws Exception {
         // Launch a singleTop activity
         final Activity singleTopActivity = launchActivityAndWait(SingleTopActivity.class);
-        LifecycleVerifier.assertLaunchSequence(SingleTopActivity.class, getLifecycleLog());
+        assertLaunchSequence(SingleTopActivity.class, getTransitionLog());
 
         // Launch something on top
         final Activity secondActivity = new Launcher(SecondActivity.class)
@@ -813,7 +820,7 @@
         waitAndAssertActivityStates(state(singleTopActivity, ON_STOP));
 
         // Try to launch again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
                 .setNoInstance()
@@ -827,15 +834,14 @@
             expectedSequence = Arrays.asList(ON_RESTART, ON_START, ON_NEW_INTENT, ON_RESUME,
                     ON_TOP_POSITION_GAINED);
         }
-        LifecycleVerifier.assertSequence(SingleTopActivity.class, getLifecycleLog(),
-                expectedSequence, "newIntent");
+        assertSequence(SingleTopActivity.class, getTransitionLog(), expectedSequence, "newIntent");
     }
 
     @Test
     public void testOnNewIntentFromPaused() throws Exception {
         // Launch a singleTop activity
         final Activity singleTopActivity = launchActivityAndWait(SingleTopActivity.class);
-        LifecycleVerifier.assertLaunchSequence(SingleTopActivity.class, getLifecycleLog());
+        assertLaunchSequence(SingleTopActivity.class, getTransitionLog());
 
         // Launch translucent activity, which will make the first one paused.
         launchActivityAndWait(TranslucentActivity.class);
@@ -844,7 +850,7 @@
         waitAndAssertActivityStates(state(singleTopActivity, ON_PAUSE));
 
         // Try to launch again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TOP)
                 .setNoInstance()
@@ -855,8 +861,7 @@
         final List<String> expectedSequence =
                 Arrays.asList(ON_NEW_INTENT, ON_RESUME, ON_TOP_POSITION_GAINED);
         waitForActivityTransitions(SingleTopActivity.class, expectedSequence);
-        LifecycleVerifier.assertSequence(SingleTopActivity.class, getLifecycleLog(),
-                expectedSequence, "newIntent");
+        assertSequence(SingleTopActivity.class, getTransitionLog(), expectedSequence, "newIntent");
     }
 
     @Test
@@ -955,8 +960,7 @@
         // Launch an activity on top, which will make the first one paused or stopped.
         launchActivityAndWait(launchOnTopClass);
 
-        final List<String> expectedSequence =
-                LifecycleVerifier.getLaunchAndDestroySequence(activityClass);
+        final List<String> expectedSequence = getLaunchAndDestroySequence(activityClass);
         waitAndAssertActivityTransitions(activityClass, expectedSequence, "finish in " + stageName);
     }
 
@@ -966,13 +970,13 @@
 
         launchActivityAndWait(TranslucentCallbackTrackingActivity.class);
         waitAndAssertActivityStates(state(bottomActivity, ON_PAUSE));
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         waitForIdle();
         bottomActivity.finish();
         waitAndAssertActivityStates(state(bottomActivity, ON_DESTROY));
-        LifecycleVerifier.assertEmptySequence(TranslucentCallbackTrackingActivity.class,
-                getLifecycleLog(), "finishBelow");
+        assertEmptySequence(TranslucentCallbackTrackingActivity.class,
+                getTransitionLog(), "finishBelow");
     }
 
     @Test
@@ -981,13 +985,12 @@
 
         launchActivityAndWait(FirstActivity.class);
         waitAndAssertActivityStates(state(bottomActivity, ON_STOP));
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         waitForIdle();
         bottomActivity.finish();
         waitAndAssertActivityStates(state(bottomActivity, ON_DESTROY));
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(),
-                "finishBelow");
+        assertEmptySequence(FirstActivity.class, getTransitionLog(), "finishBelow");
     }
 
     @Test
@@ -1012,7 +1015,7 @@
         waitAndAssertActivityStates(state(activity, ON_TOP_POSITION_GAINED));
 
         // Verify the result have been sent back to original activity
-        LifecycleVerifier.assertTransitionObserved(getLifecycleLog(),
+        assertTransitionObserved(getTransitionLog(),
                 transition(SingleTopActivity.class, ON_ACTIVITY_RESULT),"activityResult");
     }
 
@@ -1022,11 +1025,11 @@
                 .setExtraFlags(EXTRA_ACTIVITY_ON_USER_LEAVE_HINT)
                 .launch();
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         launchActivityAndWait(SecondActivity.class);
         waitAndAssertActivityStates(state(FirstActivity.class, ON_STOP));
 
-        LifecycleVerifier.assertTransitionObserved(getLifecycleLog(),
+        assertTransitionObserved(getTransitionLog(),
                 transition(FirstActivity.class, ON_USER_LEAVE_HINT),"userLeaveHint");
     }
 
@@ -1036,13 +1039,13 @@
                 .setExtraFlags(EXTRA_ACTIVITY_ON_USER_LEAVE_HINT)
                 .launch();
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SecondActivity.class)
                 .setFlags(FLAG_ACTIVITY_NO_USER_ACTION | FLAG_ACTIVITY_NEW_TASK)
                 .launch();
         waitAndAssertActivityStates(state(FirstActivity.class, ON_STOP));
 
-        LifecycleVerifier.assertTransitionNotObserved(getLifecycleLog(),
+        assertTransitionNotObserved(getTransitionLog(),
                 transition(FirstActivity.class, ON_USER_LEAVE_HINT),"userLeaveHint");
     }
 }
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTopResumedStateTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTopResumedStateTests.java
index fffce55..9d9fd6a 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTopResumedStateTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityLifecycleTopResumedStateTests.java
@@ -39,7 +39,20 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_GAINED;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_LOST;
 import static android.server.wm.lifecycle.LifecycleConstants.getComponentName;
-import static android.server.wm.lifecycle.LifecycleVerifier.transition;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEmptySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEntireSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchAndStopSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertOrder;
+import static android.server.wm.lifecycle.TransitionVerifier.assertRelaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertResumeToStopSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertStopToResumeSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertStopToResumeSubSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.getLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.getRelaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.transition;
 import static android.view.Display.DEFAULT_DISPLAY;
 
 import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
@@ -63,6 +76,7 @@
 import org.junit.Test;
 
 import java.util.Arrays;
+import java.util.Collections;
 import java.util.List;
 
 /**
@@ -85,31 +99,30 @@
     public void testTopPositionAfterLaunch() throws Exception {
         launchActivityAndWait(CallbackTrackingActivity.class);
 
-        LifecycleVerifier.assertLaunchSequence(CallbackTrackingActivity.class, getLifecycleLog());
+        assertLaunchSequence(CallbackTrackingActivity.class, getTransitionLog());
     }
 
     @Test
     public void testTopPositionLostOnFinish() throws Exception {
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         activity.finish();
         mWmState.waitForActivityRemoved(getComponentName(CallbackTrackingActivity.class));
 
-        LifecycleVerifier.assertResumeToDestroySequence(CallbackTrackingActivity.class,
-                getLifecycleLog());
+        assertResumeToDestroySequence(CallbackTrackingActivity.class, getTransitionLog());
     }
 
     @Test
     public void testTopPositionSwitchToActivityOnTop() throws Exception {
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
-        final Activity topActivity = launchActivityAndWait(SingleTopActivity.class);
+        getTransitionLog().clear();
+        launchActivityAndWait(SingleTopActivity.class);
         waitAndAssertActivityStates(state(activity, ON_STOP));
 
-        LifecycleVerifier.assertLaunchSequence(SingleTopActivity.class,
-                CallbackTrackingActivity.class, getLifecycleLog(),
+        assertLaunchSequence(SingleTopActivity.class,
+                CallbackTrackingActivity.class, getTransitionLog(),
                 false /* launchingIsTranslucent */);
     }
 
@@ -125,7 +138,7 @@
         waitAndAssertActivityStates(state(firstActivity, ON_TOP_POSITION_GAINED));
 
         // Launch second activity on top
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Class<? extends Activity> secondActivityClass =
                 SecondProcessCallbackTrackingActivity.class;
         launchActivity(new ComponentName(firstActivity, secondActivityClass));
@@ -133,7 +146,7 @@
         // Wait and assert top position switch
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED),
                 state(firstActivity, ON_STOP));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(firstActivity.getClass(), ON_TOP_POSITION_LOST),
                 transition(secondActivityClass, ON_TOP_POSITION_GAINED)),
                 "launchOnTop");
@@ -152,7 +165,7 @@
         final Class<? extends Activity> firstActivityClass = firstActivity.getClass();
 
         // Launch second activity on top
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Class<? extends Activity> secondActivityClass =
                 SecondProcessCallbackTrackingActivity.class;
         launchActivity(new ComponentName(firstActivity, secondActivityClass));
@@ -160,18 +173,18 @@
         // Wait and assert top position switch,
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED),
                 state(firstActivity, ON_STOP));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_GAINED),
                 transition(firstActivityClass, ON_TOP_POSITION_LOST)),
                 "launchOnTop");
 
         // Wait 5 seconds more to make sure that no new messages received after top resumed state
         // released by the slow activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         Thread.sleep(5000);
-        LifecycleVerifier.assertEmptySequence(firstActivityClass, getLifecycleLog(),
+        assertEmptySequence(firstActivityClass, getTransitionLog(),
                 "topStateLossTimeout");
-        LifecycleVerifier.assertEmptySequence(secondActivityClass, getLifecycleLog(),
+        assertEmptySequence(secondActivityClass, getTransitionLog(),
                 "topStateLossTimeout");
     }
 
@@ -179,13 +192,12 @@
     public void testTopPositionSwitchToTranslucentActivityOnTop() throws Exception {
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
-        final Activity topActivity = launchActivityAndWait(
-                TranslucentCallbackTrackingActivity.class);
+        getTransitionLog().clear();
+        launchActivityAndWait(TranslucentCallbackTrackingActivity.class);
         waitAndAssertActivityStates(state(activity, ON_PAUSE));
 
-        LifecycleVerifier.assertLaunchSequence(TranslucentCallbackTrackingActivity.class,
-                CallbackTrackingActivity.class, getLifecycleLog(),
+        assertLaunchSequence(TranslucentCallbackTrackingActivity.class,
+                CallbackTrackingActivity.class, getTransitionLog(),
                 true /* launchingIsTranslucent */);
     }
 
@@ -193,7 +205,7 @@
     public void testTopPositionSwitchOnDoubleLaunch() throws Exception {
         final Activity baseActivity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(LaunchForResultActivity.class)
                 .setExpectedState(ON_STOP)
                 .setNoInstance()
@@ -206,7 +218,7 @@
         waitForActivityTransitions(ResultActivity.class, expectedTopActivitySequence);
 
         final List<Pair<String, String>> observedTransitions =
-                getLifecycleLog().getLog();
+                getTransitionLog().getLog();
         final List<Pair<String, String>> expectedTransitions = Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_PAUSE),
@@ -231,8 +243,8 @@
     public void testTopPositionSwitchOnDoubleLaunchAndTopFinish() throws Exception {
         final Activity baseActivity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
-        final Activity launchForResultActivity = new Launcher(LaunchForResultActivity.class)
+        getTransitionLog().clear();
+        new Launcher(LaunchForResultActivity.class)
                 .customizeIntent(LaunchForResultActivity.forwardFlag(EXTRA_FINISH_IN_ON_RESUME,
                         EXTRA_SKIP_TOP_RESUMED_STATE))
                 // Start the TranslucentResultActivity to avoid activity below stopped sometimes
@@ -251,7 +263,7 @@
                 ON_START, ON_POST_CREATE, ON_RESUME, ON_TOP_POSITION_GAINED);
         waitForActivityTransitions(TranslucentResultActivity.class, expectedTopActivitySequence);
 
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_PAUSE),
                 transition(LaunchForResultActivity.class, ON_CREATE),
@@ -272,7 +284,7 @@
                 transition(TranslucentResultActivity.class, ON_STOP),
                 transition(TranslucentResultActivity.class, ON_DESTROY),
                 transition(CallbackTrackingActivity.class, ON_STOP)),
-                getLifecycleLog(), "Double launch sequence must match");
+                getTransitionLog(), "Double launch sequence must match");
     }
 
     @Test
@@ -303,13 +315,13 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Launch second activity to side
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
                 .launch();
 
         // Second activity must be on top now
-        LifecycleVerifier.assertLaunchSequence(SingleTopActivity.class, getLifecycleLog());
+        assertLaunchSequence(SingleTopActivity.class, getTransitionLog());
     }
 
     @Test
@@ -326,14 +338,14 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Launch second activity to side
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         final Activity secondActivity = new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
                 .launch();
 
         // Switch top between two activities
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getPrimarySplitTaskId());
         new Launcher(CallbackTrackingActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
@@ -342,13 +354,13 @@
 
         waitAndAssertActivityStates(state(firstActivity, ON_TOP_POSITION_GAINED),
                 state(secondActivity, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertSequence(CallbackTrackingActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_TOP_POSITION_GAINED), "switchTop");
-        LifecycleVerifier.assertSequence(SingleTopActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_TOP_POSITION_LOST), "switchTop");
+        assertSequence(CallbackTrackingActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_TOP_POSITION_GAINED), "switchTop");
+        assertSequence(SingleTopActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_TOP_POSITION_LOST), "switchTop");
 
         // Switch top again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
@@ -357,9 +369,9 @@
 
         waitAndAssertActivityStates(state(firstActivity, ON_TOP_POSITION_LOST),
                 state(secondActivity, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertSequence(CallbackTrackingActivity.class, getLifecycleLog(),
-                Arrays.asList(ON_TOP_POSITION_LOST), "switchTop");
-        LifecycleVerifier.assertSequence(SingleTopActivity.class, getLifecycleLog(),
+        assertSequence(CallbackTrackingActivity.class, getTransitionLog(),
+                Collections.singletonList(ON_TOP_POSITION_LOST), "switchTop");
+        assertSequence(SingleTopActivity.class, getTransitionLog(),
                 Arrays.asList(ON_PAUSE, ON_NEW_INTENT, ON_RESUME, ON_TOP_POSITION_GAINED),
                 "switchTop");
     }
@@ -370,7 +382,7 @@
         launchActivityAndWait(SingleTopActivity.class);
 
         // Launch the activity again to observe new intent
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
                 .setNoInstance()
@@ -392,7 +404,7 @@
         waitAndAssertActivityStates(state(singleTopActivity, ON_STOP));
 
         // Launch the single top activity again to observe new intent
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TOP)
                 .setNoInstance()
@@ -400,7 +412,7 @@
 
         waitAndAssertActivityStates(state(topActivity, ON_DESTROY));
 
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_PAUSE),
                 transition(SingleTopActivity.class, ON_RESTART),
@@ -410,7 +422,7 @@
                 transition(SingleTopActivity.class, ON_TOP_POSITION_GAINED),
                 transition(CallbackTrackingActivity.class, ON_STOP),
                 transition(CallbackTrackingActivity.class, ON_DESTROY)),
-                getLifecycleLog(), "Single top resolution sequence must match");
+                getTransitionLog(), "Single top resolution sequence must match");
     }
 
     @Test
@@ -424,7 +436,7 @@
         waitAndAssertActivityStates(state(singleTopActivity, ON_PAUSE));
 
         // Launch the single top activity again to observe new intent
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TOP)
                 .setNoInstance()
@@ -432,7 +444,7 @@
 
         waitAndAssertActivityStates(state(topActivity, ON_DESTROY));
 
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(TranslucentCallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(TranslucentCallbackTrackingActivity.class, ON_PAUSE),
                 transition(SingleTopActivity.class, ON_NEW_INTENT),
@@ -446,12 +458,11 @@
         final Activity topActivity = launchActivityAndWait(CallbackTrackingActivity.class);
 
         // Press HOME and verify the lifecycle
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         pressHomeButton();
         waitAndAssertActivityStates(state(topActivity, ON_STOP));
 
-        LifecycleVerifier.assertResumeToStopSequence(CallbackTrackingActivity.class,
-                getLifecycleLog());
+        assertResumeToStopSequence(CallbackTrackingActivity.class, getTransitionLog());
     }
 
     @Test
@@ -468,37 +479,37 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Launch second activity to side
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         final Activity secondActivity = new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK)
                 .launch();
 
         // Tap on first activity to switch the focus
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task dockedTask = getRootTaskForLeafTaskId(firstActivity.getTaskId());
         tapOnTaskCenter(dockedTask);
 
         // Wait and assert focus switch
         waitAndAssertActivityStates(state(firstActivity, ON_TOP_POSITION_GAINED),
                 state(secondActivity, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(SingleTopActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED)),
-                getLifecycleLog(), "Single top resolution sequence must match");
+                getTransitionLog(), "Single top resolution sequence must match");
 
         // Tap on second activity to switch the focus again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task sideTask = getRootTaskForLeafTaskId(secondActivity.getTaskId());
         tapOnTaskCenter(sideTask);
 
         // Wait and assert focus switch
         waitAndAssertActivityStates(state(firstActivity, ON_TOP_POSITION_LOST),
                 state(secondActivity, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(SingleTopActivity.class, ON_TOP_POSITION_GAINED)),
-                getLifecycleLog(), "Single top resolution sequence must match");
+                getTransitionLog(), "Single top resolution sequence must match");
     }
 
     @Test
@@ -521,7 +532,7 @@
         moveTaskToPrimarySplitScreenAndVerify(firstActivity, sideActivity);
 
         // Launch second activity to side
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         final Class<? extends Activity> secondActivityClass =
                 SecondProcessCallbackTrackingActivity.class;
@@ -538,27 +549,27 @@
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED));
 
         // Tap on first activity to switch the top resumed one
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task dockedTask = getRootTaskForLeafTaskId(firstActivity.getTaskId());
         tapOnTaskCenter(dockedTask);
 
         // Wait and assert top resumed position switch
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_LOST),
                 state(firstActivityClass, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_LOST),
                 transition(firstActivityClass, ON_TOP_POSITION_GAINED)),
                 "tapOnTask");
 
         // Tap on second activity to switch the top resumed activity again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task sideTask = mWmState.getTaskByActivity(secondActivityComponent);
         tapOnTaskCenter(sideTask);
 
         // Wait and assert top resumed position switch
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED),
                 state(firstActivityClass, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(firstActivityClass, ON_TOP_POSITION_LOST),
                 transition(secondActivityClass, ON_TOP_POSITION_GAINED)),
                 "tapOnTask");
@@ -584,7 +595,7 @@
         moveTaskToPrimarySplitScreenAndVerify(slowActivity, sideActivity);
 
         // Launch second activity to side
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         mTaskOrganizer.setLaunchRoot(mTaskOrganizer.getSecondarySplitTaskId());
         final Class<? extends Activity> secondActivityClass =
                 SecondProcessCallbackTrackingActivity.class;
@@ -601,20 +612,20 @@
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED));
 
         // Tap on first activity to switch the top resumed one
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task dockedTask = getRootTaskForLeafTaskId(slowActivity.getTaskId());
         tapOnTaskCenter(dockedTask);
 
         // Wait and assert top resumed position switch.
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_LOST),
                 state(slowActivityClass, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_LOST),
                 transition(slowActivityClass, ON_TOP_POSITION_GAINED)),
                 "tapOnTask");
 
         // Tap on second activity to switch the top resumed activity again
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task sideTask = mWmState
                 .getTaskByActivity(secondActivityComponent);
         tapOnTaskCenter(sideTask);
@@ -623,18 +634,18 @@
         // be reported to the first activity before second will finish handling it.
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED),
                 state(slowActivityClass, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_GAINED),
                 transition(slowActivityClass, ON_TOP_POSITION_LOST)),
                 "tapOnTask");
 
         // Wait 5 seconds more to make sure that no new messages received after top resumed state
         // released by the slow activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         Thread.sleep(5000);
-        LifecycleVerifier.assertEmptySequence(slowActivityClass, getLifecycleLog(),
+        assertEmptySequence(slowActivityClass, getTransitionLog(),
                 "topStateLossTimeout");
-        LifecycleVerifier.assertEmptySequence(secondActivityClass, getLifecycleLog(),
+        assertEmptySequence(secondActivityClass, getTransitionLog(),
                 "topStateLossTimeout");
     }
 
@@ -642,11 +653,11 @@
     public void testTopPositionPreservedOnLocalRelaunch() throws Exception {
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         getInstrumentation().runOnMainSync(activity::recreate);
         waitAndAssertActivityStates(state(activity, ON_TOP_POSITION_GAINED));
 
-        LifecycleVerifier.assertRelaunchSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertRelaunchSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 ON_TOP_POSITION_GAINED);
     }
 
@@ -661,23 +672,21 @@
                     .setExpectedState(ON_STOP)
                     .setNoInstance()
                     .launch();
-            LifecycleVerifier.assertLaunchAndStopSequence(CallbackTrackingActivity.class,
-                    getLifecycleLog(), true /* onTop */);
+            assertLaunchAndStopSequence(CallbackTrackingActivity.class, getTransitionLog(),
+                    true /* onTop */);
 
-            getLifecycleLog().clear();
+            getTransitionLog().clear();
         }
 
         // Lock screen removed - activity should be on top now
         if (isCar()) {
-            LifecycleVerifier.assertStopToResumeSubSequence(CallbackTrackingActivity.class,
-                    getLifecycleLog());
+            assertStopToResumeSubSequence(CallbackTrackingActivity.class, getTransitionLog());
             waitAndAssertActivityCurrentState(CallbackTrackingActivity.class,
                     ON_TOP_POSITION_GAINED);
         } else {
             waitAndAssertActivityStates(
                     state(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED));
-            LifecycleVerifier.assertStopToResumeSequence(CallbackTrackingActivity.class,
-                    getLifecycleLog());
+            assertStopToResumeSequence(CallbackTrackingActivity.class, getTransitionLog());
         }
     }
 
@@ -687,26 +696,26 @@
 
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         try (final LockScreenSession lockScreenSession = new LockScreenSession()) {
             lockScreenSession.setLockCredential().gotoKeyguard();
 
             waitAndAssertActivityStates(state(activity, ON_STOP));
-            LifecycleVerifier.assertResumeToStopSequence(CallbackTrackingActivity.class,
-                    getLifecycleLog());
+            assertResumeToStopSequence(CallbackTrackingActivity.class,
+                    getTransitionLog());
 
-            getLifecycleLog().clear();
+            getTransitionLog().clear();
         }
 
         // Lock screen removed - activity should be on top now
         if (isCar()) {
-            LifecycleVerifier.assertStopToResumeSubSequence(CallbackTrackingActivity.class,
-                    getLifecycleLog());
+            assertStopToResumeSubSequence(CallbackTrackingActivity.class,
+                    getTransitionLog());
             waitAndAssertActivityCurrentState(activity.getClass(), ON_TOP_POSITION_GAINED);
         } else {
             waitAndAssertActivityStates(state(activity, ON_TOP_POSITION_GAINED));
-            LifecycleVerifier.assertStopToResumeSequence(CallbackTrackingActivity.class,
-                    getLifecycleLog());
+            assertStopToResumeSequence(CallbackTrackingActivity.class,
+                    getTransitionLog());
         }
     }
 
@@ -725,21 +734,21 @@
                                 .launch();
 
             // TODO(b/123432490): Fix extra pause/resume
-            LifecycleVerifier.assertSequence(ShowWhenLockedCallbackTrackingActivity.class,
-                    getLifecycleLog(),
+            assertSequence(ShowWhenLockedCallbackTrackingActivity.class,
+                    getTransitionLog(),
                     Arrays.asList(ON_CREATE, ON_START, ON_POST_CREATE, ON_RESUME,
                             ON_TOP_POSITION_GAINED, ON_TOP_POSITION_LOST, ON_PAUSE, ON_RESUME,
                             ON_TOP_POSITION_GAINED),
                     "launchAboveKeyguard");
 
-            getLifecycleLog().clear();
+            getTransitionLog().clear();
         }
 
         // When the lock screen is removed, the ShowWhenLocked activity will be dismissed using the
         // back button, which should finish the activity.
         waitAndAssertActivityStates(state(showWhenLockedActivity, ON_DESTROY));
-        LifecycleVerifier.assertResumeToDestroySequence(
-                ShowWhenLockedCallbackTrackingActivity.class, getLifecycleLog());
+        assertResumeToDestroySequence(
+                ShowWhenLockedCallbackTrackingActivity.class, getTransitionLog());
     }
 
     @Test
@@ -757,7 +766,7 @@
         waitAndAssertTopResumedActivity(getComponentName(CallbackTrackingActivity.class),
                 DEFAULT_DISPLAY, "Activity launched on default display must be focused");
         waitAndAssertActivityTransitions(CallbackTrackingActivity.class,
-                LifecycleVerifier.getLaunchSequence(CallbackTrackingActivity.class), "launch");
+                getLaunchSequence(CallbackTrackingActivity.class), "launch");
 
         try (final VirtualDisplaySession virtualDisplaySession = new VirtualDisplaySession()) {
             // Create new simulated display
@@ -765,7 +774,7 @@
                     = virtualDisplaySession.setSimulateDisplay(true).createDisplay();
 
             // Launch another activity on new secondary display.
-            getLifecycleLog().clear();
+            getTransitionLog().clear();
             launchOptions.setLaunchDisplayId(newDisplay.mId);
             new Launcher(SingleTopActivity.class)
                     .setFlags(FLAG_ACTIVITY_NEW_TASK)
@@ -775,20 +784,19 @@
                     newDisplay.mId, "Activity launched on secondary display must be focused");
 
             waitAndAssertActivityTransitions(SingleTopActivity.class,
-                    LifecycleVerifier.getLaunchSequence(SingleTopActivity.class), "launch");
-            LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+                    getLaunchSequence(SingleTopActivity.class), "launch");
+            assertOrder(getTransitionLog(), Arrays.asList(
                     transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                     transition(SingleTopActivity.class, ON_TOP_POSITION_GAINED)),
                     "launchOnOtherDisplay");
 
-            getLifecycleLog().clear();
+            getTransitionLog().clear();
         }
 
         // Secondary display was removed - activity will be moved to the default display
         waitForActivityTransitions(SingleTopActivity.class,
-                LifecycleVerifier.getRelaunchSequence(
-                        ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+                getRelaunchSequence(ON_TOP_POSITION_GAINED));
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(SingleTopActivity.class, ON_TOP_POSITION_LOST),
                 transition(SingleTopActivity.class, ON_TOP_POSITION_GAINED)),
                 "hostingDisplayRemoved");
@@ -815,7 +823,7 @@
                 .createDisplay();
 
         // Launch another activity on new secondary display.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         launchOptions.setLaunchDisplayId(newDisplay.mId);
         new Launcher(SingleTopActivity.class)
                 .setFlags(FLAG_ACTIVITY_NEW_TASK)
@@ -824,7 +832,7 @@
         waitAndAssertTopResumedActivity(getComponentName(SingleTopActivity.class),
                 newDisplay.mId, "Activity launched on secondary display must be focused");
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Tap on task center to switch the top activity.
         final Task callbackTrackingTask = mWmState
@@ -836,12 +844,12 @@
                 Arrays.asList(ON_TOP_POSITION_LOST), "tapOnFocusSwitch");
         waitAndAssertActivityTransitions(CallbackTrackingActivity.class,
                 Arrays.asList(ON_TOP_POSITION_GAINED), "tapOnFocusSwitch");
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(SingleTopActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED)),
-                getLifecycleLog(), "Top activity must be switched on tap");
+                getTransitionLog(), "Top activity must be switched on tap");
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Tap on task center to switch the top activity.
         final Task singleTopActivityTask = mWmState
@@ -854,10 +862,10 @@
                 Arrays.asList(ON_TOP_POSITION_LOST), "tapOnFocusSwitch");
         waitAndAssertActivityTransitions(SingleTopActivity.class,
                 Arrays.asList(ON_TOP_POSITION_GAINED), "tapOnFocusSwitch");
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
+        assertEntireSequence(Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(SingleTopActivity.class, ON_TOP_POSITION_GAINED)),
-                getLifecycleLog(), "Top activity must be switched on tap");
+                getTransitionLog(), "Top activity must be switched on tap");
     }
 
     @Test
@@ -883,7 +891,7 @@
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED));
 
         // Launch activity on default display, which will be slow to release top position.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final ActivityOptions launchOptions = ActivityOptions.makeBasic();
         launchOptions.setLaunchDisplayId(DEFAULT_DISPLAY);
         final Class<? extends Activity> defaultActivityClass = SlowActivity.class;
@@ -899,13 +907,13 @@
         // Wait and assert focus switch
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_LOST),
                 state(defaultActivityClass, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_LOST),
                 transition(defaultActivityClass, ON_TOP_POSITION_GAINED)),
                 "launchOnDifferentDisplay");
 
         // Tap on task center to switch the top activity.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final Task secondActivityTask = mWmState
                 .getTaskByActivity(getComponentName(SecondProcessCallbackTrackingActivity.class));
         tapOnTaskCenter(secondActivityTask);
@@ -913,12 +921,12 @@
         // Wait and assert top resumed position switch.
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED),
                 state(defaultActivityClass, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(defaultActivityClass, ON_TOP_POSITION_LOST),
                 transition(secondActivityClass, ON_TOP_POSITION_GAINED)),
                 "tapOnDifferentDisplay");
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         // Tap on task center to switch the top activity.
         final Task defaultActivityTask = mWmState
                 .getTaskByActivity(getComponentName(defaultActivityClass));
@@ -927,7 +935,7 @@
         // Wait and assert top resumed position switch.
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_LOST),
                 state(defaultActivityClass, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_LOST),
                 transition(defaultActivityClass, ON_TOP_POSITION_GAINED)),
                 "tapOnDifferentDisplay");
@@ -956,7 +964,7 @@
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED));
 
         // Launch activity on default display, which will be slow to release top position.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final ActivityOptions launchOptions = ActivityOptions.makeBasic();
         launchOptions.setLaunchDisplayId(DEFAULT_DISPLAY);
         final Class<? extends Activity> defaultActivityClass = SlowActivity.class;
@@ -972,31 +980,31 @@
         // Wait and assert focus switch.
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_LOST),
                 state(defaultActivityClass, ON_TOP_POSITION_GAINED));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_LOST),
                 transition(defaultActivityClass, ON_TOP_POSITION_GAINED)),
                 "launchOnDifferentDisplay");
 
         // Tap on secondary display to switch the top activity.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         tapOnDisplayCenter(newDisplay.mId);
 
         // Wait and assert top resumed position switch. Because of timeout top position gain
         // will appear before top position loss handling is finished.
         waitAndAssertActivityStates(state(secondActivityClass, ON_TOP_POSITION_GAINED),
                 state(defaultActivityClass, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(secondActivityClass, ON_TOP_POSITION_GAINED),
                 transition(defaultActivityClass, ON_TOP_POSITION_LOST)),
                 "tapOnDifferentDisplay");
 
         // Wait 5 seconds more to make sure that no new messages received after top resumed state
         // released by the slow activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         SystemClock.sleep(5000);
-        LifecycleVerifier.assertEmptySequence(defaultActivityClass, getLifecycleLog(),
+        assertEmptySequence(defaultActivityClass, getTransitionLog(),
                 "topStateLossTimeout");
-        LifecycleVerifier.assertEmptySequence(secondActivityClass, getLifecycleLog(),
+        assertEmptySequence(secondActivityClass, getTransitionLog(),
                 "topStateLossTimeout");
     }
 
@@ -1021,7 +1029,7 @@
                 .createDisplay();
 
         // Launch another activity on new secondary display.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final ActivityOptions launchOptions = ActivityOptions.makeBasic();
         launchOptions.setLaunchDisplayId(newDisplay.mId);
         new Launcher(SingleTopActivity.class)
@@ -1032,18 +1040,18 @@
                 newDisplay.mId, "Activity launched on secondary display must be focused");
         // An activity is launched on the new display, so the activity on default display should
         // lose the top state.
-        LifecycleVerifier.assertSequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertSequence(CallbackTrackingActivity.class, getTransitionLog(),
                 Arrays.asList(ON_TOP_POSITION_LOST), "launchFocusSwitch");
 
         // Finish the activity on the default display.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         callbackTrackingActivity.finish();
 
         // Verify that activity was actually destroyed.
         waitAndAssertActivityStates(state(CallbackTrackingActivity.class, ON_DESTROY));
         // Verify that the original focused display is not affected by the finished activity on
         // non-focused display.
-        LifecycleVerifier.assertEmptySequence(SingleTopActivity.class, getLifecycleLog(),
+        assertEmptySequence(SingleTopActivity.class, getTransitionLog(),
                 "destructionOnDifferentDisplay");
     }
 
@@ -1065,7 +1073,7 @@
                 .createDisplay();
 
         // Launch another activity on new secondary display.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         final ActivityOptions launchOptions = ActivityOptions.makeBasic();
         launchOptions.setLaunchDisplayId(newDisplay.mId);
         new Launcher(SingleTopActivity.class)
@@ -1082,14 +1090,14 @@
         waitAndAssertActivityStates(state(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED));
 
         // Finish the focused activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         callbackTrackingActivity.finish();
 
         // Verify that lifecycle of the activity on a different display did not change.
         // Top resumed state will be given to home activity on that display.
         waitAndAssertActivityStates(state(CallbackTrackingActivity.class, ON_DESTROY),
                 state(SecondActivity.class, ON_RESUME));
-        LifecycleVerifier.assertEmptySequence(SingleTopActivity.class, getLifecycleLog(),
+        assertEmptySequence(SingleTopActivity.class, getTransitionLog(),
                 "destructionOnDifferentDisplay");
     }
 
@@ -1101,7 +1109,7 @@
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
         // Clear the log before launching to Pip
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Launch Pip-capable activity and enter Pip immediately
         final Activity pipActivity = new Launcher(PipActivity.class)
@@ -1123,21 +1131,21 @@
                 , "wait PipMenuActivity lost top focus");
         waitAndAssertActivityStates(state(activity, ON_TOP_POSITION_GAINED));
 
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_PAUSE),
                 transition(CallbackTrackingActivity.class, ON_RESUME),
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED)), "startPIP");
 
         // Exit PiP
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         pipActivity.finish();
 
         waitAndAssertActivityStates(state(pipActivity, ON_DESTROY));
-        LifecycleVerifier.assertSequence(PipActivity.class, getLifecycleLog(),
+        assertSequence(PipActivity.class, getTransitionLog(),
                 Arrays.asList(
                         ON_STOP, ON_DESTROY), "finishPip");
-        LifecycleVerifier.assertEmptySequence(CallbackTrackingActivity.class, getLifecycleLog(),
+        assertEmptySequence(CallbackTrackingActivity.class, getTransitionLog(),
                 "finishPip");
     }
 
@@ -1149,7 +1157,7 @@
         final Activity activity = launchActivityAndWait(CallbackTrackingActivity.class);
 
         // Clear the log before launching to Pip
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Launch Pip-capable activity and enter Pip immediately
         final Activity pipActivity = new Launcher(PipActivity.class)
@@ -1165,20 +1173,20 @@
                 launchActivityAndWait(AlwaysFocusablePipActivity.class);
         waitAndAssertActivityStates(state(pipActivity, ON_STOP),
                 state(activity, ON_TOP_POSITION_LOST));
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_LOST),
                 transition(AlwaysFocusablePipActivity.class, ON_TOP_POSITION_GAINED)),
                 "launchAlwaysFocusablePip");
 
         // Finish always focusable activity - top position should go back to fullscreen activity
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         alwaysFocusableActivity.finish();
 
         waitAndAssertActivityStates(state(alwaysFocusableActivity, ON_DESTROY),
                 state(activity, ON_TOP_POSITION_GAINED), state(pipActivity, ON_PAUSE));
-        LifecycleVerifier.assertResumeToDestroySequence(AlwaysFocusablePipActivity.class,
-                getLifecycleLog());
-        LifecycleVerifier.assertOrder(getLifecycleLog(), Arrays.asList(
+        assertResumeToDestroySequence(AlwaysFocusablePipActivity.class,
+                getTransitionLog());
+        assertOrder(getTransitionLog(), Arrays.asList(
                 transition(AlwaysFocusablePipActivity.class, ON_TOP_POSITION_LOST),
                 transition(CallbackTrackingActivity.class, ON_TOP_POSITION_GAINED)),
                 "finishAlwaysFocusablePip");
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityStarterTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityStarterTests.java
index 95c9c4a..7888595 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityStarterTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityStarterTests.java
@@ -98,7 +98,7 @@
         // Navigate home
         launchHomeActivity();
         waitAndAssertActivityStates(state(FirstActivity.class, ON_STOP));
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
 
         // Start activity again with flags in question. Verify activity is resumed.
         // A new instance of activity will be created, and the old one destroyed.
diff --git a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityTests.java b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityTests.java
index 7f42519..5739935 100644
--- a/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityTests.java
+++ b/tests/framework/base/windowmanager/src/android/server/wm/lifecycle/ActivityTests.java
@@ -27,7 +27,12 @@
 import static android.server.wm.lifecycle.LifecycleConstants.ON_STOP;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_GAINED;
 import static android.server.wm.lifecycle.LifecycleConstants.ON_TOP_POSITION_LOST;
-import static android.server.wm.lifecycle.LifecycleVerifier.transition;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEmptySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertEntireSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchAndDestroySequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertLaunchSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.assertSequence;
+import static android.server.wm.lifecycle.TransitionVerifier.transition;
 
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
@@ -40,6 +45,7 @@
 import org.junit.Test;
 
 import java.util.Arrays;
+import java.util.Collections;
 
 /**
  * Tests for {@link Activity} class APIs.
@@ -56,10 +62,9 @@
         final Activity activity = launchActivityAndWait(FirstActivity.class);
         waitAndAssertActivityStates(state(activity, ON_RESUME));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         assertFalse("Launched and visible activity must be released", activity.releaseInstance());
-        LifecycleVerifier.assertEmptySequence(FirstActivity.class, getLifecycleLog(),
-                "tryReleaseInstance");
+        assertEmptySequence(FirstActivity.class, getTransitionLog(), "tryReleaseInstance");
     }
 
     @Test
@@ -71,18 +76,18 @@
         mWmState.waitForActivityState(firstActivity.getComponentName(), STATE_STOPPED);
 
         // Release the instance of the non-visible activity below.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         assertTrue("It must be possible to release an instance of an invisible activity",
                 firstActivity.releaseInstance());
         waitAndAssertActivityStates(state(firstActivity, ON_DESTROY));
-        LifecycleVerifier.assertEmptySequence(SecondActivity.class, getLifecycleLog(),
+        assertEmptySequence(SecondActivity.class, getTransitionLog(),
                 "releaseInstance");
 
         // Finish the top activity to navigate back to the first one and re-create it.
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondActivity.finish();
         waitAndAssertActivityStates(state(secondActivity, ON_DESTROY));
-        LifecycleVerifier.assertLaunchSequence(FirstActivity.class, getLifecycleLog());
+        assertLaunchSequence(FirstActivity.class, getTransitionLog());
     }
 
     /**
@@ -98,16 +103,16 @@
         waitAndAssertActivityStates(state(rootActivity, ON_STOP),
                 state(topActivity, ON_TOP_POSITION_GAINED));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         rootActivity.finishAndRemoveTask();
 
         waitAndAssertActivityStates(state(rootActivity, ON_DESTROY),
                 state(topActivity, ON_DESTROY));
         // Cannot guarantee exact sequence among top and bottom activities, so verifying
         // independently
-        LifecycleVerifier.assertSequence(rootActivityClass, getLifecycleLog(),
-                Arrays.asList(ON_DESTROY), "finishAndRemoveTask");
-        LifecycleVerifier.assertSequence(topActivityClass, getLifecycleLog(),
+        assertSequence(rootActivityClass, getTransitionLog(),
+                Collections.singletonList(ON_DESTROY), "finishAndRemoveTask");
+        assertSequence(topActivityClass, getTransitionLog(),
                 Arrays.asList(ON_TOP_POSITION_LOST, ON_PAUSE, ON_STOP, ON_DESTROY),
                 "finishAndRemoveTask");
     }
@@ -126,16 +131,16 @@
         waitAndAssertActivityStates(state(rootActivity, ON_PAUSE),
                 state(topActivity, ON_TOP_POSITION_GAINED));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         rootActivity.finishAndRemoveTask();
 
         waitAndAssertActivityStates(state(rootActivity, ON_DESTROY),
                 state(topActivity, ON_DESTROY));
         // Cannot guarantee exact sequence among top and bottom activities, so verifying
         // independently
-        LifecycleVerifier.assertSequence(rootActivityClass, getLifecycleLog(),
+        assertSequence(rootActivityClass, getTransitionLog(),
                 Arrays.asList(ON_STOP, ON_DESTROY), "finishAndRemoveTask");
-        LifecycleVerifier.assertSequence(topActivityClass, getLifecycleLog(),
+        assertSequence(topActivityClass, getTransitionLog(),
                 Arrays.asList(ON_TOP_POSITION_LOST, ON_PAUSE, ON_STOP, ON_DESTROY),
                 "finishAndRemoveTask");
     }
@@ -155,13 +160,12 @@
         waitAndAssertActivityStates(state(rootActivity, ON_STOP), state(midActivity, ON_STOP),
                 state(topActivity, ON_TOP_POSITION_GAINED));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         midActivity.finishAndRemoveTask();
 
         waitAndAssertActivityStates(state(midActivity, ON_DESTROY));
-        LifecycleVerifier.assertEntireSequence(Arrays.asList(
-                transition(midActivityClass, ON_DESTROY)), getLifecycleLog(),
-                "finishAndRemoveTask");
+        assertEntireSequence(Collections.singletonList(transition(midActivityClass, ON_DESTROY)),
+                getTransitionLog(), "finishAndRemoveTask");
     }
 
     /**
@@ -171,16 +175,15 @@
     @Test
     public void testFinishAfterTransition() throws Exception {
         final TransitionSourceActivity rootActivity =
-                (TransitionSourceActivity) launchActivityAndWait(TransitionSourceActivity.class);
+                launchActivityAndWait(TransitionSourceActivity.class);
         waitAndAssertActivityStates(state(rootActivity, ON_RESUME));
 
         // Launch activity with configured shared element transition. It will call
         // finishAfterTransition() on its own after transition completes.
-        rootActivity.runOnUiThread(() -> rootActivity.launchActivityWithTransition());
+        rootActivity.runOnUiThread(rootActivity::launchActivityWithTransition);
         waitAndAssertActivityStates(state(TransitionDestinationActivity.class, ON_DESTROY),
                 state(rootActivity, ON_RESUME));
-        LifecycleVerifier.assertLaunchAndDestroySequence(TransitionDestinationActivity.class,
-                getLifecycleLog());
+        assertLaunchAndDestroySequence(TransitionDestinationActivity.class, getTransitionLog());
     }
 
     /**
@@ -192,10 +195,10 @@
         final Activity activity = launchActivityAndWait(FirstActivity.class);
         waitAndAssertActivityStates(state(activity, ON_RESUME));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         activity.finishAfterTransition();
         waitAndAssertActivityStates(state(FirstActivity.class, ON_DESTROY));
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
+        assertSequence(FirstActivity.class, getTransitionLog(),
                 Arrays.asList(ON_PAUSE, ON_STOP, ON_DESTROY), "finishAfterTransition");
     }
 
@@ -209,10 +212,10 @@
         final Activity topActivity = launchActivityAndWait(SecondActivity.class);
         waitAndAssertActivityStates(state(topActivity, ON_RESUME), state(rootActivity, ON_STOP));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         topActivity.finishAfterTransition();
         waitAndAssertActivityStates(state(SecondActivity.class, ON_DESTROY));
-        LifecycleVerifier.assertSequence(SecondActivity.class, getLifecycleLog(),
+        assertSequence(SecondActivity.class, getTransitionLog(),
                 Arrays.asList(ON_PAUSE, ON_STOP, ON_DESTROY), "finishAfterTransition");
     }
 
@@ -228,12 +231,11 @@
         waitAndAssertActivityStates(state(thirdActivity, ON_RESUME), state(secondActivity, ON_STOP),
                 state(firstActivity, ON_STOP));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondActivity.finishAffinity();
         waitAndAssertActivityStates(state(FirstActivity.class, ON_DESTROY),
                 state(SecondActivity.class, ON_DESTROY));
-        LifecycleVerifier.assertEmptySequence(ThirdActivity.class, getLifecycleLog(),
-                "finishAffinityBelow");
+        assertEmptySequence(ThirdActivity.class, getTransitionLog(), "finishAffinityBelow");
     }
 
     /**
@@ -249,10 +251,10 @@
         waitAndAssertActivityStates(state(differentAffinityActivity, ON_RESUME),
                 state(firstActivity, ON_STOP));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         differentAffinityActivity.finishAffinity();
         waitAndAssertActivityStates(state(DifferentAffinityActivity.class, ON_DESTROY));
-        LifecycleVerifier.assertSequence(FirstActivity.class, getLifecycleLog(),
+        assertSequence(FirstActivity.class, getTransitionLog(),
                 Arrays.asList(ON_RESTART, ON_START, ON_RESUME), "finishAffinity");
     }
 
@@ -271,7 +273,7 @@
         waitAndAssertActivityStates(state(secondActivity, ON_RESUME),
                 state(firstActivity, ON_STOP));
 
-        getLifecycleLog().clear();
+        getTransitionLog().clear();
         secondActivity.finishAffinity();
         waitAndAssertActivityStates(state(SecondActivity.class, ON_DESTROY),
                 state(firstActivity, ON_RESUME));
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/ActivityManagerTestBase.java b/tests/framework/base/windowmanager/util/src/android/server/wm/ActivityManagerTestBase.java
index c0f376e..e3792ae 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/ActivityManagerTestBase.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/ActivityManagerTestBase.java
@@ -238,7 +238,7 @@
     private static final int UI_MODE_TYPE_MASK = 0x0f;
     private static final int UI_MODE_TYPE_VR_HEADSET = 0x07;
 
-    static final boolean ENABLE_SHELL_TRANSITIONS =
+    public static final boolean ENABLE_SHELL_TRANSITIONS =
             SystemProperties.getBoolean("persist.wm.debug.shell_transit", false);
 
     private static Boolean sHasHomeScreen = null;
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerState.java b/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerState.java
index 8585638..adf308d 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerState.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerState.java
@@ -1672,6 +1672,7 @@
         public boolean translucent;
         private WindowContainer mParent;
         private boolean mEnableRecentsScreenshot;
+        private int mLastDropInputMode;
 
         Activity(ActivityRecordProto proto, WindowContainer parent) {
             super(proto.windowToken.windowContainer);
@@ -1687,6 +1688,7 @@
             }
             translucent = proto.translucent;
             mEnableRecentsScreenshot = proto.enableRecentsScreenshot;
+            mLastDropInputMode = proto.lastDropInputMode;
             mParent = parent;
         }
 
@@ -1730,6 +1732,10 @@
             return mEnableRecentsScreenshot;
         }
 
+        public int getLastDropInputMode() {
+            return mLastDropInputMode;
+        }
+
         @Override
         public Rect getBounds() {
             if (mBounds == null) {
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerStateHelper.java b/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerStateHelper.java
index c6d96f4..e957e94 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerStateHelper.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/WindowManagerStateHelper.java
@@ -735,7 +735,8 @@
         final List<Task> tasks = getRootTasks();
         for (Task task : tasks) {
             task.forAllTasks((t) -> assertWithMessage("Empty task was found, id = " + t.mTaskId)
-                    .that(t.mTasks.size() + t.mActivities.size()).isGreaterThan(0));
+                    .that(t.mTasks.size() + t.mTaskFragments.size() + t.mActivities.size())
+                    .isGreaterThan(0));
             if (task.isLeafTask()) {
                 continue;
             }
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/CallbackTrackingActivity.java b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/CallbackTrackingActivity.java
index 8666b61..3316c81 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/CallbackTrackingActivity.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/CallbackTrackingActivity.java
@@ -36,32 +36,32 @@
     @Override
     protected void onActivityResult(int requestCode, int resultCode, Intent data) {
         super.onActivityResult(requestCode, resultCode, data);
-        mLifecycleLogClient.onActivityCallback(ON_ACTIVITY_RESULT);
+        mEventLogClient.onCallback(ON_ACTIVITY_RESULT);
     }
 
     @Override
     protected void onPostCreate(Bundle savedInstanceState) {
         super.onPostCreate(savedInstanceState);
-        mLifecycleLogClient.onActivityCallback(ON_POST_CREATE);
+        mEventLogClient.onCallback(ON_POST_CREATE);
     }
 
     @Override
     protected void onNewIntent(Intent intent) {
         super.onNewIntent(intent);
-        mLifecycleLogClient.onActivityCallback(ON_NEW_INTENT);
+        mEventLogClient.onCallback(ON_NEW_INTENT);
         setIntent(intent);
     }
 
     @Override
     public void onTopResumedActivityChanged(boolean isTopResumedActivity) {
         if (!getIntent().getBooleanExtra(EXTRA_SKIP_TOP_RESUMED_STATE, false)) {
-            mLifecycleLogClient.onActivityCallback(
+            mEventLogClient.onCallback(
                     isTopResumedActivity ? ON_TOP_POSITION_GAINED : ON_TOP_POSITION_LOST);
         }
     }
 
     @Override
     public void onMultiWindowModeChanged(boolean isInMultiWindowMode, Configuration newConfig) {
-        mLifecycleLogClient.onActivityCallback(ON_MULTI_WINDOW_MODE_CHANGED);
+        mEventLogClient.onCallback(ON_MULTI_WINDOW_MODE_CHANGED);
     }
 }
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleLog.java b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/EventLog.java
similarity index 76%
rename from tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleLog.java
rename to tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/EventLog.java
index 9b8dd43..a9e680b 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleLog.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/EventLog.java
@@ -33,17 +33,17 @@
 import java.util.List;
 
 /**
- * Used as a shared log storage of activity lifecycle transitions. Methods must be synchronized to
- * prevent concurrent modification of the log store.
+ * Used as a shared log storage of events such as activity lifecycle. Methods must be
+ * synchronized to prevent concurrent modification of the log store.
  */
-public class LifecycleLog extends ContentProvider {
+public class EventLog extends ContentProvider {
 
-    interface LifecycleTrackerCallback {
-        void onActivityLifecycleChanged();
+    interface EventTrackerCallback {
+        void onEventObserved();
     }
 
     /** Identifies the activity to which the event corresponds. */
-    private static final String EXTRA_KEY_ACTIVITY = "key_activity";
+    private static final String EXTRA_KEY_TAG = "key_activity";
     /** Puts a lifecycle or callback into the container. */
     private static final String METHOD_ADD_CALLBACK = "add_callback";
     /** Content provider URI for cross-process lifecycle transitions collecting. */
@@ -56,9 +56,9 @@
     private static final List<Pair<String, String>> sLog = new ArrayList<>();
 
     /**
-     * Lifecycle tracker interface that waits for correct states or sequences.
+     * Event tracker interface that waits for correct states or sequences.
      */
-    private static LifecycleTrackerCallback sLifecycleTracker;
+    private static EventTrackerCallback sEventTracker;
 
     /** Clear the entire transition log. */
     public void clear() {
@@ -67,8 +67,10 @@
         }
     }
 
-    public void setLifecycleTracker(LifecycleTrackerCallback lifecycleTracker) {
-        sLifecycleTracker = lifecycleTracker;
+    public void setEventTracker(EventTrackerCallback eventTracker) {
+        synchronized (sLog) {
+            sEventTracker = eventTracker;
+        }
     }
 
     /** Add activity callback to the log. */
@@ -78,8 +80,8 @@
         }
         log("Activity " + activityCanonicalName + " receiver callback " + callback);
         // Trigger check for valid state in the tracker
-        if (sLifecycleTracker != null) {
-            sLifecycleTracker.onActivityLifecycleChanged();
+        if (sEventTracker != null) {
+            sEventTracker.onEventObserved();
         }
     }
 
@@ -109,28 +111,28 @@
 
     // ContentProvider implementation for cross-process tracking
 
-    public static class LifecycleLogClient implements AutoCloseable {
+    public static class EventLogClient implements AutoCloseable {
         private static final String EMPTY_ARG = "";
         private final ContentProviderClient mClient;
-        private final String mOwner;
+        private final String mTag;
 
-        public LifecycleLogClient(ContentProviderClient client, String owner) {
+        public EventLogClient(ContentProviderClient client, String tag) {
             mClient = client;
-            mOwner = owner;
+            mTag = tag;
         }
 
-        public void onActivityCallback(String callback) {
-            onActivityCallback(callback, mOwner);
+        public void onCallback(String callback) {
+            onCallback(callback, mTag);
         }
 
-        public void onActivityCallback(String callback, Activity owner) {
-            onActivityCallback(callback, owner.getClass().getCanonicalName());
+        public void onCallback(String callback, Activity activity) {
+            onCallback(callback, activity.getClass().getCanonicalName());
         }
 
-        public void onActivityCallback(String callback, String owner) {
+        public void onCallback(String callback, String tag) {
             final Bundle extras = new Bundle();
             extras.putString(METHOD_ADD_CALLBACK, callback);
-            extras.putString(EXTRA_KEY_ACTIVITY, owner);
+            extras.putString(EXTRA_KEY_TAG, tag);
             try {
                 mClient.call(METHOD_ADD_CALLBACK, EMPTY_ARG, extras);
             } catch (RemoteException e) {
@@ -143,13 +145,13 @@
             mClient.close();
         }
 
-        public static LifecycleLogClient create(String owner, Context context) {
+        public static EventLogClient create(String owner, Context context) {
             final ContentProviderClient client = context.getContentResolver()
                     .acquireContentProviderClient(URI);
             if (client == null) {
                 throw new RuntimeException("Unable to acquire " + URI);
             }
-            return new LifecycleLogClient(client, owner);
+            return new EventLogClient(client, owner);
         }
     }
 
@@ -158,7 +160,7 @@
         if (!METHOD_ADD_CALLBACK.equals(method)) {
             throw new UnsupportedOperationException();
         }
-        onActivityCallback(extras.getString(EXTRA_KEY_ACTIVITY), extras.getString(method));
+        onActivityCallback(extras.getString(EXTRA_KEY_TAG), extras.getString(method));
         return null;
     }
 
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTracker.java b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/EventTracker.java
similarity index 86%
rename from tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTracker.java
rename to tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/EventTracker.java
index 31bb9ae..fae5657 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTracker.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/EventTracker.java
@@ -29,13 +29,13 @@
  * Gets notified about activity lifecycle updates and provides blocking mechanism to wait until
  * expected activity states are reached.
  */
-public class LifecycleTracker implements LifecycleLog.LifecycleTrackerCallback {
+public class EventTracker implements EventLog.EventTrackerCallback {
     private static final int TIMEOUT = 5 * 1000;
-    private LifecycleLog mLifecycleLog;
+    private EventLog mEventLog;
 
-    public LifecycleTracker(LifecycleLog lifecycleLog) {
-        mLifecycleLog = lifecycleLog;
-        mLifecycleLog.setLifecycleTracker(this);
+    public EventTracker(EventLog eventLog) {
+        mEventLog = eventLog;
+        mEventLog.setEventTracker(this);
     }
 
     void waitAndAssertActivityStates(
@@ -51,14 +51,14 @@
     void waitAndAssertActivityCurrentState(Class<? extends Activity> activityClass,
             String expectedState) {
         final boolean waitResult = waitForConditionWithTimeout(() -> {
-            List<String> activityLog = mLifecycleLog.getActivityLog(activityClass);
+            List<String> activityLog = mEventLog.getActivityLog(activityClass);
             String currentState = activityLog.get(activityLog.size() - 1);
             return expectedState.equals(currentState);
         });
 
         if (!waitResult) {
             fail("Lifecycle state did not settle with the expected current state of "
-                    + expectedState + " : " + mLifecycleLog.getActivityLog(activityClass));
+                    + expectedState + " : " + mEventLog.getActivityLog(activityClass));
         }
     }
 
@@ -71,11 +71,11 @@
     public void waitForActivityTransitions(Class<? extends Activity> activityClass,
             List<String> expectedTransitions) {
         waitForConditionWithTimeout(
-                () -> mLifecycleLog.getActivityLog(activityClass).equals(expectedTransitions));
+                () -> mEventLog.getActivityLog(activityClass).equals(expectedTransitions));
     }
 
     @Override
-    public synchronized void onActivityLifecycleChanged() {
+    public synchronized void onEventObserved() {
         notify();
     }
 
@@ -88,7 +88,7 @@
         for (Pair<Class<? extends Activity>, String> callbackPair : activityCallbacks) {
             final Class<? extends Activity> activityClass = callbackPair.first;
             final List<String> transitionList =
-                    mLifecycleLog.getActivityLog(activityClass);
+                    mEventLog.getActivityLog(activityClass);
             if (transitionList.isEmpty()
                     || !transitionList.get(transitionList.size() - 1).equals(callbackPair.second)) {
                 // The activity either hasn't got any state transitions yet or the current state is
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTrackingActivity.java b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTrackingActivity.java
index f3ce34f..5c64485 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTrackingActivity.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleTrackingActivity.java
@@ -40,14 +40,14 @@
 
 /** Base activity that only tracks fundamental activity lifecycle states. */
 public class LifecycleTrackingActivity extends Activity {
-    LifecycleLog.LifecycleLogClient mLifecycleLogClient;
+    EventLog.EventLogClient mEventLogClient;
 
     @Override
     protected void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
-        mLifecycleLogClient = LifecycleLog.LifecycleLogClient.create(
+        mEventLogClient = EventLog.EventLogClient.create(
                 this.getClass().getCanonicalName(), this);
-        mLifecycleLogClient.onActivityCallback(ON_CREATE);
+        mEventLogClient.onCallback(ON_CREATE);
 
         final Intent intent = getIntent();
         final Intent startOnCreate =
@@ -72,7 +72,7 @@
     @Override
     protected void onStart() {
         super.onStart();
-        mLifecycleLogClient.onActivityCallback(ON_START);
+        mEventLogClient.onCallback(ON_START);
 
         if (getIntent().getBooleanExtra(EXTRA_FINISH_IN_ON_START, false)) {
             finish();
@@ -82,7 +82,7 @@
     @Override
     protected void onResume() {
         super.onResume();
-        mLifecycleLogClient.onActivityCallback(ON_RESUME);
+        mEventLogClient.onCallback(ON_RESUME);
 
         final Intent intent = getIntent();
         if (intent.getBooleanExtra(EXTRA_FINISH_IN_ON_RESUME, false)) {
@@ -93,7 +93,7 @@
     @Override
     protected void onPause() {
         super.onPause();
-        mLifecycleLogClient.onActivityCallback(ON_PAUSE);
+        mEventLogClient.onCallback(ON_PAUSE);
 
         if (getIntent().getBooleanExtra(EXTRA_FINISH_IN_ON_PAUSE, false)) {
             finish();
@@ -103,7 +103,7 @@
     @Override
     protected void onStop() {
         super.onStop();
-        mLifecycleLogClient.onActivityCallback(ON_STOP);
+        mEventLogClient.onCallback(ON_STOP);
 
         if (getIntent().getBooleanExtra(EXTRA_FINISH_IN_ON_STOP, false)) {
             finish();
@@ -113,14 +113,14 @@
     @Override
     protected void onDestroy() {
         super.onDestroy();
-        mLifecycleLogClient.onActivityCallback(ON_DESTROY);
-        mLifecycleLogClient.close();
+        mEventLogClient.onCallback(ON_DESTROY);
+        mEventLogClient.close();
     }
 
     @Override
     protected void onRestart() {
         super.onRestart();
-        mLifecycleLogClient.onActivityCallback(ON_RESTART);
+        mEventLogClient.onCallback(ON_RESTART);
     }
 
     @Override
@@ -128,7 +128,7 @@
         super.onUserLeaveHint();
 
         if (getIntent().getBooleanExtra(EXTRA_ACTIVITY_ON_USER_LEAVE_HINT, false)) {
-            mLifecycleLogClient.onActivityCallback(ON_USER_LEAVE_HINT);
+            mEventLogClient.onCallback(ON_USER_LEAVE_HINT);
         }
     }
 }
diff --git a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleVerifier.java b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/TransitionVerifier.java
similarity index 85%
rename from tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleVerifier.java
rename to tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/TransitionVerifier.java
index b9a6b66..db6a243 100644
--- a/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/LifecycleVerifier.java
+++ b/tests/framework/base/windowmanager/util/src/android/server/wm/lifecycle/TransitionVerifier.java
@@ -41,17 +41,17 @@
 import java.util.Arrays;
 import java.util.List;
 
-/** Util class that verifies correct activity state transition sequences. */
-public class LifecycleVerifier {
+/** Util class that verifies correct event and state transition sequences. */
+public class TransitionVerifier {
 
     private static final Class CALLBACK_TRACKING_CLASS = CallbackTrackingActivity.class;
     private static final Class CONFIG_CHANGE_HANDLING_CLASS =
             LifecycleConfigChangeHandlingActivity.class;
 
     static void assertLaunchSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog, String... expectedSubsequentEvents) {
+            EventLog eventLog, String... expectedSubsequentEvents) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "launch");
 
@@ -81,7 +81,7 @@
     }
 
     static void assertLaunchSequence(Class<? extends Activity> launchingActivity,
-            Class<? extends Activity> existingActivity, LifecycleLog lifecycleLog,
+            Class<? extends Activity> existingActivity, EventLog eventLog,
             boolean launchingIsTranslucent) {
         final boolean includingCallbacks;
         if (CALLBACK_TRACKING_CLASS.isAssignableFrom(launchingActivity)
@@ -97,7 +97,7 @@
         }
 
 
-        final List<Pair<String, String>> observedTransitions = lifecycleLog.getLog();
+        final List<Pair<String, String>> observedTransitions = eventLog.getLog();
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(launchingActivity, "launch");
 
@@ -125,15 +125,15 @@
     }
 
     static void assertLaunchAndStopSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
-        assertLaunchAndStopSequence(activityClass, lifecycleLog,
+            EventLog eventLog) {
+        assertLaunchAndStopSequence(activityClass, eventLog,
                 false /* onTop */);
     }
 
     static void assertLaunchAndStopSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog, boolean onTop) {
+            EventLog eventLog, boolean onTop) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "launch and stop");
 
@@ -153,9 +153,9 @@
     }
 
     static void assertLaunchAndPauseSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "launch and pause");
 
@@ -165,9 +165,9 @@
     }
 
     static void assertRestartSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "restart");
 
@@ -177,9 +177,9 @@
     }
 
     static void assertRestartAndResumeSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "restart and pause");
 
@@ -194,22 +194,22 @@
      * state is resolved.
      */
     static void assertRestartAndResumeSubSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
 
         final List<Pair<String, String>> expectedTransitions =
                 Arrays.asList(transition(activityClass, ON_RESTART),
                         transition(activityClass, ON_START), transition(activityClass, ON_RESUME));
 
-        assertOrder(lifecycleLog, expectedTransitions, "restart and resume");
+        assertOrder(eventLog, expectedTransitions, "restart and resume");
     }
 
     static void assertRecreateAndResumeSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "recreateA  and pause");
 
@@ -219,9 +219,9 @@
     }
 
     static void assertLaunchAndDestroySequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "launch and destroy");
 
@@ -231,9 +231,9 @@
     }
 
     static void assertResumeToDestroySequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "launch and destroy");
 
@@ -250,9 +250,9 @@
     }
 
     static void assertResumeToStopSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "resumed to stopped");
         final boolean includeCallbacks = CALLBACK_TRACKING_CLASS.isAssignableFrom(activityClass);
@@ -268,9 +268,9 @@
     }
 
     static void assertStopToResumeSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, "stopped to resumed");
         final boolean includeCallbacks = CALLBACK_TRACKING_CLASS.isAssignableFrom(activityClass);
@@ -290,9 +290,9 @@
      * state is resolved.
      */
     static void assertStopToResumeSubSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog) {
+            EventLog eventLog) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final boolean includeCallbacks = CALLBACK_TRACKING_CLASS.isAssignableFrom(activityClass);
 
@@ -303,13 +303,13 @@
             expectedTransitions.add(transition(activityClass, ON_TOP_POSITION_GAINED));
         }
 
-        assertOrder(lifecycleLog, expectedTransitions, "stop and resume");
+        assertOrder(eventLog, expectedTransitions, "stop and resume");
     }
 
     static void assertRelaunchSequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog, String startState) {
+            EventLog eventLog, String startState) {
         final List<String> expectedTransitions = getRelaunchSequence(startState);
-        assertSequence(activityClass, lifecycleLog, expectedTransitions, "relaunch");
+        assertSequence(activityClass, eventLog, expectedTransitions, "relaunch");
     }
 
     static List<String> getRelaunchSequence(String startState) {
@@ -361,10 +361,10 @@
         return newTransitions;
     }
 
-    static void assertSequence(Class<? extends Activity> activityClass, LifecycleLog lifecycleLog,
+    static void assertSequence(Class<? extends Activity> activityClass, EventLog eventLog,
             List<String> expectedTransitions, String transition) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, transition);
 
@@ -378,13 +378,13 @@
      * Use this method when there is no need to verify the entire sequence, only that some
      * transitions happened after another.
      */
-    static void assertOrder(LifecycleLog lifecycleLog, Class<? extends Activity> activityClass,
+    static void assertOrder(EventLog eventLog, Class<? extends Activity> activityClass,
             List<String> expectedTransitionsOrder, String transition) {
         List<Pair<String, String>> expectedTransitions = new ArrayList<>();
         for (String callback : expectedTransitionsOrder) {
             expectedTransitions.add(transition(activityClass, callback));
         }
-        assertOrder(lifecycleLog, expectedTransitions, transition);
+        assertOrder(eventLog, expectedTransitions, transition);
     }
 
     /**
@@ -394,10 +394,10 @@
      * Use this method when there is no need to verify the entire sequence, only that some
      * transitions happened after another.
      */
-    public static void assertOrder(LifecycleLog lifecycleLog,
+    public static void assertOrder(EventLog eventLog,
             List<Pair<String, String>> expectedTransitionsOrder,
             String transition) {
-        String result = checkOrderAndReturnError(lifecycleLog, expectedTransitionsOrder,
+        String result = checkOrderAndReturnError(eventLog, expectedTransitionsOrder,
                 transition);
         if (result != null) {
             fail(result);
@@ -405,12 +405,12 @@
     }
 
     /**
-     * Same as {@link #assertOrder(LifecycleLog, List, String)}, but returns the String with error
+     * Same as {@link #assertOrder(EventLog, List, String)}, but returns the String with error
      * if it occurs. Otherwise returns {@code null}
      */
-    public static String checkOrderAndReturnError(LifecycleLog lifecycleLog,
+    public static String checkOrderAndReturnError(EventLog eventLog,
             List<Pair<String, String>> expectedTransitionsOrder, String transition) {
-        final List<Pair<String, String>> observedTransitions = lifecycleLog.getLog();
+        final List<Pair<String, String>> observedTransitions = eventLog.getLog();
         int nextObservedPosition = 0;
         for (Pair<String, String> expectedTransition
                 : expectedTransitionsOrder) {
@@ -429,42 +429,42 @@
     /**
      * Assert that a transition was observer, no particular order.
      */
-    public static void assertTransitionObserved(LifecycleLog lifecycleLog,
+    public static void assertTransitionObserved(EventLog eventLog,
             Pair<String, String> expectedTransition, String transition) {
         assertTrue("Transition " + expectedTransition + " must be observed during " + transition,
-                lifecycleLog.getLog().contains(expectedTransition));
+                eventLog.getLog().contains(expectedTransition));
     }
 
     /**
-     * Same as {@link #checkOrderAndReturnError(LifecycleLog, List, String)}, but returns
+     * Same as {@link #checkOrderAndReturnError(EventLog, List, String)}, but returns
      * {@code false} if the order does not match. Otherwise returns {@code true}
      */
-    public static boolean checkOrder(LifecycleLog lifecycleLog,
+    public static boolean checkOrder(EventLog eventLog,
             List<Pair<String, String>> expectedTransitionsOrder) {
-        String result = checkOrderAndReturnError(lifecycleLog, expectedTransitionsOrder, null);
+        String result = checkOrderAndReturnError(eventLog, expectedTransitionsOrder, null);
         return result == null;
     }
 
     /**
      * Assert that a transition was not observer, no particular order.
      */
-    static void assertTransitionNotObserved(LifecycleLog lifecycleLog,
+    static void assertTransitionNotObserved(EventLog eventLog,
             Pair<String, String> expectedTransition, String transition) {
         assertFalse("Transition " + expectedTransition + " must not be observed during "
-                        + transition, lifecycleLog.getLog().contains(expectedTransition));
+                        + transition, eventLog.getLog().contains(expectedTransition));
     }
 
     static void assertEmptySequence(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog, String transition) {
-        assertSequence(activityClass, lifecycleLog, new ArrayList<>(), transition);
+            EventLog eventLog, String transition) {
+        assertSequence(activityClass, eventLog, new ArrayList<>(), transition);
     }
 
     /** Assert that a lifecycle sequence matches one of the possible variants. */
     static void assertSequenceMatchesOneOf(Class<? extends Activity> activityClass,
-            LifecycleLog lifecycleLog, List<List<String>> expectedTransitions,
+            EventLog eventLog, List<List<String>> expectedTransitions,
             String transition) {
         final List<String> observedTransitions =
-                lifecycleLog.getActivityLog(activityClass);
+                eventLog.getActivityLog(activityClass);
         log("Observed sequence: " + observedTransitions);
         final String errorMessage = errorDuringTransition(activityClass, transition);
 
@@ -483,8 +483,8 @@
     /** Assert the entire sequence for all involved activities. */
     static void assertEntireSequence(
             List<Pair<String, String>> expectedTransitions,
-            LifecycleLog lifecycleLog, String message) {
-        final List<Pair<String, String>> observedTransitions = lifecycleLog.getLog();
+            EventLog eventLog, String message) {
+        final List<Pair<String, String>> observedTransitions = eventLog.getLog();
         assertEquals(message, expectedTransitions, observedTransitions);
     }
 
diff --git a/tests/mediapc/src/android/mediapc/cts/CodecInitializationLatencyTest.java b/tests/mediapc/src/android/mediapc/cts/CodecInitializationLatencyTest.java
new file mode 100644
index 0000000..e1260e7
--- /dev/null
+++ b/tests/mediapc/src/android/mediapc/cts/CodecInitializationLatencyTest.java
@@ -0,0 +1,662 @@
+/*
+ * Copyright (C) 2021 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 android.mediapc.cts;
+
+import static android.mediapc.cts.CodecTestBase.SELECT_ALL;
+import static android.mediapc.cts.CodecTestBase.SELECT_AUDIO;
+import static android.mediapc.cts.CodecTestBase.SELECT_HARDWARE;
+import static android.mediapc.cts.CodecTestBase.SELECT_VIDEO;
+import static android.mediapc.cts.CodecTestBase.getMimesOfAvailableCodecs;
+import static android.mediapc.cts.CodecTestBase.selectCodecs;
+import static android.mediapc.cts.CodecTestBase.selectHardwareCodecs;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assume.assumeFalse;
+import static org.junit.Assume.assumeTrue;
+
+import android.app.Instrumentation;
+import android.content.Context;
+import android.content.pm.PackageManager;
+import android.media.MediaCodec;
+import android.media.MediaCodecInfo;
+import android.media.MediaFormat;
+import android.media.MediaRecorder;
+import android.mediapc.cts.common.Utils;
+import android.os.Build;
+import android.util.Log;
+import android.util.Pair;
+import android.view.Surface;
+
+import androidx.test.filters.LargeTest;
+import androidx.test.platform.app.InstrumentationRegistry;
+import androidx.test.rule.ActivityTestRule;
+
+import com.android.compatibility.common.util.CddTest;
+import com.android.compatibility.common.util.DeviceReportLog;
+import com.android.compatibility.common.util.ResultType;
+import com.android.compatibility.common.util.ResultUnit;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.Parameterized;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * The following test class validates the codec initialization latency (time for codec create +
+ * configure) for the audio codecs and hardware video codecs available in the device, under the
+ * load condition (Transcode + MediaRecorder session Audio(Microphone) and 1080p Video(Camera)).
+ */
+@RunWith(Parameterized.class)
+public class CodecInitializationLatencyTest {
+    private static final String LOG_TAG = CodecInitializationLatencyTest.class.getSimpleName();
+    private static final boolean[] boolStates = {false, true};
+    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_R_MS = 50;
+    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_R_MS = 65;
+    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_S_MS = 40;
+    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_S_MS = 50;
+    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_T_MS = 30;
+    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_T_MS = 40;
+    private static final int MAX_AUDIODEC_INITIALIZATION_LATENCY_PC_T_MS = 30;
+    private static final int MAX_VIDEODEC_INITIALIZATION_LATENCY_PC_T_MS = 40;
+
+    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_MS;
+    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_MS;
+    private static final int MAX_AUDIODEC_INITIALIZATION_LATENCY_MS;
+    private static final int MAX_VIDEODEC_INITIALIZATION_LATENCY_MS;
+    private static final String AVC = MediaFormat.MIMETYPE_VIDEO_AVC;
+    private static final String HEVC = MediaFormat.MIMETYPE_VIDEO_HEVC;
+    private static final String AVC_TRANSCODE_FILE = "bbb_1280x720_3mbps_30fps_avc.mp4";
+    private static String AVC_DECODER_NAME;
+    private static String AVC_ENCODER_NAME;
+    private static final Map<String, String> mTestFiles = new HashMap<>();
+
+    static {
+        if (Utils.isRPerfClass()) {
+            MAX_AUDIOENC_INITIALIZATION_LATENCY_MS = MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_R_MS;
+            MAX_VIDEOENC_INITIALIZATION_LATENCY_MS = MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_R_MS;
+        } else if (Utils.isSPerfClass()) {
+            MAX_AUDIOENC_INITIALIZATION_LATENCY_MS = MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_S_MS;
+            MAX_VIDEOENC_INITIALIZATION_LATENCY_MS = MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_S_MS;
+        } else {
+            // Performance class Build.VERSION_CODES.TIRAMISU and beyond
+            MAX_AUDIOENC_INITIALIZATION_LATENCY_MS = MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_T_MS;
+            MAX_VIDEOENC_INITIALIZATION_LATENCY_MS = MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_T_MS;
+        }
+        if (Utils.isTPerfClass()) {
+            MAX_AUDIODEC_INITIALIZATION_LATENCY_MS = MAX_AUDIODEC_INITIALIZATION_LATENCY_PC_T_MS;
+            MAX_VIDEODEC_INITIALIZATION_LATENCY_MS = MAX_VIDEODEC_INITIALIZATION_LATENCY_PC_T_MS;
+        } else {
+            // no requirement below performance class Build.VERSION_CODES.TIRAMISU
+            MAX_AUDIODEC_INITIALIZATION_LATENCY_MS = Integer.MAX_VALUE;
+            MAX_VIDEODEC_INITIALIZATION_LATENCY_MS = Integer.MAX_VALUE;
+        }
+        // TODO(b/222006626): Add tests vectors for remaining media types
+        // Audio media types
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_AAC, "bbb_stereo_48kHz_128kbps_aac.mp4");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_AMR_NB, "bbb_mono_8kHz_12.2kbps_amrnb.3gp");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_AMR_WB, "bbb_1ch_16kHz_23kbps_amrwb.3gp");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_FLAC, "bbb_1ch_12kHz_lvl4_flac.mka");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_G711_ALAW, "bbb_2ch_8kHz_alaw.wav");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_G711_MLAW, "bbb_2ch_8kHz_mulaw.wav");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_MPEG, "bbb_1ch_8kHz_lame_cbr.mp3");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_MSGSM, "bbb_1ch_8kHz_gsm.wav");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_OPUS, "bbb_2ch_48kHz_opus.mka");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_RAW, "bbb_1ch_8kHz.wav");
+        mTestFiles.put(MediaFormat.MIMETYPE_AUDIO_VORBIS, "bbb_stereo_48kHz_128kbps_vorbis.ogg");
+
+        // Video media types
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_AV1, "bbb_1920x1080_4mbps_30fps_av1.mp4");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_AVC, "bbb_1920x1080_6mbps_30fps_avc.mp4");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_H263, "bbb_cif_768kbps_30fps_h263.mp4");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_HEVC, "bbb_1920x1080_4mbps_30fps_hevc.mp4");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_MPEG2, "bbb_1920x1080_mpeg2_main_high.mp4");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_MPEG4, "bbb_cif_768kbps_30fps_mpeg4.mkv");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_VP8, "bbb_1920x1080_6mbps_30fps_vp8.webm");
+        mTestFiles.put(MediaFormat.MIMETYPE_VIDEO_VP9, "bbb_1920x1080_4mbps_30fps_vp9.webm");
+    }
+
+    private final String mMime;
+    private final String mCodecName;
+
+    private LoadStatus mTranscodeLoadStatus = null;
+    private Thread mTranscodeLoadThread = null;
+    private MediaRecorder mMediaRecorderLoad = null;
+    private File mTempRecordedFile = null;
+    private Surface mSurface = null;
+    private Exception mException = null;
+
+    @Before
+    public void setUp() throws Exception {
+        Utils.assumeDeviceMeetsPerformanceClassPreconditions();
+
+        ArrayList<String> listOfAvcHwDecoders = selectHardwareCodecs(AVC, null, null, false);
+        assumeFalse("Test requires h/w avc decoder", listOfAvcHwDecoders.isEmpty());
+        AVC_DECODER_NAME = listOfAvcHwDecoders.get(0);
+
+        ArrayList<String> listOfAvcHwEncoders = selectHardwareCodecs(AVC, null, null, true);
+        assumeFalse("Test requires h/w avc encoder", listOfAvcHwEncoders.isEmpty());
+        AVC_ENCODER_NAME = listOfAvcHwEncoders.get(0);
+
+        Instrumentation instrumentation = InstrumentationRegistry.getInstrumentation();
+        Context context = instrumentation.getTargetContext();
+        PackageManager packageManager = context.getPackageManager();
+        assertNotNull(packageManager.getSystemAvailableFeatures());
+        assumeTrue("The device doesn't have a camera",
+                packageManager.hasSystemFeature(PackageManager.FEATURE_CAMERA_ANY));
+        assumeTrue("The device doesn't have a microphone",
+                packageManager.hasSystemFeature(PackageManager.FEATURE_MICROPHONE));
+        createSurface();
+        startLoad();
+    }
+
+    @After
+    public void tearDown() throws Exception {
+        stopLoad();
+        releaseSurface();
+    }
+
+    public CodecInitializationLatencyTest(String mimeType, String codecName) {
+        mMime = mimeType;
+        mCodecName = codecName;
+    }
+
+    @Rule
+    public ActivityTestRule<TestActivity> mActivityRule =
+            new ActivityTestRule<>(TestActivity.class);
+
+    /**
+     * Returns the list of parameters with mimetype and their codecs(for audio - all codecs,
+     * video - hardware codecs).
+     *
+     * @return Collection of Parameters {0}_{1} -- MIME_CodecName
+     */
+    @Parameterized.Parameters(name = "{index}({0}_{1})")
+    public static Collection<Object[]> inputParams() {
+        // Prepares the params list with the required Hardware video codecs and all available
+        // audio codecs present in the device.
+        final List<Object[]> argsList = new ArrayList<>();
+        Set<String> mimeSet = getMimesOfAvailableCodecs(SELECT_VIDEO, SELECT_HARDWARE);
+        mimeSet.addAll(getMimesOfAvailableCodecs(SELECT_AUDIO, SELECT_ALL));
+        for (String mime : mimeSet) {
+            ArrayList<String> listOfCodecs;
+            if (mime.startsWith("audio/")) {
+                listOfCodecs = selectCodecs(mime, null, null, true);
+                listOfCodecs.addAll(selectCodecs(mime, null, null, false));
+            } else {
+                listOfCodecs = selectHardwareCodecs(mime, null, null, true);
+                listOfCodecs.addAll(selectHardwareCodecs(mime, null, null, false));
+            }
+            for (String codec : listOfCodecs) {
+                argsList.add(new Object[]{mime, codec});
+            }
+        }
+        return argsList;
+    }
+
+    private MediaRecorder createMediaRecorderLoad(Surface surface) throws Exception {
+        MediaRecorder mediaRecorder = new MediaRecorder(InstrumentationRegistry.getInstrumentation()
+                .getContext());
+        mediaRecorder.setAudioSource(MediaRecorder.AudioSource.MIC);
+        mediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA);
+        mediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.DEFAULT);
+        mediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AAC);
+        mediaRecorder.setVideoEncoder(mMime.equalsIgnoreCase(HEVC) ?
+                MediaRecorder.VideoEncoder.HEVC : MediaRecorder.VideoEncoder.H264);
+        mediaRecorder.setOutputFile(mTempRecordedFile);
+        mediaRecorder.setVideoSize(1920, 1080);
+        mediaRecorder.setOrientationHint(0);
+        mediaRecorder.setPreviewDisplay(surface);
+        mediaRecorder.prepare();
+        return mediaRecorder;
+    }
+
+    private void startLoad() throws Exception {
+        // TODO: b/183671436
+        // Create Transcode load (AVC Decoder(720p) + AVC Encoder(720p))
+        mTranscodeLoadStatus = new LoadStatus();
+        mTranscodeLoadThread = new Thread(() -> {
+            try {
+                TranscodeLoad transcodeLoad = new TranscodeLoad(AVC, AVC_TRANSCODE_FILE,
+                        AVC_DECODER_NAME, AVC_ENCODER_NAME, mTranscodeLoadStatus);
+                transcodeLoad.doTranscode();
+            } catch (Exception e) {
+                mException = e;
+            }
+        });
+        // Create MediaRecorder Session - Audio (Microphone) + 1080p Video (Camera)
+        // Create a temp file to dump the MediaRecorder output. Later it will be deleted.
+        mTempRecordedFile = new File(WorkDir.getMediaDirString() + "tempOut.mp4");
+        mTempRecordedFile.createNewFile();
+        mMediaRecorderLoad = createMediaRecorderLoad(mSurface);
+        // Start the Loads
+        mTranscodeLoadThread.start();
+        mMediaRecorderLoad.start();
+    }
+
+    private void stopLoad() throws Exception {
+        if (mTranscodeLoadStatus != null) {
+            mTranscodeLoadStatus.setLoadFinished();
+            mTranscodeLoadStatus = null;
+        }
+        if (mTranscodeLoadThread != null) {
+            mTranscodeLoadThread.join();
+            mTranscodeLoadThread = null;
+        }
+        if (mMediaRecorderLoad != null) {
+            // Note that a RuntimeException is intentionally thrown to the application, if no valid
+            // audio/video data has been received when stop() is called. This happens if stop() is
+            // called immediately after start(). So sleep for 1000ms inorder to make sure some
+            // data has been received between start() and stop().
+            Thread.sleep(1000);
+            mMediaRecorderLoad.stop();
+            mMediaRecorderLoad.release();
+            mMediaRecorderLoad = null;
+            if (mTempRecordedFile != null && mTempRecordedFile.exists()) {
+                mTempRecordedFile.delete();
+                mTempRecordedFile = null;
+            }
+        }
+        if (mException != null) throw mException;
+    }
+
+    private void createSurface() throws InterruptedException {
+        mActivityRule.getActivity().waitTillSurfaceIsCreated();
+        mSurface = mActivityRule.getActivity().getSurface();
+        assertNotNull("Surface created is null.", mSurface);
+        assertTrue("Surface created is invalid.", mSurface.isValid());
+        mActivityRule.getActivity().setScreenParams(1920, 1080, true);
+    }
+
+    private void releaseSurface() {
+        if (mSurface != null) {
+            mSurface.release();
+            mSurface = null;
+        }
+    }
+
+    /**
+     * This test validates the initialization latency (time for codec create + configure) for
+     * audio and hw video codecs.
+     *
+     * <p>Measurements are taken 5 * 2(sync/async) * [1 or 2]
+     * (surface/non-surface for video) times. This also logs the stats: min, max, avg of the codec
+     * initialization latencies.
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    @CddTest(requirements = {
+        "2.2.7.1/5.1/H-1-7",
+        "2.2.7.1/5.1/H-1-8",})
+    public void testInitializationLatency() throws Exception {
+        MediaCodec codec = MediaCodec.createByCodecName(mCodecName);
+        boolean isEncoder = codec.getCodecInfo().isEncoder();
+        boolean isAudio = mMime.startsWith("audio/");
+        codec.release();
+        final int NUM_MEASUREMENTS = 5;
+        // Test gathers initialization latency for a number of iterations and
+        // percentile is a variable used to control how many of these iterations
+        // need to meet the pass criteria. For eg. if NUM_MEASUREMENTS = 5, audio, sync and Async
+        // modes which is a total of 10 iterations, this translates to index 7.
+        final int percentile = 70;
+        long expectedMaxCodecInitializationLatencyMs = isAudio ?
+                isEncoder ? MAX_AUDIOENC_INITIALIZATION_LATENCY_MS :
+                        MAX_AUDIODEC_INITIALIZATION_LATENCY_MS :
+                isEncoder ? MAX_VIDEOENC_INITIALIZATION_LATENCY_MS :
+                        MAX_VIDEODEC_INITIALIZATION_LATENCY_MS;
+        long sumOfCodecInitializationLatencyMs = 0;
+        int count = 0;
+        int numOfActualMeasurements =
+                NUM_MEASUREMENTS * boolStates.length * ((!isEncoder && !isAudio) ? 2 : 1);
+        long[] codecInitializationLatencyMs = new long[numOfActualMeasurements];
+        for (int i = 0; i < NUM_MEASUREMENTS; i++) {
+            for (boolean isAsync : boolStates) {
+                long latency;
+                if (isEncoder) {
+                    EncoderInitializationLatency encoderInitializationLatency =
+                            new EncoderInitializationLatency(mMime, mCodecName, isAsync);
+                    latency = encoderInitializationLatency.calculateInitLatency();
+                    codecInitializationLatencyMs[count] = latency;
+                    sumOfCodecInitializationLatencyMs += latency;
+                    count++;
+                } else {
+                    String testFile = mTestFiles.get(mMime);
+                    assumeTrue("Add test vector for media type: " + mMime, testFile != null);
+                    if (isAudio) {
+                        DecoderInitializationLatency decoderInitializationLatency =
+                                new DecoderInitializationLatency(mMime, mCodecName, testFile,
+                                        isAsync, false);
+                        latency = decoderInitializationLatency.calculateInitLatency();
+                        codecInitializationLatencyMs[count] = latency;
+                        sumOfCodecInitializationLatencyMs += latency;
+                        count++;
+                    } else {
+                        for (boolean surfaceMode : boolStates) {
+                            DecoderInitializationLatency decoderInitializationLatency =
+                                    new DecoderInitializationLatency(mMime, mCodecName,
+                                            testFile,
+                                            isAsync, surfaceMode);
+                            latency = decoderInitializationLatency.calculateInitLatency();
+                            codecInitializationLatencyMs[count] = latency;
+                            sumOfCodecInitializationLatencyMs += latency;
+                            count++;
+                        }
+                    }
+                }
+            }
+        }
+        Arrays.sort(codecInitializationLatencyMs);
+
+        String statsLog = String.format("CodecInitialization latency for mime: %s, " +
+                "Codec: %s, in Ms :: ", mMime, mCodecName);
+        Log.i(LOG_TAG, "Min " + statsLog + codecInitializationLatencyMs[0]);
+        Log.i(LOG_TAG, "Max " + statsLog + codecInitializationLatencyMs[count - 1]);
+        Log.i(LOG_TAG, "Avg " + statsLog + (sumOfCodecInitializationLatencyMs / count));
+        long initializationLatency = codecInitializationLatencyMs[percentile * count / 100];
+        if (Utils.isPerfClass()) {
+            String errorLog = String.format(
+                    "CodecInitialization latency for mime: %s, Codec: %s is not as expected."
+                            + "act/exp in Ms :: %d/%d", mMime, mCodecName, initializationLatency,
+                    expectedMaxCodecInitializationLatencyMs);
+            assertTrue(errorLog, initializationLatency <= expectedMaxCodecInitializationLatencyMs);
+        } else {
+            int pc;
+            if (mMime.startsWith("audio/")) {
+                pc = initializationLatency < MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_T_MS ?
+                        Build.VERSION_CODES.TIRAMISU :
+                        initializationLatency < MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_S_MS ?
+                                Build.VERSION_CODES.S : initializationLatency <
+                                MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_R_MS ?
+                                Build.VERSION_CODES.R : 0;
+            } else {
+                pc = initializationLatency < MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_T_MS ?
+                        Build.VERSION_CODES.TIRAMISU :
+                        initializationLatency < MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_S_MS ?
+                                Build.VERSION_CODES.S : initializationLatency <
+                                MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_R_MS ?
+                                Build.VERSION_CODES.R : 0;
+            }
+            DeviceReportLog log = new DeviceReportLog("MediaPerformanceClassLogs",
+                    "InitializationLatency_" + mCodecName);
+            log.addValue("codec", mCodecName, ResultType.NEUTRAL, ResultUnit.NONE);
+            log.addValue("initialization_latency", initializationLatency, ResultType.LOWER_BETTER,
+                    ResultUnit.NONE);
+            log.setSummary("CDD 2.2.7.1/5.1/H-1-7,H-1-8 performance_class", pc, ResultType.NEUTRAL,
+                    ResultUnit.NONE);
+            log.submit(InstrumentationRegistry.getInstrumentation());
+        }
+    }
+
+    /**
+     * The following class calculates the encoder initialization latency (time for codec create +
+     * configure).
+     *
+     * <p>And also logs the time taken by the encoder for:
+     * (create + configure + start),
+     * (create + configure + start + first frame to enqueue),
+     * (create + configure + start + first frame to dequeue).
+     */
+    static class EncoderInitializationLatency extends CodecEncoderTestBase {
+        private static final String LOG_TAG = EncoderInitializationLatency.class.getSimpleName();
+
+        private final String mEncoderName;
+        private final boolean mIsAsync;
+
+        EncoderInitializationLatency(String mime, String encoderName, boolean isAsync) {
+            super(mime);
+            mEncoderName = encoderName;
+            mIsAsync = isAsync;
+            mSampleRate = 8000;
+            mFrameRate = 60;
+        }
+
+        private MediaFormat setUpFormat() throws IOException {
+            MediaFormat format = new MediaFormat();
+            format.setString(MediaFormat.KEY_MIME, mMime);
+            if (mIsAudio) {
+                if (mMime.equals(MediaFormat.MIMETYPE_AUDIO_FLAC)) {
+                    format.setInteger(MediaFormat.KEY_FLAC_COMPRESSION_LEVEL, 10000);
+                } else {
+                    format.setInteger(MediaFormat.KEY_BIT_RATE, 128000);
+                }
+                format.setInteger(MediaFormat.KEY_SAMPLE_RATE, mSampleRate);
+                format.setInteger(MediaFormat.KEY_CHANNEL_COUNT, 1);
+            } else {
+                MediaCodec codec = MediaCodec.createByCodecName(mEncoderName);
+                MediaCodecInfo.CodecCapabilities codecCapabilities =
+                        codec.getCodecInfo().getCapabilitiesForType(mMime);
+                if (codecCapabilities.getVideoCapabilities().isSizeSupported(1920, 1080)) {
+                    format.setInteger(MediaFormat.KEY_WIDTH, 1920);
+                    format.setInteger(MediaFormat.KEY_HEIGHT, 1080);
+                    format.setInteger(MediaFormat.KEY_BIT_RATE, 8000000);
+                } else if (codecCapabilities.getVideoCapabilities().isSizeSupported(1280, 720)) {
+                    format.setInteger(MediaFormat.KEY_WIDTH, 1280);
+                    format.setInteger(MediaFormat.KEY_HEIGHT, 720);
+                    format.setInteger(MediaFormat.KEY_BIT_RATE, 5000000);
+                } else if (codecCapabilities.getVideoCapabilities().isSizeSupported(640, 480)) {
+                    format.setInteger(MediaFormat.KEY_WIDTH, 640);
+                    format.setInteger(MediaFormat.KEY_HEIGHT, 480);
+                    format.setInteger(MediaFormat.KEY_BIT_RATE, 2000000);
+                } else if (codecCapabilities.getVideoCapabilities().isSizeSupported(352, 288)) {
+                    format.setInteger(MediaFormat.KEY_WIDTH, 352);
+                    format.setInteger(MediaFormat.KEY_HEIGHT, 288);
+                    format.setInteger(MediaFormat.KEY_BIT_RATE, 512000);
+                } else {
+                    format.setInteger(MediaFormat.KEY_WIDTH, 176);
+                    format.setInteger(MediaFormat.KEY_HEIGHT, 144);
+                    format.setInteger(MediaFormat.KEY_BIT_RATE, 128000);
+                }
+                codec.release();
+                format.setInteger(MediaFormat.KEY_FRAME_RATE, mFrameRate);
+                format.setFloat(MediaFormat.KEY_I_FRAME_INTERVAL, 1.0f);
+                format.setInteger(MediaFormat.KEY_COLOR_FORMAT,
+                        MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible);
+            }
+            return format;
+        }
+
+        public long calculateInitLatency() throws Exception {
+            MediaFormat format = setUpFormat();
+            if (mIsAudio) {
+                mSampleRate = format.getInteger(MediaFormat.KEY_SAMPLE_RATE);
+                mChannels = format.getInteger(MediaFormat.KEY_CHANNEL_COUNT);
+            } else {
+                mWidth = format.getInteger(MediaFormat.KEY_WIDTH);
+                mHeight = format.getInteger(MediaFormat.KEY_HEIGHT);
+            }
+            setUpSource(mInputFile);
+            MediaCodec.BufferInfo outInfo = new MediaCodec.BufferInfo();
+            long enqueueTimeStamp = 0;
+            long dequeueTimeStamp = 0;
+            long baseTimeStamp = System.nanoTime();
+            mCodec = MediaCodec.createByCodecName(mEncoderName);
+            resetContext(mIsAsync, false);
+            mAsyncHandle.setCallBack(mCodec, mIsAsync);
+            mCodec.configure(format, null, MediaCodec.CONFIGURE_FLAG_ENCODE, null);
+            long configureTimeStamp = System.nanoTime();
+            mCodec.start();
+            long startTimeStamp = System.nanoTime();
+            if (mIsAsync) {
+                // We will keep on feeding the input to encoder until we see the first dequeued
+                // frame.
+                while (!mAsyncHandle.hasSeenError() && !mSawInputEOS) {
+                    Pair<Integer, MediaCodec.BufferInfo> element = mAsyncHandle.getWork();
+                    if (element != null) {
+                        int bufferID = element.first;
+                        MediaCodec.BufferInfo info = element.second;
+                        if (info != null) {
+                            dequeueTimeStamp = System.nanoTime();
+                            dequeueOutput(bufferID, info);
+                            break;
+                        } else {
+                            if (enqueueTimeStamp == 0) {
+                                enqueueTimeStamp = System.nanoTime();
+                            }
+                            enqueueInput(bufferID);
+                        }
+                    }
+                }
+            } else {
+                while (!mSawOutputEOS) {
+                    if (!mSawInputEOS) {
+                        int inputBufferId = mCodec.dequeueInputBuffer(Q_DEQ_TIMEOUT_US);
+                        if (inputBufferId > 0) {
+                            if (enqueueTimeStamp == 0) {
+                                enqueueTimeStamp = System.nanoTime();
+                            }
+                            enqueueInput(inputBufferId);
+                        }
+                    }
+                    int outputBufferId = mCodec.dequeueOutputBuffer(outInfo, Q_DEQ_TIMEOUT_US);
+                    if (outputBufferId >= 0) {
+                        dequeueTimeStamp = System.nanoTime();
+                        dequeueOutput(outputBufferId, outInfo);
+                        break;
+                    }
+                }
+            }
+            queueEOS();
+            waitForAllOutputs();
+            mCodec.stop();
+            mCodec.release();
+            Log.d(LOG_TAG, "Encode Mime: " + mMime + " Encoder: " + mEncoderName +
+                    " Time for (create + configure) in ns: " +
+                    (configureTimeStamp - baseTimeStamp));
+            Log.d(LOG_TAG, "Encode Mime: " + mMime + " Encoder: " + mEncoderName +
+                    " Time for (create + configure + start) in ns: " +
+                    (startTimeStamp - baseTimeStamp));
+            Log.d(LOG_TAG, "Encode Mime: " + mMime + " Encoder: " + mEncoderName +
+                    " Time for (create + configure + start + first frame to enqueue) in ns: " +
+                    (enqueueTimeStamp - baseTimeStamp));
+            Log.d(LOG_TAG, "Encode Mime: " + mMime + " Encoder: " + mEncoderName +
+                    " Time for (create + configure + start + first frame to dequeue) in ns: " +
+                    (dequeueTimeStamp - baseTimeStamp));
+            long timeToConfigureMs = (configureTimeStamp - baseTimeStamp) / 1000000;
+            return timeToConfigureMs;
+        }
+    }
+
+    /**
+     * The following class calculates the decoder initialization latency (time for codec create +
+     * configure).
+     * And also logs the time taken by the decoder for:
+     * (create + configure + start),
+     * (create + configure + start + first frame to enqueue),
+     * (create + configure + start + first frame to dequeue).
+     */
+    static class DecoderInitializationLatency extends CodecDecoderTestBase {
+        private static final String LOG_TAG = DecoderInitializationLatency.class.getSimpleName();
+
+        private final String mDecoderName;
+        private final boolean mIsAsync;
+
+        DecoderInitializationLatency(String mediaType, String decoderName, String testFile,
+                boolean isAsync, boolean surfaceMode) {
+            super(mediaType, testFile);
+            mDecoderName = decoderName;
+            mIsAsync = isAsync;
+            mSurface = mIsAudio ? null :
+                    surfaceMode ? MediaCodec.createPersistentInputSurface() : null;
+        }
+
+        public long calculateInitLatency() throws Exception {
+            MediaCodec.BufferInfo outInfo = new MediaCodec.BufferInfo();
+            MediaFormat format = setUpSource(mTestFile);
+            long enqueueTimeStamp = 0;
+            long dequeueTimeStamp = 0;
+            long baseTimeStamp = System.nanoTime();
+            mCodec = MediaCodec.createByCodecName(mDecoderName);
+            resetContext(mIsAsync, false);
+            mAsyncHandle.setCallBack(mCodec, mIsAsync);
+            mCodec.configure(format, mSurface, 0, null);
+            long configureTimeStamp = System.nanoTime();
+            mCodec.start();
+            long startTimeStamp = System.nanoTime();
+            if (mIsAsync) {
+                // We will keep on feeding the input to decoder until we see the first dequeued
+                // frame.
+                while (!mAsyncHandle.hasSeenError() && !mSawInputEOS) {
+                    Pair<Integer, MediaCodec.BufferInfo> element = mAsyncHandle.getWork();
+                    if (element != null) {
+                        int bufferID = element.first;
+                        MediaCodec.BufferInfo info = element.second;
+                        if (info != null) {
+                            dequeueTimeStamp = System.nanoTime();
+                            dequeueOutput(bufferID, info);
+                            break;
+                        } else {
+                            if (enqueueTimeStamp == 0) {
+                                enqueueTimeStamp = System.nanoTime();
+                            }
+                            enqueueInput(bufferID);
+                        }
+                    }
+                }
+            } else {
+                while (!mSawOutputEOS) {
+                    if (!mSawInputEOS) {
+                        int inputBufferId = mCodec.dequeueInputBuffer(Q_DEQ_TIMEOUT_US);
+                        if (inputBufferId >= 0) {
+                            if (enqueueTimeStamp == 0) {
+                                enqueueTimeStamp = System.nanoTime();
+                            }
+                            enqueueInput(inputBufferId);
+                        }
+                    }
+                    int outputBufferId = mCodec.dequeueOutputBuffer(outInfo, Q_DEQ_TIMEOUT_US);
+                    if (outputBufferId >= 0) {
+                        dequeueTimeStamp = System.nanoTime();
+                        dequeueOutput(outputBufferId, outInfo);
+                        break;
+                    }
+                }
+            }
+            queueEOS();
+            waitForAllOutputs();
+            mCodec.stop();
+            mCodec.release();
+            if (mSurface != null) {
+                mSurface.release();
+            }
+            Log.d(LOG_TAG, "Decode Mime: " + mMime + " Decoder: " + mDecoderName +
+                    " Time for (create + configure) in ns: " +
+                    (configureTimeStamp - baseTimeStamp));
+            Log.d(LOG_TAG, "Decode Mime: " + mMime + " Decoder: " + mDecoderName +
+                    " Time for (create + configure + start) in ns: " +
+                    (startTimeStamp - baseTimeStamp));
+            Log.d(LOG_TAG, "Decode Mime: " + mMime + " Decoder: " + mDecoderName +
+                    " Time for (create + configure + start + first frame to enqueue) in ns: " +
+                    (enqueueTimeStamp - baseTimeStamp));
+            Log.d(LOG_TAG, "Decode Mime: " + mMime + " Decoder: " + mDecoderName +
+                    " Time for (create + configure + start + first frame to dequeue) in ns: " +
+                    (dequeueTimeStamp - baseTimeStamp));
+            long timeToConfigureMs = (configureTimeStamp - baseTimeStamp) / 1000000;
+            return timeToConfigureMs;
+        }
+    }
+}
diff --git a/tests/mediapc/src/android/mediapc/cts/CodecTestBase.java b/tests/mediapc/src/android/mediapc/cts/CodecTestBase.java
index c6a0c60..c75fffb 100644
--- a/tests/mediapc/src/android/mediapc/cts/CodecTestBase.java
+++ b/tests/mediapc/src/android/mediapc/cts/CodecTestBase.java
@@ -42,7 +42,9 @@
 import java.io.IOException;
 import java.nio.ByteBuffer;
 import java.util.ArrayList;
+import java.util.HashSet;
 import java.util.LinkedList;
+import java.util.Set;
 import java.util.concurrent.Callable;
 import java.util.concurrent.locks.Condition;
 import java.util.concurrent.locks.Lock;
@@ -178,6 +180,8 @@
     static final int SELECT_ALL = 0; // Select all codecs
     static final int SELECT_HARDWARE = 1; // Select Hardware codecs only
     static final int SELECT_SOFTWARE = 2; // Select Software codecs only
+    static final int SELECT_AUDIO = 3; // Select Audio codecs only
+    static final int SELECT_VIDEO = 4; // Select Video codecs only
     // Maintain Timeouts in sync with their counterpart in NativeMediaCommon.h
     static final long Q_DEQ_TIMEOUT_US = 5000; // block at most 5ms while looking for io buffers
     static final int RETRY_LIMIT = 100; // max poll counter before test aborts and returns error
@@ -339,12 +343,23 @@
 
     static ArrayList<String> selectHardwareCodecs(String mime, ArrayList<MediaFormat> formats,
             String[] features, boolean isEncoder) {
-        return selectCodecs(mime, formats, features, isEncoder, SELECT_HARDWARE);
+        return selectHardwareCodecs(mime, formats, features, isEncoder, false);
+    }
+
+    static ArrayList<String> selectHardwareCodecs(String mime, ArrayList<MediaFormat> formats,
+            String[] features, boolean isEncoder, boolean allCodecs) {
+        return selectCodecs(mime, formats, features, isEncoder, SELECT_HARDWARE, allCodecs);
     }
 
     static ArrayList<String> selectCodecs(String mime, ArrayList<MediaFormat> formats,
             String[] features, boolean isEncoder, int selectCodecOption) {
-        MediaCodecList codecList = new MediaCodecList(MediaCodecList.REGULAR_CODECS);
+        return selectCodecs(mime, formats, features, isEncoder, selectCodecOption, false);
+    }
+
+    static ArrayList<String> selectCodecs(String mime, ArrayList<MediaFormat> formats,
+            String[] features, boolean isEncoder, int selectCodecOption, boolean allCodecs) {
+        int kind = allCodecs ? MediaCodecList.ALL_CODECS : MediaCodecList.REGULAR_CODECS;
+        MediaCodecList codecList = new MediaCodecList(kind);
         MediaCodecInfo[] codecInfos = codecList.getCodecInfos();
         ArrayList<String> listOfCodecs = new ArrayList<>();
         for (MediaCodecInfo codecInfo : codecInfos) {
@@ -382,6 +397,31 @@
         }
         return listOfCodecs;
     }
+
+    static Set<String> getMimesOfAvailableCodecs(int codecAV, int codecType) {
+        MediaCodecList codecList = new MediaCodecList(MediaCodecList.REGULAR_CODECS);
+        MediaCodecInfo[] codecInfos = codecList.getCodecInfos();
+        Set<String> listOfMimes = new HashSet<>();
+        for (MediaCodecInfo codecInfo : codecInfos) {
+            if (codecType == SELECT_HARDWARE && !codecInfo.isHardwareAccelerated()) {
+                continue;
+            }
+            if (codecType == SELECT_SOFTWARE && !codecInfo.isSoftwareOnly()) {
+                continue;
+            }
+            String[] types = codecInfo.getSupportedTypes();
+            for (String type : types) {
+                if (codecAV == SELECT_AUDIO && !type.startsWith("audio/")) {
+                    continue;
+                }
+                if (codecAV == SELECT_VIDEO && !type.startsWith("video/")) {
+                    continue;
+                }
+                listOfMimes.add(type);
+            }
+        }
+        return listOfMimes;
+    }
 }
 
 class CodecDecoderTestBase extends CodecTestBase {
diff --git a/tests/mediapc/src/android/mediapc/cts/EncoderInitializationLatencyTest.java b/tests/mediapc/src/android/mediapc/cts/EncoderInitializationLatencyTest.java
deleted file mode 100644
index ae09b14..0000000
--- a/tests/mediapc/src/android/mediapc/cts/EncoderInitializationLatencyTest.java
+++ /dev/null
@@ -1,507 +0,0 @@
-/*
- * Copyright (C) 2021 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 android.mediapc.cts;
-
-import static android.mediapc.cts.CodecTestBase.selectCodecs;
-import static android.mediapc.cts.CodecTestBase.selectHardwareCodecs;
-
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-import static org.junit.Assume.assumeFalse;
-import static org.junit.Assume.assumeTrue;
-
-import android.app.Instrumentation;
-import android.content.Context;
-import android.content.pm.PackageManager;
-import android.media.MediaCodec;
-import android.media.MediaCodecInfo;
-import android.media.MediaCodecList;
-import android.media.MediaFormat;
-import android.media.MediaRecorder;
-import android.mediapc.cts.common.Utils;
-import android.os.Build;
-import android.util.Log;
-import android.util.Pair;
-import android.view.Surface;
-
-import androidx.test.filters.LargeTest;
-import androidx.test.platform.app.InstrumentationRegistry;
-import androidx.test.rule.ActivityTestRule;
-
-import com.android.compatibility.common.util.CddTest;
-import com.android.compatibility.common.util.DeviceReportLog;
-import com.android.compatibility.common.util.ResultType;
-import com.android.compatibility.common.util.ResultUnit;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-
-import java.io.File;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.List;
-
-/**
- * The following test class validates the codec initialization latency (time for codec create +
- * configure) for the audio encoders and hardware video encoders available in the device, under the
- * load condition (Transcode + MediaRecorder session Audio(Microphone) and 1080p Video(Camera)).
- */
-@RunWith(Parameterized.class)
-public class EncoderInitializationLatencyTest {
-    private static final String LOG_TAG = EncoderInitializationLatencyTest.class.getSimpleName();
-    private static final boolean[] boolStates = {false, true};
-    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_R_MS = 50;
-    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_R_MS = 65;
-    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_S_MS = 40;
-    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_S_MS = 50;
-    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_T_MS = 30;
-    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_T_MS = 40;
-
-    private static final int MAX_AUDIOENC_INITIALIZATION_LATENCY_MS;
-    private static final int MAX_VIDEOENC_INITIALIZATION_LATENCY_MS;
-    private static final String AVC = MediaFormat.MIMETYPE_VIDEO_AVC;
-    private static final String HEVC = MediaFormat.MIMETYPE_VIDEO_HEVC;
-    private static final String AVC_TRANSCODE_FILE = "bbb_1280x720_3mbps_30fps_avc.mp4";
-    private static String AVC_DECODER_NAME;
-    private static String AVC_ENCODER_NAME;
-
-    static {
-        if (Utils.isRPerfClass()) {
-            MAX_AUDIOENC_INITIALIZATION_LATENCY_MS = MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_R_MS;
-            MAX_VIDEOENC_INITIALIZATION_LATENCY_MS = MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_R_MS;
-        } else if (Utils.isSPerfClass()) {
-            MAX_AUDIOENC_INITIALIZATION_LATENCY_MS = MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_S_MS;
-            MAX_VIDEOENC_INITIALIZATION_LATENCY_MS = MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_S_MS;
-        } else {
-            // Performance class Build.VERSION_CODES.TIRAMISU and beyond
-            MAX_AUDIOENC_INITIALIZATION_LATENCY_MS = MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_T_MS;
-            MAX_VIDEOENC_INITIALIZATION_LATENCY_MS = MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_T_MS;
-        }
-    }
-
-    private final String mMime;
-    private final String mEncoderName;
-
-    private LoadStatus mTranscodeLoadStatus = null;
-    private Thread mTranscodeLoadThread = null;
-    private MediaRecorder mMediaRecorderLoad = null;
-    private File mTempRecordedFile = null;
-    private Surface mSurface = null;
-    private Exception mException = null;
-
-    @Before
-    public void setUp() throws Exception {
-        Utils.assumeDeviceMeetsPerformanceClassPreconditions();
-
-        ArrayList<String> listOfAvcHwDecoders = selectHardwareCodecs(AVC, null, null, false);
-        assumeFalse("Test requires h/w avc decoder", listOfAvcHwDecoders.isEmpty());
-        AVC_DECODER_NAME = listOfAvcHwDecoders.get(0);
-
-        ArrayList<String> listOfAvcHwEncoders = selectHardwareCodecs(AVC, null, null, true);
-        assumeFalse("Test requires h/w avc encoder", listOfAvcHwEncoders.isEmpty());
-        AVC_ENCODER_NAME = listOfAvcHwEncoders.get(0);
-
-        Instrumentation instrumentation = InstrumentationRegistry.getInstrumentation();
-        Context context = instrumentation.getTargetContext();
-        PackageManager packageManager = context.getPackageManager();
-        assertNotNull(packageManager.getSystemAvailableFeatures());
-        assumeTrue("The device doesn't have a camera",
-                packageManager.hasSystemFeature(PackageManager.FEATURE_CAMERA_ANY));
-        assumeTrue("The device doesn't have a microphone",
-                packageManager.hasSystemFeature(PackageManager.FEATURE_MICROPHONE));
-        createSurface();
-        startLoad();
-    }
-
-    @After
-    public void tearDown() throws Exception {
-        stopLoad();
-        releaseSurface();
-    }
-
-    public EncoderInitializationLatencyTest(String mimeType, String encoderName) {
-        mMime = mimeType;
-        mEncoderName = encoderName;
-    }
-
-    @Rule
-    public ActivityTestRule<TestActivity> mActivityRule =
-            new ActivityTestRule<>(TestActivity.class);
-
-    // Returns the list of all available hardware video encoders in the device.
-    static ArrayList<String> getMimesOfAvailableHardwareVideoEncoders() {
-        MediaCodecList codecList = new MediaCodecList(MediaCodecList.REGULAR_CODECS);
-        MediaCodecInfo[] codecInfos = codecList.getCodecInfos();
-        ArrayList<String> listOfMimes = new ArrayList<>();
-        for (MediaCodecInfo codecInfo : codecInfos) {
-            if (!codecInfo.isEncoder() || !codecInfo.isHardwareAccelerated()) continue;
-            String[] types = codecInfo.getSupportedTypes();
-            for (String type : types) {
-                if (type.startsWith("video/") && !listOfMimes.contains(type)) {
-                    listOfMimes.add(type);
-                }
-            }
-        }
-        return listOfMimes;
-    }
-
-    // Returns the list of all available audio encoders in the device.
-    static ArrayList<String> getMimesOfAvailableAudioEncoders() {
-        MediaCodecList codecList = new MediaCodecList(MediaCodecList.REGULAR_CODECS);
-        MediaCodecInfo[] codecInfos = codecList.getCodecInfos();
-        ArrayList<String> listOfMimes = new ArrayList<>();
-        for (MediaCodecInfo codecInfo : codecInfos) {
-            if (!codecInfo.isEncoder()) continue;
-            String[] types = codecInfo.getSupportedTypes();
-            for (String type : types) {
-                if (type.startsWith("audio/") && !listOfMimes.contains(type)) {
-                    listOfMimes.add(type);
-                }
-            }
-        }
-        return listOfMimes;
-    }
-
-    // Returns the list of parameters with mimetype and their encoder(for audio - all encoders,
-    // video - hardware encoders).
-    // Parameters {0}_{1} -- Mime_EncoderName
-    @Parameterized.Parameters(name = "{index}({0}_{1})")
-    public static Collection<Object[]> inputParams() {
-        // Prepares the params list with the required Hardware video encoders and all available
-        // audio encoders present in the device.
-        final List<Object[]> argsList = new ArrayList<>();
-        ArrayList<String> mimesList = getMimesOfAvailableHardwareVideoEncoders();
-        mimesList.addAll(getMimesOfAvailableAudioEncoders());
-        for (String mime : mimesList) {
-            ArrayList<String> listOfEncoders;
-            if (mime.startsWith("audio/")) {
-                listOfEncoders = selectCodecs(mime, null, null, true);
-            } else {
-                listOfEncoders = selectHardwareCodecs(mime, null, null, true);
-            }
-            for (String encoder : listOfEncoders) {
-                argsList.add(new Object[]{mime, encoder});
-            }
-        }
-        return argsList;
-    }
-
-    private MediaRecorder createMediaRecorderLoad(Surface surface) throws Exception {
-        MediaRecorder mediaRecorder = new MediaRecorder(InstrumentationRegistry.getInstrumentation()
-                .getContext());
-        mediaRecorder.setAudioSource(MediaRecorder.AudioSource.MIC);
-        mediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA);
-        mediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.DEFAULT);
-        mediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AAC);
-        mediaRecorder.setVideoEncoder(mMime.equalsIgnoreCase(HEVC) ?
-                MediaRecorder.VideoEncoder.HEVC : MediaRecorder.VideoEncoder.H264);
-        mediaRecorder.setOutputFile(mTempRecordedFile);
-        mediaRecorder.setVideoSize(1920, 1080);
-        mediaRecorder.setOrientationHint(0);
-        mediaRecorder.setPreviewDisplay(surface);
-        mediaRecorder.prepare();
-        return mediaRecorder;
-    }
-
-    private void startLoad() throws Exception {
-        // TODO: b/183671436
-        // Create Transcode load (AVC Decoder(720p) + AVC Encoder(720p))
-        mTranscodeLoadStatus = new LoadStatus();
-        mTranscodeLoadThread = new Thread(() -> {
-            try {
-                TranscodeLoad transcodeLoad = new TranscodeLoad(AVC, AVC_TRANSCODE_FILE,
-                        AVC_DECODER_NAME, AVC_ENCODER_NAME, mTranscodeLoadStatus);
-                transcodeLoad.doTranscode();
-            } catch (Exception e) {
-                mException = e;
-            }
-        });
-        // Create MediaRecorder Session - Audio (Microphone) + 1080p Video (Camera)
-        // Create a temp file to dump the MediaRecorder output. Later it will be deleted.
-        mTempRecordedFile = new File(WorkDir.getMediaDirString() + "tempOut.mp4");
-        mTempRecordedFile.createNewFile();
-        mMediaRecorderLoad = createMediaRecorderLoad(mSurface);
-        // Start the Loads
-        mTranscodeLoadThread.start();
-        mMediaRecorderLoad.start();
-    }
-
-    private void stopLoad() throws Exception {
-        if (mTranscodeLoadStatus != null) {
-            mTranscodeLoadStatus.setLoadFinished();
-            mTranscodeLoadStatus = null;
-        }
-        if (mTranscodeLoadThread != null) {
-            mTranscodeLoadThread.join();
-            mTranscodeLoadThread = null;
-        }
-        if (mMediaRecorderLoad != null) {
-            // Note that a RuntimeException is intentionally thrown to the application, if no valid
-            // audio/video data has been received when stop() is called. This happens if stop() is
-            // called immediately after start(). So sleep for 1000ms inorder to make sure some
-            // data has been received between start() and stop().
-            Thread.sleep(1000);
-            mMediaRecorderLoad.stop();
-            mMediaRecorderLoad.release();
-            mMediaRecorderLoad = null;
-            if (mTempRecordedFile != null && mTempRecordedFile.exists()) {
-                mTempRecordedFile.delete();
-                mTempRecordedFile = null;
-            }
-        }
-        if (mException != null) throw mException;
-    }
-
-    private void createSurface() throws InterruptedException {
-        mActivityRule.getActivity().waitTillSurfaceIsCreated();
-        mSurface = mActivityRule.getActivity().getSurface();
-        assertTrue("Surface created is null.", mSurface != null);
-        assertTrue("Surface created is invalid.", mSurface.isValid());
-        mActivityRule.getActivity().setScreenParams(1920, 1080, true);
-    }
-
-    private void releaseSurface() {
-        if (mSurface != null) {
-            mSurface.release();
-            mSurface = null;
-        }
-    }
-
-    /**
-     * This test validates that the initialization latency(time for codec create + configure)
-     * for the audio encoders <= 30ms and for video encoders <= 40ms measuring 10 times in
-     * succession(5 times alternating sync and async modes). This also logs the stats min, max, avg
-     * of the encoder initialization latencies.
-     */
-    @LargeTest
-    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
-    @CddTest(requirement = "2.2.7.1/5.1/H-1-7,H-1-8")
-    public void testInitializationLatency() throws Exception {
-        final int NUM_MEASUREMENTS = 5;
-        // Test gathers initialization latency for a number of iterations and
-        // percentile is a variable used to control how many of these iterations
-        // need to meet the pass criteria. For NUM_MEASUREMENTS at 5, sync and Async
-        // modes which is a total of 10 iterations, this translates to index 7.
-        final int percentile = 70;
-        long expectedMaxCodecInitializationLatencyMs = mMime.startsWith("audio/") ?
-                MAX_AUDIOENC_INITIALIZATION_LATENCY_MS : MAX_VIDEOENC_INITIALIZATION_LATENCY_MS;
-        long sumOfEncoderInitializationLatencyMs = 0;
-        int count = 0;
-        long[] encoderInitializationLatencyMs = new long[NUM_MEASUREMENTS * boolStates.length];
-        for (int i = 0; i < NUM_MEASUREMENTS; i++) {
-            for (boolean isAsync : boolStates) {
-                EncoderInitializationLatency encoderInitializationLatency =
-                        new EncoderInitializationLatency(mMime, mEncoderName, isAsync);
-                long latency = encoderInitializationLatency.calculateEncoderInitializationLatency();
-                encoderInitializationLatencyMs[count] = latency;
-                sumOfEncoderInitializationLatencyMs += latency;
-                count++;
-            }
-        }
-        Arrays.sort(encoderInitializationLatencyMs);
-
-        String statsLog = String.format("CodecInitialization latency for mime: %s, " +
-                "Encoder: %s, in Ms :: ", mMime, mEncoderName);
-        Log.i(LOG_TAG, "Min " + statsLog + encoderInitializationLatencyMs[0]);
-        Log.i(LOG_TAG, "Max " + statsLog + encoderInitializationLatencyMs[count - 1]);
-        Log.i(LOG_TAG, "Avg " + statsLog + (sumOfEncoderInitializationLatencyMs / count));
-        long initializationLatency = encoderInitializationLatencyMs[percentile * count / 100];
-        if (Utils.isPerfClass()) {
-            String errorLog = String.format(
-                    "CodecInitialization latency for mime: %s, Encoder: %s is not as expected. "
-                            + "act/exp in Ms :: %d/%d", mMime, mEncoderName, initializationLatency,
-                    expectedMaxCodecInitializationLatencyMs);
-            assertTrue(errorLog, initializationLatency <= expectedMaxCodecInitializationLatencyMs);
-        } else {
-            int pc;
-            if (mMime.startsWith("audio/")) {
-                pc = initializationLatency < MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_T_MS ?
-                        Build.VERSION_CODES.TIRAMISU :
-                        initializationLatency < MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_S_MS ?
-                                Build.VERSION_CODES.S : initializationLatency <
-                                MAX_AUDIOENC_INITIALIZATION_LATENCY_PC_R_MS ?
-                                Build.VERSION_CODES.R : 0;
-            } else {
-                pc = initializationLatency < MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_T_MS ?
-                        Build.VERSION_CODES.TIRAMISU :
-                        initializationLatency < MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_S_MS ?
-                                Build.VERSION_CODES.S : initializationLatency <
-                                MAX_VIDEOENC_INITIALIZATION_LATENCY_PC_R_MS ?
-                                Build.VERSION_CODES.R : 0;
-            }
-            DeviceReportLog log = new DeviceReportLog("MediaPerformanceClassLogs",
-                    "InitializationLatency_" + mEncoderName);
-            log.addValue("encoder", mEncoderName, ResultType.NEUTRAL, ResultUnit.NONE);
-            log.addValue("initialization_latency", initializationLatency, ResultType.LOWER_BETTER,
-                    ResultUnit.NONE);
-            log.setSummary("CDD 2.2.7.1/5.1/H-1-7,H-1-8 performance_class", pc, ResultType.NEUTRAL,
-                    ResultUnit.NONE);
-            log.submit(InstrumentationRegistry.getInstrumentation());
-        }
-    }
-}
-
-/**
- * The following class calculates the encoder initialization latency (time for codec create +
- * configure). And also logs the time taken by the encoder for:
- * (create + configure + start),
- * (create + configure + start + first frame to enqueue),
- * (create + configure + start + first frame to dequeue).
- */
-class EncoderInitializationLatency extends CodecEncoderTestBase {
-    private static final String LOG_TAG = EncoderInitializationLatency.class.getSimpleName();
-
-    private final String mEncoderName;
-    private final boolean mIsAsync;
-
-    EncoderInitializationLatency(String mime, String encoderName, boolean isAsync) {
-        super(mime);
-        mEncoderName = encoderName;
-        mIsAsync = isAsync;
-        mSampleRate = 8000;
-        mFrameRate = 60;
-    }
-
-    private MediaFormat setUpFormat() throws IOException {
-        MediaFormat format = new MediaFormat();
-        format.setString(MediaFormat.KEY_MIME, mMime);
-        if (mIsAudio) {
-            if (mMime.equals(MediaFormat.MIMETYPE_AUDIO_FLAC)) {
-                format.setInteger(MediaFormat.KEY_FLAC_COMPRESSION_LEVEL, 10000);
-            } else {
-                format.setInteger(MediaFormat.KEY_BIT_RATE, 128000);
-            }
-            format.setInteger(MediaFormat.KEY_SAMPLE_RATE, mSampleRate);
-            format.setInteger(MediaFormat.KEY_CHANNEL_COUNT, 1);
-        } else {
-            MediaCodec codec = MediaCodec.createByCodecName(mEncoderName);
-            MediaCodecInfo.CodecCapabilities codecCapabilities =
-                    codec.getCodecInfo().getCapabilitiesForType(mMime);
-            if (codecCapabilities.getVideoCapabilities().isSizeSupported(1920, 1080)) {
-                format.setInteger(MediaFormat.KEY_WIDTH, 1920);
-                format.setInteger(MediaFormat.KEY_HEIGHT, 1080);
-                format.setInteger(MediaFormat.KEY_BIT_RATE, 8000000);
-            } else if (codecCapabilities.getVideoCapabilities().isSizeSupported(1280, 720)) {
-                format.setInteger(MediaFormat.KEY_WIDTH, 1280);
-                format.setInteger(MediaFormat.KEY_HEIGHT, 720);
-                format.setInteger(MediaFormat.KEY_BIT_RATE, 5000000);
-            } else if (codecCapabilities.getVideoCapabilities().isSizeSupported(640, 480)) {
-                format.setInteger(MediaFormat.KEY_WIDTH, 640);
-                format.setInteger(MediaFormat.KEY_HEIGHT, 480);
-                format.setInteger(MediaFormat.KEY_BIT_RATE, 2000000);
-            } else if (codecCapabilities.getVideoCapabilities().isSizeSupported(352, 288)) {
-                format.setInteger(MediaFormat.KEY_WIDTH, 352);
-                format.setInteger(MediaFormat.KEY_HEIGHT, 288);
-                format.setInteger(MediaFormat.KEY_BIT_RATE, 512000);
-            } else {
-                format.setInteger(MediaFormat.KEY_WIDTH, 176);
-                format.setInteger(MediaFormat.KEY_HEIGHT, 144);
-                format.setInteger(MediaFormat.KEY_BIT_RATE, 128000);
-            }
-            codec.release();
-            format.setInteger(MediaFormat.KEY_FRAME_RATE, mFrameRate);
-            format.setFloat(MediaFormat.KEY_I_FRAME_INTERVAL, 1.0f);
-            format.setInteger(MediaFormat.KEY_COLOR_FORMAT,
-                    MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible);
-        }
-        return format;
-    }
-
-    public long calculateEncoderInitializationLatency() throws Exception {
-        MediaFormat format = setUpFormat();
-        if (mIsAudio) {
-            mSampleRate = format.getInteger(MediaFormat.KEY_SAMPLE_RATE);
-            mChannels = format.getInteger(MediaFormat.KEY_CHANNEL_COUNT);
-        } else {
-            mWidth = format.getInteger(MediaFormat.KEY_WIDTH);
-            mHeight = format.getInteger(MediaFormat.KEY_HEIGHT);
-        }
-        setUpSource(mInputFile);
-        MediaCodec.BufferInfo outInfo = new MediaCodec.BufferInfo();
-        long enqueueTimeStamp = 0;
-        long dequeueTimeStamp = 0;
-        long baseTimeStamp = System.nanoTime();
-        mCodec = MediaCodec.createByCodecName(mEncoderName);
-        resetContext(mIsAsync, false);
-        mAsyncHandle.setCallBack(mCodec, mIsAsync);
-        mCodec.configure(format, null, MediaCodec.CONFIGURE_FLAG_ENCODE, null);
-        long configureTimeStamp = System.nanoTime();
-        mCodec.start();
-        long startTimeStamp = System.nanoTime();
-        if (mIsAsync) {
-            // We will keep on feeding the input to encoder until we see the first dequeued frame.
-            while (!mAsyncHandle.hasSeenError() && !mSawInputEOS) {
-                Pair<Integer, MediaCodec.BufferInfo> element = mAsyncHandle.getWork();
-                if (element != null) {
-                    int bufferID = element.first;
-                    MediaCodec.BufferInfo info = element.second;
-                    if (info != null) {
-                        dequeueTimeStamp = System.nanoTime();
-                        dequeueOutput(bufferID, info);
-                        break;
-                    } else {
-                        if (enqueueTimeStamp == 0) {
-                            enqueueTimeStamp = System.nanoTime();
-                        }
-                        enqueueInput(bufferID);
-                    }
-                }
-            }
-        } else {
-            while (!mSawOutputEOS) {
-                if (!mSawInputEOS) {
-                    int inputBufferId = mCodec.dequeueInputBuffer(Q_DEQ_TIMEOUT_US);
-                    if (inputBufferId > 0) {
-                        if (enqueueTimeStamp == 0) {
-                            enqueueTimeStamp = System.nanoTime();
-                        }
-                        enqueueInput(inputBufferId);
-                    }
-                }
-                int outputBufferId = mCodec.dequeueOutputBuffer(outInfo, Q_DEQ_TIMEOUT_US);
-                if (outputBufferId >= 0) {
-                    dequeueTimeStamp = System.nanoTime();
-                    dequeueOutput(outputBufferId, outInfo);
-                    break;
-                }
-            }
-        }
-        queueEOS();
-        waitForAllOutputs();
-        mCodec.stop();
-        mCodec.release();
-        Log.d(LOG_TAG, "Encode mMime: " + mMime + " Encoder: " + mEncoderName +
-                " Time for (create + configure) in ns: " + (configureTimeStamp - baseTimeStamp));
-        Log.d(LOG_TAG, "Encode mMime: " + mMime + " Encoder: " + mEncoderName +
-                " Time for (create + configure + start) in ns: " +
-                (startTimeStamp - baseTimeStamp));
-        Log.d(LOG_TAG, "Encode mMime: " + mMime + " Encoder: " + mEncoderName +
-                " Time for (create + configure + start + first frame to enqueue) in ns: " +
-                (enqueueTimeStamp - baseTimeStamp));
-        Log.d(LOG_TAG, "Encode mMime: " + mMime + " Encoder: " + mEncoderName +
-                " Time for (create + configure + start + first frame to dequeue) in ns: " +
-                (dequeueTimeStamp - baseTimeStamp));
-        long timeToConfigureMs = (configureTimeStamp - baseTimeStamp) / 1000000;
-        return timeToConfigureMs;
-    }
-}
diff --git a/tests/mediapc/src/android/mediapc/cts/MultiCodecPerfTestBase.java b/tests/mediapc/src/android/mediapc/cts/MultiCodecPerfTestBase.java
index ec27bf9..4e82515 100644
--- a/tests/mediapc/src/android/mediapc/cts/MultiCodecPerfTestBase.java
+++ b/tests/mediapc/src/android/mediapc/cts/MultiCodecPerfTestBase.java
@@ -16,6 +16,7 @@
 
 package android.mediapc.cts;
 
+import static android.media.MediaCodecInfo.CodecCapabilities.FEATURE_SecurePlayback;
 import static android.mediapc.cts.CodecTestBase.selectHardwareCodecs;
 
 import static org.junit.Assert.assertTrue;
@@ -25,9 +26,11 @@
 import android.media.MediaCodecInfo.VideoCapabilities.PerformancePoint;
 import android.media.MediaFormat;
 import android.mediapc.cts.common.Utils;
+import android.os.Build;
 import android.util.Log;
 import android.util.Pair;
 
+import org.junit.Assume;
 import org.junit.Before;
 
 import java.io.IOException;
@@ -49,6 +52,7 @@
     static ArrayList<String> mMimeList = new ArrayList<>();
     static Map<String, String> mTestFiles = new HashMap<>();
     static Map<String, String> m720pTestFiles = new HashMap<>();
+    static Map<String, String> m1080pTestFiles = new HashMap<>();
 
     static {
         mMimeList.add(MediaFormat.MIMETYPE_VIDEO_AVC);
@@ -57,14 +61,18 @@
         m720pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_AVC, "bbb_1280x720_3mbps_30fps_avc.mp4");
         m720pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_HEVC, "bbb_1280x720_3mbps_30fps_hevc.mp4");
 
-        // Test VP9 and AV1 as well for Build.VERSION_CODES.S
-        if (Utils.isSPerfClass()) {
+        // Test VP9 and AV1 as well for Build.VERSION_CODES.S and beyond
+        if (Utils.getPerfClass() >= Build.VERSION_CODES.S) {
             mMimeList.add(MediaFormat.MIMETYPE_VIDEO_VP9);
             mMimeList.add(MediaFormat.MIMETYPE_VIDEO_AV1);
 
             m720pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_VP9, "bbb_1280x720_3mbps_30fps_vp9.webm");
             m720pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_AV1, "bbb_1280x720_3mbps_30fps_av1.mp4");
         }
+        m1080pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_AVC, "bbb_1920x1080_6mbps_30fps_avc.mp4");
+        m1080pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_HEVC, "bbb_1920x1080_4mbps_30fps_hevc.mp4");
+        m1080pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_VP9, "bbb_1920x1080_4mbps_30fps_vp9.webm");
+        m1080pTestFiles.put(MediaFormat.MIMETYPE_VIDEO_AV1, "bbb_1920x1080_4mbps_30fps_av1.mp4");
     }
 
     String mMime;
@@ -86,6 +94,11 @@
 
     // Returns the list of hardware codecs for given mime
     public static ArrayList<String> getHardwareCodecsForMime(String mime, boolean isEncoder) {
+        return getHardwareCodecsForMime(mime, isEncoder, false);
+    }
+
+    public static ArrayList<String> getHardwareCodecsForMime(String mime, boolean isEncoder,
+            boolean allCodecs) {
         // All the multi-instance tests are limited to codecs that support at least 1280x720 @ 30fps
         // This will exclude hevc constant quality encoders that are limited to max resolution of
         // 512x512
@@ -93,7 +106,7 @@
         fmt.setInteger(MediaFormat.KEY_FRAME_RATE, 30);
         ArrayList<MediaFormat> formatsList = new ArrayList<>();
         formatsList.add(fmt);
-        return selectHardwareCodecs(mime, formatsList, null, isEncoder);
+        return selectHardwareCodecs(mime, formatsList, null, isEncoder, allCodecs);
     }
 
     // Returns the max number of 30 fps instances that the given list of mimeCodecPairs
@@ -160,4 +173,30 @@
         }
         return REQUIRED_MIN_CONCURRENT_INSTANCES;
     }
+
+    boolean isSecureSupportedCodec(String codecName, String mime) throws IOException {
+        boolean isSecureSupported;
+        MediaCodec codec = MediaCodec.createByCodecName(codecName);
+        isSecureSupported = codec.getCodecInfo().getCapabilitiesForType(mime).isFeatureSupported(
+                FEATURE_SecurePlayback);
+        codec.release();
+        return isSecureSupported;
+    }
+
+    boolean codecSupportsPP(String codecName, String mime, PerformancePoint reqPP)
+            throws IOException {
+        MediaCodec codec = MediaCodec.createByCodecName(codecName);
+        List<PerformancePoint> suppPPs =
+                codec.getCodecInfo().getCapabilitiesForType(mime).getVideoCapabilities()
+                        .getSupportedPerformancePoints();
+        assertTrue("Performance point not published by codec: " + codecName, suppPPs != null);
+        boolean codecSupportsReqPP = false;
+        for (PerformancePoint pp : suppPPs) {
+            if (pp.covers(reqPP)) {
+                codecSupportsReqPP = true;
+            }
+        }
+        codec.release();
+        return codecSupportsReqPP;
+    }
 }
diff --git a/tests/mediapc/src/android/mediapc/cts/MultiDecoderPairPerfTest.java b/tests/mediapc/src/android/mediapc/cts/MultiDecoderPairPerfTest.java
index 31c069f..832f9d0 100644
--- a/tests/mediapc/src/android/mediapc/cts/MultiDecoderPairPerfTest.java
+++ b/tests/mediapc/src/android/mediapc/cts/MultiDecoderPairPerfTest.java
@@ -18,6 +18,7 @@
 
 import static org.junit.Assert.assertTrue;
 
+import android.media.MediaCodecInfo;
 import android.media.MediaFormat;
 import android.mediapc.cts.common.Utils;
 import android.os.Build;
@@ -55,6 +56,7 @@
 @RunWith(Parameterized.class)
 public class MultiDecoderPairPerfTest extends MultiCodecPerfTestBase {
     private static final String LOG_TAG = MultiDecoderPairPerfTest.class.getSimpleName();
+    private static final int REQUIRED_CONCURRENT_NON_SECURE_INSTANCES_WITH_SECURE = 3;
 
     private final Pair<String, String> mFirstPair;
     private final Pair<String, String> mSecondPair;
@@ -74,7 +76,7 @@
         final List<Object[]> argsList = new ArrayList<>();
         ArrayList<Pair<String, String>> mimeTypeDecoderPairs = new ArrayList<>();
         for (String mime : mMimeList) {
-            ArrayList<String> listOfDecoders = getHardwareCodecsForMime(mime, false);
+            ArrayList<String> listOfDecoders = getHardwareCodecsForMime(mime, false, true);
             for (String decoder : listOfDecoders) {
                 mimeTypeDecoderPairs.add(Pair.create(mime, decoder));
             }
@@ -102,6 +104,9 @@
     @CddTest(requirement = "2.2.7.1/5.1/H-1-1,H-1-2")
     public void test720p() throws Exception {
         Assume.assumeTrue(Utils.isSPerfClass() || Utils.isRPerfClass() || !Utils.isPerfClass());
+        Assume.assumeFalse("Skipping regular performance tests for secure codecs",
+                isSecureSupportedCodec(mFirstPair.second, mFirstPair.first) ||
+                        isSecureSupportedCodec(mSecondPair.second, mSecondPair.first));
 
         boolean hasVP9 = mFirstPair.first.equals(MediaFormat.MIMETYPE_VIDEO_VP9) ||
                 mSecondPair.first.equals(MediaFormat.MIMETYPE_VIDEO_VP9);
@@ -109,6 +114,69 @@
         testCodec(m720pTestFiles, 720, 1280, requiredMinInstances);
     }
 
+    /**
+     * This test calculates the number of 1080p 30 fps decoder instances that the given two
+     * (mime - decoder) pairs can support. Assigns the same number of instances to the two pairs
+     * (if max instances are even), or one more to one pair (if odd) and ensures that all the
+     * concurrent sessions succeed in decoding with meeting the expected frame rate.
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    @CddTest(requirement = "2.2.7.1/5.1/H-1-1,H-1-2")
+    public void test1080p() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        Assume.assumeFalse("Skipping regular performance tests for secure codecs",
+                isSecureSupportedCodec(mFirstPair.second, mFirstPair.first) ||
+                        isSecureSupportedCodec(mSecondPair.second, mSecondPair.first));
+        testCodec(m1080pTestFiles, 1080, 1920, REQUIRED_MIN_CONCURRENT_INSTANCES);
+    }
+
+    /**
+     * Validates if hardware decoder pairs where one or both supports secure decode and required
+     * perf are present
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    // TODO(b/218771970) Add @CddTest annotation
+    public void testReqSecureDecodeSupport() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        Assume.assumeTrue("Skipping secure decode support tests if both are non-secure codecs",
+                isSecureSupportedCodec(mFirstPair.second, mFirstPair.first) ||
+                        isSecureSupportedCodec(mSecondPair.second, mSecondPair.first));
+
+        MediaCodecInfo.VideoCapabilities.PerformancePoint reqSecurePP =
+                new MediaCodecInfo.VideoCapabilities.PerformancePoint(1920, 1080, 30);
+
+        MediaCodecInfo.VideoCapabilities.PerformancePoint reqNonSecurePP =
+                new MediaCodecInfo.VideoCapabilities.PerformancePoint(1920, 1080,
+                        30 * REQUIRED_CONCURRENT_NON_SECURE_INSTANCES_WITH_SECURE);
+
+        boolean codecSupportsReqPP = codecSupportsPP(mFirstPair.second, mFirstPair.first,
+                isSecureSupportedCodec(mFirstPair.second, mFirstPair.first) ? reqSecurePP :
+                        reqNonSecurePP);
+
+        codecSupportsReqPP &= codecSupportsPP(mSecondPair.second, mSecondPair.first,
+                isSecureSupportedCodec(mSecondPair.second, mSecondPair.first) ? reqSecurePP :
+                        reqNonSecurePP);
+
+
+        if (Utils.isTPerfClass()) {
+            assertTrue(
+                    "Required Secure Decode Support required for MPC >= Android T, unsupported " +
+                            "codec pair: " + mFirstPair.second + "," + mSecondPair.second,
+                    codecSupportsReqPP);
+        } else {
+            DeviceReportLog log =
+                    new DeviceReportLog("MediaPerformanceClassLogs", "SecureDecodeSupport");
+            log.addValue("Req Secure Decode Support pair: " + mFirstPair.second + "," +
+                    mSecondPair.second, codecSupportsReqPP, ResultType.NEUTRAL, ResultUnit.NONE);
+            // TODO(b/218771970) Log CDD sections
+            log.setSummary("MPC 13: Secure Decode requirements", 0, ResultType.NEUTRAL,
+                    ResultUnit.NONE);
+            log.submit(InstrumentationRegistry.getInstrumentation());
+        }
+    }
+
     private void testCodec(Map<String, String> testFiles, int height, int width,
             int requiredMinInstances) throws Exception {
         mTestFiles = testFiles;
diff --git a/tests/mediapc/src/android/mediapc/cts/MultiDecoderPerfTest.java b/tests/mediapc/src/android/mediapc/cts/MultiDecoderPerfTest.java
index 1c1aeea..803ec62 100644
--- a/tests/mediapc/src/android/mediapc/cts/MultiDecoderPerfTest.java
+++ b/tests/mediapc/src/android/mediapc/cts/MultiDecoderPerfTest.java
@@ -18,6 +18,7 @@
 
 import static org.junit.Assert.assertTrue;
 
+import android.media.MediaCodecInfo.VideoCapabilities.PerformancePoint;
 import android.media.MediaFormat;
 import android.mediapc.cts.common.Utils;
 import android.os.Build;
@@ -53,6 +54,7 @@
 @RunWith(Parameterized.class)
 public class MultiDecoderPerfTest extends MultiCodecPerfTestBase {
     private static final String LOG_TAG = MultiDecoderPerfTest.class.getSimpleName();
+    private static final int REQUIRED_MIN_CONCURRENT_SECURE_INSTANCES = 2;
 
     private final String mDecoderName;
 
@@ -68,7 +70,7 @@
     public static Collection<Object[]> inputParams() {
         final List<Object[]> argsList = new ArrayList<>();
         for (String mime : mMimeList) {
-            ArrayList<String> listOfDecoders = getHardwareCodecsForMime(mime, false);
+            ArrayList<String> listOfDecoders = getHardwareCodecsForMime(mime, false, true);
             for (String decoder : listOfDecoders) {
                 for (boolean isAsync : boolStates) {
                     argsList.add(new Object[]{mime, decoder, isAsync});
@@ -88,12 +90,60 @@
     @CddTest(requirement = "2.2.7.1/5.1/H-1-1,H-1-2")
     public void test720p() throws Exception {
         Assume.assumeTrue(Utils.isSPerfClass() || Utils.isRPerfClass() || !Utils.isPerfClass());
-
+        Assume.assumeFalse("Skipping regular performance tests for secure codecs",
+                isSecureSupportedCodec(mDecoderName, mMime));
         boolean hasVP9 = mMime.equals(MediaFormat.MIMETYPE_VIDEO_VP9);
         int requiredMinInstances = getRequiredMinConcurrentInstances(hasVP9);
         testCodec(m720pTestFiles, 720, 1280, requiredMinInstances);
     }
 
+    /**
+     * This test validates that the decoder can support at least 6 concurrent 1080p 30fps
+     * decoder instances. Also ensures that all the concurrent sessions succeed in decoding
+     * with meeting the expected frame rate.
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    @CddTest(requirement = "2.2.7.1/5.1/H-1-1,H-1-2")
+    public void test1080p() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        Assume.assumeFalse("Skipping regular performance tests for secure codecs",
+                isSecureSupportedCodec(mDecoderName, mMime));
+        testCodec(m1080pTestFiles, 1080, 1920, REQUIRED_MIN_CONCURRENT_INSTANCES);
+    }
+
+    /**
+     * Validates if hardware decoder that supports required secure decode perf is present
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    // TODO(b/218771970) Add @CddTest annotation
+    public void testReqSecureDecodeSupport() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        Assume.assumeTrue("Skipping secure decode support tests for non-secure codecs",
+                isSecureSupportedCodec(mDecoderName, mMime));
+
+        PerformancePoint reqPP =
+                new PerformancePoint(1920, 1080, 30 * REQUIRED_MIN_CONCURRENT_SECURE_INSTANCES);
+
+        boolean codecSupportsReqPP = codecSupportsPP(mDecoderName, mMime, reqPP);
+
+        if (Utils.isTPerfClass()) {
+            assertTrue(
+                    "Required Secure Decode Support required for MPC >= Android T, unsupported " +
+                            "codec: " + mDecoderName, codecSupportsReqPP);
+        } else {
+            DeviceReportLog log =
+                    new DeviceReportLog("MediaPerformanceClassLogs", "SecureDecodeSupport");
+            log.addValue("Req Secure Decode Support: " + mDecoderName, codecSupportsReqPP,
+                    ResultType.NEUTRAL, ResultUnit.NONE);
+            // TODO(b/218771970) Log CDD sections
+            log.setSummary("MPC 13: Secure Decode requirements", 0, ResultType.NEUTRAL,
+                    ResultUnit.NONE);
+            log.submit(InstrumentationRegistry.getInstrumentation());
+        }
+    }
+
     private void testCodec(Map<String, String> testFiles, int height, int width,
             int requiredMinInstances) throws Exception {
         mTestFile = testFiles.get(mMime);
diff --git a/tests/mediapc/src/android/mediapc/cts/MultiEncoderPairPerfTest.java b/tests/mediapc/src/android/mediapc/cts/MultiEncoderPairPerfTest.java
index edc2d6c..01e68d3 100644
--- a/tests/mediapc/src/android/mediapc/cts/MultiEncoderPairPerfTest.java
+++ b/tests/mediapc/src/android/mediapc/cts/MultiEncoderPairPerfTest.java
@@ -109,6 +109,20 @@
         testCodec(720, 1280, 4000000, requiredMinInstances);
     }
 
+    /**
+     * This test calculates the number of 1080p 30 fps encoder instances that the given two
+     * (mime - encoder) pairs can support. Assigns the same number of instances to the two pairs
+     * (if max instances are even), or one more to one pair (if odd) and ensures that all the
+     * concurrent sessions succeed in encoding.
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    @CddTest(requirement = "2.2.7.1/5.1/H-1-3,H-1-4")
+    public void test1080p() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        testCodec(1080, 1920, 10000000, REQUIRED_MIN_CONCURRENT_INSTANCES);
+    }
+
     private void testCodec(int height, int width, int bitrate, int requiredMinInstances)
             throws Exception {
         ArrayList<Pair<String, String>> mimeEncoderPairs = new ArrayList<>();
diff --git a/tests/mediapc/src/android/mediapc/cts/MultiEncoderPerfTest.java b/tests/mediapc/src/android/mediapc/cts/MultiEncoderPerfTest.java
index 3a2f1d9..28c7fbd 100644
--- a/tests/mediapc/src/android/mediapc/cts/MultiEncoderPerfTest.java
+++ b/tests/mediapc/src/android/mediapc/cts/MultiEncoderPerfTest.java
@@ -94,6 +94,18 @@
         testCodec(720, 1280, 4000000, requiredMinInstances);
     }
 
+    /**
+     * This test validates that the encoder can support at least 6 concurrent 1080p 30fps
+     * encoder instances. Also ensures that all the concurrent sessions succeed in encoding.
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    @CddTest(requirement = "2.2.7.1/5.1/H-1-3,H-1-4")
+    public void test1080p() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        testCodec(1080, 1920, 10000000, REQUIRED_MIN_CONCURRENT_INSTANCES);
+    }
+
     private void testCodec(int height, int width, int bitrate, int requiredMinInstances)
             throws Exception {
         ArrayList<Pair<String, String>> mimeEncoderPairs = new ArrayList<>();
diff --git a/tests/mediapc/src/android/mediapc/cts/MultiTranscoderPerfTest.java b/tests/mediapc/src/android/mediapc/cts/MultiTranscoderPerfTest.java
index d7d8445..9312637 100644
--- a/tests/mediapc/src/android/mediapc/cts/MultiTranscoderPerfTest.java
+++ b/tests/mediapc/src/android/mediapc/cts/MultiTranscoderPerfTest.java
@@ -119,6 +119,21 @@
         testCodec(m720pTestFiles, 720, 1280, requiredMinInstances);
     }
 
+    /**
+     * This test calculates the validates number of concurrent 1080p Transcode sessions that
+     * it can support by the (mime, decoder - mime, encoder) pairs. Creates maxInstances / 2
+     * Transcode sessions. If maximum instances is odd, creates one additional decoder which decodes
+     * to surface and render. And ensures that all the supported sessions succeed in
+     * transcoding/decoding with meeting the expected frame rate.
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    @CddTest(requirement = "2.2.7.1/5.1/H-1-5,H-1-6")
+    public void test1080p() throws Exception {
+        Assume.assumeTrue(Utils.isTPerfClass() || !Utils.isPerfClass());
+        testCodec(m1080pTestFiles, 1080, 1920, REQUIRED_MIN_CONCURRENT_INSTANCES / 2);
+    }
+
     private void testCodec(Map<String, String> testFiles, int height, int width,
             int requiredMinInstances) throws Exception {
         mTestFiles = testFiles;
diff --git a/tests/mediapc/src/android/mediapc/cts/VideoCodecRequirementsTest.java b/tests/mediapc/src/android/mediapc/cts/VideoCodecRequirementsTest.java
new file mode 100644
index 0000000..0afc209
--- /dev/null
+++ b/tests/mediapc/src/android/mediapc/cts/VideoCodecRequirementsTest.java
@@ -0,0 +1,170 @@
+/*
+ * Copyright (C) 2022 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 android.mediapc.cts;
+
+import static android.media.MediaFormat.MIMETYPE_VIDEO_AV1;
+import static android.mediapc.cts.CodecTestBase.SELECT_HARDWARE;
+import static android.mediapc.cts.CodecTestBase.SELECT_VIDEO;
+import static android.mediapc.cts.CodecTestBase.getMimesOfAvailableCodecs;
+import static android.mediapc.cts.CodecTestBase.selectHardwareCodecs;
+import static org.junit.Assert.assertTrue;
+
+import android.media.MediaCodec;
+import android.media.MediaCodecInfo.CodecCapabilities;
+import android.media.MediaCodecInfo.VideoCapabilities.PerformancePoint;
+import android.media.MediaFormat;
+import android.mediapc.cts.common.Utils;
+import android.os.Build;
+import android.util.Log;
+
+import androidx.test.filters.LargeTest;
+import androidx.test.platform.app.InstrumentationRegistry;
+
+import com.android.compatibility.common.util.DeviceReportLog;
+import com.android.compatibility.common.util.ResultType;
+import com.android.compatibility.common.util.ResultUnit;
+
+import org.junit.Test;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+public class VideoCodecRequirementsTest {
+    private static final String LOG_TAG = VideoCodecRequirementsTest.class.getSimpleName();
+    private static final String FILE_AV1_REQ_SUPPORT =
+            "dpov_1920x1080_60fps_av1_10bit_film_grain.mp4";
+
+    private Set<String> get4k60HwCodecSet(boolean isEncoder) throws IOException {
+        Set<String> codecSet = new HashSet<>();
+        Set<String> codecMediaTypes = getMimesOfAvailableCodecs(SELECT_VIDEO, SELECT_HARDWARE);
+        PerformancePoint PP4k60 = new PerformancePoint(3840, 2160, 60);
+        for (String codecMediaType : codecMediaTypes) {
+            ArrayList<String> hwVideoCodecs =
+                    selectHardwareCodecs(codecMediaType, null, null, isEncoder);
+            for (String hwVideoCodec : hwVideoCodecs) {
+                MediaCodec codec = MediaCodec.createByCodecName(hwVideoCodec);
+                CodecCapabilities capabilities =
+                        codec.getCodecInfo().getCapabilitiesForType(codecMediaType);
+                List<PerformancePoint> pps =
+                        capabilities.getVideoCapabilities().getSupportedPerformancePoints();
+                for (PerformancePoint pp : pps) {
+                    if (pp.covers(PP4k60)) {
+                        codecSet.add(hwVideoCodec);
+                        Log.d(LOG_TAG,
+                                "Performance point 4k60 supported by codec: " + hwVideoCodec);
+                        break;
+                    }
+                }
+                codec.release();
+            }
+        }
+        return codecSet;
+    }
+
+    /**
+     * Validates AV1 hardware decoder is present and supports: Main 10, Level 4.1, Film Grain
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    // TODO(b/218771970) Add @CddTest annotation
+    public void testAV1HwDecoderRequirements() throws Exception {
+        MediaFormat format = MediaFormat.createVideoFormat(MIMETYPE_VIDEO_AV1, 1920, 1080);
+        format.setInteger(MediaFormat.KEY_FRAME_RATE, 60);
+        ArrayList<MediaFormat> formats = new ArrayList<>();
+        formats.add(format);
+        ArrayList<String> av1HwDecoders =
+                selectHardwareCodecs(MIMETYPE_VIDEO_AV1, formats, null, false);
+        boolean oneCodecDecoding = false;
+        for (String codec : av1HwDecoders) {
+            Decode decode = new Decode(MIMETYPE_VIDEO_AV1, FILE_AV1_REQ_SUPPORT, codec, true);
+            double achievedRate = decode.doDecode();
+            if (achievedRate > 0) {
+                oneCodecDecoding = true;
+            }
+        }
+        if (Utils.isTPerfClass()) {
+            assertTrue("One AV1 HW decoder with supported features required for MPC >= Android T",
+                    oneCodecDecoding);
+        } else {
+            int pc = oneCodecDecoding ? Build.VERSION_CODES.TIRAMISU : 0;
+            DeviceReportLog log =
+                    new DeviceReportLog("MediaPerformanceClassLogs", "VideoCodecRequirements");
+            log.addValue("AV1DecoderFeatureSupport", oneCodecDecoding, ResultType.NEUTRAL,
+                    ResultUnit.NONE);
+            // TODO(b/218771970) Log CDD sections
+            log.setSummary(
+                    "Video Codec Requirements: AV1 HW decoder: Main 10, Level 4.1, Film Grain", pc,
+                    ResultType.HIGHER_BETTER, ResultUnit.NONE);
+            log.submit(InstrumentationRegistry.getInstrumentation());
+        }
+    }
+
+    /**
+     * Validates if a hardware decoder that supports 4k60 is present
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    // TODO(b/218771970) Add @CddTest annotation
+    public void test4k60Decoder() throws IOException {
+        Set<String> decoderSet = get4k60HwCodecSet(false);
+        boolean oneCodecSupportsRequiredPerformance = !decoderSet.isEmpty();
+
+        if (Utils.isTPerfClass()) {
+            assertTrue("At least one 4k60 HW decoder required for MPC >= Android T",
+                    oneCodecSupportsRequiredPerformance);
+        } else {
+            int pc = oneCodecSupportsRequiredPerformance ? Build.VERSION_CODES.TIRAMISU : 0;
+            DeviceReportLog log =
+                    new DeviceReportLog("MediaPerformanceClassLogs", "VideoCodecRequirements");
+            log.addValue("4k60DecodeHW", oneCodecSupportsRequiredPerformance, ResultType.NEUTRAL,
+                    ResultUnit.NONE);
+            // TODO(b/218771970) Log CDD sections
+            log.setSummary("Video Codec Requirements: 1 HW video decoder supporting 4K60", pc,
+                    ResultType.HIGHER_BETTER, ResultUnit.NONE);
+            log.submit(InstrumentationRegistry.getInstrumentation());
+        }
+    }
+
+    /**
+     * Validates if a hardware encoder that supports 4k60 is present
+     */
+    @LargeTest
+    @Test(timeout = CodecTestBase.PER_TEST_TIMEOUT_LARGE_TEST_MS)
+    // TODO(b/218771970) Add @CddTest annotation
+    public void test4k60Encoder() throws IOException {
+        Set<String> encoderSet = get4k60HwCodecSet(true);
+        boolean oneCodecSupportsRequiredPerformance = !encoderSet.isEmpty();
+
+        if (Utils.isTPerfClass()) {
+            assertTrue("At least one 4k60 HW encoder required for MPC >= Android T",
+                    oneCodecSupportsRequiredPerformance);
+        } else {
+            int pc = oneCodecSupportsRequiredPerformance ? Build.VERSION_CODES.TIRAMISU : 0;
+            DeviceReportLog log =
+                    new DeviceReportLog("MediaPerformanceClassLogs", "VideoCodecRequirements");
+            log.addValue("4k60EncodeHW", oneCodecSupportsRequiredPerformance, ResultType.NEUTRAL,
+                    ResultUnit.NONE);
+            // TODO(b/218771970) Log CDD sections
+            log.setSummary("Video Codec Requirements: 1 HW video encoder supporting 4K60", pc,
+                    ResultType.HIGHER_BETTER, ResultUnit.NONE);
+            log.submit(InstrumentationRegistry.getInstrumentation());
+        }
+    }
+}
diff --git a/tests/tests/companion/common/src/android/companion/cts/common/CompanionService.kt b/tests/tests/companion/common/src/android/companion/cts/common/CompanionService.kt
index 4d09333..7ca994b 100644
--- a/tests/tests/companion/common/src/android/companion/cts/common/CompanionService.kt
+++ b/tests/tests/companion/common/src/android/companion/cts/common/CompanionService.kt
@@ -59,6 +59,7 @@
     override fun onDeviceAppeared(associationInfo: AssociationInfo) {
         Log.d(TAG, "$this.onDevice_Appeared(), association=$associationInfo")
         _connectedDevices[associationInfo.id] = associationInfo
+
         super.onDeviceAppeared(associationInfo)
     }
 
@@ -86,6 +87,10 @@
         instanceHolder.instance = null
         super.onDestroy()
     }
+
+    fun removeConnectedDevice(associationId: Int) {
+        _connectedDevices.remove(associationId)
+    }
 }
 
 sealed class InstanceHolder<T : CompanionService<T>> {
@@ -127,6 +132,13 @@
         }
         if (!gone) throw AssertionError("""Association with $associationId hasn't "disappeared"""")
     }
+
+    // This is a useful function to use to conveniently "forget" that a device is currently present.
+    // Use to bypass the "unbinding while there are connected devices" for simulated devices.
+    // (Don't worry! they would have removed themselves after 1 minute anyways!)
+    fun forgetDevicePresence(associationId: Int) {
+        instance?.removeConnectedDevice(associationId)
+    }
 }
 
 class PrimaryCompanionService : CompanionService<PrimaryCompanionService>(Companion) {
diff --git a/tests/tests/companion/common/src/android/companion/cts/common/TestBase.kt b/tests/tests/companion/common/src/android/companion/cts/common/TestBase.kt
index 2525769..8c03abd 100644
--- a/tests/tests/companion/common/src/android/companion/cts/common/TestBase.kt
+++ b/tests/tests/companion/common/src/android/companion/cts/common/TestBase.kt
@@ -36,11 +36,14 @@
 import org.junit.AssumptionViolatedException
 import org.junit.Before
 import java.io.IOException
+import kotlin.test.assertContains
+import kotlin.test.assertContentEquals
 import kotlin.test.assertEquals
 import kotlin.test.assertFalse
 import kotlin.test.assertIs
 import kotlin.test.assertTrue
 import kotlin.time.Duration
+import kotlin.time.Duration.Companion.milliseconds
 import kotlin.time.Duration.Companion.seconds
 
 /**
@@ -156,6 +159,89 @@
         expected = expected)
 
 /**
+ * Assert that CDM binds valid CompanionDeviceServices, both primary and secondary.
+ * Use when services are expected to switch its state to "bound".
+ */
+fun assertValidCompanionDeviceServicesBind() =
+        assertTrue("Both valid CompanionDeviceServices - Primary and Secondary - should bind") {
+            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
+                PrimaryCompanionService.isBound && SecondaryCompanionService.isBound
+            }
+        }
+
+/**
+ * Assert both primary and secondary CompanionDeviceServices stay bound.
+ * Use when services are expected to be in "bound" state already.
+ */
+fun assertValidCompanionDeviceServicesRemainBound() =
+        assertFalse("Both valid CompanionDeviceServices should stay bound") {
+            waitFor(timeout = 3.seconds, interval = 100.milliseconds) {
+                !PrimaryCompanionService.isBound || !SecondaryCompanionService.isBound
+            }
+        }
+
+/**
+ * Assert that CDM unbinds valid CompanionDeviceServices, both primary and secondary.
+ * Use when services are expected to switch its state to "unbound".
+ */
+fun assertValidCompanionDeviceServicesUnbind() =
+        assertTrue("CompanionDeviceServices should not bind") {
+            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
+                !PrimaryCompanionService.isBound && !SecondaryCompanionService.isBound
+            }
+        }
+
+/**
+ * Assert that neither primary nor secondary CompanionDeviceService is bound.
+ * Use when services are expected to be in "unbound" state already.
+ */
+fun assertValidCompanionDeviceServicesRemainUnbound() =
+        assertFalse("CompanionDeviceServices should not be bound") {
+            waitFor(timeout = 3.seconds, interval = 100.milliseconds) {
+                PrimaryCompanionService.isBound || SecondaryCompanionService.isBound
+            }
+        }
+
+/**
+ * Assert that CDM did not bind invalid CompanionDeviceServices
+ * (i.e. missing permission or intent-filter).
+ */
+fun assertInvalidCompanionDeviceServicesNotBound() =
+        assertFalse("CompanionDeviceServices that do not require " +
+                "BIND_COMPANION_DEVICE_SERVICE permission or do not declare an intent-filter for " +
+                "\"android.companion.CompanionDeviceService\" action should not be bound") {
+            MissingPermissionCompanionService.isBound ||
+                    MissingIntentFilterActionCompanionService.isBound
+    }
+
+/**
+ * Assert that device (dis)appearance detection callback is only triggered for the primary
+ * CompanionDeviceService and not on any of the non-primary or invalid CompanionDeviceServices.
+ */
+fun assertOnlyPrimaryCompanionDeviceServiceNotified(associationId: Int, appeared: Boolean) {
+    val snapshotSecondary = HashSet(SecondaryCompanionService.connectedDevices)
+    val snapshotUnauthorized = HashSet(MissingPermissionCompanionService.connectedDevices)
+    val snapshotInvalid = HashSet(MissingIntentFilterActionCompanionService.connectedDevices)
+
+    // Check that the primary CompanionDeviceService received onDevice(Dis)Appeared() callback
+    if (appeared) {
+        PrimaryCompanionService.waitAssociationToAppear(associationId)
+        assertContains(PrimaryCompanionService.associationIdsForConnectedDevices, associationId)
+    } else {
+        PrimaryCompanionService.waitAssociationToDisappear(associationId)
+        assertFalse(PrimaryCompanionService.associationIdsForConnectedDevices
+                .contains(associationId))
+    }
+
+    // ... while neither the non-primary nor incorrectly defined CompanionDeviceServices -
+    // have NOT. (Give it 1 more second.)
+    sleepFor(1.seconds)
+    assertContentEquals(snapshotSecondary, SecondaryCompanionService.connectedDevices)
+    assertContentEquals(snapshotUnauthorized, MissingPermissionCompanionService.connectedDevices)
+    assertContentEquals(snapshotInvalid, MissingIntentFilterActionCompanionService.connectedDevices)
+}
+
+/**
  * @return whether the condition was met before time ran out.
  */
 fun waitFor(
diff --git a/tests/tests/companion/core/src/android/companion/cts/core/ObservingDevicePresenceTest.kt b/tests/tests/companion/core/src/android/companion/cts/core/ObservingDevicePresenceTest.kt
index 9bc5c53..4c0d4bf 100644
--- a/tests/tests/companion/core/src/android/companion/cts/core/ObservingDevicePresenceTest.kt
+++ b/tests/tests/companion/core/src/android/companion/cts/core/ObservingDevicePresenceTest.kt
@@ -1,25 +1,40 @@
+/*
+ * Copyright (C) 2022 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 android.companion.cts.core
 
 import android.Manifest
 import android.companion.cts.common.MAC_ADDRESS_A
-import android.companion.cts.common.MissingIntentFilterActionCompanionService
-import android.companion.cts.common.MissingPermissionCompanionService
+import android.companion.cts.common.MAC_ADDRESS_B
 import android.companion.cts.common.PrimaryCompanionService
 import android.companion.cts.common.SecondaryCompanionService
+import android.companion.cts.common.assertValidCompanionDeviceServicesBind
+import android.companion.cts.common.assertValidCompanionDeviceServicesRemainBound
+import android.companion.cts.common.assertValidCompanionDeviceServicesRemainUnbound
+import android.companion.cts.common.assertValidCompanionDeviceServicesUnbind
 import android.companion.cts.common.assertEmpty
-import android.companion.cts.common.sleepFor
+import android.companion.cts.common.assertInvalidCompanionDeviceServicesNotBound
+import android.companion.cts.common.assertOnlyPrimaryCompanionDeviceServiceNotified
 import android.companion.cts.common.toUpperCaseString
-import android.companion.cts.common.waitFor
 import android.platform.test.annotations.AppModeFull
 import androidx.test.ext.junit.runners.AndroidJUnit4
 import org.junit.Test
 import org.junit.runner.RunWith
 import kotlin.test.assertContentEquals
 import kotlin.test.assertFailsWith
-import kotlin.test.assertFalse
-import kotlin.test.assertTrue
-import kotlin.time.Duration.Companion.milliseconds
-import kotlin.time.Duration.Companion.seconds
 
 /**
  * Test CDM APIs for observing device presence.
@@ -41,13 +56,9 @@
 
         simulateDeviceAppeared(associationId)
 
-        // Make sure CDM does not bind CompanionDeviceServices
-        assertFalse("CompanionDeviceServices should not be bound when observing device presence " +
-                "is off") {
-            waitFor(timeout = 3.seconds, interval = 100.milliseconds) {
-                PrimaryCompanionService.isBound || SecondaryCompanionService.isBound
-            }
-        }
+        // Make sure CDM does not bind application
+        assertValidCompanionDeviceServicesRemainUnbound()
+
         // ... and does not trigger onDeviceAppeared ()
         assertEmpty(PrimaryCompanionService.connectedDevices)
         assertEmpty(SecondaryCompanionService.connectedDevices)
@@ -87,53 +98,26 @@
         // Simulate device appeared.
         simulateDeviceAppeared(associationId)
 
-        // Make sure CDM binds valid CompanionDeviceServices...
-        assertTrue("Both valid CompanionDeviceServices - Primary and Secondary - should be bound " +
-                "now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                PrimaryCompanionService.isBound && SecondaryCompanionService.isBound
-            }
-        }
-        // ... and does not bind incorrectly defined CompanionDeviceServices.
-        assertFalse("CompanionDeviceServices that do not require " +
-                "BIND_COMPANION_DEVICE_SERVICE permission or do not declare an intent-filter for " +
-                "\"android.companion.CompanionDeviceService\" action should not be bound") {
-            MissingPermissionCompanionService.isBound ||
-                    MissingIntentFilterActionCompanionService.isBound
-        }
+        // Make sure valid CompanionDeviceServices are bound
+        assertValidCompanionDeviceServicesBind()
+
+        // ... and incorrectly defined CompanionDeviceServices are not
+        assertInvalidCompanionDeviceServicesNotBound()
 
         // Check that only the primary CompanionDeviceService has received the onDeviceAppeared()
         // callback...
-        PrimaryCompanionService.waitAssociationToAppear(associationId)
-        assertContentEquals(
-                actual = PrimaryCompanionService.associationIdsForConnectedDevices,
-                expected = setOf(associationId)
-        )
-        // ... while the non-primary and incorrectly defined CompanionDeviceServices - have NOT.
-        // (Give it 1 more second.)
-        sleepFor(1.seconds)
-        assertEmpty(SecondaryCompanionService.connectedDevices)
-        assertEmpty(MissingPermissionCompanionService.connectedDevices)
-        assertEmpty(MissingIntentFilterActionCompanionService.connectedDevices)
+        assertOnlyPrimaryCompanionDeviceServiceNotified(associationId, appeared = true)
 
-        assertFalse("Both valid CompanionDeviceServices - Primary and Secondary - should stay " +
-                "bound ") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound || !SecondaryCompanionService.isBound
-            }
-        }
+        // Make sure that both primary and secondary CompanionDeviceServices still bind.
+        assertValidCompanionDeviceServicesRemainBound()
 
         simulateDeviceDisappeared(associationId)
 
         // Check that only the primary services has received the onDeviceDisappeared() callback.
-        PrimaryCompanionService.waitAssociationToDisappear(associationId)
-        assertEmpty(PrimaryCompanionService.connectedDevices)
+        assertOnlyPrimaryCompanionDeviceServiceNotified(associationId, appeared = false)
 
-        assertTrue("Both Services - Primary and Secondary - should be unbound now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound && !SecondaryCompanionService.isBound
-            }
-        }
+        // Both primary and secondary CompanionDeviceServices should unbind now.
+        assertValidCompanionDeviceServicesUnbind()
     }
 
     @Test
@@ -148,16 +132,12 @@
             cdm.stopObservingDevicePresence(MAC_ADDRESS_A.toUpperCaseString())
         }
 
-        // Simulate device disappeared.
+        // Simulate device appeared.
         simulateDeviceAppeared(associationId)
 
-        // Make sure CDM does not bind CompanionDeviceServices
-        assertFalse("CompanionDeviceServices should not be bound when observing device presence " +
-                "is off") {
-            waitFor(timeout = 3.seconds, interval = 100.milliseconds) {
-                PrimaryCompanionService.isBound || SecondaryCompanionService.isBound
-            }
-        }
+        // Make sure CDM does not bind application
+        assertValidCompanionDeviceServicesRemainUnbound()
+
         // ... and does not trigger onDeviceAppeared ()
         assertEmpty(PrimaryCompanionService.connectedDevices)
         assertEmpty(SecondaryCompanionService.connectedDevices)
@@ -166,6 +146,130 @@
         simulateDeviceDisappeared(associationId)
     }
 
+    @Test
+    fun test_startObservingDevicePresence_alreadyPresent() {
+        // Create a regular (not self-managed) association.
+        targetApp.associate(MAC_ADDRESS_A)
+        val associationId = cdm.myAssociations[0].id
+
+        // Simulate device appearing before observing it
+        simulateDeviceAppeared(associationId)
+
+        // Make sure CDM doesn't bind application yet
+        assertValidCompanionDeviceServicesRemainUnbound()
+
+        // Start observing presence of an already present device.
+        withShellPermissionIdentity(Manifest.permission.REQUEST_OBSERVE_COMPANION_DEVICE_PRESENCE) {
+            cdm.startObservingDevicePresence(MAC_ADDRESS_A.toUpperCaseString())
+        }
+
+        // Make sure valid CompanionDeviceServices are bound
+        assertValidCompanionDeviceServicesBind()
+        assertInvalidCompanionDeviceServicesNotBound()
+
+        // Clean-up
+        simulateDeviceDisappeared(associationId)
+    }
+
+    @Test
+    fun test_startObservingDevicePresence_multipleDevices() {
+        // Create two regular (not self-managed) associations.
+        targetApp.associate(MAC_ADDRESS_A)
+        targetApp.associate(MAC_ADDRESS_B)
+        val idA = cdm.myAssociations[0].id
+        val idB = cdm.myAssociations[1].id
+
+        // Start observing presence of both devices.
+        withShellPermissionIdentity(Manifest.permission.REQUEST_OBSERVE_COMPANION_DEVICE_PRESENCE) {
+            cdm.startObservingDevicePresence(MAC_ADDRESS_A.toUpperCaseString())
+            cdm.startObservingDevicePresence(MAC_ADDRESS_B.toUpperCaseString())
+        }
+
+        simulateDeviceAppeared(idA)
+
+        // Assert only the valid CompanionDeviceServices (primary + secondary) bind
+        assertValidCompanionDeviceServicesBind()
+        assertInvalidCompanionDeviceServicesNotBound()
+
+        // Assert only the primary CompanionDeviceService is notified of device A's appearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idA, appeared = true)
+        assertContentEquals(
+                actual = PrimaryCompanionService.associationIdsForConnectedDevices,
+                expected = setOf(idA)
+        )
+
+        simulateDeviceAppeared(idB)
+
+        // Assert only the primary CompanionDeviceService is notified of device B's appearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idB, appeared = true)
+        assertContentEquals(
+                actual = PrimaryCompanionService.associationIdsForConnectedDevices,
+                expected = setOf(idA, idB)
+        )
+
+        // Make sure both valid services stay bound.
+        assertValidCompanionDeviceServicesRemainBound()
+
+        // "Disconnect" first device (A).
+        simulateDeviceDisappeared(idA)
+
+        // Assert only the primary CompanionDeviceService is notified of device A's disappearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idA, appeared = false)
+
+        // Both valid services should stay bound for as long as there is at least one connected
+        // device - device B in this case.
+        assertValidCompanionDeviceServicesRemainBound()
+
+        // "Disconnect" second (and last remaining) device (B).
+        simulateDeviceDisappeared(idB)
+
+        // Assert only the primary CompanionDeviceService is notified of device B's disappearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idB, appeared = false)
+
+        // Both valid services should unbind now.
+        assertValidCompanionDeviceServicesUnbind()
+    }
+
+    @Test
+    fun test_stopObservingDevicePresence_unbindsApplication() {
+        // Create two regular (not self-managed) association.s
+        targetApp.associate(MAC_ADDRESS_A)
+        targetApp.associate(MAC_ADDRESS_B)
+        val idA = cdm.myAssociations[0].id
+        val idB = cdm.myAssociations[1].id
+
+        // Start observing presence of both devices.
+        withShellPermissionIdentity(Manifest.permission.REQUEST_OBSERVE_COMPANION_DEVICE_PRESENCE) {
+            cdm.startObservingDevicePresence(MAC_ADDRESS_A.toUpperCaseString())
+            cdm.startObservingDevicePresence(MAC_ADDRESS_B.toUpperCaseString())
+        }
+
+        simulateDeviceAppeared(idA)
+        simulateDeviceAppeared(idB)
+
+        // Assert only the valid CompanionDeviceServices (primary + secondary) bind
+        assertValidCompanionDeviceServicesBind()
+        assertInvalidCompanionDeviceServicesNotBound()
+
+        // Stop observing presence of device A.
+        PrimaryCompanionService.forgetDevicePresence(idA)
+        withShellPermissionIdentity(Manifest.permission.REQUEST_OBSERVE_COMPANION_DEVICE_PRESENCE) {
+            cdm.stopObservingDevicePresence(MAC_ADDRESS_A.toUpperCaseString())
+        }
+
+        // Make sure both valid services stay bound.
+        assertValidCompanionDeviceServicesRemainBound()
+
+        // Stop observing presence of device B.
+        PrimaryCompanionService.forgetDevicePresence(idB)
+        withShellPermissionIdentity(Manifest.permission.REQUEST_OBSERVE_COMPANION_DEVICE_PRESENCE) {
+            cdm.stopObservingDevicePresence(MAC_ADDRESS_B.toUpperCaseString())
+        }
+
+        // Both valid services should unbind now.
+        assertValidCompanionDeviceServicesUnbind()
+    }
+
     private fun simulateDeviceAppeared(associationId: Int) = runShellCommand(
             "cmd companiondevice simulate-device-appeared $associationId")
 
diff --git a/tests/tests/companion/core/src/android/companion/cts/core/SelfPresenceReportingTest.kt b/tests/tests/companion/core/src/android/companion/cts/core/SelfPresenceReportingTest.kt
index f34e828..0305da7 100644
--- a/tests/tests/companion/core/src/android/companion/cts/core/SelfPresenceReportingTest.kt
+++ b/tests/tests/companion/core/src/android/companion/cts/core/SelfPresenceReportingTest.kt
@@ -20,15 +20,14 @@
 import android.companion.cts.common.DEVICE_DISPLAY_NAME_A
 import android.companion.cts.common.DEVICE_DISPLAY_NAME_B
 import android.companion.cts.common.MAC_ADDRESS_A
-import android.companion.cts.common.MissingIntentFilterActionCompanionService
-import android.companion.cts.common.MissingPermissionCompanionService
 import android.companion.cts.common.PrimaryCompanionService
 import android.companion.cts.common.Repeat
 import android.companion.cts.common.RepeatRule
-import android.companion.cts.common.SecondaryCompanionService
-import android.companion.cts.common.assertEmpty
-import android.companion.cts.common.waitFor
-import android.os.SystemClock.sleep
+import android.companion.cts.common.assertValidCompanionDeviceServicesBind
+import android.companion.cts.common.assertValidCompanionDeviceServicesRemainBound
+import android.companion.cts.common.assertValidCompanionDeviceServicesUnbind
+import android.companion.cts.common.assertInvalidCompanionDeviceServicesNotBound
+import android.companion.cts.common.assertOnlyPrimaryCompanionDeviceServiceNotified
 import android.platform.test.annotations.AppModeFull
 import androidx.test.ext.junit.runners.AndroidJUnit4
 import org.junit.Rule
@@ -36,10 +35,6 @@
 import org.junit.runner.RunWith
 import kotlin.test.assertContentEquals
 import kotlin.test.assertFailsWith
-import kotlin.test.assertFalse
-import kotlin.test.assertTrue
-import kotlin.time.Duration.Companion.milliseconds
-import kotlin.time.Duration.Companion.seconds
 
 /**
  * Tests CDM APIs for notifying the presence of status of the companion devices for self-managed
@@ -65,51 +60,23 @@
 
         cdm.notifyDeviceAppeared(associationId)
 
-        assertTrue("Both valid CompanionDeviceServices - Primary and Secondary - should be bound " +
-                "now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                PrimaryCompanionService.isBound && SecondaryCompanionService.isBound
-            }
-        }
-        assertFalse("CompanionDeviceServices that do not require " +
-                "BIND_COMPANION_DEVICE_SERVICE permission or do not declare an intent-filter for " +
-                "\"android.companion.CompanionDeviceService\" action should not be bound") {
-            MissingPermissionCompanionService.isBound ||
-                    MissingIntentFilterActionCompanionService.isBound
-        }
+        // Assert only the valid CompanionDeviceServices (primary + secondary) are bound
+        assertValidCompanionDeviceServicesBind()
+        assertInvalidCompanionDeviceServicesNotBound()
 
-        // Check that only the primary CompanionDeviceService has received the onDeviceAppeared()
-        // callback...
-        PrimaryCompanionService.waitAssociationToAppear(associationId)
-        assertContentEquals(
-                actual = PrimaryCompanionService.associationIdsForConnectedDevices,
-                expected = setOf(associationId)
-        )
-        // ... while neither the non-primary nor incorrectly defined CompanionDeviceServices -
-        // have NOT. (Give it 1 more second.)
-        sleep(1000)
-        assertEmpty(SecondaryCompanionService.connectedDevices)
-        assertEmpty(MissingPermissionCompanionService.connectedDevices)
-        assertEmpty(MissingIntentFilterActionCompanionService.connectedDevices)
+        // Assert only the primary CompanionDeviceService is notified of device appearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(associationId, appeared = true)
 
-        assertFalse("Both valid CompanionDeviceServices - Primary and Secondary - should stay " +
-                "bound ") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound || !SecondaryCompanionService.isBound
-            }
-        }
+        // Assert both valid CompanionDeviceServices stay bound
+        assertValidCompanionDeviceServicesRemainBound()
 
         cdm.notifyDeviceDisappeared(associationId)
 
-        // Check that only the primary services has received the onDeviceDisappeared() callback.
-        PrimaryCompanionService.waitAssociationToDisappear(associationId)
-        assertEmpty(PrimaryCompanionService.connectedDevices)
+        // Assert only the primary CompanionDeviceService is notified of device disappearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(associationId, appeared = false)
 
-        assertTrue("Both Services - Primary and Secondary - should be unbound now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound && !SecondaryCompanionService.isBound
-            }
-        }
+        // Assert both services are unbound now
+        assertValidCompanionDeviceServicesUnbind()
     }
 
     @Test
@@ -119,71 +86,47 @@
 
         cdm.notifyDeviceAppeared(idA)
 
-        assertTrue("Both valid CompanionDeviceServices - Primary and Secondary - should be bound " +
-                "now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                PrimaryCompanionService.isBound && SecondaryCompanionService.isBound
-            }
-        }
-        assertFalse("CompanionDeviceServices that do not require " +
-                "BIND_COMPANION_DEVICE_SERVICE permission or do not declare an intent-filter for " +
-                "\"android.companion.CompanionDeviceService\" action should not be bound") {
-            MissingPermissionCompanionService.isBound ||
-                    MissingIntentFilterActionCompanionService.isBound
-        }
+        // Assert only the valid CompanionDeviceServices (primary + secondary) are bound
+        assertValidCompanionDeviceServicesBind()
+        assertInvalidCompanionDeviceServicesNotBound()
 
-        // Check that only the primary services has received the onDeviceAppeared() callback...
-        PrimaryCompanionService.waitAssociationToAppear(idA)
+        // Assert only the primary CompanionDeviceService is notified of device A's appearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idA, appeared = true)
         assertContentEquals(
-            actual = PrimaryCompanionService.associationIdsForConnectedDevices,
-            expected = setOf(idA)
+                actual = PrimaryCompanionService.associationIdsForConnectedDevices,
+                expected = setOf(idA)
         )
-        // ... while neither the non-primary nor incorrectly defined CompanionDeviceServices -
-        // have NOT. (Give it 1 more second.)
-        sleep(1000)
-        assertEmpty(SecondaryCompanionService.connectedDevices)
-        assertEmpty(MissingPermissionCompanionService.connectedDevices)
-        assertEmpty(MissingIntentFilterActionCompanionService.connectedDevices)
 
         cdm.notifyDeviceAppeared(idB)
 
-        // Check that only the primary services has received the onDeviceAppeared() callback.
-        PrimaryCompanionService.waitAssociationToAppear(idB)
+        // Assert only the primary CompanionDeviceService is notified of device B's appearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idB, appeared = true)
         assertContentEquals(
             actual = PrimaryCompanionService.associationIdsForConnectedDevices,
             expected = setOf(idA, idB)
         )
 
         // Make sure both valid services stay bound.
-        assertFalse("Both valid CompanionDeviceServices - Primary and Secondary - should stay " +
-                "bound ") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound || !SecondaryCompanionService.isBound
-            }
-        }
+        assertValidCompanionDeviceServicesRemainBound()
 
         // "Disconnect" first device (A).
         cdm.notifyDeviceDisappeared(idA)
 
-        PrimaryCompanionService.waitAssociationToDisappear(idA)
+        // Assert only the primary CompanionDeviceService is notified of device A's disappearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idA, appeared = false)
+
         // Both valid services should stay bound for as long as there is at least one connected
         // device - device B in this case.
-        assertFalse("Both valid CompanionDeviceServices - Primary and Secondary - should stay " +
-                "bound ") {
-            waitFor(timeout = 3.seconds, interval = 1.milliseconds) {
-                !PrimaryCompanionService.isBound || !SecondaryCompanionService.isBound
-            }
-        }
+        assertValidCompanionDeviceServicesRemainBound()
 
-        // "Disconnect" second device (B).
+        // "Disconnect" second (and last remaining) device (B).
         cdm.notifyDeviceDisappeared(idB)
 
-        PrimaryCompanionService.waitAssociationToDisappear(idB)
-        assertTrue("Both Services - Primary and Secondary - should be unbound now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound && !SecondaryCompanionService.isBound
-            }
-        }
+        // Assert only the primary CompanionDeviceService is notified of device B's disappearance
+        assertOnlyPrimaryCompanionDeviceServiceNotified(idB, appeared = false)
+
+        // Both valid services should unbind now.
+        assertValidCompanionDeviceServicesUnbind()
     }
 
     @Test
@@ -220,21 +163,12 @@
         }
 
         // Make sure CDM binds both CompanionDeviceServices.
-        assertTrue("Both valid CompanionDeviceServices - Primary and Secondary - should be bound " +
-                "now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                PrimaryCompanionService.isBound && SecondaryCompanionService.isBound
-            }
-        }
+        assertValidCompanionDeviceServicesBind()
 
         // Notify CDM that devices has disconnected.
         cdm.notifyDeviceDisappeared(associationId)
 
         // Make sure CDM unbinds both CompanionDeviceServices.
-        assertTrue("Both Services - Primary and Secondary - should be unbound now") {
-            waitFor(timeout = 1.seconds, interval = 100.milliseconds) {
-                !PrimaryCompanionService.isBound && !SecondaryCompanionService.isBound
-            }
-        }
+        assertValidCompanionDeviceServicesUnbind()
     }
 }
\ No newline at end of file
diff --git a/tests/tests/cronet/Android.bp b/tests/tests/cronet/Android.bp
deleted file mode 100644
index fc8ec7f..0000000
--- a/tests/tests/cronet/Android.bp
+++ /dev/null
@@ -1,40 +0,0 @@
-// Copyright (C) 2019 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.
-
-
-// TODO: Move this target to cts/tests/tests/net/cronet
-package {
-    default_applicable_licenses: ["Android-Apache-2.0"],
-}
-
-android_test {
-    name: "CtsCronetTestCases",
-    defaults: ["cts_defaults"],
-
-    // Include both the 32 and 64 bit versions
-    compile_multilib: "both",
-
-    static_libs: [
-        "CronetApiCommonTests",
-        "ctstestrunner-axt",
-    ],
-
-    // Tag this module as a cts test artifact
-    test_suites: [
-        "cts",
-        "general-tests",
-        "mts-cronet",
-    ],
-
-}
diff --git a/tests/tests/cronet/AndroidManifest.xml b/tests/tests/cronet/AndroidManifest.xml
deleted file mode 100644
index b7ae844..0000000
--- a/tests/tests/cronet/AndroidManifest.xml
+++ /dev/null
@@ -1,36 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
- * Copyright (C) 2007 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.
- -->
-
-<manifest xmlns:android="http://schemas.android.com/apk/res/android"
-    package="android.cronet.cts" >
-
-    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
-    <uses-permission android:name="android.permission.INTERNET" />
-
-    <application android:usesCleartextTraffic="true">
-        <uses-library android:name="android.test.runner" />
-        <uses-library android:name="org.chromium.net.cronet" />
-    </application>
-
-    <instrumentation android:name="androidx.test.runner.AndroidJUnitRunner"
-                     android:targetPackage="android.cronet.cts"
-                     android:label="CTS tests of android.cronet">
-        <meta-data android:name="listener"
-            android:value="com.android.cts.runner.CtsTestRunListener" />
-    </instrumentation>
-
-</manifest>
diff --git a/tests/tests/cronet/AndroidTest.xml b/tests/tests/cronet/AndroidTest.xml
deleted file mode 100644
index 79c37f7..0000000
--- a/tests/tests/cronet/AndroidTest.xml
+++ /dev/null
@@ -1,30 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2019 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.
--->
-<configuration description="Config for CTS Cronet test cases">
-    <option name="test-suite-tag" value="cts" />
-    <option name="config-descriptor:metadata" key="component" value="networking" />
-    <option name="config-descriptor:metadata" key="parameter" value="instant_app" />
-    <option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
-    <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
-    <target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
-        <option name="cleanup-apks" value="true" />
-        <option name="test-file-name" value="CtsCronetTestCases.apk" />
-    </target_preparer>
-    <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
-        <option name="package" value="android.cronet.cts" />
-        <option name="runtime-hint" value="10s" />
-    </test>
-</configuration>
\ No newline at end of file
diff --git a/tests/tests/cronet/OWNERS b/tests/tests/cronet/OWNERS
deleted file mode 100644
index 9b1555e..0000000
--- a/tests/tests/cronet/OWNERS
+++ /dev/null
@@ -1,3 +0,0 @@
-# Bug component: 31808
-set noparent
-include platform/packages/modules/Connectivity:/tests/cts/OWNERS
diff --git a/tests/tests/cronet/TEST_MAPPING b/tests/tests/cronet/TEST_MAPPING
deleted file mode 100644
index b1f3088..0000000
--- a/tests/tests/cronet/TEST_MAPPING
+++ /dev/null
@@ -1,7 +0,0 @@
-{
-  "presubmit": [
-    {
-      "name": "CtsCronetTestCases"
-    }
-  ]
-}
diff --git a/tests/tests/dreams/src/android/service/dreams/cts/DreamOverlayTest.java b/tests/tests/dreams/src/android/service/dreams/cts/DreamOverlayTest.java
index fed0c91..8c836fa 100644
--- a/tests/tests/dreams/src/android/service/dreams/cts/DreamOverlayTest.java
+++ b/tests/tests/dreams/src/android/service/dreams/cts/DreamOverlayTest.java
@@ -21,6 +21,7 @@
 import android.content.Context;
 import android.content.Intent;
 import android.content.IntentFilter;
+import android.content.pm.PackageManager;
 import android.server.wm.ActivityManagerTestBase;
 import android.server.wm.DreamCoordinator;
 import android.view.Display;
@@ -31,6 +32,7 @@
 import static com.google.common.truth.Truth.assertThat;
 
 import org.junit.After;
+import org.junit.Assume;
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
@@ -84,6 +86,9 @@
 
     @Test
     public void testDreamOverlayAppearance() throws InterruptedException {
+        Assume.assumeFalse(mContext.getPackageManager().hasSystemFeature(
+                PackageManager.FEATURE_AUTOMOTIVE));
+
         // Listen for the overlay to be shown
         final CountDownLatch countDownLatch = new CountDownLatch(1);
         mContext.registerReceiver(
diff --git a/tests/tests/graphics/res/xml/valid_themes.xml b/tests/tests/graphics/res/xml/valid_themes.xml
index 64437f9..ad8b953 100644
--- a/tests/tests/graphics/res/xml/valid_themes.xml
+++ b/tests/tests/graphics/res/xml/valid_themes.xml
@@ -19,48 +19,48 @@
     <theme color="ffb9567a">
         <spritz>ffffff,fffbfa,ffecf1,f9dbe2,dcc0c6,c0a4ab,a48a91,877076,6f595e,564147,3e2b31,27171c,000000,ffffff,fffbfa,ffecf1,f2dee2,d5c2c6,b9a6aa,9e8c90,827276,6a5a5e,514347,392d30,23191b,000000,ffffff,fffbfa,ffecf1,ffd9e2,e2bdc6,c5a2ab,a98891,8d6e76,74565f,5b3f47,422a31,2b151c,000000,ffffff,fffbfa,f6efef,e8e1e1,cbc5c5,b0aaaa,958f90,7a7575,625d5e,4a4646,333030,1e1b1b,000000,ffffff,fffbfa,f6efef,e8e1e1,cbc5c5,b0aaaa,958f90,7a7575,625d5e,4a4646,333030,1e1b1b,000000</spritz>
         <tonal_spot>ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,e495ad,c57b93,a76078,8c4a60,703349,541d32,39071d,000000,ffffff,fffbfa,ffecf1,ffd9e2,e2bdc6,c5a2ab,a98891,8d6e76,74565f,5b3f47,422a31,2b151c,000000,ffffff,fffbfa,ffeddf,ffdcbf,efbc94,d1a27a,b48762,976d4a,7c5635,623f20,48290b,2f1500,000000,ffffff,fffbfa,faeeef,ebe0e1,cfc4c5,b3a8aa,988f90,7d7475,655c5e,4c4546,352f30,201a1c,000000,ffffff,fffbfa,ffecf1,f2dee2,d5c2c6,b9a6aa,9e8c90,827276,6a5a5e,514347,392d30,23191b,000000</tonal_spot>
-        <vibrant>ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,f889ae,d86f94,b85579,9b3e61,7d2649,600d33,3e001c,000000,ffffff,fffbfa,ffecf1,ffd9e4,efb7c7,d29dac,b58392,986977,7e525f,633b48,4a2531,31101d,000000,ffffff,fffbfa,ffecf1,ffd9e4,fcb2c8,de98ad,c07e92,a26378,874c60,6b3648,511f32,370b1d,000000,ffffff,fffbfa,ffecf1,f6dce2,d9c0c6,bca5ab,a18b91,857175,6c5a5e,534247,3c2c31,25181c,000000,ffffff,fffbfa,ffecf1,f9dbe2,dcc0c6,c0a4ab,a48a91,877076,6f595e,564147,3e2b31,27171c,000000</vibrant>
-        <expressive>ffffff,fafcff,e4f2ff,c7e7ff,8bcefd,6eb3e0,5297c4,337da7,0b648e,004c6f,00344e,001e2f,000000,ffffff,fffbfa,ffecf1,ffd9e4,efb7c7,d29dac,b58392,986977,7e525f,633b48,4a2531,31101d,000000,ffffff,fffbfa,ffecf1,ffd9e4,fcb2c8,de98ad,c07e92,a26378,874c60,6b3648,511f32,370b1d,000000,ffffff,fffbfa,ffeded,f4ddde,d7c1c2,bba7a7,9f8c8d,837272,6b5b5b,534344,3b2d2d,241919,000000,ffffff,fffbfa,ffeced,fcdbdb,debfc0,c2a4a5,a68a8b,8a6f70,715859,574142,402b2c,281718,000000</expressive>
+        <vibrant>ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,f889ae,d86f94,b85579,9b3e61,7d2649,600d33,3e001c,000000,ffffff,fffbfa,ffeceb,ffdad9,f5b7b7,d79c9c,b98382,9c6869,815152,663a3b,4c2525,331012,000000,ffffff,fffbfa,ffede7,ffdacf,ffb49d,e49882,c57f6a,a66551,8b4e3c,6e3727,532213,380d03,000000,ffffff,fffbfa,ffecf1,f9dbe2,dcc0c6,c0a4ab,a48a91,877076,6f595e,564147,3e2b31,27171c,000000,ffffff,fffbfa,ffecf1,fcdae2,dfbec6,c3a3ab,a78991,8a6f76,71575f,584047,402a31,29161c,000000</vibrant>
+        <expressive>ffffff,fafcff,e4f2ff,c7e7ff,8bcefd,6eb3e0,5297c4,337da7,0b648e,004c6f,00344e,001e2f,000000,ffffff,fffbfa,ffede4,ffdbc9,f4ba9e,d69f84,b9856c,9b6b53,80543d,653d28,4a2714,311303,000000,ffffff,fcffd6,ecf8ad,dee9a0,c1cd86,a6b16e,8c9656,717b3e,5a6328,424b12,2b3400,181e00,000000,ffffff,fffbfa,ffeded,f4ddde,d7c1c2,bba7a7,9f8c8d,837272,6b5b5b,534344,3b2d2d,241919,000000,ffffff,fffbfa,ffeced,fcdbdb,debfc0,c2a4a5,a68a8b,8a6f70,715859,574142,402b2c,281718,000000</expressive>
         <rainbow>ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,f48aae,d57294,b55779,984061,7b2849,5e1033,3e001c,000000,ffffff,fffbfa,ffecf1,ffd9e2,e2bdc6,c5a2ab,a98891,8d6e76,74565f,5b3f47,422a31,2b151c,000000,ffffff,fffbfa,ffeddf,ffdcbf,efbc94,d1a27a,b48762,976d4a,7c5635,623f20,48290b,2f1500,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000</rainbow>
         <fruit_salad>ffffff,fffbfb,faecff,f1dbff,deb8ff,c499f1,a97ed4,8c64b7,734c9d,5b3383,431a6b,2b0053,000000,ffffff,fffbfb,faecff,f1dbff,dabaf9,be9edc,a384c0,866aa4,6e538b,553b71,3d2458,270d42,000000,ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,e495ad,c57b93,a76078,8c4a60,703349,541d32,39071d,000000,ffffff,fffbfa,ffecf1,f6dce2,d9c0c6,bca5ab,a18b91,857175,6c5a5e,534247,3c2c31,25181c,000000,ffffff,fffbfa,ffecf1,ffd9e2,e2bdc6,c5a2ab,a98891,8d6e76,74565f,5b3f47,422a31,2b151c,000000</fruit_salad>
     </theme>
     <theme color="ffb16307">
         <spritz>ffffff,fffbfa,ffeddf,faddc9,dcc2ae,c0a794,a48c7a,887261,6f5b4a,564334,3e2d1f,27180c,000000,ffffff,fffbfa,ffede0,f3dfd1,d5c3b6,baa89c,9e8e82,837368,6a5b51,51443b,3a2e26,231a12,000000,ffffff,fffbfa,ffeddf,ffdcc1,e2c0a5,c5a58b,aa8b72,8d705a,745943,5a422d,412c19,2a1707,000000,ffffff,fffbfa,f7efec,e8e1de,ccc5c2,b0aaa7,958f8d,7a7572,625e5b,4a4643,33302d,1d1b19,000000,ffffff,fffbfa,f7efec,e8e1de,ccc5c2,b0aaa7,958f8d,7a7572,625e5b,4a4643,33302d,1d1b19,000000</spritz>
         <tonal_spot>ffffff,fffbfa,ffeddf,ffdcbf,ffb879,e19d61,c28349,a46932,88521c,6b3b05,4d2700,2f1500,000000,ffffff,fffbfa,ffeddf,ffdcc1,e2c0a5,c5a58b,aa8b72,8d705a,745943,5a422d,412c19,2a1707,000000,ffffff,fdffd7,eef5be,e0e8b1,c4cb97,a8af7e,8e9565,727a4d,5b6238,444a22,2d330e,191e00,000000,ffffff,fffbfa,faeee8,ece0da,cfc4be,b3a9a3,988f89,7d746f,655d58,4c4641,362f2b,201a16,000000,ffffff,fffbfa,ffede0,f3dfd1,d5c3b6,baa89c,9e8e82,837368,6a5b51,51443b,3a2e26,231a12,000000</tonal_spot>
-        <vibrant>ffffff,fffbfa,ffeddf,ffdcbf,ffb776,f1963f,d17c26,b06306,8f4e00,6d3900,4d2700,2f1500,000000,ffffff,fffbfa,ffecf0,ffd9e3,f0b8c6,d29dab,b68391,986976,7e525e,643b47,4a2531,31111c,000000,ffffff,fffbfa,ffecf0,ffd9e3,fcb2c7,de97ac,c17d91,a26377,874d5f,6c3547,512031,370b1c,000000,ffffff,fffbfa,ffeddf,f6decd,d9c2b2,bda798,a18d7e,857264,6c5b4e,534437,3c2d22,26190f,000000,ffffff,fffbfa,ffeddf,faddc9,dcc2ae,c0a794,a48c7a,887261,6f5b4a,564334,3e2d1f,27180c,000000</vibrant>
-        <expressive>ffffff,fffbfd,f7edff,eadcff,d1bcff,b5a0e8,9a85cc,7e6baf,665395,4e3c7c,372464,220b4e,000000,ffffff,fffbfa,ffedea,ffdad7,f5b8b4,d79c99,ba8380,9c6966,81524f,663b39,4d2524,321110,000000,ffffff,fffbfa,ffedea,ffdad6,ffb3b0,e49794,c67d7a,a76461,8b4c4a,6f3634,542020,380c0c,000000,ffffff,fffbf9,feeedd,efe0cf,d3c4b5,b7a99a,9b8f80,807467,675d50,4f4539,382f24,221a10,000000,ffffff,fffbf9,ffeed9,f5dfc6,d8c4ab,bca891,a08e77,84745e,6b5c48,534432,3b2e1d,241a0a,000000</expressive>
+        <vibrant>ffffff,fffbfa,ffeddf,ffdcbf,ffb776,f1963f,d17c26,b06306,8f4e00,6d3900,4d2700,2f1500,000000,ffffff,fffbf9,ffeedb,ffddb3,e9c08e,cba475,af8a5e,917045,785830,5d411b,442b07,2a1700,000000,ffffff,fffbf8,ffefd2,ffde9c,e7c277,caa75f,ad8c48,907230,775a1a,5c4301,412d00,261900,000000,ffffff,fffbfa,ffeddf,faddc9,dcc2ae,c0a794,a48c7a,887261,6f5b4a,564334,3e2d1f,27180c,000000,ffffff,fffbfa,ffeddf,fddcc4,dfc1a9,c3a58f,a78b76,8a715d,715a47,584331,402c1c,281809,000000</vibrant>
+        <expressive>ffffff,fffbfd,f7edff,eadcff,d1bcff,b5a0e8,9a85cc,7e6baf,665395,4e3c7c,372464,220b4e,000000,ffffff,fffbf7,fbf2b7,ece4a9,d0c88f,b4ad77,99925e,7e7747,656031,4d481c,363107,1f1c00,000000,ffffff,f0fffa,b9ffec,abf0de,8fd4c2,74b8a7,599d8d,3d8173,22695b,005143,00382e,002019,000000,ffffff,fffbf9,feeedd,efe0cf,d3c4b5,b7a99a,9b8f80,807467,675d50,4f4539,382f24,221a10,000000,ffffff,fffbf9,ffeed9,f5dfc6,d8c4ab,bca891,a08e77,84745e,6b5c48,534432,3b2e1d,241a0a,000000</expressive>
         <rainbow>ffffff,fffbfa,ffeddf,ffdcbf,ffb776,ee9744,cf7d2c,af6311,8f4d00,6d3900,4d2700,2f1500,000000,ffffff,fffbfa,ffeddf,ffdcc1,e2c0a5,c5a58b,aa8b72,8d705a,745943,5a422d,412c19,2a1707,000000,ffffff,fdffd7,eef5be,e0e8b1,c4cb97,a8af7e,8e9565,727a4d,5b6238,444a22,2d330e,191e00,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000</rainbow>
         <fruit_salad>ffffff,fffbfa,ffedef,ffdadf,ffb2be,f98b9c,d97082,b85769,9c4052,7d293b,5f1126,400012,000000,ffffff,fffbfa,ffedef,ffdadf,ffb2be,e894a0,c97a86,aa606c,8e4a55,72333e,561c28,3b0714,000000,ffffff,fffbfa,ffeddf,ffdcbf,ffb879,e19d61,c28349,a46932,88521c,6b3b05,4d2700,2f1500,000000,ffffff,fffbfa,ffeddf,f6decd,d9c2b2,bda798,a18d7e,857264,6c5b4e,534437,3c2d22,26190f,000000,ffffff,fffbfa,ffeddf,ffdcc1,e2c0a5,c5a58b,aa8b72,8d705a,745943,5a422d,412c19,2a1707,000000</fruit_salad>
     </theme>
     <theme color="ff6e7e0f">
         <spritz>ffffff,fdfee4,f1f2d8,e3e4cb,c7c8b0,abad96,90927c,757862,5e604c,464835,2f3220,1a1d0d,000000,ffffff,fefdec,f2f2e0,e4e4d3,c7c7b7,acac9d,919283,767769,5e6052,46483b,303126,1b1c12,000000,ffffff,fcffdc,f0f3d0,e2e5c2,c6c9a8,aaae8e,909375,74795b,5c6145,454930,2f321b,1a1d08,000000,ffffff,fffbf7,f4f0ec,e5e2dd,c9c6c2,adaba7,92918d,777672,605e5b,474744,31302e,1c1b19,000000,ffffff,fffbf7,f4f0ec,e5e2dd,c9c6c2,adaba7,92918d,777672,605e5b,474744,31302e,1c1b19,000000</spritz>
         <tonal_spot>ffffff,fcffd5,ebf8a4,ddea96,c1cd7d,a5b264,8b974d,707c35,596320,414b08,2b3400,181e00,000000,ffffff,fcffdc,f0f3d0,e2e5c2,c6c9a8,aaae8e,909375,74795b,5c6145,454930,2f321b,1a1d08,000000,ffffff,f0fffa,cbfbed,bdeddf,a1d0c3,87b4a8,6d9a8e,527e73,3b665c,224e45,05372f,002019,000000,ffffff,fffcf4,f3f1e8,e5e3da,c8c7bf,adaba4,929189,777670,5f5f58,474741,30312b,1c1c17,000000,ffffff,fefdec,f2f2e0,e4e4d3,c7c7b7,acac9d,919283,767769,5e6052,46483b,303126,1b1c12,000000</tonal_spot>
-        <vibrant>ffffff,fdffd7,eaf99a,d9ed76,bdd05d,a2b444,87992c,6e7d0e,566500,404c00,2b3400,181e00,000000,ffffff,fffbfa,ffeddf,ffdcbe,eebd93,d0a27a,b48762,966e4a,7c5635,613f20,48290b,2e1500,000000,ffffff,fffbfa,ffeddf,ffdcbe,fab981,db9e69,bd8551,9f6b3a,845325,683d0f,4d2700,2e1500,000000,ffffff,fdfee7,f2f2dd,e3e4ce,c7c8b3,abad99,919280,767766,5e604f,464839,2f3223,1a1d0f,000000,ffffff,fdfee4,f1f2d8,e3e4cb,c7c8b0,abad96,90927c,757862,5e604c,464835,2f3220,1a1d0d,000000</vibrant>
-        <expressive>ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,e992ae,cb7793,ac5e78,904761,732f49,581933,3c031e,000000,ffffff,fffbf9,ffeed4,ffdea7,e3c28c,c6a673,aa8c5c,8d7243,735b2e,594319,412d05,281900,000000,ffffff,fffbf9,ffeed4,ffdea6,eac077,cea560,b08b48,937030,78591a,5e4102,422c00,281900,000000,ffffff,fafeef,eff2e4,e1e4d6,c4c8bb,a8ad9f,8e9286,73786b,5b6055,44483e,2d3228,181d14,000000,ffffff,f9ffea,ebf4dd,dde5cf,c1cab4,a6ae9a,8b9380,707966,59614f,424939,2b3324,171e10,000000</expressive>
+        <vibrant>ffffff,fdffd7,eaf99a,d9ed76,bdd05d,a2b444,87992c,6e7d0e,566500,404c00,2b3400,181e00,000000,ffffff,f8ffe3,e4f8c7,d6e9b9,bacd9f,9fb185,85976c,6a7c53,53643e,3c4c28,263514,121f03,000000,ffffff,f5ffec,d1fdc5,c3eeb8,a7d29e,8db684,739b6b,598053,42673d,2a4f27,133812,002202,000000,ffffff,fdfee4,f1f2d8,e3e4cb,c7c8b0,abad96,90927c,757862,5e604c,464835,2f3220,1a1d0d,000000,ffffff,fcffdf,f1f3d4,e2e5c7,c6c9ab,abae91,8f9378,75785f,5d6048,454932,2f321e,1a1d0b,000000</vibrant>
+        <expressive>ffffff,fffbfa,ffecf1,ffd9e4,ffb0ca,e992ae,cb7793,ac5e78,904761,732f49,581933,3c031e,000000,ffffff,f2fff6,d0fbe1,c2ecd3,a7d0b8,8cb49d,729983,587e6a,406653,284e3c,103727,002113,000000,ffffff,fafcff,e4f2ff,c7e7ff,9ccdf0,81b1d3,6696b8,4b7b9c,316383,134b6a,00344e,001e2f,000000,ffffff,fafeef,eff2e4,e1e4d6,c4c8bb,a8ad9f,8e9286,73786b,5b6055,44483e,2d3228,181d14,000000,ffffff,f9ffea,ebf4dd,dde5cf,c1cab4,a6ae9a,8b9380,707966,59614f,424939,2b3324,171e10,000000</expressive>
         <rainbow>ffffff,fdffd7,eaf99a,daec7b,becf61,a2b449,889931,6e7d16,566500,404c00,2b3400,181e00,000000,ffffff,fcffdc,f0f3d0,e2e5c2,c6c9a8,aaae8e,909375,74795b,5c6145,454930,2f321b,1a1d08,000000,ffffff,f0fffa,cbfbed,bdeddf,a1d0c3,87b4a8,6d9a8e,527e73,3b665c,224e45,05372f,002019,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000</rainbow>
         <fruit_salad>ffffff,fffbf9,ffeedc,ffddb6,ffb85d,e69c38,c7821d,a76800,875300,663d00,482a00,2b1700,000000,ffffff,fffbf9,ffeedc,ffddb6,f8bb71,daa059,bc8641,9e6b2a,825414,663d00,482a00,2b1700,000000,ffffff,fcffd5,ebf8a4,ddea96,c1cd7d,a5b264,8b974d,707c35,596320,414b08,2b3400,181e00,000000,ffffff,fdfee7,f2f2dd,e3e4ce,c7c8b3,abad99,919280,767766,5e604f,464839,2f3223,1a1d0f,000000,ffffff,fcffdc,f0f3d0,e2e5c2,c6c9a8,aaae8e,909375,74795b,5c6145,454930,2f321b,1a1d08,000000</fruit_salad>
     </theme>
     <theme color="ff008772">
         <spritz>ffffff,f0fffa,e2f5ed,d4e7df,b8cbc4,9dafa9,83958e,687a74,51625c,3a4a45,23342f,0f1e1a,000000,ffffff,f4fefa,e9f3ef,dae5e0,bec9c4,a3ada9,88938f,6e7875,57615d,3f4945,29322f,141d1b,000000,ffffff,f0fffa,dbf7ed,cde9df,b1ccc3,96b1a8,7d968e,627b74,4b635c,334b45,1c352e,06201a,000000,ffffff,fdfcfb,f2f1ef,e3e2e1,c7c7c5,ababaa,90918f,767675,5e5e5d,464746,2f3130,1a1c1b,000000,ffffff,fdfcfb,f2f1ef,e3e2e1,c7c7c5,ababaa,90918f,767675,5e5e5d,464746,2f3130,1a1c1b,000000</spritz>
         <tonal_spot>ffffff,f0fffa,b3ffec,a1f2dd,85d5c1,69baa6,4e9e8c,308372,086b5a,005143,00382d,002019,000000,ffffff,f0fffa,dbf7ed,cde9df,b1ccc3,96b1a8,7d968e,627b74,4b635c,334b45,1c352e,06201a,000000,ffffff,fafcff,e4f3ff,c6e7ff,aacae3,8fafc8,7594ac,5a7a90,426278,2a4a5f,103447,001e2f,000000,ffffff,fafdfa,eff1ef,e0e3e0,c4c7c5,a8aca9,8e918f,737775,5c5f5d,444846,2e3130,191c1b,000000,ffffff,f4fefa,e9f3ef,dae5e0,bec9c4,a3ada9,88938f,6e7875,57615d,3f4945,29322f,141d1b,000000</tonal_spot>
-        <vibrant>ffffff,f0fffa,b3ffec,79f8da,5bdbbf,37bfa4,00a38a,00856f,006b59,005143,00382d,002019,000000,ffffff,fdffd8,eef6be,e0e8b1,c4cb97,a8af7e,8e9565,727a4d,5b6238,444a22,2d330e,181e00,000000,ffffff,fdffd8,ecf7ad,dee9a0,c1cd86,a6b16e,8c9656,717b3e,5a6329,424b12,2b3400,181e00,000000,ffffff,f1fffa,e5f4ee,d7e6e0,bbcac4,a0aea9,86948e,6c7974,54615d,3d4945,26332f,111e1a,000000,ffffff,f0fffa,e2f5ed,d4e7df,b8cbc4,9dafa9,83958e,687a74,51625c,3a4a45,23342f,0f1e1a,000000</vibrant>
-        <expressive>ffffff,fffbfa,ffede0,ffdcc0,ffb778,e69a59,c78041,a86729,8b5013,6e3900,4d2600,2f1500,000000,ffffff,f6ffe9,def9cd,d0eabf,b5cea5,99b38b,7f9872,657d59,4e6543,374c2d,213618,0c2006,000000,ffffff,f6ffe9,d5fcc1,c7eeb3,acd199,92b580,789a67,5e7f4e,466738,304e23,1a370f,042100,000000,ffffff,f4fffd,e9f3f1,dae5e3,bec9c7,a3adac,889391,6e7877,566060,3f4848,293232,141d1d,000000,ffffff,effffe,e2f5f3,d4e6e5,b8cac9,9dafad,829493,687978,506260,394a48,233333,0e1e1e,000000</expressive>
+        <vibrant>ffffff,f0fffa,b3ffec,79f8da,5bdbbf,37bfa4,00a38a,00856f,006b59,005143,00382d,002019,000000,ffffff,effffd,cafaf5,bbece7,a0cfcb,85b4af,6b9995,517e7a,396662,1f4e4a,013734,00201e,000000,ffffff,efffff,befbff,a8eef5,8dd2d8,71b6bd,569ba1,398086,1a686e,004f54,00363a,002022,000000,ffffff,f0fffa,e2f5ed,d4e7df,b8cbc4,9dafa9,83958e,687a74,51625c,3a4a45,23342f,0f1e1a,000000,ffffff,f0fffa,dff6ed,d1e7df,b5ccc4,9ab0a8,80958e,657b74,4e635c,364b45,21342f,0b1f1b,000000</vibrant>
+        <expressive>ffffff,fffbfa,ffede0,ffdcc0,ffb778,e69a59,c78041,a86729,8b5013,6e3900,4d2600,2f1500,000000,ffffff,f8fdff,dcf5ff,c0e9fa,a4cddd,8ab1c2,6f96a6,547c8b,3c6472,234c5a,063543,001f29,000000,ffffff,fffbfe,f6edff,eaddff,cfbef7,b2a3da,9788be,7d6ea2,645788,4c3f6f,352857,201241,000000,ffffff,f4fffd,e9f3f1,dae5e3,bec9c7,a3adac,889391,6e7877,566060,3f4848,293232,141d1d,000000,ffffff,effffe,e2f5f3,d4e6e5,b8cac9,9dafad,829493,687978,506260,394a48,233333,0e1e1e,000000</expressive>
         <rainbow>ffffff,f0fffa,b3ffec,79f8da,5bdbbf,37bfa4,00a38a,00856f,006b59,005143,00382d,002019,000000,ffffff,f0fffa,dbf7ed,cde9df,b1ccc3,96b1a8,7d968e,627b74,4b635c,334b45,1c352e,06201a,000000,ffffff,fafcff,e4f3ff,c6e7ff,aacae3,8fafc8,7594ac,5a7a90,426278,2a4a5f,103447,001e2f,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000</rainbow>
         <fruit_salad>ffffff,f9ffe1,ddfca5,c9ef88,aed36f,93b757,799c3e,608026,48680d,334f00,213600,121f00,000000,ffffff,f9ffe1,dffbad,d1eca0,b5d086,9ab46e,809956,667e3e,4f6628,384d13,233600,121f00,000000,ffffff,f0fffa,b3ffec,a1f2dd,85d5c1,69baa6,4e9e8c,308372,086b5a,005143,00382d,002019,000000,ffffff,f1fffa,e5f4ee,d7e6e0,bbcac4,a0aea9,86948e,6c7974,54615d,3d4945,26332f,111e1a,000000,ffffff,f0fffa,dbf7ed,cde9df,b1ccc3,96b1a8,7d968e,627b74,4b635c,334b45,1c352e,06201a,000000</fruit_salad>
     </theme>
     <theme color="ff007fb6">
         <spritz>ffffff,fafcff,e6f2fe,d8e4ef,bcc8d3,a1adb7,86929d,6c7882,546069,3d4852,27323a,111d25,000000,ffffff,fafcff,ecf1f9,dee3ea,c2c7ce,a6acb2,8b9198,70777d,595f65,41474d,2b3137,171c21,000000,ffffff,fafcff,e4f2ff,d3e5f5,b7c9d8,9caebd,8193a1,677887,50606e,384956,22323f,0c1d29,000000,ffffff,fefcfc,f2f0f1,e4e2e3,c7c6c7,acabab,919192,767677,5e5e5f,464748,303031,1b1b1c,000000,ffffff,fefcfc,f2f0f1,e4e2e3,c7c6c7,acabab,919192,767677,5e5e5f,464748,303031,1b1b1c,000000</spritz>
         <tonal_spot>ffffff,fafcff,e4f2ff,c7e6ff,94cdf7,79b1da,5e97be,417ca2,256489,004b6f,00344f,001e30,000000,ffffff,fafcff,e4f2ff,d3e5f5,b7c9d8,9caebd,8193a1,677887,50606e,384956,22323f,0c1d29,000000,ffffff,fffbfd,f7edff,ebdcff,cfc0e9,b2a5cc,978bb0,7c7095,64597b,4c4163,352b4a,201634,000000,ffffff,fbfcff,f0f0f3,e2e2e5,c6c6c9,aaabae,909194,757679,5c5e61,454749,2f3032,191c1e,000000,ffffff,fafcff,ecf1f9,dee3ea,c2c7ce,a6acb2,8b9198,70777d,595f65,41474d,2b3137,171c21,000000</tonal_spot>
-        <vibrant>ffffff,fafcff,e4f2ff,c7e6ff,86ceff,57b4ee,3599d2,007db5,006492,004b6f,00344f,001e30,000000,ffffff,f0fffb,cbfaee,bdece1,a1d0c4,87b4aa,6c9a8f,527e75,3a665d,214e46,043730,00201a,000000,ffffff,f0fffb,b8feee,aaf0e1,8ed4c4,73b8a9,589d8f,3c8275,21695d,005045,00382f,00201a,000000,ffffff,fafcff,e9f1fb,dbe4ed,bfc8d1,a4acb5,89919a,6e777f,576067,3f484f,293138,141c23,000000,ffffff,fafcff,e6f2fe,d8e4ef,bcc8d3,a1adb7,86929d,6c7882,546069,3d4852,27323a,111d25,000000</vibrant>
-        <expressive>ffffff,fcffd8,e8fa9c,d9eb8f,bdcf76,a3b35d,889846,6e7c2e,566417,3f4c00,2a3500,171e00,000000,ffffff,efffff,cafafc,bcebee,a0cfd1,85b3b6,6b989b,507d80,386568,1e4d50,003739,002022,000000,ffffff,efffff,b9fcff,a8eff3,8cd2d7,71b6bb,559ca0,388085,1a686d,004f53,00373a,002022,000000,ffffff,fdfcff,edf0fa,dfe2eb,c3c7cf,a8abb4,8d9099,72767e,5a5e66,43474e,2d3137,171c22,000000,ffffff,fdfcff,e9f1ff,dbe3f1,bfc7d5,a4acb9,8a919f,6f7783,575f6b,404753,29313b,141c26,000000</expressive>
+        <vibrant>ffffff,fafcff,e4f2ff,c7e6ff,86ceff,57b4ee,3599d2,007db5,006492,004b6f,00344f,001e30,000000,ffffff,fcfcff,e8f1ff,cfe4ff,b1c9e8,96adcc,7b92b0,617894,4a607b,314962,19324a,011d34,000000,ffffff,fdfbff,ecf0ff,d6e2ff,b1c7f9,95abdc,7b90c0,6076a3,485e8a,314671,183059,001a43,000000,ffffff,fafcff,e6f2fe,d8e4ef,bcc8d3,a1adb7,86929d,6c7882,546069,3d4852,27323a,111d25,000000,ffffff,fafcff,e4f2ff,d6e4f3,bac8d6,9fadba,84929f,697884,52606c,3a4853,24323c,0e1d27,000000</vibrant>
+        <expressive>ffffff,fcffd8,e8fa9c,d9eb8f,bdcf76,a3b35d,889846,6e7c2e,566417,3f4c00,2a3500,171e00,000000,ffffff,fefbff,f1efff,e2dfff,c4c3ea,a9a7ce,8e8db3,737396,5c5b7d,444364,2d2d4d,191837,000000,ffffff,fffbfa,ffecf0,ffd9e3,fdb2c6,df97ab,c17e91,a36476,874c5f,6c3647,511f31,370b1c,000000,ffffff,fdfcff,edf0fa,dfe2eb,c3c7cf,a8abb4,8d9099,72767e,5a5e66,43474e,2d3137,171c22,000000,ffffff,fdfcff,e9f1ff,dbe3f1,bfc7d5,a4acb9,8a919f,6f7783,575f6b,404753,29313b,141c26,000000</expressive>
         <rainbow>ffffff,fafcff,e4f2ff,c7e6ff,86ceff,57b4ee,3599d2,007db5,006492,004b6f,00344f,001e30,000000,ffffff,fafcff,e4f2ff,d3e5f5,b7c9d8,9caebd,8193a1,677887,50606e,384956,22323f,0c1d29,000000,ffffff,fffbfd,f7edff,ebdcff,cfc0e9,b2a5cc,978bb0,7c7095,64597b,4c4163,352b4a,201634,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000</rainbow>
         <fruit_salad>ffffff,effffd,affff9,71f7ee,4fdbd2,24beb6,00a29a,00847d,006a64,00504b,003733,00201e,000000,ffffff,effffd,affff9,9df1ea,80d5ce,65b9b3,489e98,27837d,006a65,00504b,003734,00201e,000000,ffffff,fafcff,e4f2ff,c7e6ff,94cdf7,79b1da,5e97be,417ca2,256489,004b6f,00344f,001e30,000000,ffffff,fafcff,e9f1fb,dbe4ed,bfc8d1,a4acb5,89919a,6e777f,576067,3f484f,293138,141c23,000000,ffffff,fafcff,e4f2ff,d3e5f5,b7c9d8,9caebd,8193a1,677887,50606e,384956,22323f,0c1d29,000000</fruit_salad>
     </theme>
     <theme color="ff8267c2">
         <spritz>ffffff,fffbfd,f6eeff,e8dff1,cbc4d5,b0a8ba,958e9e,7a7383,615c6b,4a4453,332e3c,1d1a26,000000,ffffff,fffbfd,f5eefa,e7e0eb,cbc4cf,afa9b4,948f99,79747e,615c66,49454f,322f37,1d1a22,000000,ffffff,fffbfd,f7edff,e9def8,ccc3dc,b1a7c0,958da4,7a7389,625b71,4a4358,332d41,1e182b,000000,ffffff,fffbfd,f4eff1,e6e1e3,cac5c7,aeaaac,939091,787577,605e5f,484648,313031,1c1b1d,000000,ffffff,fffbfd,f4eff1,e6e1e3,cac5c7,aeaaac,939091,787577,605e5f,484648,313031,1c1b1d,000000</spritz>
         <tonal_spot>ffffff,fffbfd,f7edff,ebddff,d1bcfe,b5a1e1,9987c4,7e6da8,66558e,4d3d75,37265d,211047,000000,ffffff,fffbfd,f7edff,e9def8,ccc3dc,b1a7c0,958da4,7a7389,625b71,4a4358,332d41,1e182b,000000,ffffff,fffbfa,ffecf0,ffd8e3,f0b7c7,d29dab,b68391,986976,7e525f,633b48,4a2531,31101c,000000,ffffff,fffbfd,f5eff4,e6e1e5,c9c5c9,aeaaae,939094,787579,605d62,484649,313033,1c1b1e,000000,ffffff,fffbfd,f5eefa,e7e0eb,cbc4cf,afa9b4,948f99,79747e,615c66,49454f,322f37,1d1a22,000000</tonal_spot>
-        <vibrant>ffffff,fffbfd,f7edff,ebddff,d2bcff,b89bfb,9d81de,8166c1,694ea7,51358d,391c76,22005c,000000,ffffff,fafcff,e4f2ff,c7e6ff,abcbe4,90afc8,7694ad,5b7991,436278,2b4a5f,123348,001e30,000000,ffffff,fafcff,e4f2ff,c7e6ff,9dccf0,82b0d4,6796b8,4c7b9c,336383,154b6a,00344f,001e30,000000,ffffff,fffbfd,f5eefd,e7e0ee,cbc3d2,afa8b6,948e9c,797480,615c69,494550,322f3a,1d1a24,000000,ffffff,fffbfd,f6eeff,e8dff1,cbc4d5,b0a8ba,958e9e,7a7383,615c6b,4a4453,332e3c,1d1a26,000000</vibrant>
-        <expressive>ffffff,f0fffa,b5ffee,95f4de,78d8c2,5bbca7,3ea08d,168572,006b5a,005144,00382e,00201a,000000,ffffff,fdfcff,ebf1ff,d4e3ff,b6c7ea,9aaccd,8092b1,657795,4e5f7c,364764,1f314c,071c36,000000,ffffff,fdfcff,ebf1ff,d4e3ff,acc7f8,92acdb,7792bf,5c77a3,455f8a,2c4770,123158,001b3d,000000,ffffff,fffbfb,f8eef8,eadfea,cdc4ce,b2a8b3,968e98,7b747d,645c65,4b454d,342f37,1f1a21,000000,ffffff,fffbfb,fbecfd,ecdeef,d0c2d3,b4a7b7,998d9c,7e7282,655b69,4d4451,362d3b,201925,000000</expressive>
+        <vibrant>ffffff,fffbfd,f7edff,ebddff,d2bcff,b89bfb,9d81de,8166c1,694ea7,51358d,391c76,22005c,000000,ffffff,fffbfb,fbebff,f3daff,d6bee5,baa3c9,9e89ad,836e91,6a5778,514060,3a2a48,241532,000000,ffffff,fffbfb,ffeaff,ffd6ff,e5b8e9,c89dcd,ac83b1,906996,77517c,5d3a63,45234b,2e0d35,000000,ffffff,fffbfd,f6eeff,e8dff1,cbc4d5,b0a8ba,958e9e,7a7383,615c6b,4a4453,332e3c,1d1a26,000000,ffffff,fffbfd,f7edff,e8dff5,cbc3d8,b0a8bc,958ea1,797386,625b6e,494455,332e3e,1e1928,000000</vibrant>
+        <expressive>ffffff,f0fffa,b5ffee,95f4de,78d8c2,5bbca7,3ea08d,168572,006b5a,005144,00382e,00201a,000000,ffffff,fffbfa,ffebf5,ffd7ed,e9b9d2,cc9eb8,af849c,926a81,795369,5f3c51,46263a,2e1124,000000,ffffff,fffbfa,ffeddf,ffdcbf,fab982,dc9e69,be8452,9f6a3a,845325,683d0f,4d2700,2e1500,000000,ffffff,fffbfb,f8eef8,eadfea,cdc4ce,b2a8b3,968e98,7b747d,645c65,4b454d,342f37,1f1a21,000000,ffffff,fffbfb,fbecfd,ecdeef,d0c2d3,b4a7b7,998d9c,7e7282,655b69,4d4451,362d3b,201925,000000</expressive>
         <rainbow>ffffff,fffbfd,f7edff,ebddff,d2bcff,b79df7,9c82da,8167be,684fa3,503789,391d72,22005c,000000,ffffff,fffbfd,f7edff,e9def8,ccc3dc,b1a7c0,958da4,7a7389,625b71,4a4358,332d41,1e182b,000000,ffffff,fffbfa,ffecf0,ffd8e3,f0b7c7,d29dab,b68391,986976,7e525f,633b48,4a2531,31101c,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000,ffffff,fcfcfc,f1f1f1,e2e2e2,c6c6c6,ababab,919191,767676,5e5e5e,474747,303030,1b1b1b,000000</rainbow>
         <fruit_salad>ffffff,fcfcff,e8f2ff,cee5ff,97cbff,68b1f4,4a96d8,277bbb,00629f,004a7a,003355,001d35,000000,ffffff,fcfcff,e8f2ff,cee5ff,9dcbfb,82afdf,6795c2,4b7aa6,31628d,124a73,003355,001d35,000000,ffffff,fffbfd,f7edff,ebddff,d1bcfe,b5a1e1,9987c4,7e6da8,66558e,4d3d75,37265d,211047,000000,ffffff,fffbfd,f5eefd,e7e0ee,cbc3d2,afa8b6,948e9c,797480,615c69,494550,322f3a,1d1a24,000000,ffffff,fffbfd,f7edff,e9def8,ccc3dc,b1a7c0,958da4,7a7389,625b71,4a4358,332d41,1e182b,000000</fruit_salad>
     </theme>
diff --git a/tests/tests/keystore/src/android/keystore/cts/Curve25519Test.java b/tests/tests/keystore/src/android/keystore/cts/Curve25519Test.java
index 30bd40b..8a37b16 100644
--- a/tests/tests/keystore/src/android/keystore/cts/Curve25519Test.java
+++ b/tests/tests/keystore/src/android/keystore/cts/Curve25519Test.java
@@ -30,14 +30,23 @@
 import org.junit.runner.RunWith;
 
 import java.security.InvalidAlgorithmParameterException;
+import java.security.InvalidKeyException;
+import java.security.KeyPair;
 import java.security.KeyPairGenerator;
 import java.security.KeyStore;
 import java.security.KeyStoreException;
 import java.security.NoSuchAlgorithmException;
 import java.security.NoSuchProviderException;
-import java.security.ProviderException;
+import java.security.Signature;
+import java.security.SignatureException;
+import java.security.interfaces.EdECPublicKey;
 import java.security.spec.ECGenParameterSpec;
+import java.security.spec.InvalidKeySpecException;
 import java.security.spec.NamedParameterSpec;
+import java.util.Arrays;
+import java.util.Base64;
+
+import javax.crypto.KeyAgreement;
 
 @RunWith(AndroidJUnit4.class)
 public class Curve25519Test {
@@ -52,45 +61,77 @@
 
     @Test
     public void x25519KeyAgreementTest() throws NoSuchAlgorithmException, NoSuchProviderException,
-            InvalidAlgorithmParameterException {
+            InvalidAlgorithmParameterException, InvalidKeySpecException, InvalidKeyException {
         KeyPairGenerator kpg = KeyPairGenerator.getInstance("EC", "AndroidKeyStore");
-        final String alias = "x25519-alias";
-        deleteEntry(alias);
+        // Aliases for both keys.
+        final String firstKeyAlias = "x25519-alias";
+        deleteEntry(firstKeyAlias);
+        final String secondKeyAlias = "x25519-alias-second";
+        deleteEntry(secondKeyAlias);
 
-        KeyGenParameterSpec keySpec = new KeyGenParameterSpec.Builder(alias,
-                        KeyProperties.PURPOSE_AGREE_KEY)
+        // Generate first x25519 key pair.
+        KeyGenParameterSpec firstKeySpec = new KeyGenParameterSpec.Builder(firstKeyAlias,
+                KeyProperties.PURPOSE_AGREE_KEY)
                 .setAlgorithmParameterSpec(new ECGenParameterSpec("x25519")).build();
-        kpg.initialize(keySpec);
+        kpg.initialize(firstKeySpec);
+        KeyPair firstKeyPair = kpg.generateKeyPair();
 
-        //TODO(b/214203951): Remove this try/catch once Conscrypt class are available.
-        try {
-            kpg.generateKeyPair();
-            fail("Should not be supported yet");
-        } catch (ProviderException e) {
-            assertThat(e.getMessage()).isEqualTo("Curve XDH not supported yet");
-        }
+        // Generate second x25519 key pair.
+        KeyGenParameterSpec secondKeySpec = new KeyGenParameterSpec.Builder(secondKeyAlias,
+                KeyProperties.PURPOSE_AGREE_KEY)
+                .setAlgorithmParameterSpec(new ECGenParameterSpec("x25519")).build();
+        kpg.initialize(secondKeySpec);
+        KeyPair secondKeyPair = kpg.generateKeyPair();
+
+        // Attempt a key agreement with the private key from the first key pair and the public
+        // key from the second key pair.
+        KeyAgreement secondKa = KeyAgreement.getInstance("XDH");
+        secondKa.init(firstKeyPair.getPrivate());
+        secondKa.doPhase(secondKeyPair.getPublic(), true);
+        byte[] secondSecret = secondKa.generateSecret();
+
+        // Attempt a key agreement "the other way around": using the private key from the second
+        // key pair and the public key from the first key pair.
+        KeyAgreement firstKa = KeyAgreement.getInstance("XDH");
+        firstKa.init(secondKeyPair.getPrivate());
+        firstKa.doPhase(firstKeyPair.getPublic(), true);
+        byte[] firstSecret = firstKa.generateSecret();
+
+        // Both secrets being equal means the key agreement was successful.
+        assertThat(Arrays.compare(firstSecret, secondSecret)).isEqualTo(0);
     }
 
     @Test
     public void ed25519KeyGenerationAndSigningTest()
             throws NoSuchAlgorithmException, NoSuchProviderException,
-            InvalidAlgorithmParameterException {
+            InvalidAlgorithmParameterException, InvalidKeyException, SignatureException {
         KeyPairGenerator kpg = KeyPairGenerator.getInstance("EC", "AndroidKeyStore");
         final String alias = "ed25519-alias";
         deleteEntry(alias);
 
         KeyGenParameterSpec keySpec = new KeyGenParameterSpec.Builder(alias,
                 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY)
-                .setAlgorithmParameterSpec(new ECGenParameterSpec("ed25519")).build();
+                .setAlgorithmParameterSpec(new ECGenParameterSpec("ed25519"))
+                .setDigests(KeyProperties.DIGEST_NONE).build();
         kpg.initialize(keySpec);
 
-        //TODO(b/214203951): Remove this try/catch once Conscrypt class are available.
-        try {
-            kpg.generateKeyPair();
-            fail("Should not be supported yet");
-        } catch (ProviderException e) {
-            assertThat(e.getMessage()).isEqualTo("Curve 1.3.101.112 not supported yet");
-        }
+        KeyPair kp = kpg.generateKeyPair();
+        assertThat(kp.getPublic()).isInstanceOf(EdECPublicKey.class);
+
+        byte[] data = "helloxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx".getBytes();
+        Signature signer = Signature.getInstance("Ed25519");
+        signer.initSign(kp.getPrivate());
+        signer.update(data);
+        byte[] sigBytes = signer.sign();
+        assertThat(sigBytes.length).isEqualTo(64);
+        EdECPublicKey publicKey = (EdECPublicKey) kp.getPublic();
+        android.util.Log.i("Curve25519Test", "Manually validate: Payload "
+                + Base64.getEncoder().encodeToString(data) + " encoded key: "
+                + Base64.getEncoder().encodeToString(kp.getPublic().getEncoded())
+                + " signature: " + Base64.getEncoder().encodeToString(sigBytes));
+
+        //TODO: Verify signature over the data when Conscrypt supports validating Ed25519
+        // signatures.
     }
 
     @Test
@@ -150,4 +191,4 @@
             assertThat(e.getMessage()).contains("cannot be initialized using NamedParameterSpec");
         }
     }
-}
\ No newline at end of file
+}
diff --git a/tests/tests/permission/src/android/permission/cts/LocationAccessCheckTest.java b/tests/tests/permission/src/android/permission/cts/LocationAccessCheckTest.java
index fee9001..ab7a15d 100644
--- a/tests/tests/permission/src/android/permission/cts/LocationAccessCheckTest.java
+++ b/tests/tests/permission/src/android/permission/cts/LocationAccessCheckTest.java
@@ -33,6 +33,7 @@
 import static com.android.compatibility.common.util.SystemUtil.runShellCommand;
 import static com.android.compatibility.common.util.SystemUtil.runWithShellPermissionIdentity;
 import static com.android.server.job.nano.JobPackageHistoryProto.START_PERIODIC_JOB;
+import static com.android.server.job.nano.JobPackageHistoryProto.STOP_JOB;
 import static com.android.server.job.nano.JobPackageHistoryProto.STOP_PERIODIC_JOB;
 
 import static org.junit.Assert.assertFalse;
@@ -83,6 +84,7 @@
 import com.android.compatibility.common.util.ProtoUtils;
 import com.android.compatibility.common.util.mainline.MainlineModule;
 import com.android.compatibility.common.util.mainline.ModuleDetector;
+import com.android.modules.utils.build.SdkLevel;
 import com.android.server.job.nano.JobPackageHistoryProto;
 import com.android.server.job.nano.JobSchedulerServiceDumpProto;
 import com.android.server.job.nano.JobSchedulerServiceDumpProto.RegisteredJob;
@@ -315,7 +317,12 @@
         // We can't simply require startTime <= endTime because the time being reported isn't
         // accurate, and sometimes the end time may come before the start time by around 100 ms.
         eventually(() -> {
-            long stopTime = getLastJobTime(STOP_PERIODIC_JOB);
+            long stopTime;
+            if (SdkLevel.isAtLeastT()) {
+                stopTime = getLastJobTime(STOP_PERIODIC_JOB);
+            } else {
+                stopTime = getLastJobTime(STOP_JOB);
+            }
             assertTrue(stopTime + " !> " + beforeJob, stopTime > beforeJob);
         }, EXPECTED_TIMEOUT_MILLIS);
     }
diff --git a/tests/tests/permission2/res/raw/android_manifest.xml b/tests/tests/permission2/res/raw/android_manifest.xml
index c68b9dd..162f66a 100644
--- a/tests/tests/permission2/res/raw/android_manifest.xml
+++ b/tests/tests/permission2/res/raw/android_manifest.xml
@@ -6419,11 +6419,11 @@
 
     <!-- @SystemApi Must be required by a safety source to send an update using the
              {@link android.safetycenter.SafetyCenterManager}.
-             <p>Protection level: signature|privileged
+             <p>Protection level: internal|privileged
              @hide
         -->
     <permission android:name="android.permission.SEND_SAFETY_CENTER_UPDATE"
-                android:protectionLevel="signature|privileged" />
+                android:protectionLevel="internal|privileged" />
 
     <!-- @SystemApi Allows an application to launch device manager setup screens.
          <p>Not for use by third-party applications.
diff --git a/tests/tests/permission3/src/android/permission3/cts/BaseUsePermissionTest.kt b/tests/tests/permission3/src/android/permission3/cts/BaseUsePermissionTest.kt
index c197d47..bc3947f 100644
--- a/tests/tests/permission3/src/android/permission3/cts/BaseUsePermissionTest.kt
+++ b/tests/tests/permission3/src/android/permission3/cts/BaseUsePermissionTest.kt
@@ -96,7 +96,6 @@
         const val DENY_RADIO_BUTTON = "com.android.permissioncontroller:id/deny_radio_button"
 
         const val NOTIF_TEXT = "permgrouprequest_notifications"
-        const val NOTIF_CONTINUE_TEXT = "permgrouprequestcontinue_notifications"
         const val ALLOW_BUTTON_TEXT = "grant_dialog_button_allow"
         const val ALLOW_FOREGROUND_BUTTON_TEXT = "grant_dialog_button_allow_foreground"
         const val ALLOW_FOREGROUND_PREFERENCE_TEXT = "permission_access_only_foreground"
@@ -353,9 +352,7 @@
         }
 
         if (waitFindObjectOrNull(By.text(getPermissionControllerString(
-                NOTIF_CONTINUE_TEXT, APP_PACKAGE_NAME)), 1000) != null ||
-                waitFindObjectOrNull(By.text(getPermissionControllerString(
-                        NOTIF_TEXT, APP_PACKAGE_NAME)), 1000) != null) {
+                NOTIF_TEXT, APP_PACKAGE_NAME)), 1000) != null) {
             if (isAutomotive) {
                 click(By.text(getPermissionControllerString(ALLOW_BUTTON_TEXT)))
             } else {
@@ -598,7 +595,7 @@
                 button.click()
             }
 
-            val shouldShowStorageWarning = !isTv && !isWatch &&
+            val shouldShowStorageWarning = !isWatch &&
                 SdkLevel.isAtLeastT() && targetSdk <= Build.VERSION_CODES.S_V2 &&
                 permission in MEDIA_PERMISSIONS
             if (shouldShowStorageWarning) {
diff --git a/tests/tests/permission3/src/android/permission3/cts/NotificationPermissionTest.kt b/tests/tests/permission3/src/android/permission3/cts/NotificationPermissionTest.kt
index b29e99f..eeb3a71 100644
--- a/tests/tests/permission3/src/android/permission3/cts/NotificationPermissionTest.kt
+++ b/tests/tests/permission3/src/android/permission3/cts/NotificationPermissionTest.kt
@@ -55,7 +55,6 @@
 const val ACTIVITY_LABEL = "CreateNotif"
 const val SECOND_ACTIVITY_LABEL = "EmptyActivity"
 const val ALLOW = "to send you"
-const val CONTINUE_ALLOW = "to continue sending you"
 const val INTENT_ACTION = "usepermission.createchannels.MAIN"
 const val BROADCAST_ACTION = "usepermission.createchannels.BROADCAST"
 const val NOTIFICATION_PERMISSION_ENABLED = "notification_permission_enabled"
@@ -124,18 +123,8 @@
     }
 
     @Test
-    fun reviewRequiredClearedForTAppsOnLaunch() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_33, expectSuccess = true)
-        setReviewRequired()
-        assertNotificationReviewRequiredState(shouldBeSet = true)
-        launchApp()
-        assertNotificationReviewRequiredState(shouldBeSet = false)
-    }
-
-    @Test
     fun notificationPromptShowsForLegacyAppAfterCreatingNotificationChannels() {
         installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_31, expectSuccess = true)
-        setReviewRequired()
         launchApp()
         clickPermissionRequestAllowButton()
     }
@@ -143,21 +132,12 @@
     @Test
     fun notificationPromptShowsForLegacyAppWithNotificationChannelsOnStart() {
         installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_31, expectSuccess = true)
-        setReviewRequired()
         // create channels, then leave the app
         launchApp()
         killTestApp()
         launchApp()
-        waitFindObject(By.textContains(CONTINUE_ALLOW))
-        clickPermissionRequestAllowButton()
-    }
-
-    @Test
-    fun nonReviewRequiredLegacyAppsDontShowContinuePrompt() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_31, expectSuccess = true)
-        setReviewRequired(false)
-        launchApp()
         waitFindObject(By.textContains(ALLOW))
+        clickPermissionRequestAllowButton()
     }
 
     @Test
@@ -254,49 +234,11 @@
     }
 
     @Test
-    fun reviewRequiredNotClearedOnNonLauncherIntentCategoryLaunches() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_33, expectSuccess = true)
-        setReviewRequired()
-        launchApp(launcherCategory = false)
-        assertNotificationReviewRequiredState(true)
-    }
-
-    @Test
-    fun reviewRequiredNotClearedOnNonMainIntentActionLaunches() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_33, expectSuccess = true)
-        setReviewRequired()
-        launchApp(mainIntent = false)
-        assertNotificationReviewRequiredState(true)
-    }
-
-    @Test
-    fun reviewRequiredClearedIfActivityOptionSet() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_33, expectSuccess = true)
-        setReviewRequired()
-        launchApp(isEligibleForPromptOption = true)
-        assertNotificationReviewRequiredState(false)
-    }
-
-    @Test
-    fun notificationGrantedAndReviewRequiredClearedOnLegacyGrant() {
+    fun notificationGrantedOnLegacyGrant() {
         installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_31, expectSuccess = true)
-        setReviewRequired()
         launchApp()
         clickPermissionRequestAllowButton()
         assertAppPermissionGrantedState(POST_NOTIFICATIONS, granted = true)
-        assertNotificationReviewRequiredState(shouldBeSet = false)
-    }
-
-    @Test
-    fun notificationReviewRequiredClearedOnLegacyDeny() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_31, expectSuccess = true)
-        setReviewRequired()
-        launchApp()
-        clickPermissionRequestDenyButton()
-        waitForIdle()
-        SystemUtil.eventually {
-            assertNotificationReviewRequiredState(shouldBeSet = false)
-        }
     }
 
     @Test
@@ -367,23 +309,6 @@
     }
 
     @Test
-    fun reviewRequiredTAppsShowContinueMessage() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_33, expectSuccess = true)
-        setReviewRequired(true)
-        assertNotificationReviewRequiredState(true)
-        launchApp(requestPermissions = true)
-        waitFindObject(By.textContains(CONTINUE_ALLOW))
-    }
-
-    @Test
-    fun nonReviewRequiredTAppsShowAllowMessage() {
-        installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_33, expectSuccess = true)
-        assertNotificationReviewRequiredState(false)
-        launchApp(requestPermissions = true)
-        waitFindObject(By.textContains(ALLOW))
-    }
-
-    @Test
     fun legacyAppCannotExplicitlyRequestNotifications() {
         installPackage(APP_APK_PATH_CREATE_NOTIFICATION_CHANNELS_31, expectSuccess = true)
         launchApp(createChannels = false, requestNotificationPermission = true)
@@ -404,27 +329,6 @@
         }
     }
 
-    private fun assertNotificationReviewRequiredState(shouldBeSet: Boolean) {
-        val flagSet = callWithShellPermissionIdentity {
-            (context.packageManager.getPermissionFlags(POST_NOTIFICATIONS,
-                APP_PACKAGE_NAME, Process.myUserHandle()) and FLAG_PERMISSION_REVIEW_REQUIRED) != 0
-        }
-        Assert.assertEquals("Unexpected REVIEW_REQUIRED state for POST_NOTIFICATIONS: ",
-            shouldBeSet, flagSet)
-    }
-
-    private fun setReviewRequired(set: Boolean = true) {
-        val flag = if (set) {
-            FLAG_PERMISSION_REVIEW_REQUIRED
-        } else {
-            0
-        }
-        runWithShellPermissionIdentity {
-            context.packageManager.updatePermissionFlags(POST_NOTIFICATIONS, APP_PACKAGE_NAME,
-                FLAG_PERMISSION_REVIEW_REQUIRED, flag, Process.myUserHandle())
-        }
-    }
-
     private fun launchApp(
         createChannels: Boolean = true,
         createChannelsDelayed: Boolean = false,
diff --git a/tests/tests/provider/Android.bp b/tests/tests/provider/Android.bp
index 5a1b7a0..b88fcf5 100644
--- a/tests/tests/provider/Android.bp
+++ b/tests/tests/provider/Android.bp
@@ -47,8 +47,7 @@
     // uncomment when b/140885436 is fixed
     // sdk_version: "test_current",
     min_sdk_version: "21",
-    //TODO(b/227617884): Change target_sdk_version to 33 after T SDK finalization is complete
-    target_sdk_version: "10000",
+    target_sdk_version: "33",
 
     platform_apis: true,
 
diff --git a/tests/tests/provider/src/android/provider/cts/contacts/CallLogTest.java b/tests/tests/provider/src/android/provider/cts/contacts/CallLogTest.java
index 8c62f21..c2a2795 100644
--- a/tests/tests/provider/src/android/provider/cts/contacts/CallLogTest.java
+++ b/tests/tests/provider/src/android/provider/cts/contacts/CallLogTest.java
@@ -30,6 +30,7 @@
 import android.os.ParcelFileDescriptor;
 import android.os.UserHandle;
 import android.provider.CallLog;
+import android.provider.CallLog.Calls;
 import android.provider.cts.R;
 import android.test.InstrumentationTestCase;
 import android.util.Pair;
@@ -43,20 +44,172 @@
 import java.io.FileInputStream;
 import java.io.FileNotFoundException;
 import java.io.InputStream;
+import java.util.HashMap;
+import java.util.Map;
 import java.util.concurrent.CompletableFuture;
 import java.util.concurrent.Executors;
 import java.util.concurrent.TimeUnit;
 
 public class CallLogTest extends InstrumentationTestCase {
-
+    // Test Call Log Entry
     private static final String TEST_NUMBER = "5625698388";
+    private static final int TEST_DATE = 1000;
+    private static final int TEST_DURATION = 30;
+    // Test Voicemail Log Entry
+    private static final String TEST_VOICEMAIL_NUMBER = "1119871234";
+    private static final int TEST_VOCIEMAIL_DATE = 1;
+    private static final int TEST_VOICEMAIL_DURATION = 5;
+    // Timeout
     private static final long CONTENT_RESOLVER_TIMEOUT_MS = 5000;
+    // SQL Selection Column Names
+    private static final String SELECTION_TYPE = "type";
+    private static final String SELECTION_NUMBER = "number";
+    private static final String SELECTION_DATE = "date";
+    private static final String SELECTION_DURATION = "duration";
+    private static final String SELECTION_NEW = "new";
+    // SQL Selection as array
+    private static final String[] SELECTION =
+            new String[]{SELECTION_TYPE, SELECTION_NUMBER, SELECTION_DATE,
+                    SELECTION_DURATION, SELECTION_NEW};
+    // Test filter URI that throws Security Exception
+    private static final Uri INVALID_FILTER_URI = Uri.parse(
+            "content://call_log/calls/filter/test\uD83D')) union select type,name,"
+                    + "tbl_name,rootpage,sql FROM SQLITE_MASTER; --");
+    // Test call composer URI that throws Security Exception
     private static final Uri INVALID_CALL_LOG_URI = Uri.parse(
             "content://call_log/call_composer/%2fdata%2fdata%2fcom.android.providers"
                     + ".contacts%2fshared_prefs%2fContactsUpgradeReceiver.xml");
-
+    // Test Failure Error
     private static final String TEST_FAIL_DID_NOT_TRHOW_SE =
             "fail test because Security Exception was not throw";
+    // Instance vars
+    private ContentResolver mContentResolver;
+
+    // Class to objectify the call log data (returned from a Cursor object)
+    public class LogEntry {
+        // properties
+        public Integer type;
+        public String number;
+        public Integer date;
+        public Integer duration;
+        public Integer newCount;
+        public String extras;
+
+        // setter
+        public void setValue(String selectionColumn, String value) {
+            if (value == null) {
+                // Integer.valueOf(value) throws NumberFormatException if string is null.
+                // so return early if value is null.
+                return;
+            }
+            try {
+                switch (selectionColumn) {
+                    case SELECTION_TYPE:
+                        type = Integer.valueOf(value);
+                        break;
+                    case SELECTION_NUMBER:
+                        number = value;
+                        break;
+                    case SELECTION_DATE:
+                        date = Integer.valueOf(value);
+                        break;
+                    case SELECTION_DURATION:
+                        duration = Integer.valueOf(value);
+                        break;
+                    case SELECTION_NEW:
+                        newCount = Integer.valueOf(value);
+                        break;
+                    default:
+                        extras = value;
+                }
+            } catch (NumberFormatException e) {
+                // pass through
+            }
+        }
+    }
+
+    @Override
+    public void setUp() throws Exception {
+        // Sets up this package as default dialer in super.
+        super.setUp();
+        mContentResolver = getInstrumentation().getContext().getContentResolver();
+    }
+
+    @Override
+    public void tearDown() throws Exception {
+        super.tearDown();
+    }
+
+    /**
+     * Ensure that the existing query functionality still works.  To verify the functionality,
+     * this test adds a single call and voicemail entry to the logs, queries the logs,
+     * and asserts the entries are returned.
+     */
+    public void testPopulateAndQueryCallAndVoicemailLogs() {
+        try {
+            // needed in order to populate call log database
+            ShellUtils.runShellCommand("telecom set-default-dialer %s",
+                    getInstrumentation().getContext().getPackageName());
+
+            populateLogsWithDefaults();
+
+            // query and get cursor
+            Cursor cursor = mContentResolver
+                    .query(Calls.CONTENT_URI_WITH_VOICEMAIL, SELECTION, null, null);
+
+            // extract the data from the cursor and put the objects in a map
+            Map<String, LogEntry> entries = collectCursorEntries(cursor);
+
+            // cleanup
+            cursor.close();
+
+            // call entry
+            assertEquals(TEST_NUMBER, entries.get(TEST_NUMBER).number);
+            // voicemail entry
+            assertEquals(TEST_VOICEMAIL_NUMBER, entries.get(TEST_VOICEMAIL_NUMBER).number);
+        } finally {
+            //cleanup
+            deletePopulatedLogs();
+            ShellUtils.runShellCommand("telecom set-default-dialer default");
+        }
+    }
+
+    /**
+     * Test scenario where an app calls {@link ContentResolver#query} with an invalid URI.
+     *
+     * The URI is invalid because it attempts to bypass voicemail permissions and grab the voicemail
+     * log data without the proper voicemail permissions.
+     *
+     * Therefore, a Security Exception is thrown.
+     */
+    public void testInvalidQueryToCallLog() {
+        try {
+            // needed in order to populate call log database
+            ShellUtils.runShellCommand("telecom set-default-dialer %s",
+                    getInstrumentation().getContext().getPackageName());
+
+            populateLogsWithDefaults();
+
+            // drop voicemail permissions
+            ShellUtils.runShellCommand("telecom set-default-dialer default");
+
+            // query and get cursor  (expecting to hit Security Exception with call)
+            Cursor cursor = mContentResolver
+                    .query(INVALID_FILTER_URI, SELECTION, null, null);
+
+            // the previous line should throw an exception
+            fail(TEST_FAIL_DID_NOT_TRHOW_SE);
+        } catch (SecurityException e) {
+            // success...
+            assertNotNull(e.toString());
+        } finally {
+            //cleanup
+            ShellUtils.runShellCommand("telecom set-default-dialer %s",
+                    getInstrumentation().getContext().getPackageName());
+            deletePopulatedLogs();
+            ShellUtils.runShellCommand("telecom set-default-dialer default");
+        }
+    }
 
     /**
      * Tests scenario where an app gives {@link ContentResolver} a file to open that is not in the
@@ -297,4 +450,66 @@
         } catch (InterruptedException e) {
         }
     }
+
+    private ContentValues getDefaultValues(int type, String number, int date, int duration) {
+        ContentValues values = new ContentValues();
+        values.put(Calls.TYPE, type);
+        values.put(Calls.NUMBER, number);
+        values.put(Calls.NUMBER_PRESENTATION, Calls.PRESENTATION_ALLOWED);
+        values.put(Calls.DATE, date);
+        values.put(Calls.DURATION, duration);
+        values.put(Calls.NEW, 1);
+        return values;
+    }
+
+    private ContentValues getDefaultCallValues() {
+        return getDefaultValues(Calls.INCOMING_TYPE, TEST_NUMBER, TEST_DATE, TEST_DURATION);
+    }
+
+    private ContentValues getDefaultVoicemailValues() {
+        return getDefaultValues(Calls.VOICEMAIL_TYPE, TEST_VOICEMAIL_NUMBER, TEST_VOCIEMAIL_DATE,
+                TEST_VOICEMAIL_DURATION);
+    }
+
+    private void deletePopulatedLogs() {
+        // delete TEST_NUMBER in the call logs
+        mContentResolver.delete(CallLog.Calls.CONTENT_URI,
+                Calls.NUMBER + "=" + TEST_NUMBER, null);
+        // delete TEST_VOICEMAIL_NUMBER in the voicemail logs
+        mContentResolver.delete(Calls.CONTENT_URI_WITH_VOICEMAIL,
+                Calls.NUMBER + "=" + TEST_VOICEMAIL_NUMBER, null);
+        // cleanup extra entry created in this test that does not have a Calls.NUMBER
+        mContentResolver.delete(Calls.CONTENT_URI_WITH_VOICEMAIL,
+                Calls.DATE + "=" + "0", null);
+    }
+
+    private void populateLogsWithDefaults() {
+        // add call log entry
+        mContentResolver.insert(Calls.CONTENT_URI, getDefaultCallValues());
+        // add voicemail entry
+        mContentResolver.insert(Calls.CONTENT_URI_WITH_VOICEMAIL, getDefaultVoicemailValues());
+    }
+
+    /**
+     * Helper method for a test that wants to objectify the cursor data into LogEntry objects.
+     * NOTE: The key for the map is the phone number, so you can only store one object per number.
+     *
+     * @return all the data in the cursor in a LogEntry map
+     */
+    public Map<String, LogEntry> collectCursorEntries(Cursor cursor) {
+        Map<String, LogEntry> entries = new HashMap<>();
+        // iterate through every row in the cursor
+        while (cursor.moveToNext()) {
+            LogEntry e = new LogEntry();
+            // iterate through each column (should be the SELECTION given to query)
+            for (int i = 0; i < cursor.getColumnCount(); i++) {
+                e.setValue(cursor.getColumnName(i), cursor.getString(i));
+            }
+            // don't add if bad number (should never happen)
+            if (e.number != null || !e.number.isEmpty()) {
+                entries.put(e.number, e);
+            }
+        }
+        return entries;
+    }
 }
diff --git a/tests/tests/sensorprivacy/src/android/sensorprivacy/cts/SensorPrivacyBaseTest.kt b/tests/tests/sensorprivacy/src/android/sensorprivacy/cts/SensorPrivacyBaseTest.kt
index ac1e9df..52feb93 100644
--- a/tests/tests/sensorprivacy/src/android/sensorprivacy/cts/SensorPrivacyBaseTest.kt
+++ b/tests/tests/sensorprivacy/src/android/sensorprivacy/cts/SensorPrivacyBaseTest.kt
@@ -230,7 +230,9 @@
         val latchEnabled = CountDownLatch(1)
         val listenerSensorEnabled = object : OnSensorPrivacyChangedListener {
             override fun onSensorPrivacyChanged(params: SensorPrivacyChangedParams) {
-                if (params.isEnabled && params.sensor == sensor) {
+                if (params.isEnabled &&
+                        params.sensor == sensor &&
+                        params.toggleType == TOGGLE_TYPE_SOFTWARE) {
                     latchEnabled.countDown()
                 }
             }
@@ -250,7 +252,9 @@
         val latchDisabled = CountDownLatch(1)
         val listenerSensorDisabled = object : OnSensorPrivacyChangedListener {
             override fun onSensorPrivacyChanged(params: SensorPrivacyChangedParams) {
-                if (!params.isEnabled && params.sensor == sensor) {
+                if (!params.isEnabled &&
+                        params.sensor == sensor &&
+                        params.toggleType == TOGGLE_TYPE_SOFTWARE) {
                     latchDisabled.countDown()
                 }
             }
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java b/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java
index 0b05c5f..d37a28c 100644
--- a/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java
@@ -146,7 +146,6 @@
 import java.util.concurrent.TimeUnit;
 import java.util.concurrent.atomic.AtomicReference;
 import java.util.function.Consumer;
-import java.util.function.Predicate;
 import java.util.regex.Pattern;
 import java.util.stream.Collectors;
 import java.util.stream.IntStream;
@@ -316,32 +315,26 @@
                     TelephonyManager.NETWORK_TYPE_GPRS,
                     TelephonyManager.NETWORK_TYPE_EDGE}));
         sNetworkTypes.put(CellIdentityWcdma.class,
-                Arrays.asList(new Integer[]{
-                    TelephonyManager.NETWORK_TYPE_UMTS,
-                    TelephonyManager.NETWORK_TYPE_HSDPA,
-                    TelephonyManager.NETWORK_TYPE_HSUPA,
-                    TelephonyManager.NETWORK_TYPE_HSPA,
-                    TelephonyManager.NETWORK_TYPE_HSPAP}));
+                Arrays.asList(TelephonyManager.NETWORK_TYPE_UMTS,
+                        TelephonyManager.NETWORK_TYPE_HSDPA,
+                        TelephonyManager.NETWORK_TYPE_HSUPA,
+                        TelephonyManager.NETWORK_TYPE_HSPA,
+                        TelephonyManager.NETWORK_TYPE_HSPAP));
         sNetworkTypes.put(CellIdentityCdma.class,
-                Arrays.asList(new Integer[]{
-                    TelephonyManager.NETWORK_TYPE_CDMA,
-                    TelephonyManager.NETWORK_TYPE_1xRTT,
-                    TelephonyManager.NETWORK_TYPE_EVDO_0,
-                    TelephonyManager.NETWORK_TYPE_EVDO_A,
-                    TelephonyManager.NETWORK_TYPE_EVDO_B,
-                    TelephonyManager.NETWORK_TYPE_EHRPD}));
+                Arrays.asList(TelephonyManager.NETWORK_TYPE_CDMA,
+                        TelephonyManager.NETWORK_TYPE_1xRTT,
+                        TelephonyManager.NETWORK_TYPE_EVDO_0,
+                        TelephonyManager.NETWORK_TYPE_EVDO_A,
+                        TelephonyManager.NETWORK_TYPE_EVDO_B,
+                        TelephonyManager.NETWORK_TYPE_EHRPD));
         sNetworkTypes.put(CellIdentityLte.class,
-                Arrays.asList(new Integer[]{
-                    TelephonyManager.NETWORK_TYPE_LTE}));
+                Arrays.asList(TelephonyManager.NETWORK_TYPE_LTE));
         sNetworkTypes.put(CellIdentityNr.class,
-                Arrays.asList(new Integer[]{
-                    TelephonyManager.NETWORK_TYPE_NR}));
+                Arrays.asList(TelephonyManager.NETWORK_TYPE_NR));
         sNetworkTypes.put(CellIdentityTdscdma.class,
-                Arrays.asList(new Integer[]{
-                    TelephonyManager.NETWORK_TYPE_TD_SCDMA}));
+                Arrays.asList(TelephonyManager.NETWORK_TYPE_TD_SCDMA));
     }
 
-
     private int mTestSub;
     private TelephonyManagerTest.CarrierConfigReceiver mReceiver;
     private int mRadioVersion;
@@ -427,28 +420,20 @@
             mAllowedNetworkTypesList = new HashMap<>();
         }
         long allowedNetworkTypesUser = ShellIdentityUtils.invokeMethodWithShellPermissions(
-                mTelephonyManager, (tm) -> {
-                    return tm.getAllowedNetworkTypesForReason(
-                            TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_USER);
-                }
+                mTelephonyManager, (tm) -> tm.getAllowedNetworkTypesForReason(
+                        TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_USER)
         );
         long allowedNetworkTypesPower = ShellIdentityUtils.invokeMethodWithShellPermissions(
-                mTelephonyManager, (tm) -> {
-                    return tm.getAllowedNetworkTypesForReason(
-                            TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_POWER);
-                }
+                mTelephonyManager, (tm) -> tm.getAllowedNetworkTypesForReason(
+                        TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_POWER)
         );
         long allowedNetworkTypesCarrier = ShellIdentityUtils.invokeMethodWithShellPermissions(
-                mTelephonyManager, (tm) -> {
-                    return tm.getAllowedNetworkTypesForReason(
-                            TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_CARRIER);
-                }
+                mTelephonyManager, (tm) -> tm.getAllowedNetworkTypesForReason(
+                        TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_CARRIER)
         );
         long allowedNetworkTypesEnable2g = ShellIdentityUtils.invokeMethodWithShellPermissions(
-                mTelephonyManager, (tm) -> {
-                    return tm.getAllowedNetworkTypesForReason(
-                            TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_ENABLE_2G);
-                }
+                mTelephonyManager, (tm) -> tm.getAllowedNetworkTypesForReason(
+                        TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_ENABLE_2G)
         );
         mAllowedNetworkTypesList.put(TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_USER,
                 allowedNetworkTypesUser);
@@ -598,27 +583,25 @@
 
         grantLocationPermissions();
 
-        TestThread t = new TestThread(new Runnable() {
-            public void run() {
-                Looper.prepare();
-                mListener = new PhoneStateListener() {
-                    @Override
-                    public void onCellLocationChanged(CellLocation location) {
-                        if(!mOnCellLocationChangedCalled) {
-                            synchronized (mLock) {
-                                mOnCellLocationChangedCalled = true;
-                                mLock.notify();
-                            }
+        TestThread t = new TestThread(() -> {
+            Looper.prepare();
+            mListener = new PhoneStateListener() {
+                @Override
+                public void onCellLocationChanged(CellLocation location) {
+                    if (!mOnCellLocationChangedCalled) {
+                        synchronized (mLock) {
+                            mOnCellLocationChangedCalled = true;
+                            mLock.notify();
                         }
                     }
-                };
-
-                synchronized (mLock) {
-                    mLock.notify(); // mListener is ready
                 }
+            };
 
-                Looper.loop();
+            synchronized (mLock) {
+                mLock.notify(); // mListener is ready
             }
+
+            Looper.loop();
         });
 
         synchronized (mLock) {
@@ -1438,22 +1421,20 @@
             return;
         }
 
-        TestThread t = new TestThread(new Runnable() {
-            public void run() {
-                Looper.prepare();
+        TestThread t = new TestThread(() -> {
+            Looper.prepare();
 
-                mListener = new PhoneStateListener() {
-                    @Override
-                    public void onServiceStateChanged(ServiceState serviceState) {
-                        synchronized (mLock) {
-                            mServiceState = serviceState;
-                            mLock.notify();
-                        }
+            mListener = new PhoneStateListener() {
+                @Override
+                public void onServiceStateChanged(ServiceState serviceState) {
+                    synchronized (mLock) {
+                        mServiceState = serviceState;
+                        mLock.notify();
                     }
-                };
-                mTelephonyManager.listen(mListener, PhoneStateListener.LISTEN_SERVICE_STATE);
-                Looper.loop();
-            }
+                }
+            };
+            mTelephonyManager.listen(mListener, PhoneStateListener.LISTEN_SERVICE_STATE);
+            Looper.loop();
         });
 
         synchronized (mLock) {
@@ -3357,8 +3338,7 @@
         // test without permission: verify SecurityException
         long allowedNetworkTypes1 = TelephonyManager.NETWORK_TYPE_BITMASK_NR
                 | TelephonyManager.NETWORK_TYPE_BITMASK_UMTS;
-        long allowedNetworkTypes2 = TelephonyManager.NETWORK_TYPE_BITMASK_LTE
-                | TelephonyManager.NETWORK_TYPE_BITMASK_LTE_CA;
+        long allowedNetworkTypes2 = TelephonyManager.NETWORK_TYPE_BITMASK_LTE;
         long allowedNetworkTypes3 = TelephonyManager.NETWORK_TYPE_BITMASK_NR
                 | TelephonyManager.NETWORK_TYPE_BITMASK_LTE
                 | TelephonyManager.NETWORK_TYPE_BITMASK_UMTS;
@@ -3699,7 +3679,7 @@
         // NPMS will set policy data to true after tests set it to false,
         // so retry disabling policy data to prevent flaky test failures.
         // TODO: Set empty policies once we can suppress default policies.
-        while ((isDataEnabledForReason || isDataConnectionAvailable) && retry < 10) {
+        while ((isDataEnabledForReason || isDataConnectionAvailable) && retry < 30) {
             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
                     mTelephonyManager,
                     (tm) -> tm.setDataEnabledForReason(TelephonyManager.DATA_ENABLED_REASON_POLICY,
@@ -4764,12 +4744,7 @@
         return major * 100 + minor;
     }
 
-    private Executor mSimpleExecutor = new Executor() {
-        @Override
-        public void execute(Runnable r) {
-            r.run();
-        }
-    };
+    private Executor mSimpleExecutor = Runnable::run;
 
     private static MockSignalStrengthsTelephonyCallback mMockSignalStrengthsTelephonyCallback;
 
@@ -4834,16 +4809,14 @@
         }
         grantLocationPermissions();
 
-        TestThread t = new TestThread(new Runnable() {
-            public void run() {
-                Looper.prepare();
-                mMockCellInfoListener = new MockCellInfoListener();
-                synchronized (mLock) {
-                    mLock.notify(); // listener is ready
-                }
-
-                Looper.loop();
+        TestThread t = new TestThread(() -> {
+            Looper.prepare();
+            mMockCellInfoListener = new MockCellInfoListener();
+            synchronized (mLock) {
+                mLock.notify(); // listener is ready
             }
+
+            Looper.loop();
         });
 
         synchronized (mLock) {
@@ -5165,6 +5138,37 @@
             // expected
         }
     }
+
+    @Test
+    public void testIgnoreInvalidNetworkType() {
+        if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_TELEPHONY)) {
+            return;
+        }
+
+        // NETWORK_TYPE_BITMASK_LTE_CA is invalid, should be converted into NETWORK_TYPE_BITMASK_LTE
+        long invalidAllowedNetworkTypes = TelephonyManager.NETWORK_TYPE_BITMASK_NR
+                | TelephonyManager.NETWORK_TYPE_BITMASK_LTE_CA;
+        long expectedAllowedNetworkTypes = TelephonyManager.NETWORK_TYPE_BITMASK_NR
+                | TelephonyManager.NETWORK_TYPE_BITMASK_LTE;
+        try {
+            ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
+                    mTelephonyManager,
+                    (tm) -> tm.setAllowedNetworkTypesForReason(
+                            TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_POWER,
+                            invalidAllowedNetworkTypes));
+
+            long deviceAllowedNetworkTypes = ShellIdentityUtils.invokeMethodWithShellPermissions(
+                    mTelephonyManager, (tm) -> {
+                        return tm.getAllowedNetworkTypesForReason(
+                                TelephonyManager.ALLOWED_NETWORK_TYPES_REASON_POWER);
+                    }
+            );
+            assertEquals(expectedAllowedNetworkTypes, deviceAllowedNetworkTypes);
+        } catch (SecurityException se) {
+            fail("testIgnoreInvalidNetworkType: SecurityException not expected");
+        }
+    }
+
     @Test
     public void getSimSlotMappingTest() {
         assumeTrue(hasFeature(PackageManager.FEATURE_TELEPHONY_SUBSCRIPTION));
@@ -5196,103 +5200,54 @@
         return true;
     }
 
-    private static class ServiceStateListener extends TelephonyCallback
-            implements TelephonyCallback.ServiceStateListener {
-        CountDownLatch mLatch;
-        Predicate<ServiceState> mStateToWaitFor;
+    private static class ServiceStateRadioStateListener extends TelephonyCallback
+            implements TelephonyCallback.ServiceStateListener,
+            TelephonyCallback.RadioPowerStateListener {
+        ServiceState mServiceState;
+        int mRadioPowerState;
 
-        ServiceStateListener(Predicate<ServiceState> stateToWaitFor) {
-            mLatch = new CountDownLatch(1);
-            mStateToWaitFor = stateToWaitFor;
+        ServiceStateRadioStateListener(ServiceState serviceState, int radioPowerState) {
+            mServiceState = serviceState;
+            mRadioPowerState = radioPowerState;
         }
 
         @Override
         public void onServiceStateChanged(ServiceState ss) {
-            if (mStateToWaitFor.test(ss)) {
-                mLatch.countDown();
-            }
-        }
-
-        public void waitForServiceStateChange(long timeout, TimeUnit unit) throws Exception {
-            if (!mLatch.await(timeout, unit)) {
-                throw new IllegalStateException("ServiceState did not change to satisfy condition");
-            }
-        }
-    }
-
-    private void waitForServiceState(Predicate<ServiceState> condition, long timeout, TimeUnit unit)
-            throws Exception {
-        ServiceStateListener callback = new ServiceStateListener(condition);
-        ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
-                mTelephonyManager,
-                tm -> tm.registerTelephonyCallback(Runnable::run, callback));
-        try {
-            callback.waitForServiceStateChange(timeout, unit);
-        } finally {
-            mTelephonyManager.unregisterTelephonyCallback(callback);
-        }
-    }
-
-    private static class RadioPowerStateListener extends TelephonyCallback
-            implements TelephonyCallback.RadioPowerStateListener {
-        CountDownLatch mLatch;
-        @RadioPowerState int mStateToWaitFor;
-
-        RadioPowerStateListener(@RadioPowerState int stateToWaitFor) {
-            mLatch = new CountDownLatch(1);
-            mStateToWaitFor = stateToWaitFor;
+            mServiceState = ss;
         }
 
         @Override
-        public void onRadioPowerStateChanged(@RadioPowerState int state) {
-            if (state == mStateToWaitFor) {
-                mLatch.countDown();
-            }
-        }
-
-        public void waitForRadioPowerStateChange() throws Exception {
-            if (!mLatch.await(10, TimeUnit.SECONDS)) {
-                throw new IllegalStateException(
-                        "Radio power state did not change to " + mStateToWaitFor);
-            }
-        }
-    }
-
-    private void setRadioPower(boolean powerOn) throws Exception {
-        RadioPowerStateListener callback =
-                new RadioPowerStateListener(
-                        powerOn
-                                ? TelephonyManager.RADIO_POWER_ON
-                                : TelephonyManager.RADIO_POWER_OFF);
-        ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
-                mTelephonyManager,
-                tm -> tm.registerTelephonyCallback(Runnable::run, callback),
-                permission.READ_PRIVILEGED_PHONE_STATE);
-        try {
-            ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
-                    mTelephonyManager,
-                    tm -> tm.setRadioPower(powerOn),
-                    permission.MODIFY_PHONE_STATE);
-            callback.waitForRadioPowerStateChange();
-        } finally {
-            mTelephonyManager.unregisterTelephonyCallback(callback);
+        public void onRadioPowerStateChanged(int radioState) {
+            mRadioPowerState = radioState;
         }
     }
 
     @Test
-    public void testSetVoiceServiceStateOverride() throws Exception {
+    public void testSetVoiceServiceStateOverride() {
         assumeTrue(hasFeature(PackageManager.FEATURE_TELEPHONY_CALLING));
+        ServiceStateRadioStateListener callback = new ServiceStateRadioStateListener(
+                mTelephonyManager.getServiceState(), mTelephonyManager.getRadioPowerState());
+        ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mTelephonyManager,
+                tm -> tm.registerTelephonyCallback(Runnable::run, callback));
 
         boolean turnedRadioOff = false;
         boolean setServiceStateOverride = false;
         try {
             if (mTelephonyManager.getServiceState().getState() == ServiceState.STATE_IN_SERVICE) {
                 Log.i(TAG, "testSetVoiceServiceStateOverride: turning radio off to force OOS");
-                setRadioPower(false);
+                ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mTelephonyManager,
+                        tm -> tm.setRadioPower(false), permission.MODIFY_PHONE_STATE);
                 turnedRadioOff = true;
                 // Wait until ServiceState reflects the power change
-                waitForServiceState(
-                        ss -> ss.getState() != ServiceState.STATE_IN_SERVICE, 10, TimeUnit.SECONDS);
+                int retry = 0;
+                while ((callback.mRadioPowerState != TelephonyManager.RADIO_POWER_OFF
+                        || callback.mServiceState.getState() == ServiceState.STATE_IN_SERVICE)
+                        && retry < 10) {
+                    retry++;
+                    waitForMs(1000);
+                }
+                assertEquals(TelephonyManager.RADIO_POWER_OFF, callback.mRadioPowerState);
+                assertNotEquals(ServiceState.STATE_IN_SERVICE, callback.mServiceState.getState());
             }
             // This could be OUT_OF_SERVICE or POWER_OFF, it doesn't really matter for this test as
             // long as it's not IN_SERVICE
@@ -5300,35 +5255,42 @@
             Log.i(TAG, "testSetVoiceServiceStateOverride: originalSS = " + originalServiceState);
             assertNotEquals(ServiceState.STATE_IN_SERVICE, originalServiceState);
 
-            // Wait for device to finish processing RADIO_POWER_OFF.
-            // Otherwise, Telecom will clear the voice state override before SST processes it.
-            waitForMs(10000);
+            // Telecom will sometimes remove the override after radio reboots.
+            // Retry setting the override to prevent flaky test failures.
+            int listenerState = callback.mServiceState.getState();
+            int telephonyManagerState = originalServiceState;
+            int retry = 0;
+            while ((listenerState != ServiceState.STATE_IN_SERVICE
+                    || telephonyManagerState != ServiceState.STATE_IN_SERVICE) && retry < 3) {
+                // We should see the override in both ServiceStateListener and getServiceState
+                ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mTelephonyManager,
+                        tm -> tm.setVoiceServiceStateOverride(true),
+                        permission.BIND_TELECOM_CONNECTION_SERVICE);
+                setServiceStateOverride = true;
 
-            // We should see the override reflected by both ServiceStateListener and getServiceState
-            ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
-                    mTelephonyManager,
-                    tm -> tm.setVoiceServiceStateOverride(true),
-                    permission.BIND_TELECOM_CONNECTION_SERVICE);
-            setServiceStateOverride = true;
-            waitForServiceState(
-                    ss -> ss.getState() == ServiceState.STATE_IN_SERVICE, 5, TimeUnit.SECONDS);
-            assertEquals(
-                    ServiceState.STATE_IN_SERVICE, mTelephonyManager.getServiceState().getState());
+                ServiceState serviceState = mTelephonyManager.getServiceState();
+                if (serviceState != null) {
+                    telephonyManagerState = serviceState.getState();
+                }
+                listenerState = callback.mServiceState.getState();
+                retry++;
+                waitForMs(5000);
+            }
+            assertEquals(ServiceState.STATE_IN_SERVICE, listenerState);
+            assertEquals(ServiceState.STATE_IN_SERVICE, telephonyManagerState);
 
             // When we take away the override, things flip back to the original state since there
             // were no other material changes made to the device that would impact ServiceState
-            ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
-                    mTelephonyManager,
+            ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mTelephonyManager,
                     tm -> tm.setVoiceServiceStateOverride(false),
                     permission.BIND_TELECOM_CONNECTION_SERVICE);
-            waitForServiceState(ss -> ss.getState() == originalServiceState, 5, TimeUnit.SECONDS);
+            assertEquals(originalServiceState, callback.mServiceState.getState());
             assertEquals(originalServiceState, mTelephonyManager.getServiceState().getState());
         } finally {
             if (setServiceStateOverride) {
                 // No harm in calling this again if we already did, but call just in case we failed
                 // an assertion related to setOverride(true)
-                ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
-                        mTelephonyManager,
+                ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mTelephonyManager,
                         tm -> tm.setVoiceServiceStateOverride(false),
                         permission.BIND_TELECOM_CONNECTION_SERVICE);
             }
@@ -5336,11 +5298,18 @@
                 // Turn the radio back on and wait for ServiceState to become stable again so we
                 // don't cause flakes in other tests
                 Log.i(TAG, "testSetVoiceServiceStateOverride: turning radio back on");
-                setRadioPower(true);
-                waitForServiceState(
-                        ss -> ss.getState() == ServiceState.STATE_IN_SERVICE, 30, TimeUnit.SECONDS);
+                ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mTelephonyManager,
+                        tm -> tm.setRadioPower(true), permission.MODIFY_PHONE_STATE);
+                int retry = 0;
+                while ((callback.mRadioPowerState != TelephonyManager.RADIO_POWER_ON
+                        || callback.mServiceState.getState() != ServiceState.STATE_IN_SERVICE)
+                        && retry < 10) {
+                    retry++;
+                    waitForMs(1000);
+                }
+                assertEquals(TelephonyManager.RADIO_POWER_ON, callback.mRadioPowerState);
+                assertEquals(ServiceState.STATE_IN_SERVICE, callback.mServiceState.getState());
             }
         }
     }
 }
-
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTestOnMockModem.java b/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTestOnMockModem.java
index 81850a8..7a76aca 100644
--- a/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTestOnMockModem.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTestOnMockModem.java
@@ -179,6 +179,7 @@
 
         // Remove the SIM
         assertTrue(sMockModemManager.removeSimCard(slotId));
+        TimeUnit.SECONDS.sleep(2);
         simCardState = sTelephonyManager.getSimCardState();
         assertEquals(TelephonyManager.SIM_STATE_ABSENT, simCardState);
     }
diff --git a/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsDownloadSessionTest.java b/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsDownloadSessionTest.java
index 910050f..eed8158 100644
--- a/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsDownloadSessionTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsDownloadSessionTest.java
@@ -57,6 +57,10 @@
         // Make sure we got the streaming services
         List<FileServiceInfo> serviceInfos =
                 (List<FileServiceInfo>) mCallback.waitOnFileServicesUpdated().arg1;
+        if (!CtsDownloadService.FILE_SERVICE_INFO.equals(serviceInfos.get(0))) {
+            mDownloadSession.requestUpdateFileServices(testClasses);
+            serviceInfos = (List<FileServiceInfo>) mCallback.waitOnFileServicesUpdated().arg1;
+        }
         assertEquals(CtsDownloadService.FILE_SERVICE_INFO, serviceInfos.get(0));
         assertEquals(0, mCallback.getNumErrorCalls());
 
diff --git a/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsStreamingSessionTest.java b/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsStreamingSessionTest.java
index 436f611..a6850b2 100644
--- a/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsStreamingSessionTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/embms/cts/MbmsStreamingSessionTest.java
@@ -24,12 +24,12 @@
 import android.telephony.mbms.MbmsErrors;
 import android.telephony.mbms.StreamingServiceInfo;
 
+import org.junit.Test;
+
 import java.util.Arrays;
 import java.util.Collections;
 import java.util.List;
 
-import org.junit.Test;
-
 public class MbmsStreamingSessionTest extends MbmsStreamingTestBase {
     @Test
     public void testDuplicateSession() throws Exception {
@@ -50,6 +50,11 @@
         // Make sure we got the streaming services
         List<StreamingServiceInfo> serviceInfos =
                 (List<StreamingServiceInfo>) mCallback.waitOnStreamingServicesUpdated().arg1;
+        if (!CtsStreamingService.STREAMING_SERVICE_INFO.equals(serviceInfos.get(0))) {
+            mStreamingSession.requestUpdateStreamingServices(testClasses);
+            serviceInfos =
+                    (List<StreamingServiceInfo>) mCallback.waitOnStreamingServicesUpdated().arg1;
+        }
         assertEquals(CtsStreamingService.STREAMING_SERVICE_INFO, serviceInfos.get(0));
         assertEquals(0, mCallback.getNumErrorCalls());
 
diff --git a/tests/tests/wifi/src/android/net/wifi/cts/WifiManagerTest.java b/tests/tests/wifi/src/android/net/wifi/cts/WifiManagerTest.java
index d83bdb2..3b004dd 100644
--- a/tests/tests/wifi/src/android/net/wifi/cts/WifiManagerTest.java
+++ b/tests/tests/wifi/src/android/net/wifi/cts/WifiManagerTest.java
@@ -5492,9 +5492,10 @@
                 network.setBssidAllowlist(Collections.emptyList());
                 mWifiManager.updateNetwork(network);
             }
-            // trigger a disconnect and wait for disconnect.
-            mWifiManager.disconnect();
-            waitForDisconnection();
+
+            // Disable and re-enable Wifi to avoid reconnect to the secondary candidate
+            setWifiEnabled(false);
+            setWifiEnabled(true);
 
             // Now trigger scan and ensure that the device does not connect to any networks.
             mWifiManager.startScan();