diff options
| author | 2022-04-05 16:23:28 +0000 | |
|---|---|---|
| committer | 2022-04-05 16:23:28 +0000 | |
| commit | 29b5a95a86a19fb52378d45ee6b2a29c2c41d67f (patch) | |
| tree | 9c36b30e2cb79df255d93bf78ed59731500f6cdc | |
| parent | ab6aaa765b9892eed0e8af45d3148b34ea0f4e62 (diff) | |
| parent | bf7ac2254b6ce95c034e0bda7af3a1d9ff007d6d (diff) | |
Merge "Log AppBatteryTracker to statsd atom APP_BACKGROUND_RESTRICTIONS_INFO." into tm-dev
| -rw-r--r-- | core/proto/android/os/appbackgroundrestrictioninfo.proto | 199 | ||||
| -rw-r--r-- | services/core/java/com/android/server/am/AppBatteryTracker.java | 91 |
2 files changed, 290 insertions, 0 deletions
diff --git a/core/proto/android/os/appbackgroundrestrictioninfo.proto b/core/proto/android/os/appbackgroundrestrictioninfo.proto new file mode 100644 index 000000000000..8445641694dc --- /dev/null +++ b/core/proto/android/os/appbackgroundrestrictioninfo.proto @@ -0,0 +1,199 @@ +/* + * Copyright (C) 2022 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +syntax = "proto2"; +package android.os; + +option java_multiple_files = true; + +// This message is used for statsd logging and should be kept in sync with +// frameworks/proto_logging/stats/atoms.proto +/** + * Logs information about app background restrictions. + * + * Logged from: + * frameworks/base/services/core/java/com/android/server/am/AppRestrictionController.java + */ +message AppBackgroundRestrictionsInfo { + // the uid of the app. + optional int32 uid = 1; + + enum RestrictionLevel { + LEVEL_UNKNOWN = 0; + LEVEL_UNRESTRICTED = 1; + LEVEL_EXEMPTED = 2; + LEVEL_ADAPTIVE_BUCKET = 3; + LEVEL_RESTRICTED_BUCKET = 4; + LEVEL_BACKGROUND_RESTRICTED = 5; + LEVEL_HIBERNATION = 6; + } + // indicates the app background restriction level. + optional RestrictionLevel restriction_level = 2; + + enum Threshold { + THRESHOLD_UNKNOWN = 0; + THRESHOLD_RESTRICTED = 1; // app was background restricted by the system. + THRESHOLD_USER = 2; // app was background restricted by user action. + } + // indicates which threshold caused the app to be put into bg restriction. + optional Threshold threshold = 3; + + enum StateTracker { + UNKNOWN_TRACKER = 0; + BATTERY_TRACKER = 1; + BATTERY_EXEMPTION_TRACKER = 2; + FGS_TRACKER = 3; + MEDIA_SESSION_TRACKER = 4; + PERMISSION_TRACKER = 5; + BROADCAST_EVENTS_TRACKER = 6; + BIND_SERVICE_EVENTS_TRACKER = 7; + } + // indicates the reason/tracker which caused the app to hit the threshold. + optional StateTracker tracker = 4; + + message FgsTrackerInfo { + // indicates whether an fgs notification was visible for this app or not. + optional bool fgs_notification_visible = 1; + // total FGS duration for this app. + optional int64 fgs_duration = 2; + } + optional FgsTrackerInfo fgs_tracker_info = 5; + + message BatteryTrackerInfo { + // total battery usage within last 24h (percentage) + optional int32 battery_24h = 1; + // background battery usage (percentage) + optional int32 battery_usage_background = 2; + // FGS battery usage (percentage) + optional int32 battery_usage_fgs = 3; + } + optional BatteryTrackerInfo battery_tracker_info = 6; + + message BroadcastEventsTrackerInfo { + // the number of broadcasts sent by this app. + optional int32 broadcasts_sent = 1; + } + optional BroadcastEventsTrackerInfo broadcast_events_tracker_info = 7; + + message BindServiceEventsTrackerInfo { + // the number of bind service requests by this app. + optional int32 bind_service_requests = 1; + } + optional BindServiceEventsTrackerInfo bind_service_events_tracker_info = + 8; + + // The reasons listed below are defined in PowerExemptionManager.java + enum ExemptionReason { + // range 0-9 is reserved for default reasons + REASON_UNKNOWN = 0; + REASON_DENIED = 1; + REASON_OTHER = 2; + // range 10-49 is reserved for BG-FGS-launch allowed proc states + REASON_PROC_STATE_PERSISTENT = 10; + REASON_PROC_STATE_PERSISTENT_UI = 11; + REASON_PROC_STATE_TOP = 12; + REASON_PROC_STATE_BTOP = 13; + REASON_PROC_STATE_FGS = 14; + REASON_PROC_STATE_BFGS = 15; + // range 50-99 is reserved for BG-FGS-launch allowed reasons + REASON_UID_VISIBLE = 50; + REASON_SYSTEM_UID = 51; + REASON_ACTIVITY_STARTER = 52; + REASON_START_ACTIVITY_FLAG = 53; + REASON_FGS_BINDING = 54; + REASON_DEVICE_OWNER = 55; + REASON_PROFILE_OWNER = 56; + REASON_COMPANION_DEVICE_MANAGER = 57; + REASON_BACKGROUND_ACTIVITY_PERMISSION = 58; + REASON_BACKGROUND_FGS_PERMISSION = 59; + REASON_INSTR_BACKGROUND_ACTIVITY_PERMISSION = 60; + REASON_INSTR_BACKGROUND_FGS_PERMISSION = 61; + REASON_SYSTEM_ALERT_WINDOW_PERMISSION = 62; + REASON_DEVICE_DEMO_MODE = 63; + REASON_ALLOWLISTED_PACKAGE = 65; + REASON_APPOP = 66; + REASON_ACTIVITY_VISIBILITY_GRACE_PERIOD = 67; + REASON_OP_ACTIVATE_VPN = 68; + REASON_OP_ACTIVATE_PLATFORM_VPN = 69; + REASON_TEMP_ALLOWED_WHILE_IN_USE = 70; + REASON_CURRENT_INPUT_METHOD = 71; + // range 100-199 is reserved for public reasons + REASON_GEOFENCING = 100; + REASON_PUSH_MESSAGING = 101; + REASON_PUSH_MESSAGING_OVER_QUOTA = 102; + REASON_ACTIVITY_RECOGNITION = 103; + REASON_ACCOUNT_TRANSFER = 104; + // range 200-299 is reserved for broadcast actions + REASON_BOOT_COMPLETED = 200; + REASON_PRE_BOOT_COMPLETED = 201; + REASON_LOCKED_BOOT_COMPLETED = 202; + REASON_BLUETOOTH_BROADCAST = 203; + REASON_TIMEZONE_CHANGED = 204; + REASON_TIME_CHANGED = 205; + REASON_LOCALE_CHANGED = 206; + REASON_SCHEDULE_EXACT_ALARM_PERMISSION_STATE_CHANGED = 207; + REASON_REFRESH_SAFETY_SOURCES = 208; + // range 300-399 is reserved for other internal reasons + REASON_SYSTEM_ALLOW_LISTED = 300; + REASON_ALARM_MANAGER_ALARM_CLOCK = 301; + REASON_ALARM_MANAGER_WHILE_IDLE = 302; + REASON_SERVICE_LAUNCH = 303; + REASON_KEY_CHAIN = 304; + REASON_PACKAGE_VERIFIER = 305; + REASON_SYNC_MANAGER = 306; + REASON_DOMAIN_VERIFICATION_V1 = 307; + REASON_DOMAIN_VERIFICATION_V2 = 308; + REASON_VPN = 309; + REASON_NOTIFICATION_SERVICE = 310; + REASON_PACKAGE_REPLACED = 311; + REASON_LOCATION_PROVIDER = 312; + REASON_MEDIA_BUTTON = 313; + REASON_EVENT_SMS = 314; + REASON_EVENT_MMS = 315; + REASON_SHELL = 316; + REASON_MEDIA_SESSION_CALLBACK = 317; + REASON_ROLE_DIALER = 318; + REASON_ROLE_EMERGENCY = 319; + REASON_SYSTEM_MODULE = 320; + REASON_CARRIER_PRIVILEGED_APP = 321; + // app requested to be exempt + REASON_OPT_OUT_REQUESTED = 1000; + } + // indicates if the app is exempt from background restrictions and the reason if applicable. + optional ExemptionReason exemption_reason = 9; + + enum OptimizationLevel { + UNKNOWN = 0; + OPTIMIZED = 1; + BACKGROUND_RESTRICTED = 2; + NOT_OPTIMIZED = 3; + } + // the user choice for the optimization level of the app. + optional OptimizationLevel opt_level = 10; + + enum TargetSdk { + SDK_UNKNOWN = 0; + SDK_PRE_S = 1; + SDK_S = 2; + SDK_T = 3; + } + // indicates the target sdk level for this app. + optional TargetSdk target_sdk = 11; + + // indicates if the current device is a low ram device. + optional bool low_mem_device = 12; +} + diff --git a/services/core/java/com/android/server/am/AppBatteryTracker.java b/services/core/java/com/android/server/am/AppBatteryTracker.java index 032b129c4256..64ff532b026a 100644 --- a/services/core/java/com/android/server/am/AppBatteryTracker.java +++ b/services/core/java/com/android/server/am/AppBatteryTracker.java @@ -49,6 +49,7 @@ import android.content.Context; import android.content.pm.ServiceInfo; import android.content.res.Resources; import android.content.res.TypedArray; +import android.os.AppBackgroundRestrictionsInfo; import android.os.AppBatteryStatsProto; import android.os.BatteryConsumer; import android.os.BatteryConsumer.Dimensions; @@ -74,6 +75,7 @@ import com.android.internal.R; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.util.ArrayUtils; +import com.android.internal.util.FrameworkStatsLog; import com.android.server.am.AppBatteryTracker.AppBatteryPolicy; import com.android.server.am.AppRestrictionController.TrackerType; import com.android.server.am.AppRestrictionController.UidBatteryUsageProvider; @@ -175,6 +177,12 @@ final class AppBatteryTracker extends BaseAppStateTracker<AppBatteryPolicy> @GuardedBy("mLock") private long mLastUidBatteryUsageStartTs; + /** + * elapseRealTime of last time the AppBatteryTracker is reported to statsd. + */ + @GuardedBy("mLock") + private long mLastReportTime = 0; + // For debug only. private final SparseArray<ImmutableBatteryUsage> mDebugUidPercentages = new SparseArray<>(); @@ -228,9 +236,92 @@ final class AppBatteryTracker extends BaseAppStateTracker<AppBatteryPolicy> mBgHandler.postDelayed(mBgBatteryUsageStatsPolling, delay); } } + logAppBatteryTrackerIfNeeded(); } } + /** + * Log per-uid BatteryTrackerInfo to statsd every 24 hours (as the window specified in + * {@link AppBatteryPolicy#mBgCurrentDrainWindowMs}) + */ + private void logAppBatteryTrackerIfNeeded() { + final long now = SystemClock.elapsedRealtime(); + synchronized (mLock) { + final AppBatteryPolicy bgPolicy = mInjector.getPolicy(); + if (now - mLastReportTime < bgPolicy.mBgCurrentDrainWindowMs) { + return; + } else { + mLastReportTime = now; + } + } + updateBatteryUsageStatsIfNecessary(mInjector.currentTimeMillis(), true); + synchronized (mLock) { + for (int i = 0, size = mUidBatteryUsageInWindow.size(); i < size; i++) { + final int uid = mUidBatteryUsageInWindow.keyAt(i); + if (!UserHandle.isCore(uid) && !UserHandle.isApp(uid)) { + continue; + } + if (BATTERY_USAGE_NONE.equals(mUidBatteryUsageInWindow.valueAt(i))) { + continue; + } + FrameworkStatsLog.write(FrameworkStatsLog.APP_BACKGROUND_RESTRICTIONS_INFO, + uid, + FrameworkStatsLog + .APP_BACKGROUND_RESTRICTIONS_INFO__RESTRICTION_LEVEL__LEVEL_UNKNOWN, + FrameworkStatsLog + .APP_BACKGROUND_RESTRICTIONS_INFO__THRESHOLD__THRESHOLD_UNKNOWN, + FrameworkStatsLog + .APP_BACKGROUND_RESTRICTIONS_INFO__TRACKER__UNKNOWN_TRACKER, + null /*byte[] fgs_tracker_info*/, + getBatteryTrackerInfoProtoLocked(uid) /*byte[] battery_tracker_info*/, + null /*byte[] broadcast_events_tracker_info*/, + null /*byte[] bind_service_events_tracker_info*/, + FrameworkStatsLog + .APP_BACKGROUND_RESTRICTIONS_INFO__EXEMPTION_REASON__REASON_UNKNOWN, + FrameworkStatsLog + .APP_BACKGROUND_RESTRICTIONS_INFO__OPT_LEVEL__UNKNOWN, + FrameworkStatsLog + .APP_BACKGROUND_RESTRICTIONS_INFO__TARGET_SDK__SDK_UNKNOWN, + isLowRamDeviceStatic()); + } + } + } + + /** + * Get the BatteryTrackerInfo proto of a UID. + * @param uid + * @return byte array of the proto. + */ + @NonNull byte[] getBatteryTrackerInfoProtoLocked(int uid) { + final ImmutableBatteryUsage temp = mUidBatteryUsageInWindow.get(uid); + if (temp == null) { + return new byte[0]; + } + final BatteryUsage bgUsage = temp.calcPercentage(uid, mInjector.getPolicy()); + final double allUsage = bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_UNSPECIFIED] + + bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_FOREGROUND] + + bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_BACKGROUND] + + bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_FOREGROUND_SERVICE] + + bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_CACHED]; + final double usageBackground = + bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_BACKGROUND]; + final double usageFgs = + bgUsage.mPercentage[BatteryUsage.BATTERY_USAGE_INDEX_FOREGROUND_SERVICE]; + Slog.d(TAG, "getBatteryTrackerInfoProtoLocked uid:" + uid + + " allUsage:" + String.format("%4.2f%%", allUsage) + + " usageBackground:" + String.format("%4.2f%%", usageBackground) + + " usageFgs:" + String.format("%4.2f%%", usageFgs)); + final ProtoOutputStream proto = new ProtoOutputStream(); + proto.write(AppBackgroundRestrictionsInfo.BatteryTrackerInfo.BATTERY_24H, + allUsage * 10000); + proto.write(AppBackgroundRestrictionsInfo.BatteryTrackerInfo.BATTERY_USAGE_BACKGROUND, + usageBackground * 10000); + proto.write(AppBackgroundRestrictionsInfo.BatteryTrackerInfo.BATTERY_USAGE_FGS, + usageFgs * 10000); + proto.flush(); + return proto.getBytes(); + } + @Override void onUserStarted(final @UserIdInt int userId) { synchronized (mLock) { |