Merge "Add long-running recurring I/O overuse kitchensink test." into sc-v2-dev
diff --git a/FrameworkPackageStubs/res/values-my/strings.xml b/FrameworkPackageStubs/res/values-my/strings.xml
index 7becb7d..2cf332a 100644
--- a/FrameworkPackageStubs/res/values-my/strings.xml
+++ b/FrameworkPackageStubs/res/values-my/strings.xml
@@ -3,6 +3,6 @@
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
     <string name="app_name" msgid="6179574017413146651">"လုပ်ဆောင်ချက် အပိုင်း"</string>
     <string name="message_not_supported" msgid="133939962837892495">"ဤအလုပ်ကို မည်သည့်အက်ပ်မျှ မစီမံနိုင်ပါ"</string>
-    <string name="pip_not_supported" msgid="8681268258599412706">"ဤစက်တွင် \'တစ်ခုပေါ်တစ်ခုထပ်၍ ဖွင့်ခြင်း\' သုံး၍မရပါ"</string>
+    <string name="pip_not_supported" msgid="8681268258599412706">"ဤစက်တွင် \'နှစ်ခုထပ်၍ကြည့်ခြင်း\' သုံး၍မရပါ"</string>
     <string name="stub_name" msgid="3987164490218189006">"မရှိ"</string>
 </resources>
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/color/car_radio_button_checked_color.xml b/car_product/overlay-visual/frameworks/base/core/res/res/color/car_radio_button_checked_color.xml
new file mode 100644
index 0000000..e29e5b6
--- /dev/null
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/color/car_radio_button_checked_color.xml
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    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.
+-->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:state_enabled="false"
+        android:alpha="?android:attr/disabledAlpha"
+        android:color="?android:attr/colorControlActivated"/>
+    <item android:color="?android:attr/colorControlActivated"/>
+</selector>
+
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/color/car_radio_button_unchecked_color.xml b/car_product/overlay-visual/frameworks/base/core/res/res/color/car_radio_button_unchecked_color.xml
new file mode 100644
index 0000000..2fe7d66
--- /dev/null
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/color/car_radio_button_unchecked_color.xml
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    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.
+-->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:state_enabled="false"
+        android:alpha="?android:attr/disabledAlpha"
+        android:color="?android:attr/colorControlNormal"/>
+    <item android:color="?android:attr/colorControlNormal"/>
+</selector>
+
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button.xml b/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button.xml
new file mode 100644
index 0000000..aa95e82
--- /dev/null
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button.xml
@@ -0,0 +1,20 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  ~ Copyright 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.
+  -->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:state_checked="false" android:drawable="@drawable/car_radio_button_unchecked" />
+    <item android:state_checked="true" android:drawable="@drawable/car_radio_button_checked" />
+</selector>
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button_checked.xml b/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button_checked.xml
new file mode 100644
index 0000000..22803ab
--- /dev/null
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button_checked.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  ~ Copyright 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.
+  -->
+<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:gravity="center">
+        <shape
+            android:shape="oval">
+            <size
+                android:width="@dimen/car_radio_button_outer_ring_size"
+                android:height="@dimen/car_radio_button_outer_ring_size" />
+            <stroke
+                android:width="@dimen/car_radio_button_outer_ring_stroke_width"
+                android:color="@color/car_radio_button_checked_color"/>
+        </shape>
+    </item>
+    <item android:gravity="center">
+        <shape
+            android:shape="oval">
+            <size
+                android:width="@dimen/car_radio_button_inner_circle_size"
+                android:height="@dimen/car_radio_button_inner_circle_size" />
+            <solid android:color="@color/car_radio_button_checked_color"/>
+        </shape>
+    </item>
+</layer-list>
+
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button_unchecked.xml b/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button_unchecked.xml
new file mode 100644
index 0000000..f55d85b
--- /dev/null
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/drawable/car_radio_button_unchecked.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  ~ Copyright 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.
+  -->
+<shape xmlns:android="http://schemas.android.com/apk/res/android"
+    android:shape="oval">
+    <size
+        android:width="@dimen/car_radio_button_outer_ring_size"
+        android:height="@dimen/car_radio_button_outer_ring_size" />
+    <stroke
+        android:width="@dimen/car_radio_button_outer_ring_stroke_width"
+        android:color="@color/car_radio_button_unchecked_color" />
+</shape>
+
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/values/dimens.xml b/car_product/overlay-visual/frameworks/base/core/res/res/values/dimens.xml
index b1ab72a..78bb728 100644
--- a/car_product/overlay-visual/frameworks/base/core/res/res/values/dimens.xml
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/values/dimens.xml
@@ -146,6 +146,11 @@
     <!-- car_switch_thumb_size + car_switch_thumb_stroke_width == car_switch_track_height -->
     <dimen name="car_switch_thumb_size">40dp</dimen>
 
+    <!-- Radio button dimensions -->
+    <dimen name="car_radio_button_outer_ring_size">45dp</dimen>
+    <dimen name="car_radio_button_outer_ring_stroke_width">2dp</dimen>
+    <dimen name="car_radio_button_inner_circle_size">32dp</dimen>
+
     <!-- SeekBar dimensions. -->
     <!-- Allows thumb to extend out of the range of the track. -->
     <!-- For more information see android.widget.SeekBar#attr_android:thumbOffset. -->
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/values/styles_device_default.xml b/car_product/overlay-visual/frameworks/base/core/res/res/values/styles_device_default.xml
index 191b9ac..1038815 100644
--- a/car_product/overlay-visual/frameworks/base/core/res/res/values/styles_device_default.xml
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/values/styles_device_default.xml
@@ -106,6 +106,11 @@
         <item name="android:button">@*android:drawable/car_checkbox</item>
     </style>
 
+    <style name="Widget.DeviceDefault.CompoundButton.RadioButton"
+        parent="android:Widget.DeviceDefault.CompoundButton.RadioButton">
+        <item name="android:button">@drawable/car_radio_button</item>
+    </style>
+
     <style name="Widget.DeviceDefault.CompoundButton.Switch"
         parent="android:Widget.Material.CompoundButton.Switch">
         <item name="android:thumb">@drawable/car_switch_thumb</item>
diff --git a/car_product/overlay-visual/frameworks/base/core/res/res/values/themes_device_defaults.xml b/car_product/overlay-visual/frameworks/base/core/res/res/values/themes_device_defaults.xml
index 45c33d3..1e81822 100644
--- a/car_product/overlay-visual/frameworks/base/core/res/res/values/themes_device_defaults.xml
+++ b/car_product/overlay-visual/frameworks/base/core/res/res/values/themes_device_defaults.xml
@@ -43,6 +43,7 @@
         <item name="android:textAppearanceListItemSmall">@*android:style/TextAppearance.DeviceDefault.Large</item>
         <item name="android:textAppearanceListItemSecondary">@*android:style/TextAppearance.DeviceDefault.Small</item>
         <item name="android:actionBarSize">@*android:dimen/car_app_bar_height</item>
+        <item name="android:radioButtonStyle">@style/Widget.DeviceDefault.CompoundButton.RadioButton</item>
 
         <item name="colorSwitchThumbNormal">@color/car_switch_thumb_color</item>
         <item name="colorSwitchTrack">@color/car_switch_track_background_selector</item>
diff --git a/cpp/watchdog/aidl/android/automotive/watchdog/internal/ICarWatchdog.aidl b/cpp/watchdog/aidl/android/automotive/watchdog/internal/ICarWatchdog.aidl
index c9ece21..61b65c7 100644
--- a/cpp/watchdog/aidl/android/automotive/watchdog/internal/ICarWatchdog.aidl
+++ b/cpp/watchdog/aidl/android/automotive/watchdog/internal/ICarWatchdog.aidl
@@ -19,7 +19,6 @@
 import android.automotive.watchdog.internal.ComponentType;
 import android.automotive.watchdog.internal.ICarWatchdogMonitor;
 import android.automotive.watchdog.internal.ICarWatchdogServiceForSystem;
-import android.automotive.watchdog.internal.PackageResourceOveruseAction;
 import android.automotive.watchdog.internal.ResourceOveruseConfiguration;
 import android.automotive.watchdog.internal.StateType;
 
@@ -121,14 +120,6 @@
    */
   List<ResourceOveruseConfiguration> getResourceOveruseConfigurations();
 
-  /**
-   * CarWatchdogService notifies the native service with the actions taken on the resource overusing
-   * applications.
-   *
-   * @param actions              List of actions take on resource overusing packages.
-   */
-   void actionTakenOnResourceOveruse(in List<PackageResourceOveruseAction> actions);
-
    /**
     * Enable/disable the internal client health check process.
     * Disabling would stop the ANR killing process.
diff --git a/cpp/watchdog/aidl/android/automotive/watchdog/internal/PackageResourceOveruseAction.aidl b/cpp/watchdog/aidl/android/automotive/watchdog/internal/PackageResourceOveruseAction.aidl
deleted file mode 100644
index 521b604..0000000
--- a/cpp/watchdog/aidl/android/automotive/watchdog/internal/PackageResourceOveruseAction.aidl
+++ /dev/null
@@ -1,41 +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.automotive.watchdog.internal;
-
-import android.automotive.watchdog.internal.PackageIdentifier;
-import android.automotive.watchdog.internal.ResourceOveruseActionType;
-import android.automotive.watchdog.ResourceType;
-
-/**
- * Structure that describes the action taken on a package due to resource overuse.
- */
-parcelable PackageResourceOveruseAction {
-  /**
-   * Identifier for the package.
-   */
-  PackageIdentifier packageIdentifier;
-
-  /**
-   * Resources that were overused.
-   */
-  ResourceType[] resourceTypes;
-
-  /**
-   * Action taken on the package.
-   */
-  ResourceOveruseActionType resourceOveruseActionType = ResourceOveruseActionType.NOT_KILLED;
-}
diff --git a/cpp/watchdog/aidl/android/automotive/watchdog/internal/ResourceOveruseActionType.aidl b/cpp/watchdog/aidl/android/automotive/watchdog/internal/ResourceOveruseActionType.aidl
deleted file mode 100644
index 0d7d935..0000000
--- a/cpp/watchdog/aidl/android/automotive/watchdog/internal/ResourceOveruseActionType.aidl
+++ /dev/null
@@ -1,44 +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.automotive.watchdog.internal;
-
-/**
- * Describes the action taken on resource overuse.
- */
-@Backing(type="int")
-enum ResourceOveruseActionType {
-  /**
-   * The package is not killed because either it is not killable, internal error occurred, or
-   * already disabled.
-   */
-  NOT_KILLED,
-
-  /**
-   * The package is not killed as the user opted-out the package from killing on resource overuse.
-   */
-  NOT_KILLED_USER_OPTED,
-
-  /**
-   * The package is killed on resource overuse.
-   */
-  KILLED,
-
-  /**
-   * The package is killed as it has recurring resource overuse pattern.
-   */
-  KILLED_RECURRING_OVERUSE,
-}
diff --git a/cpp/watchdog/car-watchdog-lib/src/android/car/watchdoglib/CarWatchdogDaemonHelper.java b/cpp/watchdog/car-watchdog-lib/src/android/car/watchdoglib/CarWatchdogDaemonHelper.java
index e7229ba..945383a 100644
--- a/cpp/watchdog/car-watchdog-lib/src/android/car/watchdoglib/CarWatchdogDaemonHelper.java
+++ b/cpp/watchdog/car-watchdog-lib/src/android/car/watchdoglib/CarWatchdogDaemonHelper.java
@@ -23,7 +23,6 @@
 import android.automotive.watchdog.internal.ICarWatchdog;
 import android.automotive.watchdog.internal.ICarWatchdogMonitor;
 import android.automotive.watchdog.internal.ICarWatchdogServiceForSystem;
-import android.automotive.watchdog.internal.PackageResourceOveruseAction;
 import android.automotive.watchdog.internal.ResourceOveruseConfiguration;
 import android.os.Handler;
 import android.os.IBinder;
@@ -280,18 +279,6 @@
     }
 
     /**
-     * Notifies car watchdog daemon with the actions taken on resource overuse.
-     *
-     * @param actions List of actions taken on resource overuse. One action taken per resource
-     *                overusing user package.
-     * @throws RemoteException
-     */
-    public void actionTakenOnResourceOveruse(List<PackageResourceOveruseAction> actions)
-            throws RemoteException {
-        invokeDaemonMethod((daemon) -> daemon.actionTakenOnResourceOveruse(actions));
-    }
-
-    /**
      * Enable/disable the internal client health check process.
      * Disabling would stop the ANR killing process.
      *
diff --git a/cpp/watchdog/server/src/IoOveruseMonitor.cpp b/cpp/watchdog/server/src/IoOveruseMonitor.cpp
index 1164a2a..0ebe0d4 100644
--- a/cpp/watchdog/server/src/IoOveruseMonitor.cpp
+++ b/cpp/watchdog/server/src/IoOveruseMonitor.cpp
@@ -50,7 +50,6 @@
 using ::android::automotive::watchdog::internal::PackageIdentifier;
 using ::android::automotive::watchdog::internal::PackageInfo;
 using ::android::automotive::watchdog::internal::PackageIoOveruseStats;
-using ::android::automotive::watchdog::internal::PackageResourceOveruseAction;
 using ::android::automotive::watchdog::internal::ResourceOveruseConfiguration;
 using ::android::automotive::watchdog::internal::UidType;
 using ::android::automotive::watchdog::internal::UserPackageIoUsageStats;
@@ -472,7 +471,6 @@
     if (DEBUG) {
         ALOGD("Notified native packages on I/O overuse");
     }
-    // TODO(b/184310189): Upload I/O overuse metrics for native packages.
 }
 
 Result<void> IoOveruseMonitor::updateResourceOveruseConfigurations(
@@ -512,15 +510,6 @@
     return {};
 }
 
-Result<void> IoOveruseMonitor::actionTakenOnIoOveruse(
-        [[maybe_unused]] const std::vector<PackageResourceOveruseAction>& actions) {
-    // TODO(b/184310189): Upload metrics.
-    if (DEBUG) {
-        ALOGD("Recorded action taken on I/O overuse");
-    }
-    return {};
-}
-
 Result<void> IoOveruseMonitor::addIoOveruseListener(const sp<IResourceOveruseListener>& listener) {
     pid_t callingPid = IPCThreadState::self()->getCallingPid();
     uid_t callingUid = IPCThreadState::self()->getCallingUid();
diff --git a/cpp/watchdog/server/src/IoOveruseMonitor.h b/cpp/watchdog/server/src/IoOveruseMonitor.h
index 57c01c0..5fa91aa 100644
--- a/cpp/watchdog/server/src/IoOveruseMonitor.h
+++ b/cpp/watchdog/server/src/IoOveruseMonitor.h
@@ -31,7 +31,6 @@
 #include <android/automotive/watchdog/internal/IoOveruseConfiguration.h>
 #include <android/automotive/watchdog/internal/PackageInfo.h>
 #include <android/automotive/watchdog/internal/PackageIoOveruseStats.h>
-#include <android/automotive/watchdog/internal/PackageResourceOveruseAction.h>
 #include <utils/Mutex.h>
 
 #include <time.h>
@@ -81,10 +80,6 @@
     virtual android::base::Result<void> getResourceOveruseConfigurations(
             std::vector<android::automotive::watchdog::internal::ResourceOveruseConfiguration>*
                     configs) const = 0;
-    virtual android::base::Result<void> actionTakenOnIoOveruse(
-            const std::vector<
-                    android::automotive::watchdog::internal::PackageResourceOveruseAction>&
-                    actions) = 0;
 
     // Below methods support APIs from ICarWatchdog.aidl. Please refer to the AIDL for description.
     virtual android::base::Result<void> addIoOveruseListener(
@@ -155,11 +150,6 @@
             std::vector<android::automotive::watchdog::internal::ResourceOveruseConfiguration>*
                     configs) const override;
 
-    android::base::Result<void> actionTakenOnIoOveruse(
-            const std::vector<
-                    android::automotive::watchdog::internal::PackageResourceOveruseAction>& actions)
-            override;
-
     android::base::Result<void> addIoOveruseListener(
             const sp<IResourceOveruseListener>& listener) override;
 
diff --git a/cpp/watchdog/server/src/WatchdogInternalHandler.cpp b/cpp/watchdog/server/src/WatchdogInternalHandler.cpp
index be49ff9..2441ccf 100644
--- a/cpp/watchdog/server/src/WatchdogInternalHandler.cpp
+++ b/cpp/watchdog/server/src/WatchdogInternalHandler.cpp
@@ -36,7 +36,6 @@
 using aawi::ComponentType;
 using aawi::GarageMode;
 using aawi::ICarWatchdogServiceForSystem;
-using aawi::PackageResourceOveruseAction;
 using aawi::PowerCycle;
 using aawi::ResourceOveruseConfiguration;
 using ::android::sp;
@@ -256,18 +255,6 @@
     return Status::ok();
 }
 
-Status WatchdogInternalHandler::actionTakenOnResourceOveruse(
-        const std::vector<PackageResourceOveruseAction>& actions) {
-    Status status = checkSystemUser();
-    if (!status.isOk()) {
-        return status;
-    }
-    if (const auto result = mIoOveruseMonitor->actionTakenOnIoOveruse(actions); !result.ok()) {
-        return fromExceptionCode(result.error().code(), result.error().message());
-    }
-    return Status::ok();
-}
-
 Status WatchdogInternalHandler::controlProcessHealthCheck(bool disable) {
     Status status = checkSystemUser();
     if (!status.isOk()) {
diff --git a/cpp/watchdog/server/src/WatchdogInternalHandler.h b/cpp/watchdog/server/src/WatchdogInternalHandler.h
index e23620e..1000c8e 100644
--- a/cpp/watchdog/server/src/WatchdogInternalHandler.h
+++ b/cpp/watchdog/server/src/WatchdogInternalHandler.h
@@ -26,7 +26,6 @@
 #include <android/automotive/watchdog/internal/ComponentType.h>
 #include <android/automotive/watchdog/internal/ICarWatchdogMonitor.h>
 #include <android/automotive/watchdog/internal/ICarWatchdogServiceForSystem.h>
-#include <android/automotive/watchdog/internal/PackageResourceOveruseAction.h>
 #include <android/automotive/watchdog/internal/ResourceOveruseConfiguration.h>
 #include <android/automotive/watchdog/internal/StateType.h>
 #include <binder/Status.h>
@@ -89,10 +88,6 @@
     android::binder::Status getResourceOveruseConfigurations(
             std::vector<android::automotive::watchdog::internal::ResourceOveruseConfiguration>*
                     configs) override;
-    android::binder::Status actionTakenOnResourceOveruse(
-            const std::vector<
-                    android::automotive::watchdog::internal::PackageResourceOveruseAction>& actions)
-            override;
     android::binder::Status controlProcessHealthCheck(bool disable) override;
 
 protected:
diff --git a/cpp/watchdog/server/tests/MockIoOveruseMonitor.h b/cpp/watchdog/server/tests/MockIoOveruseMonitor.h
index a9d677e..294276b 100644
--- a/cpp/watchdog/server/tests/MockIoOveruseMonitor.h
+++ b/cpp/watchdog/server/tests/MockIoOveruseMonitor.h
@@ -45,11 +45,6 @@
             android::base::Result<void>, getResourceOveruseConfigurations,
             (std::vector<android::automotive::watchdog::internal::ResourceOveruseConfiguration>*),
             (const, override));
-    MOCK_METHOD(android::base::Result<void>, actionTakenOnIoOveruse,
-                (const std::vector<
-                        android::automotive::watchdog::internal::PackageResourceOveruseAction>&
-                         actions),
-                (override));
     MOCK_METHOD(android::base::Result<void>, addIoOveruseListener,
                 (const sp<IResourceOveruseListener>&), (override));
     MOCK_METHOD(android::base::Result<void>, removeIoOveruseListener,
diff --git a/cpp/watchdog/server/tests/WatchdogInternalHandlerTest.cpp b/cpp/watchdog/server/tests/WatchdogInternalHandlerTest.cpp
index 4646a11..a5abbc4 100644
--- a/cpp/watchdog/server/tests/WatchdogInternalHandlerTest.cpp
+++ b/cpp/watchdog/server/tests/WatchdogInternalHandlerTest.cpp
@@ -45,7 +45,6 @@
 using aawi::GarageMode;
 using aawi::ICarWatchdogServiceForSystem;
 using aawi::ICarWatchdogServiceForSystemDefault;
-using aawi::PackageResourceOveruseAction;
 using aawi::PowerCycle;
 using aawi::ResourceOveruseConfiguration;
 using ::android::sp;
@@ -454,22 +453,6 @@
     ASSERT_FALSE(status.isOk()) << status;
 }
 
-TEST_F(WatchdogInternalHandlerTest, TestActionTakenOnResourceOveruse) {
-    setSystemCallingUid();
-    EXPECT_CALL(*mMockIoOveruseMonitor, actionTakenOnIoOveruse(_)).WillOnce(Return(Result<void>()));
-    Status status = mWatchdogInternalHandler->actionTakenOnResourceOveruse(
-            std::vector<PackageResourceOveruseAction>{});
-    ASSERT_TRUE(status.isOk()) << status;
-}
-
-TEST_F(WatchdogInternalHandlerTest,
-       TestErrorOnActionTakenOnResourceOveruseWithNonSystemCallingUid) {
-    EXPECT_CALL(*mMockIoOveruseMonitor, actionTakenOnIoOveruse(_)).Times(0);
-    Status status = mWatchdogInternalHandler->actionTakenOnResourceOveruse(
-            std::vector<PackageResourceOveruseAction>{});
-    ASSERT_FALSE(status.isOk()) << status;
-}
-
 TEST_F(WatchdogInternalHandlerTest, TestControlProcessHealthCheck) {
     setSystemCallingUid();
     EXPECT_CALL(*mMockWatchdogProcessService, setEnabled(/*isEnabled=*/true)).Times(1);
diff --git a/packages/CarShell/AndroidManifest.xml b/packages/CarShell/AndroidManifest.xml
index 40420d7..c07083c 100644
--- a/packages/CarShell/AndroidManifest.xml
+++ b/packages/CarShell/AndroidManifest.xml
@@ -21,6 +21,8 @@
         coreApp="true"
         android:sharedUserId="android.uid.shell"
         >
+    <!-- Permission required for ATS tests - AtsAudioDeviceTest#resetVolumeMute-->
+    <uses-permission android:name="android.permission.MODIFY_AUDIO_ROUTING" />
     <!-- To pass GtsInstallPackagesWhitelistDeviceTestCases b/173156153 -->
     <uses-permission android:name="android.permission.INSTALL_PACKAGES" />
     <!-- Permission required for ATS tests - AtsCarHostTestCases, AtsCarDeviceApp -->
diff --git a/service/src/com/android/car/telemetry/databroker/DataSubscriber.java b/service/src/com/android/car/telemetry/databroker/DataSubscriber.java
index 9ab7604..d61d89c 100644
--- a/service/src/com/android/car/telemetry/databroker/DataSubscriber.java
+++ b/service/src/com/android/car/telemetry/databroker/DataSubscriber.java
@@ -57,12 +57,20 @@
 
     /**
      * Creates a {@link ScriptExecutionTask} and pushes it to the priority queue where the task
-     * will be pending execution.
+     * will be pending execution. Flag isLargeData indicates whether data is large.
+     */
+    public void push(PersistableBundle data, boolean isLargeData) {
+        ScriptExecutionTask task = new ScriptExecutionTask(
+                this, data, SystemClock.elapsedRealtime(), isLargeData);
+        mDataBroker.addTaskToQueue(task);
+    }
+
+    /**
+     * Creates a {@link ScriptExecutionTask} and pushes it to the priority queue where the task
+     * will be pending execution. Defaults isLargeData flag to false.
      */
     public void push(PersistableBundle data) {
-        ScriptExecutionTask task = new ScriptExecutionTask(
-                this, data, SystemClock.elapsedRealtime());
-        mDataBroker.addTaskToQueue(task);
+        push(data, false);
     }
 
     /** Returns the {@link TelemetryProto.MetricsConfig}. */
diff --git a/service/src/com/android/car/telemetry/databroker/ScriptExecutionTask.java b/service/src/com/android/car/telemetry/databroker/ScriptExecutionTask.java
index 18d0512..5a995d2 100644
--- a/service/src/com/android/car/telemetry/databroker/ScriptExecutionTask.java
+++ b/service/src/com/android/car/telemetry/databroker/ScriptExecutionTask.java
@@ -17,7 +17,6 @@
 package com.android.car.telemetry.databroker;
 
 import android.car.telemetry.MetricsConfigKey;
-import android.os.Parcel;
 import android.os.PersistableBundle;
 
 import com.android.car.telemetry.TelemetryProto;
@@ -30,37 +29,17 @@
  * The object can be accessed from any thread. See {@link DataSubscriber} for thread-safety.
  */
 public class ScriptExecutionTask implements Comparable<ScriptExecutionTask> {
-    // Key to the calculated bundle size, which doesn't contain implementation-dependent overhead
-    // and other allocations. It's approximately 10% smaller than the actual size of binder parcel.
-    public static final String APPROX_BUNDLE_SIZE_BYTES_KEY = "approx_bundle_size_bytes";
-
-    /**
-     * Binder transaction size limit is 1MB for all binders per process, so for large script input
-     * file pipe will be used to transfer the data to script executor instead of binder call. This
-     * is the input size threshold above which piping is used.
-     */
-    private static final int LARGE_SCRIPT_INPUT_SIZE_BYTES = 20 * 1024; // 20 kb
-
     private final long mTimestampMillis;
     private final DataSubscriber mSubscriber;
     private final PersistableBundle mData;
     private final boolean mIsLargeData;
 
     ScriptExecutionTask(DataSubscriber subscriber, PersistableBundle data,
-            long elapsedRealtimeMillis) {
+            long elapsedRealtimeMillis, boolean isLargeData) {
         mTimestampMillis = elapsedRealtimeMillis;
         mSubscriber = subscriber;
         mData = data;
-        if (mData.containsKey(APPROX_BUNDLE_SIZE_BYTES_KEY)) {
-            mIsLargeData =
-                    mData.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY) > LARGE_SCRIPT_INPUT_SIZE_BYTES;
-            mData.remove(APPROX_BUNDLE_SIZE_BYTES_KEY);
-        } else {
-            Parcel parcel = Parcel.obtain();
-            parcel.writePersistableBundle(mData);
-            mIsLargeData = parcel.dataSize() > LARGE_SCRIPT_INPUT_SIZE_BYTES;
-            parcel.recycle();
-        }
+        mIsLargeData = isLargeData;
     }
 
     /** Returns the priority of the task. */
diff --git a/service/src/com/android/car/telemetry/proto/atoms.proto b/service/src/com/android/car/telemetry/proto/atoms.proto
index ccb9021..443ec58 100644
--- a/service/src/com/android/car/telemetry/proto/atoms.proto
+++ b/service/src/com/android/car/telemetry/proto/atoms.proto
@@ -32,6 +32,7 @@
   // Pulled events will start at field 10000.
   oneof pulled {
     ProcessMemoryState process_memory_state = 10013;
+    ProcessCpuTime process_cpu_time = 10035;
   }
 }
 
@@ -68,3 +69,10 @@
   }
   optional State state = 4;
 }
+
+message ProcessCpuTime {
+  optional int32 uid = 1;
+  optional string process_name = 2;
+  optional int64 user_time_millis = 3;
+  optional int64 system_time_millis = 4;
+}
diff --git a/service/src/com/android/car/telemetry/proto/telemetry.proto b/service/src/com/android/car/telemetry/proto/telemetry.proto
index 4106098..f5b14a1 100644
--- a/service/src/com/android/car/telemetry/proto/telemetry.proto
+++ b/service/src/com/android/car/telemetry/proto/telemetry.proto
@@ -87,6 +87,8 @@
     PROCESS_MEMORY_STATE = 2;
     // Collects activity foreground/background transition events.
     ACTIVITY_FOREGROUND_STATE_CHANGED = 3;
+    // Collects process CPU usage time
+    PROCESS_CPU_TIME = 4;
   }
 
   // Required.
diff --git a/service/src/com/android/car/telemetry/publisher/StatsPublisher.java b/service/src/com/android/car/telemetry/publisher/StatsPublisher.java
index be335e9..8570d6a 100644
--- a/service/src/com/android/car/telemetry/publisher/StatsPublisher.java
+++ b/service/src/com/android/car/telemetry/publisher/StatsPublisher.java
@@ -18,8 +18,11 @@
 
 import static com.android.car.telemetry.AtomsProto.Atom.ACTIVITY_FOREGROUND_STATE_CHANGED_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.Atom.APP_START_MEMORY_STATE_CAPTURED_FIELD_NUMBER;
+import static com.android.car.telemetry.AtomsProto.Atom.PROCESS_CPU_TIME_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.Atom.PROCESS_MEMORY_STATE_FIELD_NUMBER;
 
+import static java.nio.charset.StandardCharsets.UTF_16;
+
 import android.app.StatsManager.StatsUnavailableException;
 import android.os.Handler;
 import android.os.PersistableBundle;
@@ -27,7 +30,8 @@
 import android.util.LongSparseArray;
 
 import com.android.car.CarLog;
-import com.android.car.telemetry.AtomsProto;
+import com.android.car.telemetry.AtomsProto.ProcessCpuTime;
+import com.android.car.telemetry.AtomsProto.ProcessMemoryState;
 import com.android.car.telemetry.StatsLogProto;
 import com.android.car.telemetry.StatsdConfigProto;
 import com.android.car.telemetry.StatsdConfigProto.StatsdConfig;
@@ -74,6 +78,10 @@
     static final long ACTIVITY_FOREGROUND_STATE_CHANGED_ATOM_MATCHER_ID = 5;
     @VisibleForTesting
     static final long ACTIVITY_FOREGROUND_STATE_CHANGED_EVENT_METRIC_ID = 6;
+    @VisibleForTesting
+    static final long PROCESS_CPU_TIME_MATCHER_ID = 7;
+    @VisibleForTesting
+    static final long PROCESS_CPU_TIME_GAUGE_METRIC_ID = 8;
 
     // The file that contains stats config key and stats config version
     @VisibleForTesting
@@ -85,6 +93,12 @@
 
     private static final String BUNDLE_CONFIG_KEY_PREFIX = "statsd-publisher-config-id-";
     private static final String BUNDLE_CONFIG_VERSION_PREFIX = "statsd-publisher-config-version-";
+    /**
+     * Binder transaction size limit is 1MB for all binders per process, so for large script input
+     * file pipe will be used to transfer the data to script executor instead of binder call. This
+     * is the input size threshold above which piping is used.
+     */
+    private static final int SCRIPT_INPUT_SIZE_THRESHOLD_BYTES = 20 * 1024; // 20 kb
 
     @VisibleForTesting
     static final StatsdConfigProto.FieldMatcher PROCESS_MEMORY_STATE_FIELDS_MATCHER =
@@ -92,23 +106,27 @@
                     .setField(
                             PROCESS_MEMORY_STATE_FIELD_NUMBER)
                     .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                            .setField(
-                                    AtomsProto.ProcessMemoryState.OOM_ADJ_SCORE_FIELD_NUMBER))
+                            .setField(ProcessMemoryState.OOM_ADJ_SCORE_FIELD_NUMBER))
                     .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                            .setField(
-                                    AtomsProto.ProcessMemoryState.PAGE_FAULT_FIELD_NUMBER))
+                            .setField(ProcessMemoryState.PAGE_FAULT_FIELD_NUMBER))
                     .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                            .setField(
-                                    AtomsProto.ProcessMemoryState.PAGE_MAJOR_FAULT_FIELD_NUMBER))
+                            .setField(ProcessMemoryState.PAGE_MAJOR_FAULT_FIELD_NUMBER))
                     .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                            .setField(
-                                    AtomsProto.ProcessMemoryState.RSS_IN_BYTES_FIELD_NUMBER))
+                            .setField(ProcessMemoryState.RSS_IN_BYTES_FIELD_NUMBER))
                     .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                            .setField(
-                                    AtomsProto.ProcessMemoryState.CACHE_IN_BYTES_FIELD_NUMBER))
+                            .setField(ProcessMemoryState.CACHE_IN_BYTES_FIELD_NUMBER))
                     .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                            .setField(
-                                    AtomsProto.ProcessMemoryState.SWAP_IN_BYTES_FIELD_NUMBER))
+                            .setField(ProcessMemoryState.SWAP_IN_BYTES_FIELD_NUMBER))
+            .build();
+
+    @VisibleForTesting
+    static final StatsdConfigProto.FieldMatcher PROCESS_CPU_TIME_FIELDS_MATCHER =
+            StatsdConfigProto.FieldMatcher.newBuilder()
+                    .setField(PROCESS_CPU_TIME_FIELD_NUMBER)
+                    .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
+                            .setField(ProcessCpuTime.USER_TIME_MILLIS_FIELD_NUMBER))
+                    .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
+                            .setField(ProcessCpuTime.SYSTEM_TIME_MILLIS_FIELD_NUMBER))
             .build();
 
     private final StatsManagerProxy mStatsManager;
@@ -218,6 +236,9 @@
             case ACTIVITY_FOREGROUND_STATE_CHANGED:
                 metricId = ACTIVITY_FOREGROUND_STATE_CHANGED_EVENT_METRIC_ID;
                 break;
+            case PROCESS_CPU_TIME:
+                metricId = PROCESS_CPU_TIME_GAUGE_METRIC_ID;
+                break;
             default:
                 return;
         }
@@ -226,7 +247,39 @@
                     "No reports for metric id " + metricId + " for config " + configKey);
             return;
         }
-        subscriber.push(metricBundles.get(metricId));
+        PersistableBundle bundle = metricBundles.get(metricId);
+        subscriber.push(bundle, isBundleLargeData(bundle));
+    }
+
+    @VisibleForTesting
+    boolean isBundleLargeData(PersistableBundle bundle) {
+        String[] keys = bundle.keySet().toArray(new String[0]);
+        int bytes = 0;
+        for (int i = 0; i < keys.length; ++i) {
+            Object array = bundle.get(keys[i]);
+            if (array instanceof boolean[]) {
+                boolean[] boolArray = (boolean[]) array;
+                bytes += boolArray.length;  // Java boolean is 1 byte
+            } else if (array instanceof long[]) {
+                long[] longArray = (long[]) array;
+                bytes += longArray.length * Long.BYTES;
+            } else if (array instanceof int[]) {
+                int[] intArray = (int[]) array;
+                bytes += intArray.length * Integer.BYTES;
+            } else if (array instanceof double[]) {
+                double[] doubleArray = (double[]) array;
+                bytes += doubleArray.length * Double.BYTES;
+            } else if (array instanceof String[]) {
+                String[] stringArray = (String[]) array;
+                for (String str : stringArray) {
+                    bytes += str.getBytes(UTF_16).length;
+                }
+            }
+        }
+        if (bytes < SCRIPT_INPUT_SIZE_THRESHOLD_BYTES) {
+            return false;
+        }
+        return true;
     }
 
     private void processStatsMetadata(StatsLogProto.StatsdStatsReport statsReport) {
@@ -470,6 +523,8 @@
                 return buildProcessMemoryStateStatsdConfig(builder);
             case ACTIVITY_FOREGROUND_STATE_CHANGED:
                 return buildActivityForegroundStateStatsdConfig(builder);
+            case PROCESS_CPU_TIME:
+                return buildProcessCpuTimeStatsdConfig(builder);
             default:
                 throw new IllegalArgumentException("Unsupported metric " + metric.name());
         }
@@ -503,9 +558,9 @@
                         .setDimensionsInWhat(StatsdConfigProto.FieldMatcher.newBuilder()
                                 .setField(PROCESS_MEMORY_STATE_FIELD_NUMBER)
                                 .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                                        .setField(1))  // ProcessMemoryState.uid
+                                        .setField(ProcessMemoryState.UID_FIELD_NUMBER))
                                 .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
-                                        .setField(2))  // ProcessMemoryState.process_name
+                                        .setField(ProcessMemoryState.PROCESS_NAME_FIELD_NUMBER))
                         )
                         .setGaugeFieldsFilter(StatsdConfigProto.FieldFilter.newBuilder()
                                 .setFields(PROCESS_MEMORY_STATE_FIELDS_MATCHER)
@@ -534,4 +589,35 @@
                         .setWhat(ACTIVITY_FOREGROUND_STATE_CHANGED_ATOM_MATCHER_ID))
                 .build();
     }
+
+    private static StatsdConfig buildProcessCpuTimeStatsdConfig(StatsdConfig.Builder builder) {
+        return builder
+                .addAtomMatcher(StatsdConfigProto.AtomMatcher.newBuilder()
+                        // The id must be unique within StatsdConfig/matchers
+                        .setId(PROCESS_CPU_TIME_MATCHER_ID)
+                        .setSimpleAtomMatcher(StatsdConfigProto.SimpleAtomMatcher.newBuilder()
+                                .setAtomId(PROCESS_CPU_TIME_FIELD_NUMBER)))
+                .addGaugeMetric(StatsdConfigProto.GaugeMetric.newBuilder()
+                        // The id must be unique within StatsdConfig/metrics
+                        .setId(PROCESS_CPU_TIME_GAUGE_METRIC_ID)
+                        .setWhat(PROCESS_CPU_TIME_MATCHER_ID)
+                        .setDimensionsInWhat(StatsdConfigProto.FieldMatcher.newBuilder()
+                                .setField(PROCESS_CPU_TIME_FIELD_NUMBER)
+                                .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
+                                        .setField(ProcessCpuTime.UID_FIELD_NUMBER))
+                                .addChild(StatsdConfigProto.FieldMatcher.newBuilder()
+                                        .setField(ProcessCpuTime.PROCESS_NAME_FIELD_NUMBER))
+                        )
+                        .setGaugeFieldsFilter(StatsdConfigProto.FieldFilter.newBuilder()
+                                .setFields(PROCESS_CPU_TIME_FIELDS_MATCHER)
+                        )  // setGaugeFieldsFilter
+                        .setSamplingType(
+                                StatsdConfigProto.GaugeMetric.SamplingType.RANDOM_ONE_SAMPLE)
+                        .setBucket(StatsdConfigProto.TimeUnit.FIVE_MINUTES)
+                )
+                .addPullAtomPackages(StatsdConfigProto.PullAtomPackages.newBuilder()
+                        .setAtomId(PROCESS_CPU_TIME_FIELD_NUMBER)
+                        .addPackages("AID_SYSTEM"))
+                .build();
+    }
 }
diff --git a/service/src/com/android/car/telemetry/publisher/statsconverters/AbstractAtomConverter.java b/service/src/com/android/car/telemetry/publisher/statsconverters/AbstractAtomConverter.java
index e201f1d..8e20eb4 100644
--- a/service/src/com/android/car/telemetry/publisher/statsconverters/AbstractAtomConverter.java
+++ b/service/src/com/android/car/telemetry/publisher/statsconverters/AbstractAtomConverter.java
@@ -16,10 +16,6 @@
 
 package com.android.car.telemetry.publisher.statsconverters;
 
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
-
-import static java.nio.charset.StandardCharsets.UTF_16;
-
 import android.os.PersistableBundle;
 import android.util.SparseArray;
 
@@ -102,7 +98,6 @@
             Map<Long, String> hashToStringMap) throws StatsConversionException {
         PersistableBundle bundle = new PersistableBundle();
         SparseArray<AtomFieldAccessor<T>> parserConfig = getAtomFieldAccessorMap();
-        int bundleByteSize = 0;
         // For each field, if set, add the values from all atoms to list and convert
         for (int i = 0; i < parserConfig.size(); ++i) {
             AtomFieldAccessor<T> atomFieldAccessor = parserConfig.valueAt(i);
@@ -120,13 +115,12 @@
                     }
                     valueList.add(atomFieldAccessor.getField(atomData));
                 }
-                bundleByteSize += setPersistableBundleArrayField(
+                setPersistableBundleArrayField(
                         atomFieldAccessor.getFieldName(), valueList, bundle);
             }
         }
         // Check if there are dimension fields needing conversion
         if (dimensionsFieldsIds == null || dimensionsValuesList == null) {
-            bundle.putInt(APPROX_BUNDLE_SIZE_BYTES_KEY, bundleByteSize);
             return bundle;
         }
         // Create conversions for fields encoded in dimension fields
@@ -137,12 +131,11 @@
             for (List<DimensionsValue> dvList : dimensionsValuesList) {
                 valueList.add(extractDimensionsValue(dvList.get(i), hashToStringMap));
             }
-            bundleByteSize += setPersistableBundleArrayField(
+            setPersistableBundleArrayField(
                     getAtomFieldAccessorMap().get(fieldId).getFieldName(),
                     valueList,
                     bundle);
         }
-        bundle.putInt(APPROX_BUNDLE_SIZE_BYTES_KEY, bundleByteSize);
         return bundle;
     }
 
@@ -186,58 +179,44 @@
      * @param name key value for the bundle, corresponds to atom field name.
      * @param objList the list to be converted to {@link PersistableBundle} compatible array.
      * @param bundle the {@link PersistableBundle} to put the arrays to.
-     * @return bytes written to PersistableBundle.
      */
-    private static int setPersistableBundleArrayField(
+    private static void setPersistableBundleArrayField(
             String name,
             List<Object> objList,
             PersistableBundle bundle) {
         Object e = objList.get(0);  // All elements of the list are the same type.
-        int len = objList.size();
         if (e instanceof Integer) {
             int[] intArray = new int[objList.size()];
             for (int i = 0; i < objList.size(); ++i) {
                 intArray[i] = (Integer) objList.get(i);
             }
             bundle.putIntArray(name, intArray);
-            return len * Integer.BYTES;
         } else if (e instanceof Long) {
             long[] longArray = new long[objList.size()];
             for (int i = 0; i < objList.size(); ++i) {
                 longArray[i] = (Long) objList.get(i);
             }
             bundle.putLongArray(name, longArray);
-            return len * Long.BYTES;
         } else if (e instanceof String) {
-            String[] strArray = objList.toArray(new String[0]);
-            bundle.putStringArray(name, strArray);
-            int bytes = 0;
-            for (String str : strArray) {
-                bytes += str.getBytes(UTF_16).length;
-            }
-            return bytes;
+            bundle.putStringArray(name, objList.toArray(new String[0]));
         } else if (e instanceof Boolean) {
             boolean[] boolArray = new boolean[objList.size()];
             for (int i = 0; i < objList.size(); ++i) {
                 boolArray[i] = (Boolean) objList.get(i);
             }
             bundle.putBooleanArray(name, boolArray);
-            return len;  // Java boolean is 1 byte
         } else if (e instanceof Double) {
             double[] doubleArray = new double[objList.size()];
             for (int i = 0; i < objList.size(); ++i) {
                 doubleArray[i] = (Double) objList.get(i);
             }
             bundle.putDoubleArray(name, doubleArray);
-            return len * Double.BYTES;
         } else if (e instanceof Float) {
             double[] doubleArray = new double[objList.size()];
             for (int i = 0; i < objList.size(); ++i) {
                 doubleArray[i] = ((Float) objList.get(i)).doubleValue();
             }
             bundle.putDoubleArray(name, doubleArray);
-            return len * Double.BYTES;
         }
-        return 0;
     }
 }
diff --git a/service/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverter.java b/service/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverter.java
index a854b3a..0a574dd 100644
--- a/service/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverter.java
+++ b/service/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverter.java
@@ -38,7 +38,8 @@
 
     // Map of pulled atom cases to corresponding atom converter.
     private static Map<Atom.PulledCase, AbstractAtomConverter> sPulledCaseConverters = Map.of(
-            Atom.PulledCase.PROCESS_MEMORY_STATE, new ProcessMemoryStateConverter());
+            Atom.PulledCase.PROCESS_MEMORY_STATE, new ProcessMemoryStateConverter(),
+            Atom.PulledCase.PROCESS_CPU_TIME, new ProcessCpuTimeConverter());
 
     /**
      * Converts a list of atoms to separate the atoms fields values into arrays to be put into the
diff --git a/service/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverter.java b/service/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverter.java
index f0803d6..52f9713 100644
--- a/service/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverter.java
+++ b/service/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverter.java
@@ -16,8 +16,6 @@
 
 package com.android.car.telemetry.publisher.statsconverters;
 
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
-
 import android.os.PersistableBundle;
 
 import com.android.car.telemetry.AtomsProto;
@@ -58,9 +56,6 @@
         }
         PersistableBundle bundle = AtomListConverter.convert(atoms, null, null, null);
         bundle.putLongArray(ELAPSED_TIME_NANOS, elapsedTimes);
-        int bundleSize = bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)
-                + elapsedTimes.length * Long.BYTES;
-        bundle.putInt(APPROX_BUNDLE_SIZE_BYTES_KEY, bundleSize);
         return bundle;
     }
 }
diff --git a/service/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverter.java b/service/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverter.java
index e82a6ce..32a139c 100644
--- a/service/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverter.java
+++ b/service/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverter.java
@@ -16,8 +16,6 @@
 
 package com.android.car.telemetry.publisher.statsconverters;
 
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
-
 import android.os.PersistableBundle;
 
 import com.android.car.telemetry.AtomsProto;
@@ -84,9 +82,6 @@
             elapsedTimesArray[i] = elapsedTimes.get(i);
         }
         bundle.putLongArray(ELAPSED_TIME_NANOS, elapsedTimesArray);
-        int bundleSize = bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)
-                + elapsedTimesArray.length * Long.BYTES;
-        bundle.putInt(APPROX_BUNDLE_SIZE_BYTES_KEY, bundleSize);
         return bundle;
     }
 }
diff --git a/service/src/com/android/car/telemetry/publisher/statsconverters/ProcessCpuTimeConverter.java b/service/src/com/android/car/telemetry/publisher/statsconverters/ProcessCpuTimeConverter.java
new file mode 100644
index 0000000..c56826a
--- /dev/null
+++ b/service/src/com/android/car/telemetry/publisher/statsconverters/ProcessCpuTimeConverter.java
@@ -0,0 +1,71 @@
+/*
+ * 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 com.android.car.telemetry.publisher.statsconverters;
+
+import android.util.SparseArray;
+
+import com.android.car.telemetry.AtomsProto.Atom;
+import com.android.car.telemetry.AtomsProto.ProcessCpuTime;
+
+/**
+ * Atom data converter for atoms of type {@link ProcessCpuTime}.
+ */
+public class ProcessCpuTimeConverter extends AbstractAtomConverter<ProcessCpuTime> {
+    private static final SparseArray<AtomFieldAccessor<ProcessCpuTime>> sAtomFieldAccessorMap =
+            new SparseArray<>();
+    static {
+        sAtomFieldAccessorMap.append(1, new AtomFieldAccessor<>(
+                "uid",
+                a -> a.hasUid(),
+                a -> a.getUid()
+        ));
+        sAtomFieldAccessorMap.append(2, new AtomFieldAccessor<>(
+                "process_name",
+                a -> a.hasProcessName(),
+                a -> a.getProcessName()
+        ));
+        sAtomFieldAccessorMap.append(3, new AtomFieldAccessor<>(
+                "user_time_millis",
+                a -> a.hasUserTimeMillis(),
+                a -> a.getUserTimeMillis()
+        ));
+        sAtomFieldAccessorMap.append(4, new AtomFieldAccessor<>(
+                "system_time_millis",
+                a -> a.hasSystemTimeMillis(),
+                a -> a.getSystemTimeMillis()
+        ));
+    }
+
+    ProcessCpuTimeConverter() {
+        super();
+    }
+
+    @Override
+    SparseArray<AtomFieldAccessor<ProcessCpuTime>> getAtomFieldAccessorMap() {
+        return sAtomFieldAccessorMap;
+    }
+
+    @Override
+    ProcessCpuTime getAtomData(Atom atom) {
+        return atom.getProcessCpuTime();
+    }
+
+    @Override
+    String getAtomDataClassName() {
+        return ProcessCpuTime.class.getSimpleName();
+    }
+}
diff --git a/service/src/com/android/car/watchdog/WatchdogPerfHandler.java b/service/src/com/android/car/watchdog/WatchdogPerfHandler.java
index 3464f1e..0fcaeb0 100644
--- a/service/src/com/android/car/watchdog/WatchdogPerfHandler.java
+++ b/service/src/com/android/car/watchdog/WatchdogPerfHandler.java
@@ -16,8 +16,6 @@
 
 package com.android.car.watchdog;
 
-import static android.automotive.watchdog.internal.ResourceOveruseActionType.KILLED_RECURRING_OVERUSE;
-import static android.automotive.watchdog.internal.ResourceOveruseActionType.NOT_KILLED;
 import static android.car.watchdog.CarWatchdogManager.FLAG_RESOURCE_OVERUSE_IO;
 import static android.car.watchdog.CarWatchdogManager.STATS_PERIOD_CURRENT_DAY;
 import static android.car.watchdog.CarWatchdogManager.STATS_PERIOD_PAST_15_DAYS;
@@ -31,6 +29,7 @@
 import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED;
 import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER;
 import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
+import static android.os.Process.INVALID_UID;
 
 import static com.android.car.CarStatsLog.CAR_WATCHDOG_IO_OVERUSE_STATS_REPORTED;
 import static com.android.car.CarStatsLog.CAR_WATCHDOG_KILL_STATS_REPORTED;
@@ -55,10 +54,8 @@
 import android.automotive.watchdog.internal.ComponentType;
 import android.automotive.watchdog.internal.GarageMode;
 import android.automotive.watchdog.internal.IoUsageStats;
-import android.automotive.watchdog.internal.PackageIdentifier;
 import android.automotive.watchdog.internal.PackageIoOveruseStats;
 import android.automotive.watchdog.internal.PackageMetadata;
-import android.automotive.watchdog.internal.PackageResourceOveruseAction;
 import android.automotive.watchdog.internal.PerStateIoOveruseThreshold;
 import android.automotive.watchdog.internal.ResourceSpecificConfiguration;
 import android.automotive.watchdog.internal.UserPackageIoUsageStats;
@@ -166,9 +163,6 @@
     @GuardedBy("mLock")
     private final ArrayMap<String, PackageResourceUsage> mUsageByUserPackage = new ArrayMap<>();
     @GuardedBy("mLock")
-    private final List<PackageResourceOveruseAction> mOveruseActionsByUserPackage =
-            new ArrayList<>();
-    @GuardedBy("mLock")
     private final SparseArray<ArrayList<ResourceOveruseListenerInfo>> mOveruseListenerInfosByUid =
             new SparseArray<>();
     @GuardedBy("mLock")
@@ -715,13 +709,6 @@
                     continue;
                 }
                 overusingUserPackageKeys.add(usage.getUniqueId());
-                PackageResourceOveruseAction overuseAction = new PackageResourceOveruseAction();
-                overuseAction.packageIdentifier = new PackageIdentifier();
-                overuseAction.packageIdentifier.name = genericPackageName;
-                overuseAction.packageIdentifier.uid = usage.getUid();
-                overuseAction.resourceTypes = new int[]{ ResourceType.IO };
-                overuseAction.resourceOveruseActionType = NOT_KILLED;
-                mOveruseActionsByUserPackage.add(overuseAction);
                 int killableState = usage.getKillableState();
                 if (killableState == KILLABLE_STATE_NEVER) {
                     continue;
@@ -732,9 +719,6 @@
                     mUserNotifiablePackages.add(id);
                 }
             }
-            if (!mOveruseActionsByUserPackage.isEmpty()) {
-                mMainHandler.post(this::notifyActionsTakenOnOveruse);
-            }
             if (mCurrentUxState != UX_STATE_NO_DISTRACTION
                     && (!mActionableUserPackages.isEmpty() || !mUserNotifiablePackages.isEmpty())) {
                 mMainHandler.postDelayed(() -> {
@@ -767,19 +751,35 @@
                 Slogf.i(TAG,
                         "Reset resource overuse settings and stats for user '%d' package '%s'",
                         usage.userId, usage.genericPackageName);
-                try {
-                    if (packageManager.getApplicationEnabledSetting(usage.genericPackageName,
-                            usage.userId) != COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED) {
+                List<String> packages = Collections.singletonList(usage.genericPackageName);
+                if (usage.isSharedPackage()) {
+                    int uid = usage.getUid();
+                    if (uid == INVALID_UID) {
+                        // Only enable packages that were disabled by the watchdog service. Ergo, if
+                        // the usage doesn't have a valid UID, the package was not recently disabled
+                        // by the watchdog service (unless the service crashed) and can be safely
+                        // skipped.
+                        Slogf.e(TAG, "Skipping enabling user %d's package %s", usage.userId,
+                                usage.genericPackageName);
                         continue;
                     }
-                    packageManager.setApplicationEnabledSetting(usage.genericPackageName,
-                            COMPONENT_ENABLED_STATE_ENABLED, /* flags= */ 0, usage.userId,
-                            mContext.getPackageName());
-                    Slogf.i(TAG, "Enabled user '%d' package '%s'", usage.userId,
-                            usage.genericPackageName);
-                } catch (RemoteException | IllegalArgumentException e) {
-                    Slogf.e(TAG, e, "Failed to verify and enable user %d, package '%s'",
-                            usage.userId, usage.genericPackageName);
+                    packages = mPackageInfoHandler.getPackagesForUid(uid, usage.genericPackageName);
+                }
+                for (int pkgIdx = 0; pkgIdx < packages.size(); pkgIdx++) {
+                    String packageName = packages.get(pkgIdx);
+                    try {
+                        if (packageManager.getApplicationEnabledSetting(packageName, usage.userId)
+                                != COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED) {
+                            continue;
+                        }
+                        packageManager.setApplicationEnabledSetting(packageName,
+                                COMPONENT_ENABLED_STATE_ENABLED, /* flags= */ 0, usage.userId,
+                                mContext.getPackageName());
+                        Slogf.i(TAG, "Enabled user '%d' package '%s'", usage.userId, packageName);
+                    } catch (RemoteException | IllegalArgumentException e) {
+                        Slogf.e(TAG, e, "Failed to verify and enable user %d, package '%s'",
+                                usage.userId, packageName);
+                    }
                 }
             }
         }
@@ -1313,18 +1313,12 @@
             if (killableState != KILLABLE_STATE_YES) {
                 continue;
             }
-            killedUserPackageKeys.add(usage.getUniqueId());
-            PackageResourceOveruseAction overuseAction = new PackageResourceOveruseAction();
-            overuseAction.packageIdentifier = new PackageIdentifier();
-            overuseAction.packageIdentifier.name = usage.genericPackageName;
-            overuseAction.packageIdentifier.uid = usage.getUid();
-            overuseAction.resourceTypes = new int[]{ ResourceType.IO };
-            overuseAction.resourceOveruseActionType = NOT_KILLED;
             List<String> packages = Collections.singletonList(usage.genericPackageName);
             if (usage.isSharedPackage()) {
-                packages = mPackageInfoHandler.getPackagesForUid(
-                        overuseAction.packageIdentifier.uid, usage.genericPackageName);
+                packages = mPackageInfoHandler.getPackagesForUid(usage.getUid(),
+                        usage.genericPackageName);
             }
+            boolean isKilled = false;
             for (int pkgIdx = 0; pkgIdx < packages.size(); pkgIdx++) {
                 String packageName = packages.get(pkgIdx);
                 try {
@@ -1339,28 +1333,21 @@
                     packageManager.setApplicationEnabledSetting(packageName,
                             COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED, /* flags= */ 0,
                             usage.userId, mContext.getPackageName());
+                    isKilled = true;
                     Slogf.i(TAG,
                             "Disabled user %d's package '%s' until used due to disk I/O overuse",
                             usage.userId, packageName);
-                    // TODO(b/200599130): When background apps are killed immediately regardless
-                    //  of the UX state, update the action type as KILLED only for immediately
-                    //  killed apps and KILLED_RECURRING_OVERUSE only for apps killed on
-                    //  recurring overuse.
-                    overuseAction.resourceOveruseActionType = KILLED_RECURRING_OVERUSE;
                 } catch (RemoteException e) {
                     Slogf.e(TAG, "Failed to disable application for user %d, package '%s'",
                             usage.userId, packageName);
                 }
             }
-            if (overuseAction.resourceOveruseActionType != NOT_KILLED) {
+            if (isKilled) {
                 usage.ioUsage.killed();
-                mOveruseActionsByUserPackage.add(overuseAction);
+                killedUserPackageKeys.add(usage.getUniqueId());
             }
         }
         pushIoOveruseKillMetrics(killedUserPackageKeys);
-        if (!mOveruseActionsByUserPackage.isEmpty()) {
-            mMainHandler.post(this::notifyActionsTakenOnOveruse);
-        }
         mActionableUserPackages.clear();
     }
 
@@ -1453,29 +1440,8 @@
                         writtenBytes.backgroundBytes, writtenBytes.garageModeBytes));
     }
 
-    /** Notify daemon about the actions take on resource overuse */
-    private void notifyActionsTakenOnOveruse() {
-        List<PackageResourceOveruseAction> actions;
-        synchronized (mLock) {
-            if (mOveruseActionsByUserPackage.isEmpty()) {
-                return;
-            }
-            actions = new ArrayList<>(mOveruseActionsByUserPackage);
-            mOveruseActionsByUserPackage.clear();
-        }
-        try {
-            mCarWatchdogDaemonHelper.actionTakenOnResourceOveruse(actions);
-        } catch (RemoteException | RuntimeException e) {
-            Slogf.w(TAG, e, "Failed to notify car watchdog daemon of actions taken on resource "
-                    + "overuse");
-        }
-        if (DEBUG) {
-            Slogf.d(TAG, "Notified car watchdog daemon of actions taken on resource overuse");
-        }
-    }
-
-    private static String getUserPackageUniqueId(int userId, String genericPackageName) {
-        return String.valueOf(userId) + ":" + genericPackageName;
+    private static String getUserPackageUniqueId(@UserIdInt int userId, String genericPackageName) {
+        return userId + ":" + genericPackageName;
     }
 
     @VisibleForTesting
@@ -1851,6 +1817,7 @@
             this.genericPackageName = genericPackageName;
             this.userId = userId;
             this.mKillableState = defaultKillableState;
+            this.mUid = INVALID_UID;
         }
 
         public boolean isSharedPackage() {
diff --git a/tests/EmbeddedKitchenSinkApp/res/layout/car_telemetry_test.xml b/tests/EmbeddedKitchenSinkApp/res/layout/car_telemetry_test.xml
index cfad246..1951e15 100644
--- a/tests/EmbeddedKitchenSinkApp/res/layout/car_telemetry_test.xml
+++ b/tests/EmbeddedKitchenSinkApp/res/layout/car_telemetry_test.xml
@@ -122,6 +122,31 @@
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
         android:orientation="horizontal">
+        <TextView
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="@string/process_cpu_time_config"/>
+        <Button
+            android:id="@+id/send_on_process_cpu_time_config"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="@string/add_metrics_config"/>
+        <Button
+            android:id="@+id/remove_on_process_cpu_time_config"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="@string/remove_metrics_config"/>
+        <Button
+            android:id="@+id/get_on_process_cpu_time_report"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="@string/get_report"/>
+    </LinearLayout>
+
+    <LinearLayout
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:orientation="horizontal">
         <Button
             android:id="@+id/show_mem_info_btn"
             android:layout_width="wrap_content"
diff --git a/tests/EmbeddedKitchenSinkApp/res/values/strings.xml b/tests/EmbeddedKitchenSinkApp/res/values/strings.xml
index b5f4f9b..45c12f0 100644
--- a/tests/EmbeddedKitchenSinkApp/res/values/strings.xml
+++ b/tests/EmbeddedKitchenSinkApp/res/values/strings.xml
@@ -387,6 +387,7 @@
     <string name="process_memory_config" translate="false">process_memory:</string>
     <string name="app_start_memory_state_captured_config" translate="false">app_start_memory_state_captured:</string>
     <string name="activity_foreground_state_changed_config" translate="false">activity_foreground_state_changed:</string>
+    <string name="process_cpu_time_config" translate="false">process_cpu_time:</string>
     <string name="add_metrics_config" translatable="false">Add MetricsConfig</string>
     <string name="remove_metrics_config" translatable="false">Remove MetricsConfig</string>
     <string name="get_report" translatable="false">Get Report</string>
diff --git a/tests/EmbeddedKitchenSinkApp/src/com/google/android/car/kitchensink/telemetry/CarTelemetryTestFragment.java b/tests/EmbeddedKitchenSinkApp/src/com/google/android/car/kitchensink/telemetry/CarTelemetryTestFragment.java
index 64f7aa8..7fc4705 100644
--- a/tests/EmbeddedKitchenSinkApp/src/com/google/android/car/kitchensink/telemetry/CarTelemetryTestFragment.java
+++ b/tests/EmbeddedKitchenSinkApp/src/com/google/android/car/kitchensink/telemetry/CarTelemetryTestFragment.java
@@ -18,6 +18,7 @@
 
 import static com.android.car.telemetry.TelemetryProto.StatsPublisher.SystemMetric.ACTIVITY_FOREGROUND_STATE_CHANGED;
 import static com.android.car.telemetry.TelemetryProto.StatsPublisher.SystemMetric.APP_START_MEMORY_STATE_CAPTURED;
+import static com.android.car.telemetry.TelemetryProto.StatsPublisher.SystemMetric.PROCESS_CPU_TIME;
 import static com.android.car.telemetry.TelemetryProto.StatsPublisher.SystemMetric.PROCESS_MEMORY_STATE;
 
 import android.annotation.NonNull;
@@ -49,8 +50,10 @@
 import java.util.concurrent.Executors;
 
 public class CarTelemetryTestFragment extends Fragment {
+    private static final int SCRIPT_EXECUTION_PRIORITY_HIGH = 0;
+    private static final int SCRIPT_EXECUTION_PRIORITY_LOW = 100;
 
-    /** Hello World test from vehicle property publisher by injecting gear change. */
+    /** Vehicle property via gear change section. */
     private static final String LUA_SCRIPT_ON_GEAR_CHANGE =
             "function onGearChange(published_data, state)\n"
                     + "    result = {data = \"Hello World!\"}\n"
@@ -73,13 +76,13 @@
                             TelemetryProto.Subscriber.newBuilder()
                                     .setHandler("onGearChange")
                                     .setPublisher(VEHICLE_PROPERTY_PUBLISHER)
-                                    .setPriority(100)) // low priority
+                                    .setPriority(SCRIPT_EXECUTION_PRIORITY_LOW))
                     .build();
     private static final MetricsConfigKey ON_GEAR_CHANGE_KEY_V1 = new MetricsConfigKey(
             METRICS_CONFIG_ON_GEAR_CHANGE_V1.getName(),
             METRICS_CONFIG_ON_GEAR_CHANGE_V1.getVersion());
 
-    /** Memory metrics test. */
+    /** ProcessMemoryState section. */
     private static final String LUA_SCRIPT_ON_PROCESS_MEMORY_STATE = new StringBuilder()
             .append("function calculateAverage(tbl)\n")
             .append("    sum = 0\n")
@@ -106,7 +109,6 @@
             .append("    on_script_finished(result)\n")
             .append("end\n")
             .toString();
-
     private static final TelemetryProto.Publisher PROCESS_MEMORY_PUBLISHER =
             TelemetryProto.Publisher.newBuilder()
                     .setStats(
@@ -122,13 +124,13 @@
                             TelemetryProto.Subscriber.newBuilder()
                                     .setHandler("onProcessMemory")
                                     .setPublisher(PROCESS_MEMORY_PUBLISHER)
-                                    .setPriority(0)) // high priority
+                                    .setPriority(SCRIPT_EXECUTION_PRIORITY_HIGH))
                     .build();
     private static final MetricsConfigKey PROCESS_MEMORY_KEY_V1 = new MetricsConfigKey(
             METRICS_CONFIG_PROCESS_MEMORY_V1.getName(),
             METRICS_CONFIG_PROCESS_MEMORY_V1.getVersion());
 
-    /** AppStartMemoryStateCaptured metric test. */
+    /** AppStartMemoryStateCaptured section. */
     private static final String LUA_SCRIPT_ON_APP_START_MEMORY_STATE_CAPTURED = new StringBuilder()
             .append("function calculateAverage(tbl)\n")
             .append("    sum = 0\n")
@@ -154,7 +156,6 @@
             .append("    on_script_finished(result)\n")
             .append("end\n")
             .toString();
-
     private static final TelemetryProto.Publisher APP_START_MEMORY_STATE_CAPTURED_PUBLISHER =
             TelemetryProto.Publisher.newBuilder()
                     .setStats(
@@ -170,26 +171,27 @@
                             TelemetryProto.Subscriber.newBuilder()
                                     .setHandler("onAppStartMemoryStateCaptured")
                                     .setPublisher(APP_START_MEMORY_STATE_CAPTURED_PUBLISHER)
-                                    .setPriority(0)) // high priority
+                                    .setPriority(SCRIPT_EXECUTION_PRIORITY_HIGH))
                     .build();
     private static final MetricsConfigKey APP_START_MEMORY_STATE_CAPTURED_KEY_V1 =
             new MetricsConfigKey(
                     METRICS_CONFIG_APP_START_MEMORY_V1.getName(),
                     METRICS_CONFIG_APP_START_MEMORY_V1.getVersion());
 
-    /** ActivityForegroundStateChanged metric test. */
+    /** ActivityForegroundStateChanged section. */
     private static final String LUA_SCRIPT_ON_ACTIVITY_FOREGROUND_STATE_CHANGED =
             new StringBuilder()
                 .append("function onActivityForegroundStateChanged(published_data, state)\n")
                 .append("    result = {}\n")
-                .append("    result.uid = published_data.uid\n")
-                .append("    result.pkg_name = published_data.pkg_name\n")
-                .append("    result.class_name = published_data.class_name\n")
-                .append("    result.state = published_data.state\n")
+                .append("    n = 0\n")
+                .append("    for k, v in pairs(published_data) do\n")
+                .append("        result[k] = v[1]\n")
+                .append("        n = n + 1\n")
+                .append("    end\n")
+                .append("    result.n = n\n")
                 .append("    on_script_finished(result)\n")
                 .append("end\n")
                 .toString();
-
     private static final TelemetryProto.Publisher ACTIVITY_FOREGROUND_STATE_CHANGED_PUBLISHER =
             TelemetryProto.Publisher.newBuilder()
                     .setStats(
@@ -205,13 +207,49 @@
                             TelemetryProto.Subscriber.newBuilder()
                                     .setHandler("onActivityForegroundStateChanged")
                                     .setPublisher(ACTIVITY_FOREGROUND_STATE_CHANGED_PUBLISHER)
-                                    .setPriority(0)) // high priority
+                                    .setPriority(SCRIPT_EXECUTION_PRIORITY_HIGH))
                     .build();
     private static final MetricsConfigKey ACTIVITY_FOREGROUND_STATE_CHANGED_KEY_V1 =
             new MetricsConfigKey(
                     METRICS_CONFIG_ACTIVITY_FOREGROUND_STATE_V1.getName(),
                     METRICS_CONFIG_ACTIVITY_FOREGROUND_STATE_V1.getVersion());
 
+    /* ProcessCpuTime section */
+    private static final String LUA_SCRIPT_ON_PROCESS_CPU_TIME =
+            new StringBuilder()
+                .append("function onProcessCpuTime(published_data, state)\n")
+                .append("    result = {}\n")
+                .append("    n = 0\n")
+                .append("    for k, v in pairs(published_data) do\n")
+                .append("        result[k] = v[1]\n")
+                .append("        n = n + 1\n")
+                .append("    end\n")
+                .append("    result.n = n\n")
+                .append("    on_script_finished(result)\n")
+                .append("end\n")
+                .toString();
+    private static final TelemetryProto.Publisher PROCESS_CPU_TIME_PUBLISHER =
+            TelemetryProto.Publisher.newBuilder()
+                    .setStats(
+                            TelemetryProto.StatsPublisher.newBuilder()
+                                    .setSystemMetric(PROCESS_CPU_TIME)
+                    ).build();
+    private static final TelemetryProto.MetricsConfig METRICS_CONFIG_PROCESS_CPU_TIME_V1 =
+            TelemetryProto.MetricsConfig.newBuilder()
+                    .setName("process_cpu_time_config")
+                    .setVersion(1)
+                    .setScript(LUA_SCRIPT_ON_PROCESS_CPU_TIME)
+                    .addSubscribers(
+                            TelemetryProto.Subscriber.newBuilder()
+                                    .setHandler("onProcessCpuTime")
+                                    .setPublisher(PROCESS_CPU_TIME_PUBLISHER)
+                                    .setPriority(SCRIPT_EXECUTION_PRIORITY_HIGH))
+                    .build();
+    private static final MetricsConfigKey PROCESS_CPU_TIME_KEY_V1 =
+            new MetricsConfigKey(
+                    METRICS_CONFIG_PROCESS_CPU_TIME_V1.getName(),
+                    METRICS_CONFIG_PROCESS_CPU_TIME_V1.getVersion());
+
     private final Executor mExecutor = Executors.newSingleThreadExecutor();
 
     private CarTelemetryManager mCarTelemetryManager;
@@ -260,6 +298,12 @@
                 .setOnClickListener(this::onRemoveActivityForegroundStateChangedConfigBtnClick);
         view.findViewById(R.id.get_on_activity_foreground_state_changed_report)
                 .setOnClickListener(this::onGetActivityForegroundStateChangedReportBtnClick);
+        view.findViewById(R.id.send_on_process_cpu_time_config)
+                .setOnClickListener(this::onSendProcessCpuTimeConfigBtnClick);
+        view.findViewById(R.id.remove_on_process_cpu_time_config)
+                .setOnClickListener(this::onRemoveProcessCpuTimeConfigBtnClick);
+        view.findViewById(R.id.get_on_process_cpu_time_report)
+                .setOnClickListener(this::onGetProcessCpuTimeReportBtnClick);
         view.findViewById(R.id.show_mem_info_btn).setOnClickListener(this::onShowMemInfoBtnClick);
         return view;
     }
@@ -341,6 +385,23 @@
         mCarTelemetryManager.sendFinishedReports(ACTIVITY_FOREGROUND_STATE_CHANGED_KEY_V1);
     }
 
+    private void onSendProcessCpuTimeConfigBtnClick(View view) {
+        showOutput("Sending MetricsConfig that listens for PROCESS_CPU_TIME...");
+        mCarTelemetryManager.addMetricsConfig(PROCESS_CPU_TIME_KEY_V1,
+                METRICS_CONFIG_PROCESS_CPU_TIME_V1.toByteArray());
+    }
+
+    private void onRemoveProcessCpuTimeConfigBtnClick(View view) {
+        showOutput("Removing MetricsConfig that listens for PROCESS_CPU_TIME...");
+        mCarTelemetryManager.removeMetricsConfig(PROCESS_CPU_TIME_KEY_V1);
+    }
+
+    private void onGetProcessCpuTimeReportBtnClick(View view) {
+        showOutput("Fetching report for PROCESS_CPU_TIME... If nothing shows up within 5 "
+                + "seconds, there is no result yet");
+        mCarTelemetryManager.sendFinishedReports(PROCESS_CPU_TIME_KEY_V1);
+    }
+
     /** Gets a MemoryInfo object for the device's current memory status. */
     private ActivityManager.MemoryInfo getAvailableMemory() {
         ActivityManager activityManager = getActivity().getSystemService(ActivityManager.class);
diff --git a/tests/carservice_unit_test/src/android/car/watchdoglib/CarWatchdogDaemonHelperTest.java b/tests/carservice_unit_test/src/android/car/watchdoglib/CarWatchdogDaemonHelperTest.java
index 80cab06..fe183bd 100644
--- a/tests/carservice_unit_test/src/android/car/watchdoglib/CarWatchdogDaemonHelperTest.java
+++ b/tests/carservice_unit_test/src/android/car/watchdoglib/CarWatchdogDaemonHelperTest.java
@@ -34,7 +34,6 @@
 import android.automotive.watchdog.internal.ICarWatchdogServiceForSystem;
 import android.automotive.watchdog.internal.PackageInfo;
 import android.automotive.watchdog.internal.PackageIoOveruseStats;
-import android.automotive.watchdog.internal.PackageResourceOveruseAction;
 import android.automotive.watchdog.internal.PowerCycle;
 import android.automotive.watchdog.internal.ResourceOveruseConfiguration;
 import android.automotive.watchdog.internal.StateType;
@@ -186,15 +185,6 @@
     }
 
     @Test
-    public void testIndirectCall_actionTakenOnResourceOveruse() throws Exception {
-        List<PackageResourceOveruseAction> actions = new ArrayList<>();
-
-        mCarWatchdogDaemonHelper.actionTakenOnResourceOveruse(actions);
-
-        verify(mFakeCarWatchdog).actionTakenOnResourceOveruse(eq(actions));
-    }
-
-    @Test
     public void testIndirectCall_controlProcessHealthCheck() throws Exception {
         mCarWatchdogDaemonHelper.controlProcessHealthCheck(true);
 
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/databroker/DataBrokerTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/databroker/DataBrokerTest.java
index c5f30c2..d639820 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/databroker/DataBrokerTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/databroker/DataBrokerTest.java
@@ -16,8 +16,6 @@
 
 package com.android.car.telemetry.databroker;
 
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
-
 import static com.google.common.truth.Truth.assertThat;
 import static com.google.common.truth.Truth.assertWithMessage;
 
@@ -156,11 +154,13 @@
         mHighPriorityTask = new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
                 mData,
-                SystemClock.elapsedRealtime());
+                SystemClock.elapsedRealtime(),
+                false);
         mLowPriorityTask = new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_BAR, SUBSCRIBER_BAR),
                 mData,
-                SystemClock.elapsedRealtime());
+                SystemClock.elapsedRealtime(),
+                false);
     }
 
     @Override
@@ -319,13 +319,13 @@
     }
 
     @Test
-    public void testScheduleNextTask_largeInput_shouldPipeData() throws Exception {
+    public void testScheduleNextTask_withLargeDataFlag_shouldPipeData() throws Exception {
         PersistableBundle data = new PersistableBundle();
-        data.putBooleanArray("1 MB Array", new boolean [1024 * 1024]);
         ScriptExecutionTask highPriorityTask = new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
                 data,
-                SystemClock.elapsedRealtime());
+                SystemClock.elapsedRealtime(),
+                true);
         mDataBroker.getTaskQueue().add(highPriorityTask);
 
         mDataBroker.scheduleNextTask();
@@ -335,29 +335,13 @@
     }
 
     @Test
-    public void testScheduleNextTask_largeReportWithApproxSize_shouldPipeData() throws Exception {
+    public void testScheduleNextTask_withoutLargeDataFlag_doesNotPipeData() throws Exception {
         PersistableBundle data = new PersistableBundle();
-        data.putInt(APPROX_BUNDLE_SIZE_BYTES_KEY, 21000);
         ScriptExecutionTask highPriorityTask = new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
                 data,
-                SystemClock.elapsedRealtime());
-        mDataBroker.getTaskQueue().add(highPriorityTask);
-
-        mDataBroker.scheduleNextTask();
-
-        waitForTelemetryThreadToFinish();
-        assertThat(mFakeScriptExecutor.getInvokeScriptForLargeInputCount()).isEqualTo(1);
-    }
-
-    @Test
-    public void testScheduleNextTask_smallReportWithApproxSize_doesNotPipeData() throws Exception {
-        PersistableBundle data = new PersistableBundle();
-        data.putInt(APPROX_BUNDLE_SIZE_BYTES_KEY, 1000);
-        ScriptExecutionTask highPriorityTask = new ScriptExecutionTask(
-                new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
-                data,
-                SystemClock.elapsedRealtime());
+                SystemClock.elapsedRealtime(),
+                false);
         mDataBroker.getTaskQueue().add(highPriorityTask);
 
         mDataBroker.scheduleNextTask();
@@ -369,18 +353,18 @@
     @Test
     public void testScheduleNextTask_largeInputPipeIOException_shouldIgnoreCurrentTask()
             throws Exception {
-        PersistableBundle data = new PersistableBundle();
-        data.putBooleanArray("1 MB Array", new boolean [1024 * 1024]);
         PriorityBlockingQueue<ScriptExecutionTask> taskQueue = mDataBroker.getTaskQueue();
         ScriptExecutionTask highPriorityTask = new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
-                data,
-                SystemClock.elapsedRealtime());
+                new PersistableBundle(),
+                SystemClock.elapsedRealtime(),
+                true);
         taskQueue.add(highPriorityTask); // invokeScriptForLargeInput() path
         taskQueue.add(new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
                 new PersistableBundle(),
-                SystemClock.elapsedRealtime())); // invokeScript() path
+                SystemClock.elapsedRealtime(),
+                false)); // invokeScript() path
         ParcelFileDescriptor[] fds = ParcelFileDescriptor.createPipe();
         when(ParcelFileDescriptor.createPipe()).thenReturn(fds);
         fds[1].close(); // cause IO Exception in invokeScriptForLargeInput() path
@@ -496,7 +480,8 @@
         ScriptExecutionTask taskWithMetricsConfigFoo = new ScriptExecutionTask(
                 new DataSubscriber(mDataBroker, METRICS_CONFIG_FOO, SUBSCRIBER_FOO),
                 mData,
-                SystemClock.elapsedRealtime());
+                SystemClock.elapsedRealtime(),
+                false);
         PriorityBlockingQueue<ScriptExecutionTask> taskQueue = mDataBroker.getTaskQueue();
         taskQueue.add(mHighPriorityTask); // associated with METRICS_CONFIG_FOO
         taskQueue.add(mLowPriorityTask); // associated with METRICS_CONFIG_BAR
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/StatsPublisherTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/StatsPublisherTest.java
index 25076a1..35173aa 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/StatsPublisherTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/StatsPublisherTest.java
@@ -33,6 +33,7 @@
 import static com.google.common.truth.Truth.assertThat;
 
 import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.ArgumentMatchers.anyBoolean;
 import static org.mockito.ArgumentMatchers.anyLong;
 import static org.mockito.Mockito.doThrow;
 import static org.mockito.Mockito.reset;
@@ -449,7 +450,7 @@
 
         mFakeHandlerWrapper.dispatchQueuedMessages();
 
-        verify(subscriber1).push(mBundleCaptor.capture());
+        verify(subscriber1).push(mBundleCaptor.capture(), anyBoolean());
         PersistableBundle bundle1 = mBundleCaptor.getValue();
         assertThat(bundle1.getLongArray("elapsed_timestamp_nanos"))
             .asList().containsExactly(99999999L);
@@ -457,7 +458,7 @@
         assertThat(Arrays.asList(bundle1.getStringArray("activity_name")))
             .containsExactly("activityName");
         assertThat(bundle1.getLongArray("rss_in_bytes")).asList().containsExactly(1234L);
-        verify(subscriber2).push(mBundleCaptor.capture());
+        verify(subscriber2).push(mBundleCaptor.capture(), anyBoolean());
         PersistableBundle bundle2 = mBundleCaptor.getValue();
         assertThat(bundle2.getIntArray("uid")).asList().containsExactly(234);
         assertThat(bundle2.getLongArray("rss_in_bytes")).asList().containsExactly(4567L);
@@ -466,6 +467,38 @@
     }
 
     @Test
+    public void testBundleWithLargeSize_isLargeData() throws Exception {
+        PersistableBundle bundle = new PersistableBundle();
+        bundle.putBooleanArray("bool", new boolean[1000]);
+        bundle.putLongArray("long", new long[1000]);
+        bundle.putIntArray("int", new int[1000]);
+        bundle.putDoubleArray("double", new double[1000]);
+        String[] strArray = new String[1000];
+        for (int i = 0; i < strArray.length; ++i) {
+            strArray[i] = "test";
+        }
+        bundle.putStringArray("string", strArray);
+
+        assertThat(mPublisher.isBundleLargeData(bundle)).isTrue();
+    }
+
+    @Test
+    public void testBundleWithSmallSize_isNotLargeData() throws Exception {
+        PersistableBundle bundle = new PersistableBundle();
+        bundle.putBooleanArray("bool", new boolean[100]);
+        bundle.putLongArray("long", new long[100]);
+        bundle.putIntArray("int", new int[100]);
+        bundle.putDoubleArray("double", new double[100]);
+        String[] strArray = new String[100];
+        for (int i = 0; i < strArray.length; ++i) {
+            strArray[i] = "test";
+        }
+        bundle.putStringArray("string", strArray);
+
+        assertThat(mPublisher.isBundleLargeData(bundle)).isFalse();
+    }
+
+    @Test
     public void testOnInvalidConfig_notifiesPublisherFailureListener() throws Exception {
         DataSubscriber subscriber = spy(new DataSubscriber(null, METRICS_CONFIG, SUBSCRIBER_1));
         mPublisher.addDataSubscriber(subscriber);
@@ -483,7 +516,7 @@
         mFakeHandlerWrapper.dispatchQueuedMessages();
 
         // subscriber shouldn't get data, because of EMPTY_METRICS_REPORT.
-        verify(subscriber, times(0)).push(any());
+        verify(subscriber, times(0)).push(any(), anyBoolean());
         assertThat(mFailedConfigs).containsExactly(METRICS_CONFIG);
         assertThat(mPublisherFailure).hasMessageThat().contains("Found invalid configs");
     }
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ActivityForegroundStateChangedConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ActivityForegroundStateChangedConverterTest.java
index 221c716..98a0925 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ActivityForegroundStateChangedConverterTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ActivityForegroundStateChangedConverterTest.java
@@ -20,7 +20,6 @@
 import static com.android.car.telemetry.AtomsProto.ActivityForegroundStateChanged.PKG_NAME_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.ActivityForegroundStateChanged.STATE_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.ActivityForegroundStateChanged.UID_FIELD_NUMBER;
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
 
 import static com.google.common.truth.Truth.assertThat;
 
@@ -105,8 +104,7 @@
         PersistableBundle bundle = mConverter.convert(atomsList, DIM_FIELDS_IDS,
                 dimensionsValuesList, HASH_STR_MAP);
 
-        assertThat(bundle.size()).isEqualTo(5);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(120);
+        assertThat(bundle.size()).isEqualTo(4);
         assertThat(bundle.getIntArray(accessorMap.get(UID_FIELD_NUMBER).getFieldName()))
             .asList().containsExactly(1000, 2000).inOrder();
         assertThat(Arrays.asList(
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AppStartMemoryStateCapturedConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AppStartMemoryStateCapturedConverterTest.java
index b309069..1579e00 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AppStartMemoryStateCapturedConverterTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AppStartMemoryStateCapturedConverterTest.java
@@ -24,7 +24,6 @@
 import static com.android.car.telemetry.AtomsProto.AppStartMemoryStateCaptured.RSS_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.AppStartMemoryStateCaptured.SWAP_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.AppStartMemoryStateCaptured.UID_FIELD_NUMBER;
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
 
 import static com.google.common.truth.Truth.assertThat;
 
@@ -119,8 +118,7 @@
         PersistableBundle bundle = mConverter.convert(atomsList, DIM_FIELDS_IDS,
                 dimensionsValuesList, HASH_STR_MAP);
 
-        assertThat(bundle.size()).isEqualTo(9);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(204);
+        assertThat(bundle.size()).isEqualTo(8);
         assertThat(bundle.getIntArray(accessorMap.get(UID_FIELD_NUMBER).getFieldName()))
             .asList().containsExactly(1000, 2000).inOrder();
         assertThat(Arrays.asList(
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverterTest.java
index 4704966..a8cc426 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverterTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/AtomListConverterTest.java
@@ -16,8 +16,6 @@
 
 package com.android.car.telemetry.publisher.statsconverters;
 
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
-
 import static com.google.common.truth.Truth.assertThat;
 
 import android.os.PersistableBundle;
@@ -60,8 +58,7 @@
 
         PersistableBundle bundle = AtomListConverter.convert(pushedAtomsList, null, null, null);
 
-        assertThat(bundle.size()).isEqualTo(4);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(80);
+        assertThat(bundle.size()).isEqualTo(3);
         assertThat(bundle.getIntArray(
                 accessorMap.get(AppStartMemoryStateCaptured.UID_FIELD_NUMBER).getFieldName()))
             .asList().containsExactly(1000, 1100).inOrder();
@@ -97,8 +94,7 @@
 
         PersistableBundle bundle = AtomListConverter.convert(pulledAtomsList, null, null, null);
 
-        assertThat(bundle.size()).isEqualTo(4);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(76);
+        assertThat(bundle.size()).isEqualTo(3);
         assertThat(bundle.getIntArray(
                 accessorMap.get(ProcessMemoryState.UID_FIELD_NUMBER).getFieldName()))
             .asList().containsExactly(1000, 1100).inOrder();
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverterTest.java
index 0bac4cd..dac3310 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverterTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/EventMetricDataConverterTest.java
@@ -19,7 +19,6 @@
 import static com.android.car.telemetry.AtomsProto.AppStartMemoryStateCaptured.ACTIVITY_NAME_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.AppStartMemoryStateCaptured.RSS_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.AppStartMemoryStateCaptured.UID_FIELD_NUMBER;
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
 
 import static com.google.common.truth.Truth.assertThat;
 
@@ -67,8 +66,7 @@
 
         PersistableBundle bundle = EventMetricDataConverter.convertEventDataList(eventDataList);
 
-        assertThat(bundle.size()).isEqualTo(5);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(96);
+        assertThat(bundle.size()).isEqualTo(4);
         assertThat(bundle.getLongArray(EventMetricDataConverter.ELAPSED_TIME_NANOS))
             .asList().containsExactly(12345678L, 23456789L).inOrder();
         assertThat(bundle.getIntArray(accessorMap.get(UID_FIELD_NUMBER).getFieldName()))
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverterTest.java
index 808a6a1..8e747ae 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverterTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/GaugeMetricDataConverterTest.java
@@ -21,7 +21,6 @@
 import static com.android.car.telemetry.AtomsProto.ProcessMemoryState.RSS_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.ProcessMemoryState.SWAP_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.ProcessMemoryState.UID_FIELD_NUMBER;
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
 
 import static com.google.common.truth.Truth.assertThat;
 
@@ -104,8 +103,7 @@
 
         // For each atom 2 fields were set, additionally 3 fields were encoded in dimension values,
         // and 1 elapsed time array, so 6 arrays are expected in the bundle.
-        assertThat(bundle.size()).isEqualTo(7);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(264);
+        assertThat(bundle.size()).isEqualTo(6);
         assertThat(bundle.getIntArray(accessorMap.get(UID_FIELD_NUMBER).getFieldName()))
             .asList().containsExactly(123, 123, 123, 234).inOrder();
         assertThat(Arrays.asList(bundle.getStringArray(
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessCpuTimeConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessCpuTimeConverterTest.java
new file mode 100644
index 0000000..0075391
--- /dev/null
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessCpuTimeConverterTest.java
@@ -0,0 +1,146 @@
+/*
+ * 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 com.android.car.telemetry.publisher.statsconverters;
+
+import static com.android.car.telemetry.AtomsProto.ProcessCpuTime.PROCESS_NAME_FIELD_NUMBER;
+import static com.android.car.telemetry.AtomsProto.ProcessCpuTime.SYSTEM_TIME_MILLIS_FIELD_NUMBER;
+import static com.android.car.telemetry.AtomsProto.ProcessCpuTime.UID_FIELD_NUMBER;
+import static com.android.car.telemetry.AtomsProto.ProcessCpuTime.USER_TIME_MILLIS_FIELD_NUMBER;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.junit.Assert.assertThrows;
+
+import android.os.PersistableBundle;
+import android.util.SparseArray;
+
+import com.android.car.telemetry.AtomsProto.Atom;
+import com.android.car.telemetry.AtomsProto.ProcessCpuTime;
+import com.android.car.telemetry.StatsLogProto.DimensionsValue;
+import com.android.car.telemetry.publisher.HashUtils;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.JUnit4;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+
+@RunWith(JUnit4.class)
+public class ProcessCpuTimeConverterTest {
+    private static final Atom ATOM_A =
+            Atom.newBuilder()
+                    .setProcessCpuTime(ProcessCpuTime.newBuilder()
+                            .setUserTimeMillis(234L)
+                            .setSystemTimeMillis(111L))
+                    .build();
+
+    private static final Atom ATOM_B =
+            Atom.newBuilder()
+                    .setProcessCpuTime(ProcessCpuTime.newBuilder()
+                            .setUserTimeMillis(345L)
+                            .setSystemTimeMillis(222L))
+                    .build();
+
+    private static final Atom ATOM_MISMATCH =
+            Atom.newBuilder()
+                    .setProcessCpuTime(ProcessCpuTime.newBuilder()
+                            // Some fields are not set, creating mismatch with above atoms
+                            .setSystemTimeMillis(333L))
+                    .build();
+
+    private static final List<Integer> DIM_FIELDS_IDS = Arrays.asList(1, 2);
+    private static final Long HASH_1 = HashUtils.murmur2Hash64("process.name.1");
+    private static final Long HASH_2 = HashUtils.murmur2Hash64("process.name.2");
+    private static final Map<Long, String> HASH_STR_MAP = Map.of(
+            HASH_1, "process.name.1",
+            HASH_2, "process.name.2");
+
+    private static final List<DimensionsValue> DV_PAIR_A =
+            Arrays.asList(
+                    DimensionsValue.newBuilder().setValueInt(1000).build(),
+                    DimensionsValue.newBuilder().setValueStrHash(HASH_1).build());
+
+    private static final List<DimensionsValue> DV_PAIR_B =
+            Arrays.asList(
+                    DimensionsValue.newBuilder().setValueInt(2000).build(),
+                    DimensionsValue.newBuilder().setValueStrHash(HASH_2).build());
+
+    private static final List<DimensionsValue> DV_PAIR_MALFORMED =
+            Arrays.asList(
+                    DimensionsValue.newBuilder().setValueInt(3000).build(),
+                    // Wrong format since leaf level dimension value should set value, not field
+                    DimensionsValue.newBuilder().setField(3).build());
+
+    // Subject of the test.
+    private ProcessCpuTimeConverter mConverter = new ProcessCpuTimeConverter();
+
+    @Test
+    public void testConvertAtomsListWithDimensionValues_putsCorrectDataToPersistableBundle()
+            throws StatsConversionException {
+        List<Atom> atomsList = Arrays.asList(ATOM_A, ATOM_B);
+        List<List<DimensionsValue>> dimensionsValuesList = Arrays.asList(DV_PAIR_A, DV_PAIR_B);
+        SparseArray<AtomFieldAccessor<ProcessCpuTime>> accessorMap =
+                mConverter.getAtomFieldAccessorMap();
+
+        PersistableBundle bundle = mConverter.convert(atomsList, DIM_FIELDS_IDS,
+                dimensionsValuesList, HASH_STR_MAP);
+
+        assertThat(bundle.size()).isEqualTo(4);
+        assertThat(bundle.getIntArray(accessorMap.get(UID_FIELD_NUMBER).getFieldName()))
+            .asList().containsExactly(1000, 2000).inOrder();
+        assertThat(Arrays.asList(
+                bundle.getStringArray(accessorMap.get(PROCESS_NAME_FIELD_NUMBER).getFieldName())))
+            .containsExactly("process.name.1", "process.name.2").inOrder();
+        assertThat(bundle.getLongArray(
+                accessorMap.get(USER_TIME_MILLIS_FIELD_NUMBER).getFieldName()))
+            .asList().containsExactly(234L, 345L).inOrder();
+        assertThat(bundle.getLongArray(
+                accessorMap.get(SYSTEM_TIME_MILLIS_FIELD_NUMBER).getFieldName()))
+            .asList().containsExactly(111L, 222L).inOrder();
+    }
+
+    @Test
+    public void testAtomSetFieldInconsistency_throwsException() {
+        List<Atom> atomsList = Arrays.asList(ATOM_A, ATOM_MISMATCH);
+        List<List<DimensionsValue>> dimensionsValuesList = Arrays.asList(DV_PAIR_A, DV_PAIR_B);
+
+        assertThrows(
+                StatsConversionException.class,
+                () -> mConverter.convert(
+                        atomsList,
+                        DIM_FIELDS_IDS,
+                        dimensionsValuesList,
+                        HASH_STR_MAP));
+    }
+
+    @Test
+    public void testMalformedDimensionValue_throwsException() {
+        List<Atom> atomsList = Arrays.asList(ATOM_A, ATOM_B);
+        List<List<DimensionsValue>> dimensionsValuesList =
+                Arrays.asList(DV_PAIR_A, DV_PAIR_MALFORMED);
+
+        assertThrows(
+                StatsConversionException.class,
+                () -> mConverter.convert(
+                        atomsList,
+                        DIM_FIELDS_IDS,
+                        dimensionsValuesList,
+                        HASH_STR_MAP));
+    }
+}
diff --git a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessMemoryStateConverterTest.java b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessMemoryStateConverterTest.java
index 050cb4c..f922d17 100644
--- a/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessMemoryStateConverterTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/telemetry/publisher/statsconverters/ProcessMemoryStateConverterTest.java
@@ -24,7 +24,6 @@
 import static com.android.car.telemetry.AtomsProto.ProcessMemoryState.RSS_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.ProcessMemoryState.SWAP_IN_BYTES_FIELD_NUMBER;
 import static com.android.car.telemetry.AtomsProto.ProcessMemoryState.UID_FIELD_NUMBER;
-import static com.android.car.telemetry.databroker.ScriptExecutionTask.APPROX_BUNDLE_SIZE_BYTES_KEY;
 
 import static com.google.common.truth.Truth.assertThat;
 
@@ -117,8 +116,7 @@
         PersistableBundle bundle = mConverter.convert(atomsList, DIM_FIELDS_IDS,
                 dimensionsValuesList, HASH_STR_MAP);
 
-        assertThat(bundle.size()).isEqualTo(9);
-        assertThat(bundle.getInt(APPROX_BUNDLE_SIZE_BYTES_KEY)).isEqualTo(156);
+        assertThat(bundle.size()).isEqualTo(8);
         assertThat(bundle.getIntArray(accessorMap.get(UID_FIELD_NUMBER).getFieldName()))
             .asList().containsExactly(1000, 2000).inOrder();
         assertThat(Arrays.asList(
diff --git a/tests/carservice_unit_test/src/com/android/car/watchdog/CarWatchdogServiceUnitTest.java b/tests/carservice_unit_test/src/com/android/car/watchdog/CarWatchdogServiceUnitTest.java
index e757536..cb3eb52 100644
--- a/tests/carservice_unit_test/src/com/android/car/watchdog/CarWatchdogServiceUnitTest.java
+++ b/tests/carservice_unit_test/src/com/android/car/watchdog/CarWatchdogServiceUnitTest.java
@@ -16,8 +16,6 @@
 
 package com.android.car.watchdog;
 
-import static android.automotive.watchdog.internal.ResourceOveruseActionType.KILLED_RECURRING_OVERUSE;
-import static android.automotive.watchdog.internal.ResourceOveruseActionType.NOT_KILLED;
 import static android.car.drivingstate.CarUxRestrictions.UX_RESTRICTIONS_BASELINE;
 import static android.car.test.mocks.AndroidMockitoHelper.mockUmGetAllUsers;
 import static android.car.test.mocks.AndroidMockitoHelper.mockUmGetUserHandles;
@@ -56,7 +54,6 @@
 import static org.mockito.Mockito.when;
 
 import android.app.ActivityThread;
-import android.automotive.watchdog.ResourceType;
 import android.automotive.watchdog.internal.ApplicationCategoryType;
 import android.automotive.watchdog.internal.ComponentType;
 import android.automotive.watchdog.internal.GarageMode;
@@ -67,7 +64,6 @@
 import android.automotive.watchdog.internal.PackageInfo;
 import android.automotive.watchdog.internal.PackageIoOveruseStats;
 import android.automotive.watchdog.internal.PackageMetadata;
-import android.automotive.watchdog.internal.PackageResourceOveruseAction;
 import android.automotive.watchdog.internal.PerStateIoOveruseThreshold;
 import android.automotive.watchdog.internal.PowerCycle;
 import android.automotive.watchdog.internal.ResourceSpecificConfiguration;
@@ -178,8 +174,6 @@
     @Captor private ArgumentCaptor<List<
             android.automotive.watchdog.internal.ResourceOveruseConfiguration>>
             mResourceOveruseConfigurationsCaptor;
-    @Captor private ArgumentCaptor<List<PackageResourceOveruseAction>>
-            mResourceOveruseActionsCaptor;
     @Captor private ArgumentCaptor<int[]> mIntArrayCaptor;
     @Captor private ArgumentCaptor<byte[]> mOveruseStatsCaptor;
     @Captor private ArgumentCaptor<byte[]> mKilledStatsCaptor;
@@ -1881,14 +1875,6 @@
                         WatchdogPerfHandler.constructCarWatchdogPerStateBytes(300, 600, 900)));
 
         captureAndVerifyKillStatsReported(expectedReportedKillStats);
-
-        /* {@link thirdPartyPkgUid} action is sent twice. Once before it is killed and once after
-         * it is killed. This is done because the package is killed only after the display is turned
-         * off.
-         */
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{criticalSysPkgUid, thirdPartyPkgUid},
-                /* killedRecurringOveruseUids= */ new int[]{thirdPartyPkgUid}));
     }
 
     @Test
@@ -1985,14 +1971,6 @@
                         WatchdogPerfHandler.constructCarWatchdogPerStateBytes(300, 600, 900)));
 
         captureAndVerifyKillStatsReported(expectedReportedKillStats);
-
-        /* {@link thirdPartySharedUid} action is sent twice. Once before it is killed and once after
-         * it is killed. This is done because the package is killed only after the display is turned
-         * off.
-         */
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{criticalSysSharedUid, thirdPartySharedUid},
-                /* killedRecurringOveruseUids= */ new int[]{thirdPartySharedUid}));
     }
 
     @Test
@@ -2260,11 +2238,6 @@
         verify(() -> CarStatsLog.write(eq(CarStatsLog.CAR_WATCHDOG_KILL_STATS_REPORTED),
                 anyInt(), anyInt(), anyInt(), anyInt(), any(), any()), never());
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{}));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).isEmpty();
     }
 
@@ -2284,11 +2257,6 @@
         verify(() -> CarStatsLog.write(eq(CarStatsLog.CAR_WATCHDOG_KILL_STATS_REPORTED),
                 anyInt(), anyInt(), anyInt(), anyInt(), any(), any()), never());
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{}));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).isEmpty();
     }
 
@@ -2308,11 +2276,6 @@
         verify(() -> CarStatsLog.write(eq(CarStatsLog.CAR_WATCHDOG_KILL_STATS_REPORTED),
                 anyInt(), anyInt(), anyInt(), anyInt(), any(), any()), never());
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{}));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).isEmpty();
     }
 
@@ -2341,12 +2304,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__USER_NO_INTERACTION_MODE,
                 /* killedUids= */ new int[]{10010004, 10110004, 10010005, 10110005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10010004, 10110004, 10010005, 10110005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).containsExactly(
                 "100:vendor_package.non_critical", "101:vendor_package.non_critical",
                 "100:third_party_package.A", "101:third_party_package.A",
@@ -2371,12 +2328,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__USER_NO_INTERACTION_MODE,
                 /* killedUids= */ new int[]{10010004, 10110004, 10010005, 10110005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10010004, 10110004, 10010005, 10110005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).containsExactly(
                 "100:vendor_package.non_critical", "101:vendor_package.non_critical",
                 "100:third_party_package.A", "101:third_party_package.A",
@@ -2411,12 +2362,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__USER_NO_INTERACTION_MODE,
                 /* killedUids= */ new int[]{10010004, 10110004, 10010005, 10110005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10010004, 10110004, 10010005, 10110005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).containsExactly(
                 "100:vendor_package.non_critical", "101:vendor_package.non_critical",
                 "100:third_party_package.A", "101:third_party_package.A",
@@ -2450,12 +2395,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__USER_NO_INTERACTION_MODE,
                 /* killedUids= */ new int[]{10110004, 10010005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10110004, 10010005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages)
                 .containsExactly("101:vendor_package.non_critical", "100:third_party_package.A",
                         "100:third_party_package.B");
@@ -2488,12 +2427,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__USER_NO_INTERACTION_MODE,
                 /* killedUids= */ new int[]{10110004, 10010005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10110004, 10010005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages)
                 .containsExactly("101:vendor_package.non_critical", "100:third_party_package.A",
                         "100:third_party_package.B");
@@ -2527,12 +2460,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__USER_NO_INTERACTION_MODE,
                 /* killedUids= */ new int[]{10010004, 10110004, 10010005, 10110005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10010004, 10110004, 10010005, 10110005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).containsExactly(
                 "100:vendor_package.non_critical", "101:vendor_package.non_critical",
                 "100:third_party_package.A", "101:third_party_package.A",
@@ -2559,12 +2486,6 @@
                 CAR_WATCHDOG_KILL_STATS_REPORTED__SYSTEM_STATE__GARAGE_MODE,
                 /* killedUids= */ new int[]{10010004, 10110004, 10010005, 10110005}));
 
-        verifyActionsTakenOnResourceOveruse(sampleActionTakenOnOveruse(
-                /* notKilledUids= */ new int[]{
-                        10010001, 10110001, 10010004, 10110004, 10010005, 10110005},
-                /* killedRecurringOveruseUids= */ new int[]{10010004, 10110004, 10010005, 10110005}
-        ));
-
         assertWithMessage("Disabled user packages").that(mDisabledUserPackages).containsExactly(
                 "100:vendor_package.non_critical", "101:vendor_package.non_critical",
                 "100:third_party_package.A", "101:third_party_package.A",
@@ -2582,17 +2503,12 @@
         String packageName = mMockContext.getPackageName();
         mGenericPackageNameByUid.put(10003346, packageName);
         mGenericPackageNameByUid.put(10101278, "vendor_package.critical");
-        mGenericPackageNameByUid.put(10103456, "third_party_package");
         injectIoOveruseStatsForPackages(
                 mGenericPackageNameByUid, /* killablePackages= */ new ArraySet<>(),
                 /* shouldNotifyPackages= */ new ArraySet<>());
 
-        doReturn(COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED).when(mSpiedPackageManager)
-                .getApplicationEnabledSetting(
-                        or(eq("third_party_package"), eq("vendor_package.critical")), eq(101));
-
         mWatchdogServiceForSystemImpl.resetResourceOveruseStats(
-                Arrays.asList(packageName, "third_party_package"));
+                Collections.singletonList(packageName));
 
         ResourceOveruseStats actualStats =
                 mCarWatchdogService.getResourceOveruseStatsForUserPackage(
@@ -2606,11 +2522,49 @@
         ResourceOveruseStatsSubject.assertEquals(actualStats, expectedStats);
 
         verify(mMockWatchdogStorage).deleteUserPackage(eq(user.getIdentifier()), eq(packageName));
+    }
 
-        verify(mSpiedPackageManager).getApplicationEnabledSetting(packageName, 100);
-        verify(mSpiedPackageManager).getApplicationEnabledSetting("third_party_package", 101);
-        verify(mSpiedPackageManager).setApplicationEnabledSetting(eq("third_party_package"),
-                eq(COMPONENT_ENABLED_STATE_ENABLED), anyInt(), eq(101), anyString());
+    @Test
+    public void testResetResourceOveruseStatsEnablesPackage() throws Exception {
+        injectPackageInfos(Arrays.asList(
+                constructPackageManagerPackageInfo("third_party_package.A", 10012345,
+                        /* sharedUserId= */ null),
+                constructPackageManagerPackageInfo("vendor_package.critical.A", 10014567,
+                        "vendor_shared_package.A"),
+                constructPackageManagerPackageInfo("vendor_package.critical.B", 10014567,
+                        "vendor_shared_package.A"),
+                constructPackageManagerPackageInfo("system_package.critical.A", 10001278,
+                        "system_shared_package.A"),
+                constructPackageManagerPackageInfo("third_party_package.B", 10056790,
+                        /* sharedUserId= */ null),
+                constructPackageManagerPackageInfo("system_package.non_critical.B", 10007345,
+                        "system_shared_package.B")));
+
+        injectIoOveruseStatsForPackages(
+                mGenericPackageNameByUid, /* killablePackages= */ new ArraySet<>(),
+                /* shouldNotifyPackages= */ new ArraySet<>());
+
+        doReturn(COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED).when(mSpiedPackageManager)
+                .getApplicationEnabledSetting(
+                        or(or(eq("third_party_package.A"), eq("vendor_package.critical.A")),
+                                eq("vendor_package.critical.B")), eq(100));
+
+        mWatchdogServiceForSystemImpl.resetResourceOveruseStats(
+                Arrays.asList("third_party_package.A", "shared:vendor_shared_package.A",
+                        "shared:system_shared_package.A", "third_party_package.B"));
+
+        verify(mSpiedPackageManager).getApplicationEnabledSetting("third_party_package.A", 100);
+        verify(mSpiedPackageManager).getApplicationEnabledSetting("vendor_package.critical.A", 100);
+        verify(mSpiedPackageManager).getApplicationEnabledSetting("vendor_package.critical.B", 100);
+        verify(mSpiedPackageManager).getApplicationEnabledSetting("system_package.critical.A", 100);
+        verify(mSpiedPackageManager).getApplicationEnabledSetting("third_party_package.B", 100);
+
+        verify(mSpiedPackageManager).setApplicationEnabledSetting(eq("third_party_package.A"),
+                eq(COMPONENT_ENABLED_STATE_ENABLED), anyInt(), eq(100), anyString());
+        verify(mSpiedPackageManager).setApplicationEnabledSetting(eq("vendor_package.critical.A"),
+                eq(COMPONENT_ENABLED_STATE_ENABLED), anyInt(), eq(100), anyString());
+        verify(mSpiedPackageManager).setApplicationEnabledSetting(eq("vendor_package.critical.B"),
+                eq(COMPONENT_ENABLED_STATE_ENABLED), anyInt(), eq(100), anyString());
 
         verifyNoMoreInteractions(mSpiedPackageManager);
     }
@@ -3264,25 +3218,6 @@
         delayedRunOnMainSync(() -> {}, OVERUSE_HANDLING_DELAY_MILLS * 2);
     }
 
-    private void verifyActionsTakenOnResourceOveruse(List<PackageResourceOveruseAction> expected)
-            throws Exception {
-        // notifyActionsTakenOnOveruse is posted on the main thread after taking action, so wait for
-        // this to complete by posting a task on the main thread.
-        CarServiceUtils.runOnMainSync(() -> {});
-
-        verify(mMockCarWatchdogDaemon,
-                timeout(MAX_WAIT_TIME_MS).atLeastOnce()).actionTakenOnResourceOveruse(
-                mResourceOveruseActionsCaptor.capture());
-
-        List<PackageResourceOveruseAction> actual = new ArrayList<>();
-        for (List<PackageResourceOveruseAction> actions :
-                mResourceOveruseActionsCaptor.getAllValues()) {
-            actual.addAll(actions);
-        }
-
-        PackageResourceOveruseActionSubject.assertThat(actual).containsExactlyElementsIn(expected);
-    }
-
     private void setUpSampleUserAndPackages() {
         mockUmGetUserHandles(mMockUserManager, /* excludeDying= */ true, 100, 101);
         int[] users = new int[]{100, 101};
@@ -3404,22 +3339,6 @@
         return reportedKillStats;
     }
 
-    private List<PackageResourceOveruseAction> sampleActionTakenOnOveruse(
-            int[] notKilledUids, int[] killedRecurringOveruseUids) {
-        List<PackageResourceOveruseAction> actions = new ArrayList<>();
-        for (int uid : notKilledUids) {
-            actions.add(constructPackageResourceOveruseAction(
-                    mGenericPackageNameByUid.get(uid), uid, new int[]{ResourceType.IO}, NOT_KILLED)
-            );
-        }
-        for (int uid : killedRecurringOveruseUids) {
-            actions.add(constructPackageResourceOveruseAction(
-                    mGenericPackageNameByUid.get(uid), uid, new int[]{ResourceType.IO},
-                    KILLED_RECURRING_OVERUSE));
-        }
-        return actions;
-    }
-
     private static void verifyOnOveruseCalled(List<ResourceOveruseStats> expectedStats,
             IResourceOveruseListener mockListener) throws Exception {
         ArgumentCaptor<ResourceOveruseStats> resourceOveruseStatsCaptor =
@@ -3667,17 +3586,6 @@
         return stats;
     }
 
-    private static PackageResourceOveruseAction constructPackageResourceOveruseAction(
-            String packageName, int uid, int[] resourceTypes, int resourceOveruseActionType) {
-        PackageResourceOveruseAction action = new PackageResourceOveruseAction();
-        action.packageIdentifier = new PackageIdentifier();
-        action.packageIdentifier.name = packageName;
-        action.packageIdentifier.uid = uid;
-        action.resourceTypes = resourceTypes;
-        action.resourceOveruseActionType = resourceOveruseActionType;
-        return action;
-    }
-
     private static void delayedRunOnMainSync(Runnable action, long delayMillis)
             throws InterruptedException {
         AtomicBoolean isComplete = new AtomicBoolean();
diff --git a/tests/carservice_unit_test/src/com/android/car/watchdog/PackageResourceOveruseActionSubject.java b/tests/carservice_unit_test/src/com/android/car/watchdog/PackageResourceOveruseActionSubject.java
deleted file mode 100644
index d0911a3..0000000
--- a/tests/carservice_unit_test/src/com/android/car/watchdog/PackageResourceOveruseActionSubject.java
+++ /dev/null
@@ -1,108 +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 com.android.car.watchdog;
-
-import static com.google.common.truth.Truth.assertAbout;
-import static com.google.common.truth.Truth.assertWithMessage;
-
-import android.annotation.Nullable;
-import android.automotive.watchdog.internal.PackageIdentifier;
-import android.automotive.watchdog.internal.PackageResourceOveruseAction;
-
-import com.google.common.truth.Correspondence;
-import com.google.common.truth.FailureMetadata;
-import com.google.common.truth.Subject;
-
-import java.util.Arrays;
-
-public final class PackageResourceOveruseActionSubject extends Subject {
-    /* Boiler-plate Subject.Factory for PackageResourceOveruseActionSubject. */
-    private static final Subject.Factory<
-            com.android.car.watchdog.PackageResourceOveruseActionSubject,
-            Iterable<PackageResourceOveruseAction>>
-            PACKAGE_RESOURCE_OVERUSE_ACTION_SUBJECT_FACTORY =
-            com.android.car.watchdog.PackageResourceOveruseActionSubject::new;
-
-    private final Iterable<PackageResourceOveruseAction> mActual;
-
-    /* User-defined entry point. */
-    public static PackageResourceOveruseActionSubject assertThat(
-            @Nullable Iterable<PackageResourceOveruseAction> actions) {
-        return assertAbout(PACKAGE_RESOURCE_OVERUSE_ACTION_SUBJECT_FACTORY).that(actions);
-    }
-
-    public static Subject.Factory<PackageResourceOveruseActionSubject,
-            Iterable<PackageResourceOveruseAction>> packageResourceOveruseActions() {
-        return PACKAGE_RESOURCE_OVERUSE_ACTION_SUBJECT_FACTORY;
-    }
-
-    public void containsExactly(PackageResourceOveruseAction... actions) {
-        containsExactlyElementsIn(Arrays.asList(actions));
-    }
-
-    public void containsExactlyElementsIn(
-            Iterable<PackageResourceOveruseAction> expected) {
-        assertWithMessage("Package resource overuse actions:\nExpected: %s\nActual: %s\n",
-                toString(expected), toString(mActual)).that(mActual)
-                .comparingElementsUsing(Correspondence.from(
-                        PackageResourceOveruseActionSubject::isEquals, "is equal to"))
-                .containsExactlyElementsIn(expected);
-    }
-
-    public static boolean isEquals(PackageResourceOveruseAction actual,
-            PackageResourceOveruseAction expected) {
-        if (actual == null || expected == null) {
-            return (actual == null) && (expected == null);
-        }
-        return isPackageIdentifierEquals(actual.packageIdentifier, expected.packageIdentifier)
-                && Arrays.equals(actual.resourceTypes, expected.resourceTypes)
-                && actual.resourceOveruseActionType == expected.resourceOveruseActionType;
-    }
-
-    private static boolean isPackageIdentifierEquals(PackageIdentifier lhs, PackageIdentifier rhs) {
-        return lhs.name.equals(rhs.name) && lhs.uid == rhs.uid;
-    }
-
-    public static String toString(Iterable<PackageResourceOveruseAction> actions) {
-        StringBuilder builder = new StringBuilder();
-        builder.append("[");
-        for (PackageResourceOveruseAction action : actions) {
-            builder = toStringBuilder(builder, action);
-            builder.append(", ");
-        }
-        if (builder.length() > 1) {
-            builder.delete(builder.length() - 2, builder.length());
-        }
-        builder.append("]");
-        return builder.toString();
-    }
-
-    public static StringBuilder toStringBuilder(
-            StringBuilder builder, PackageResourceOveruseAction action) {
-        return builder.append("{Package Identifier: {Name: ")
-                .append(action.packageIdentifier.name)
-                .append(", UID: ").append(action.packageIdentifier.uid)
-                .append("}, Resource Types: ").append(Arrays.toString(action.resourceTypes))
-                .append(", Action Type: ").append(action.resourceOveruseActionType).append("}");
-    }
-
-    private PackageResourceOveruseActionSubject(FailureMetadata failureMetadata,
-            @Nullable Iterable<PackageResourceOveruseAction> iterableSubject) {
-        super(failureMetadata, iterableSubject);
-        this.mActual = iterableSubject;
-    }
-}