1 /* 2 * Copyright (C) 2009 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 package com.android.internal.os; 17 18 import android.annotation.UnsupportedAppUsage; 19 import android.os.BatteryStats.Uid; 20 21 import java.util.List; 22 23 /** 24 * Contains power usage of an application, system service, or hardware type. 25 */ 26 public class BatterySipper implements Comparable<BatterySipper> { 27 @UnsupportedAppUsage 28 public int userId; 29 @UnsupportedAppUsage 30 public Uid uidObj; 31 @UnsupportedAppUsage 32 public DrainType drainType; 33 34 /** 35 * Smeared power from screen usage. 36 * We split the screen usage power and smear them among apps, based on activity time. 37 */ 38 public double screenPowerMah; 39 40 /** 41 * Smeared power using proportional method. 42 * 43 * we smear power usage from hidden sippers to all apps proportionally.(except for screen usage) 44 * 45 * @see BatteryStatsHelper#shouldHideSipper(BatterySipper) 46 * @see BatteryStatsHelper#removeHiddenBatterySippers(List) 47 */ 48 public double proportionalSmearMah; 49 50 /** 51 * Total power that adding the smeared power. 52 * 53 * @see #sumPower() 54 */ 55 public double totalSmearedPowerMah; 56 57 /** 58 * Total power before smearing 59 */ 60 @UnsupportedAppUsage 61 public double totalPowerMah; 62 63 /** 64 * Whether we should hide this sipper 65 * 66 * @see BatteryStatsHelper#shouldHideSipper(BatterySipper) 67 */ 68 public boolean shouldHide; 69 70 /** 71 * Generic usage time in milliseconds. 72 */ 73 @UnsupportedAppUsage 74 public long usageTimeMs; 75 76 /** 77 * Generic power usage in mAh. 78 */ 79 public double usagePowerMah; 80 81 // Subsystem usage times. 82 public long audioTimeMs; 83 public long bluetoothRunningTimeMs; 84 public long cameraTimeMs; 85 @UnsupportedAppUsage 86 public long cpuFgTimeMs; 87 @UnsupportedAppUsage 88 public long cpuTimeMs; 89 public long flashlightTimeMs; 90 @UnsupportedAppUsage 91 public long gpsTimeMs; 92 public long videoTimeMs; 93 @UnsupportedAppUsage 94 public long wakeLockTimeMs; 95 @UnsupportedAppUsage 96 public long wifiRunningTimeMs; 97 98 public long mobileRxPackets; 99 public long mobileTxPackets; 100 public long mobileActive; 101 public int mobileActiveCount; 102 public double mobilemspp; // milliseconds per packet 103 public long wifiRxPackets; 104 public long wifiTxPackets; 105 public long mobileRxBytes; 106 public long mobileTxBytes; 107 public long wifiRxBytes; 108 public long wifiTxBytes; 109 public long btRxBytes; 110 public long btTxBytes; 111 public double percent; 112 public double noCoveragePercent; 113 @UnsupportedAppUsage 114 public String[] mPackages; 115 @UnsupportedAppUsage 116 public String packageWithHighestDrain; 117 118 // Measured in mAh (milli-ampere per hour). 119 // These are included when summed. 120 public double audioPowerMah; 121 public double bluetoothPowerMah; 122 public double cameraPowerMah; 123 @UnsupportedAppUsage 124 public double cpuPowerMah; 125 public double flashlightPowerMah; 126 public double gpsPowerMah; 127 public double mobileRadioPowerMah; 128 public double sensorPowerMah; 129 public double videoPowerMah; 130 public double wakeLockPowerMah; 131 public double wifiPowerMah; 132 133 // **************** 134 // This list must be kept current with atoms.proto (frameworks/base/cmds/statsd/src/atoms.proto) 135 // so the ordinal values (and therefore the order) must never change. 136 // **************** 137 public enum DrainType { 138 AMBIENT_DISPLAY, 139 @UnsupportedAppUsage 140 APP, 141 BLUETOOTH, 142 CAMERA, 143 CELL, 144 FLASHLIGHT, 145 IDLE, 146 MEMORY, 147 OVERCOUNTED, 148 PHONE, 149 SCREEN, 150 UNACCOUNTED, 151 USER, 152 WIFI, 153 } 154 155 @UnsupportedAppUsage BatterySipper(DrainType drainType, Uid uid, double value)156 public BatterySipper(DrainType drainType, Uid uid, double value) { 157 this.totalPowerMah = value; 158 this.drainType = drainType; 159 uidObj = uid; 160 } 161 computeMobilemspp()162 public void computeMobilemspp() { 163 long packets = mobileRxPackets + mobileTxPackets; 164 mobilemspp = packets > 0 ? (mobileActive / (double) packets) : 0; 165 } 166 167 @Override compareTo(BatterySipper other)168 public int compareTo(BatterySipper other) { 169 // Over-counted always goes to the bottom. 170 if (drainType != other.drainType) { 171 if (drainType == DrainType.OVERCOUNTED) { 172 // This is "larger" 173 return 1; 174 } else if (other.drainType == DrainType.OVERCOUNTED) { 175 return -1; 176 } 177 } 178 // Return the flipped value because we want the items in descending order 179 return Double.compare(other.totalPowerMah, totalPowerMah); 180 } 181 182 /** 183 * Gets a list of packages associated with the current user 184 */ 185 @UnsupportedAppUsage getPackages()186 public String[] getPackages() { 187 return mPackages; 188 } 189 190 @UnsupportedAppUsage getUid()191 public int getUid() { 192 // Bail out if the current sipper is not an App sipper. 193 if (uidObj == null) { 194 return 0; 195 } 196 return uidObj.getUid(); 197 } 198 199 /** 200 * Add stats from other to this BatterySipper. 201 */ 202 @UnsupportedAppUsage add(BatterySipper other)203 public void add(BatterySipper other) { 204 totalPowerMah += other.totalPowerMah; 205 usageTimeMs += other.usageTimeMs; 206 usagePowerMah += other.usagePowerMah; 207 audioTimeMs += other.audioTimeMs; 208 cpuTimeMs += other.cpuTimeMs; 209 gpsTimeMs += other.gpsTimeMs; 210 wifiRunningTimeMs += other.wifiRunningTimeMs; 211 cpuFgTimeMs += other.cpuFgTimeMs; 212 videoTimeMs += other.videoTimeMs; 213 wakeLockTimeMs += other.wakeLockTimeMs; 214 cameraTimeMs += other.cameraTimeMs; 215 flashlightTimeMs += other.flashlightTimeMs; 216 bluetoothRunningTimeMs += other.bluetoothRunningTimeMs; 217 mobileRxPackets += other.mobileRxPackets; 218 mobileTxPackets += other.mobileTxPackets; 219 mobileActive += other.mobileActive; 220 mobileActiveCount += other.mobileActiveCount; 221 wifiRxPackets += other.wifiRxPackets; 222 wifiTxPackets += other.wifiTxPackets; 223 mobileRxBytes += other.mobileRxBytes; 224 mobileTxBytes += other.mobileTxBytes; 225 wifiRxBytes += other.wifiRxBytes; 226 wifiTxBytes += other.wifiTxBytes; 227 btRxBytes += other.btRxBytes; 228 btTxBytes += other.btTxBytes; 229 audioPowerMah += other.audioPowerMah; 230 wifiPowerMah += other.wifiPowerMah; 231 gpsPowerMah += other.gpsPowerMah; 232 cpuPowerMah += other.cpuPowerMah; 233 sensorPowerMah += other.sensorPowerMah; 234 mobileRadioPowerMah += other.mobileRadioPowerMah; 235 wakeLockPowerMah += other.wakeLockPowerMah; 236 cameraPowerMah += other.cameraPowerMah; 237 flashlightPowerMah += other.flashlightPowerMah; 238 bluetoothPowerMah += other.bluetoothPowerMah; 239 screenPowerMah += other.screenPowerMah; 240 videoPowerMah += other.videoPowerMah; 241 proportionalSmearMah += other.proportionalSmearMah; 242 totalSmearedPowerMah += other.totalSmearedPowerMah; 243 } 244 245 /** 246 * Sum all the powers and store the value into `value`. 247 * Also sum the {@code smearedTotalPowerMah} by adding smeared powerMah. 248 * 249 * @return the sum of all the power in this BatterySipper. 250 */ sumPower()251 public double sumPower() { 252 totalPowerMah = usagePowerMah + wifiPowerMah + gpsPowerMah + cpuPowerMah + 253 sensorPowerMah + mobileRadioPowerMah + wakeLockPowerMah + cameraPowerMah + 254 flashlightPowerMah + bluetoothPowerMah + audioPowerMah + videoPowerMah; 255 totalSmearedPowerMah = totalPowerMah + screenPowerMah + proportionalSmearMah; 256 257 return totalPowerMah; 258 } 259 } 260