1 /* 2 * Copyright (C) 2020 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 17 package com.android.server.power.stats; 18 19 import static android.os.BatteryConsumer.POWER_COMPONENT_ANY; 20 import static android.os.BatteryConsumer.POWER_MODEL_ENERGY_CONSUMPTION; 21 import static android.os.BatteryConsumer.POWER_MODEL_UNDEFINED; 22 import static android.os.BatteryConsumer.PROCESS_STATE_BACKGROUND; 23 import static android.os.BatteryConsumer.PROCESS_STATE_CACHED; 24 import static android.os.BatteryConsumer.PROCESS_STATE_FOREGROUND; 25 import static android.os.BatteryConsumer.PROCESS_STATE_FOREGROUND_SERVICE; 26 27 import static com.google.common.truth.Truth.assertThat; 28 29 import static org.junit.Assert.assertThrows; 30 import static org.junit.Assert.fail; 31 import static org.mockito.Mockito.mock; 32 import static org.mockito.Mockito.when; 33 34 import android.os.AggregateBatteryConsumer; 35 import android.os.BatteryConsumer; 36 import android.os.BatteryUsageStats; 37 import android.os.Parcel; 38 import android.os.UidBatteryConsumer; 39 import android.os.UserBatteryConsumer; 40 import android.util.Xml; 41 42 import androidx.test.filters.SmallTest; 43 import androidx.test.runner.AndroidJUnit4; 44 45 import com.android.modules.utils.TypedXmlPullParser; 46 import com.android.modules.utils.TypedXmlSerializer; 47 48 import org.junit.Test; 49 import org.junit.runner.RunWith; 50 51 import java.io.ByteArrayInputStream; 52 import java.io.ByteArrayOutputStream; 53 import java.io.PrintWriter; 54 import java.io.StringWriter; 55 import java.nio.charset.StandardCharsets; 56 import java.util.HashSet; 57 import java.util.List; 58 import java.util.Map; 59 import java.util.Set; 60 import java.util.stream.Collectors; 61 62 @SmallTest 63 @RunWith(AndroidJUnit4.class) 64 public class BatteryUsageStatsTest { 65 66 private static final int USER_ID = 42; 67 private static final int APP_UID1 = 271; 68 private static final int APP_UID2 = 314; 69 70 @Test testBuilder()71 public void testBuilder() { 72 BatteryUsageStats batteryUsageStats = buildBatteryUsageStats1(true).build(); 73 assertBatteryUsageStats1(batteryUsageStats, true); 74 } 75 76 @Test testBuilder_noProcessStateData()77 public void testBuilder_noProcessStateData() { 78 BatteryUsageStats batteryUsageStats = buildBatteryUsageStats1(false).build(); 79 assertBatteryUsageStats1(batteryUsageStats, false); 80 } 81 82 @Test testParcelability_smallNumberOfUids()83 public void testParcelability_smallNumberOfUids() { 84 final BatteryUsageStats outBatteryUsageStats = buildBatteryUsageStats1(true).build(); 85 final Parcel parcel = Parcel.obtain(); 86 parcel.writeParcelable(outBatteryUsageStats, 0); 87 88 assertThat(parcel.dataSize()).isLessThan(8000); 89 90 parcel.setDataPosition(0); 91 92 final BatteryUsageStats inBatteryUsageStats = 93 parcel.readParcelable(getClass().getClassLoader()); 94 assertThat(inBatteryUsageStats).isNotNull(); 95 assertBatteryUsageStats1(inBatteryUsageStats, true); 96 } 97 98 @Test testParcelability_largeNumberOfUids()99 public void testParcelability_largeNumberOfUids() { 100 final BatteryUsageStats.Builder builder = 101 new BatteryUsageStats.Builder(new String[0]); 102 103 // Without the use of a CursorWindow, this BatteryUsageStats object would generate a Parcel 104 // larger than 64 Kb 105 final int uidCount = 200; 106 for (int i = 0; i < uidCount; i++) { 107 BatteryStatsImpl.Uid mockUid = mock(BatteryStatsImpl.Uid.class); 108 when(mockUid.getUid()).thenReturn(i); 109 builder.getOrCreateUidBatteryConsumerBuilder(mockUid) 110 .setConsumedPower(BatteryConsumer.POWER_COMPONENT_SCREEN, i * 100); 111 } 112 113 BatteryUsageStats outBatteryUsageStats = builder.build(); 114 115 final Parcel parcel = Parcel.obtain(); 116 parcel.writeParcelable(outBatteryUsageStats, 0); 117 118 assertThat(parcel.dataSize()).isLessThan(2000); 119 120 parcel.setDataPosition(0); 121 122 final BatteryUsageStats inBatteryUsageStats = 123 parcel.readParcelable(getClass().getClassLoader()); 124 parcel.recycle(); 125 126 assertThat(inBatteryUsageStats.getUidBatteryConsumers()).hasSize(uidCount); 127 final Map<Integer, UidBatteryConsumer> consumersByUid = 128 inBatteryUsageStats.getUidBatteryConsumers().stream().collect( 129 Collectors.toMap(UidBatteryConsumer::getUid, c -> c)); 130 for (int i = 0; i < uidCount; i++) { 131 final UidBatteryConsumer uidBatteryConsumer = consumersByUid.get(i); 132 assertThat(uidBatteryConsumer).isNotNull(); 133 assertThat(uidBatteryConsumer.getConsumedPower()).isEqualTo(i * 100); 134 } 135 } 136 137 @Test testDefaultSessionDuration()138 public void testDefaultSessionDuration() { 139 final BatteryUsageStats stats = 140 buildBatteryUsageStats1(true).setStatsDuration(10000).build(); 141 assertThat(stats.getStatsDuration()).isEqualTo(10000); 142 } 143 144 @Test testDump()145 public void testDump() { 146 final BatteryUsageStats stats = buildBatteryUsageStats1(true).build(); 147 final StringWriter out = new StringWriter(); 148 try (PrintWriter pw = new PrintWriter(out)) { 149 stats.dump(pw, " "); 150 } 151 final String dump = out.toString(); 152 153 assertThat(dump).contains("Capacity: 4000"); 154 assertThat(dump).contains("Computed drain: 30000"); 155 assertThat(dump).contains("actual drain: 1000-2000"); 156 assertThat(dump).contains("cpu: 20100 apps: 10100 duration: 20s 300ms"); 157 assertThat(dump).contains("cpu(fg): 2333 apps: 1333 duration: 3s 332ms"); 158 assertThat(dump).contains("cpu(bg): 2444 apps: 1444 duration: 4s 442ms"); 159 assertThat(dump).contains("cpu(fgs): 2555 apps: 1555 duration: 5s 552ms"); 160 assertThat(dump).contains("cpu(cached): 123 apps: 123 duration: 456ms"); 161 assertThat(dump).contains("FOO: 20200 apps: 10200 duration: 20s 400ms"); 162 assertThat(dump).contains("UID 271: 1200 fg: 1777 bg: 1888 fgs: 1999 cached: 123 " 163 + "( screen=300 cpu=400 (600ms) cpu:fg=1777 (7s 771ms) cpu:bg=1888 (8s 881ms) " 164 + "cpu:fgs=1999 (9s 991ms) cpu:cached=123 (456ms) FOO=500 )"); 165 assertThat(dump).contains("User 42: 30.0 ( cpu=10.0 (30ms) FOO=20.0 )"); 166 } 167 168 @Test testPowerComponentNames_existAndUnique()169 public void testPowerComponentNames_existAndUnique() { 170 Set<String> allNames = new HashSet<>(); 171 for (int i = 0; i < BatteryConsumer.POWER_COMPONENT_COUNT; i++) { 172 assertThat(BatteryConsumer.powerComponentIdToString(i)).isNotNull(); 173 allNames.add(BatteryConsumer.powerComponentIdToString(i)); 174 } 175 assertThat(allNames).hasSize(BatteryConsumer.POWER_COMPONENT_COUNT); 176 } 177 178 @Test testAdd()179 public void testAdd() { 180 final BatteryUsageStats stats1 = buildBatteryUsageStats1(false).build(); 181 final BatteryUsageStats stats2 = buildBatteryUsageStats2(new String[]{"FOO"}, true).build(); 182 183 final BatteryUsageStats sum = 184 new BatteryUsageStats.Builder(new String[]{"FOO"}, true, true, 0) 185 .add(stats1) 186 .add(stats2) 187 .build(); 188 189 assertBatteryUsageStats(sum, 42345, 50, 2234, 4345, 1234, 1000, 5000, 5000); 190 191 final List<UidBatteryConsumer> uidBatteryConsumers = 192 sum.getUidBatteryConsumers(); 193 for (UidBatteryConsumer uidBatteryConsumer : uidBatteryConsumers) { 194 if (uidBatteryConsumer.getUid() == APP_UID1) { 195 assertUidBatteryConsumer(uidBatteryConsumer, 2124, null, 196 5321, 7432, 423, BatteryConsumer.POWER_MODEL_POWER_PROFILE, 745, 197 POWER_MODEL_UNDEFINED, 198 956, 1167, 1478, 199 true, 3554, 3776, 3998, 444, 3554, 15542, 3776, 17762, 3998, 19982, 200 444, 1110); 201 } else if (uidBatteryConsumer.getUid() == APP_UID2) { 202 assertUidBatteryConsumer(uidBatteryConsumer, 1332, "bar", 203 1111, 2222, 333, BatteryConsumer.POWER_MODEL_POWER_PROFILE, 444, 204 BatteryConsumer.POWER_MODEL_POWER_PROFILE, 205 555, 666, 777, 206 true, 1777, 1888, 1999, 321, 1777, 7771, 1888, 8881, 1999, 9991, 207 321, 654); 208 } else { 209 fail("Unexpected UID " + uidBatteryConsumer.getUid()); 210 } 211 } 212 213 assertAggregateBatteryConsumer(sum, 214 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_ALL_APPS, 215 20223, 20434, 20645, 20856); 216 217 assertAggregateBatteryConsumer(sum, 218 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_DEVICE, 219 40211, 40422, 40633, 40844); 220 } 221 222 @Test testAdd_customComponentMismatch()223 public void testAdd_customComponentMismatch() { 224 final BatteryUsageStats.Builder builder = 225 new BatteryUsageStats.Builder(new String[]{"FOO"}, true, true, 0); 226 final BatteryUsageStats stats = buildBatteryUsageStats2(new String[]{"BAR"}, false).build(); 227 228 assertThrows(IllegalArgumentException.class, () -> builder.add(stats)); 229 } 230 231 @Test testAdd_processStateDataMismatch()232 public void testAdd_processStateDataMismatch() { 233 final BatteryUsageStats.Builder builder = 234 new BatteryUsageStats.Builder(new String[]{"FOO"}, true, true, 0); 235 final BatteryUsageStats stats = buildBatteryUsageStats2(new String[]{"FOO"}, false).build(); 236 237 assertThrows(IllegalArgumentException.class, () -> builder.add(stats)); 238 } 239 240 @Test testXml()241 public void testXml() throws Exception { 242 ByteArrayOutputStream out = new ByteArrayOutputStream(); 243 TypedXmlSerializer serializer = Xml.newBinarySerializer(); 244 serializer.setOutput(out, StandardCharsets.UTF_8.name()); 245 serializer.startDocument(null, true); 246 final BatteryUsageStats stats = buildBatteryUsageStats1(true).build(); 247 stats.writeXml(serializer); 248 serializer.endDocument(); 249 250 ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray()); 251 TypedXmlPullParser parser = Xml.newBinaryPullParser(); 252 parser.setInput(in, StandardCharsets.UTF_8.name()); 253 final BatteryUsageStats fromXml = BatteryUsageStats.createFromXml(parser); 254 255 assertBatteryUsageStats1(fromXml, true); 256 } 257 buildBatteryUsageStats1(boolean includeUserBatteryConsumer)258 private BatteryUsageStats.Builder buildBatteryUsageStats1(boolean includeUserBatteryConsumer) { 259 final MockClock clocks = new MockClock(); 260 final MockBatteryStatsImpl batteryStats = new MockBatteryStatsImpl(clocks); 261 262 final BatteryUsageStats.Builder builder = 263 new BatteryUsageStats.Builder(new String[]{"FOO"}, true, true, 0) 264 .setBatteryCapacity(4000) 265 .setDischargePercentage(20) 266 .setDischargedPowerRange(1000, 2000) 267 .setDischargeDurationMs(1234) 268 .setStatsStartTimestamp(1000) 269 .setStatsEndTimestamp(3000); 270 271 addUidBatteryConsumer(builder, batteryStats, APP_UID1, "foo", 272 1000, 2000, 273 300, BatteryConsumer.POWER_MODEL_POWER_PROFILE, 400, 274 BatteryConsumer.POWER_MODEL_POWER_PROFILE, 500, 600, 800, 275 1777, 7771, 1888, 8881, 1999, 9991, 123, 456); 276 277 addAggregateBatteryConsumer(builder, 278 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_ALL_APPS, 0, 279 10100, 10200, 10300, 10400, 280 1333, 3331, 1444, 4441, 1555, 5551, 123, 456); 281 282 addAggregateBatteryConsumer(builder, 283 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_DEVICE, 30000, 284 20100, 20200, 20300, 20400, 285 2333, 3332, 2444, 4442, 2555, 5552, 123, 456); 286 287 if (includeUserBatteryConsumer) { 288 builder.getOrCreateUserBatteryConsumerBuilder(USER_ID) 289 .setConsumedPower( 290 BatteryConsumer.POWER_COMPONENT_CPU, 10) 291 .setConsumedPowerForCustomComponent( 292 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID, 20) 293 .setUsageDurationMillis( 294 BatteryConsumer.POWER_COMPONENT_CPU, 30) 295 .setUsageDurationForCustomComponentMillis( 296 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID, 40); 297 } 298 return builder; 299 } 300 buildBatteryUsageStats2(String[] customPowerComponentNames, boolean includeProcessStateData)301 private BatteryUsageStats.Builder buildBatteryUsageStats2(String[] customPowerComponentNames, 302 boolean includeProcessStateData) { 303 final MockClock clocks = new MockClock(); 304 final MockBatteryStatsImpl batteryStats = new MockBatteryStatsImpl(clocks); 305 306 final BatteryUsageStats.Builder builder = 307 new BatteryUsageStats.Builder(customPowerComponentNames, true, 308 includeProcessStateData, 0); 309 builder.setDischargePercentage(30) 310 .setDischargedPowerRange(1234, 2345) 311 .setStatsStartTimestamp(2000) 312 .setStatsEndTimestamp(5000); 313 314 addUidBatteryConsumer(builder, batteryStats, APP_UID1, null, 315 4321, 5432, 316 123, BatteryConsumer.POWER_MODEL_POWER_PROFILE, 345, POWER_MODEL_ENERGY_CONSUMPTION, 317 456, 567, 678, 318 1777, 7771, 1888, 8881, 1999, 9991, 321, 654); 319 320 addUidBatteryConsumer(builder, batteryStats, APP_UID2, "bar", 321 1111, 2222, 322 333, BatteryConsumer.POWER_MODEL_POWER_PROFILE, 444, 323 BatteryConsumer.POWER_MODEL_POWER_PROFILE, 555, 666, 777, 324 1777, 7771, 1888, 8881, 1999, 9991, 321, 654); 325 326 addAggregateBatteryConsumer(builder, 327 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_ALL_APPS, 0, 328 10123, 10234, 10345, 10456, 329 4333, 3334, 5444, 4445, 6555, 5556, 321, 654); 330 331 addAggregateBatteryConsumer(builder, 332 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_DEVICE, 12345, 333 20111, 20222, 20333, 20444, 334 7333, 3337, 8444, 4448, 9555, 5559, 123, 456); 335 336 return builder; 337 } 338 addUidBatteryConsumer(BatteryUsageStats.Builder builder, MockBatteryStatsImpl batteryStats, int uid, String packageWithHighestDrain, int timeInStateForeground, int timeInStateBackground, double screenPower, int screenPowerModel, double cpuPower, int cpuPowerModel, double customComponentPower, int cpuDuration, int customComponentDuration, double cpuPowerForeground, int cpuDurationForeground, double cpuPowerBackground, int cpuDurationBackground, double cpuPowerFgs, int cpuDurationFgs, double cpuPowerCached, long cpuDurationCached)339 private void addUidBatteryConsumer(BatteryUsageStats.Builder builder, 340 MockBatteryStatsImpl batteryStats, int uid, String packageWithHighestDrain, 341 int timeInStateForeground, int timeInStateBackground, double screenPower, 342 int screenPowerModel, double cpuPower, int cpuPowerModel, double customComponentPower, 343 int cpuDuration, int customComponentDuration, double cpuPowerForeground, 344 int cpuDurationForeground, double cpuPowerBackground, int cpuDurationBackground, 345 double cpuPowerFgs, int cpuDurationFgs, double cpuPowerCached, long cpuDurationCached) { 346 final BatteryStatsImpl.Uid batteryStatsUid = batteryStats.getUidStatsLocked(uid); 347 final UidBatteryConsumer.Builder uidBuilder = 348 builder.getOrCreateUidBatteryConsumerBuilder(batteryStatsUid); 349 uidBuilder 350 .setPackageWithHighestDrain(packageWithHighestDrain) 351 .setTimeInStateMs(UidBatteryConsumer.STATE_FOREGROUND, timeInStateForeground) 352 .setTimeInStateMs(UidBatteryConsumer.STATE_BACKGROUND, timeInStateBackground) 353 .setConsumedPower( 354 BatteryConsumer.POWER_COMPONENT_SCREEN, screenPower, screenPowerModel) 355 .setConsumedPower( 356 BatteryConsumer.POWER_COMPONENT_CPU, cpuPower, cpuPowerModel) 357 .setConsumedPowerForCustomComponent( 358 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID, customComponentPower) 359 .setUsageDurationMillis( 360 BatteryConsumer.POWER_COMPONENT_CPU, cpuDuration) 361 .setUsageDurationForCustomComponentMillis( 362 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID, customComponentDuration); 363 if (builder.isProcessStateDataNeeded()) { 364 final BatteryConsumer.Key cpuFgKey = uidBuilder.getKey( 365 BatteryConsumer.POWER_COMPONENT_CPU, 366 BatteryConsumer.PROCESS_STATE_FOREGROUND); 367 final BatteryConsumer.Key cpuBgKey = uidBuilder.getKey( 368 BatteryConsumer.POWER_COMPONENT_CPU, 369 BatteryConsumer.PROCESS_STATE_BACKGROUND); 370 final BatteryConsumer.Key cpuFgsKey = uidBuilder.getKey( 371 BatteryConsumer.POWER_COMPONENT_CPU, 372 BatteryConsumer.PROCESS_STATE_FOREGROUND_SERVICE); 373 final BatteryConsumer.Key cachedKey = uidBuilder.getKey( 374 BatteryConsumer.POWER_COMPONENT_CPU, 375 BatteryConsumer.PROCESS_STATE_CACHED); 376 uidBuilder 377 .setConsumedPower(cpuFgKey, cpuPowerForeground, 378 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 379 .setUsageDurationMillis(cpuFgKey, cpuDurationForeground) 380 .setConsumedPower(cpuBgKey, cpuPowerBackground, 381 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 382 .setUsageDurationMillis(cpuBgKey, cpuDurationBackground) 383 .setConsumedPower(cpuFgsKey, cpuPowerFgs, 384 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 385 .setUsageDurationMillis(cpuFgsKey, cpuDurationFgs) 386 .setConsumedPower(cachedKey, cpuPowerCached, 387 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 388 .setUsageDurationMillis(cachedKey, cpuDurationCached); 389 } 390 } 391 addAggregateBatteryConsumer(BatteryUsageStats.Builder builder, int scope, double consumedPower, int cpuPower, int customComponentPower, int cpuDuration, int customComponentDuration, double cpuPowerForeground, long cpuDurationForeground, double cpuPowerBackground, long cpuDurationBackground, double cpuPowerFgs, long cpuDurationFgs, double cpuPowerCached, long cpuDurationCached)392 private void addAggregateBatteryConsumer(BatteryUsageStats.Builder builder, int scope, 393 double consumedPower, int cpuPower, int customComponentPower, int cpuDuration, 394 int customComponentDuration, double cpuPowerForeground, long cpuDurationForeground, 395 double cpuPowerBackground, long cpuDurationBackground, double cpuPowerFgs, 396 long cpuDurationFgs, double cpuPowerCached, long cpuDurationCached) { 397 final AggregateBatteryConsumer.Builder aggBuilder = 398 builder.getAggregateBatteryConsumerBuilder(scope) 399 .setConsumedPower(consumedPower) 400 .setConsumedPower( 401 BatteryConsumer.POWER_COMPONENT_CPU, cpuPower) 402 .setConsumedPowerForCustomComponent( 403 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID, 404 customComponentPower) 405 .setUsageDurationMillis( 406 BatteryConsumer.POWER_COMPONENT_CPU, cpuDuration) 407 .setUsageDurationForCustomComponentMillis( 408 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID, 409 customComponentDuration); 410 if (builder.isProcessStateDataNeeded()) { 411 final BatteryConsumer.Key cpuFgKey = aggBuilder.getKey( 412 BatteryConsumer.POWER_COMPONENT_CPU, 413 BatteryConsumer.PROCESS_STATE_FOREGROUND); 414 final BatteryConsumer.Key cpuBgKey = aggBuilder.getKey( 415 BatteryConsumer.POWER_COMPONENT_CPU, 416 BatteryConsumer.PROCESS_STATE_BACKGROUND); 417 final BatteryConsumer.Key cpuFgsKey = aggBuilder.getKey( 418 BatteryConsumer.POWER_COMPONENT_CPU, 419 BatteryConsumer.PROCESS_STATE_FOREGROUND_SERVICE); 420 final BatteryConsumer.Key cpuCachedKey = aggBuilder.getKey( 421 BatteryConsumer.POWER_COMPONENT_CPU, 422 BatteryConsumer.PROCESS_STATE_CACHED); 423 aggBuilder 424 .setConsumedPower(cpuFgKey, cpuPowerForeground, 425 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 426 .setUsageDurationMillis(cpuFgKey, cpuDurationForeground) 427 .setConsumedPower(cpuBgKey, cpuPowerBackground, 428 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 429 .setUsageDurationMillis(cpuBgKey, cpuDurationBackground) 430 .setConsumedPower(cpuFgsKey, cpuPowerFgs, 431 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 432 .setUsageDurationMillis(cpuFgsKey, cpuDurationFgs) 433 .setConsumedPower(cpuCachedKey, cpuPowerCached, 434 BatteryConsumer.POWER_MODEL_POWER_PROFILE) 435 .setUsageDurationMillis(cpuCachedKey, cpuDurationCached); 436 } 437 } 438 assertBatteryUsageStats1(BatteryUsageStats batteryUsageStats, boolean includesUserBatteryConsumers)439 public void assertBatteryUsageStats1(BatteryUsageStats batteryUsageStats, 440 boolean includesUserBatteryConsumers) { 441 assertBatteryUsageStats(batteryUsageStats, 30000, 20, 1000, 2000, 1234, 1000, 3000, 2000); 442 443 final List<UidBatteryConsumer> uidBatteryConsumers = 444 batteryUsageStats.getUidBatteryConsumers(); 445 assertThat(uidBatteryConsumers).hasSize(1); 446 for (UidBatteryConsumer uidBatteryConsumer : uidBatteryConsumers) { 447 if (uidBatteryConsumer.getUid() == APP_UID1) { 448 assertUidBatteryConsumer(uidBatteryConsumer, 1200, "foo", 449 1000, 2000, 300, BatteryConsumer.POWER_MODEL_POWER_PROFILE, 400, 450 BatteryConsumer.POWER_MODEL_POWER_PROFILE, 451 500, 600, 800, 452 true, 1777, 1888, 1999, 123, 1777, 7771, 1888, 8881, 1999, 9991, 123, 456); 453 } else { 454 fail("Unexpected UID " + uidBatteryConsumer.getUid()); 455 } 456 } 457 458 final List<UserBatteryConsumer> userBatteryConsumers = 459 batteryUsageStats.getUserBatteryConsumers(); 460 if (includesUserBatteryConsumers) { 461 assertThat(userBatteryConsumers).hasSize(1); 462 for (UserBatteryConsumer userBatteryConsumer : userBatteryConsumers) { 463 if (userBatteryConsumer.getUserId() == USER_ID) { 464 assertUserBatteryConsumer(userBatteryConsumer, 42, 10, 20, 30, 40); 465 } else { 466 fail("Unexpected User ID " + userBatteryConsumer.getUserId()); 467 } 468 } 469 } else { 470 assertThat(userBatteryConsumers).isEmpty(); 471 } 472 473 assertAggregateBatteryConsumer(batteryUsageStats, 474 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_ALL_APPS, 475 10100, 10200, 10300, 10400); 476 477 assertAggregateBatteryConsumer(batteryUsageStats, 478 BatteryUsageStats.AGGREGATE_BATTERY_CONSUMER_SCOPE_DEVICE, 479 20100, 20200, 20300, 20400); 480 } 481 assertBatteryUsageStats(BatteryUsageStats batteryUsageStats, int consumedPower, int dischargePercentage, int dischagePowerLower, int dischargePowerUpper, int dischargeDuration, int statsStartTimestamp, int statsEndTimestamp, int statsDuration)482 private void assertBatteryUsageStats(BatteryUsageStats batteryUsageStats, int consumedPower, 483 int dischargePercentage, int dischagePowerLower, int dischargePowerUpper, 484 int dischargeDuration, int statsStartTimestamp, int statsEndTimestamp, 485 int statsDuration) { 486 assertThat(batteryUsageStats.getConsumedPower()).isEqualTo(consumedPower); 487 assertThat(batteryUsageStats.getDischargePercentage()).isEqualTo(dischargePercentage); 488 assertThat(batteryUsageStats.getDischargedPowerRange().getLower()).isEqualTo( 489 dischagePowerLower); 490 assertThat(batteryUsageStats.getDischargedPowerRange().getUpper()).isEqualTo( 491 dischargePowerUpper); 492 assertThat(batteryUsageStats.getDischargeDurationMs()).isEqualTo(dischargeDuration); 493 assertThat(batteryUsageStats.getStatsStartTimestamp()).isEqualTo(statsStartTimestamp); 494 assertThat(batteryUsageStats.getStatsEndTimestamp()).isEqualTo(statsEndTimestamp); 495 assertThat(batteryUsageStats.getStatsDuration()).isEqualTo(statsDuration); 496 } 497 assertUidBatteryConsumer(UidBatteryConsumer uidBatteryConsumer, double consumedPower, String packageWithHighestDrain, int timeInStateForeground, int timeInStateBackground, int screenPower, int screenPowerModel, double cpuPower, int cpuPowerModel, double customComponentPower, int cpuDuration, int customComponentDuration, boolean processStateDataIncluded, double totalPowerForeground, double totalPowerBackground, double totalPowerFgs, double totalPowerCached, double cpuPowerForeground, int cpuDurationForeground, double cpuPowerBackground, int cpuDurationBackground, double cpuPowerFgs, int cpuDurationFgs, int cpuPowerCached, int cpuDurationCached)498 private void assertUidBatteryConsumer(UidBatteryConsumer uidBatteryConsumer, 499 double consumedPower, String packageWithHighestDrain, int timeInStateForeground, 500 int timeInStateBackground, int screenPower, int screenPowerModel, double cpuPower, 501 int cpuPowerModel, double customComponentPower, int cpuDuration, 502 int customComponentDuration, boolean processStateDataIncluded, 503 double totalPowerForeground, double totalPowerBackground, double totalPowerFgs, 504 double totalPowerCached, double cpuPowerForeground, int cpuDurationForeground, 505 double cpuPowerBackground, 506 int cpuDurationBackground, double cpuPowerFgs, int cpuDurationFgs, 507 int cpuPowerCached, int cpuDurationCached) { 508 assertThat(uidBatteryConsumer.getConsumedPower()).isEqualTo(consumedPower); 509 assertThat(uidBatteryConsumer.getPackageWithHighestDrain()).isEqualTo( 510 packageWithHighestDrain); 511 assertThat(uidBatteryConsumer.getTimeInStateMs( 512 UidBatteryConsumer.STATE_FOREGROUND)).isEqualTo(timeInStateForeground); 513 assertThat(uidBatteryConsumer.getTimeInStateMs( 514 UidBatteryConsumer.STATE_BACKGROUND)).isEqualTo(timeInStateBackground); 515 assertThat(uidBatteryConsumer.getConsumedPower( 516 BatteryConsumer.POWER_COMPONENT_SCREEN)).isEqualTo(screenPower); 517 assertThat(uidBatteryConsumer.getPowerModel( 518 BatteryConsumer.POWER_COMPONENT_SCREEN)).isEqualTo(screenPowerModel); 519 assertThat(uidBatteryConsumer.getConsumedPower( 520 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuPower); 521 assertThat(uidBatteryConsumer.getPowerModel( 522 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuPowerModel); 523 assertThat(uidBatteryConsumer.getConsumedPowerForCustomComponent( 524 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo(customComponentPower); 525 assertThat(uidBatteryConsumer.getUsageDurationMillis( 526 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuDuration); 527 assertThat(uidBatteryConsumer.getUsageDurationForCustomComponentMillis( 528 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo( 529 customComponentDuration); 530 assertThat(uidBatteryConsumer.getCustomPowerComponentCount()).isEqualTo(1); 531 assertThat(uidBatteryConsumer.getCustomPowerComponentName( 532 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo("FOO"); 533 534 if (processStateDataIncluded) { 535 assertThat(uidBatteryConsumer.getConsumedPower( 536 new BatteryConsumer.Dimensions(POWER_COMPONENT_ANY, 537 PROCESS_STATE_FOREGROUND))) 538 .isEqualTo(totalPowerForeground); 539 assertThat(uidBatteryConsumer.getConsumedPower( 540 new BatteryConsumer.Dimensions(POWER_COMPONENT_ANY, 541 PROCESS_STATE_BACKGROUND))) 542 .isEqualTo(totalPowerBackground); 543 assertThat(uidBatteryConsumer.getConsumedPower( 544 new BatteryConsumer.Dimensions(POWER_COMPONENT_ANY, 545 PROCESS_STATE_FOREGROUND_SERVICE))) 546 .isEqualTo(totalPowerFgs); 547 assertThat(uidBatteryConsumer.getConsumedPower( 548 new BatteryConsumer.Dimensions(POWER_COMPONENT_ANY, 549 PROCESS_STATE_CACHED))) 550 .isEqualTo(totalPowerCached); 551 } 552 553 final BatteryConsumer.Key cpuFgKey = uidBatteryConsumer.getKey( 554 BatteryConsumer.POWER_COMPONENT_CPU, BatteryConsumer.PROCESS_STATE_FOREGROUND); 555 if (processStateDataIncluded) { 556 assertThat(cpuFgKey).isNotNull(); 557 assertThat(uidBatteryConsumer.getConsumedPower(cpuFgKey)) 558 .isEqualTo(cpuPowerForeground); 559 assertThat(uidBatteryConsumer.getUsageDurationMillis(cpuFgKey)) 560 .isEqualTo(cpuDurationForeground); 561 } else { 562 assertThat(cpuFgKey).isNull(); 563 } 564 565 final BatteryConsumer.Key cpuBgKey = uidBatteryConsumer.getKey( 566 BatteryConsumer.POWER_COMPONENT_CPU, BatteryConsumer.PROCESS_STATE_BACKGROUND); 567 if (processStateDataIncluded) { 568 assertThat(cpuBgKey).isNotNull(); 569 assertThat(uidBatteryConsumer.getConsumedPower(cpuBgKey)) 570 .isEqualTo(cpuPowerBackground); 571 assertThat(uidBatteryConsumer.getUsageDurationMillis(cpuBgKey)) 572 .isEqualTo(cpuDurationBackground); 573 } else { 574 assertThat(cpuBgKey).isNull(); 575 } 576 577 final BatteryConsumer.Key cpuFgsKey = uidBatteryConsumer.getKey( 578 BatteryConsumer.POWER_COMPONENT_CPU, 579 BatteryConsumer.PROCESS_STATE_FOREGROUND_SERVICE); 580 if (processStateDataIncluded) { 581 assertThat(cpuFgsKey).isNotNull(); 582 assertThat(uidBatteryConsumer.getConsumedPower(cpuFgsKey)) 583 .isEqualTo(cpuPowerFgs); 584 assertThat(uidBatteryConsumer.getUsageDurationMillis(cpuFgsKey)) 585 .isEqualTo(cpuDurationFgs); 586 } else { 587 assertThat(cpuFgsKey).isNotNull(); 588 } 589 590 final BatteryConsumer.Key cachedKey = uidBatteryConsumer.getKey( 591 BatteryConsumer.POWER_COMPONENT_CPU, 592 BatteryConsumer.PROCESS_STATE_CACHED); 593 if (processStateDataIncluded) { 594 assertThat(cachedKey).isNotNull(); 595 assertThat(uidBatteryConsumer.getConsumedPower(cachedKey)) 596 .isEqualTo(cpuPowerCached); 597 assertThat(uidBatteryConsumer.getUsageDurationMillis(cachedKey)) 598 .isEqualTo(cpuDurationCached); 599 } else { 600 assertThat(cpuFgsKey).isNotNull(); 601 } 602 } 603 assertUserBatteryConsumer(UserBatteryConsumer userBatteryConsumer, int userId, int cpuPower, int customComponentPower, int cpuDuration, int customComponentDuration)604 private void assertUserBatteryConsumer(UserBatteryConsumer userBatteryConsumer, 605 int userId, int cpuPower, int customComponentPower, 606 int cpuDuration, int customComponentDuration) { 607 assertThat(userBatteryConsumer.getConsumedPower( 608 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuPower); 609 assertThat(userBatteryConsumer.getConsumedPowerForCustomComponent( 610 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo(customComponentPower); 611 assertThat(userBatteryConsumer.getUsageDurationMillis( 612 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuDuration); 613 assertThat(userBatteryConsumer.getUsageDurationForCustomComponentMillis( 614 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo( 615 customComponentDuration); 616 assertThat(userBatteryConsumer.getCustomPowerComponentCount()).isEqualTo(1); 617 assertThat(userBatteryConsumer.getCustomPowerComponentName( 618 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo("FOO"); 619 } 620 assertAggregateBatteryConsumer(BatteryUsageStats batteryUsageStats, int aggregateBatteryConsumerScopeAllApps, int cpuPower, int customComponentPower, int cpuDuration, int customComponentDuration)621 private void assertAggregateBatteryConsumer(BatteryUsageStats batteryUsageStats, 622 int aggregateBatteryConsumerScopeAllApps, int cpuPower, int customComponentPower, 623 int cpuDuration, int customComponentDuration) { 624 final BatteryConsumer appsBatteryConsumer = batteryUsageStats.getAggregateBatteryConsumer( 625 aggregateBatteryConsumerScopeAllApps); 626 assertThat(appsBatteryConsumer.getConsumedPower( 627 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuPower); 628 assertThat(appsBatteryConsumer.getConsumedPowerForCustomComponent( 629 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo(customComponentPower); 630 assertThat(appsBatteryConsumer.getUsageDurationMillis( 631 BatteryConsumer.POWER_COMPONENT_CPU)).isEqualTo(cpuDuration); 632 assertThat(appsBatteryConsumer.getUsageDurationForCustomComponentMillis( 633 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo( 634 customComponentDuration); 635 assertThat(appsBatteryConsumer.getCustomPowerComponentCount()).isEqualTo(1); 636 assertThat(appsBatteryConsumer.getCustomPowerComponentName( 637 BatteryConsumer.FIRST_CUSTOM_POWER_COMPONENT_ID)).isEqualTo("FOO"); 638 } 639 } 640