BatteryStats.java revision 0c820db22c83808fdb06c7cb06aaf13ef4b559a3
1/* 2 * Copyright (C) 2008 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 17package android.os; 18 19import java.io.PrintWriter; 20import java.util.ArrayList; 21import java.util.Collections; 22import java.util.Comparator; 23import java.util.Formatter; 24import java.util.HashMap; 25import java.util.List; 26import java.util.Map; 27 28import android.content.Context; 29import android.content.pm.ApplicationInfo; 30import android.telephony.SignalStrength; 31import android.text.format.DateFormat; 32import android.util.ArrayMap; 33import android.util.Printer; 34import android.util.SparseArray; 35import android.util.SparseIntArray; 36import android.util.TimeUtils; 37import android.view.Display; 38import com.android.internal.os.BatterySipper; 39import com.android.internal.os.BatteryStatsHelper; 40 41/** 42 * A class providing access to battery usage statistics, including information on 43 * wakelocks, processes, packages, and services. All times are represented in microseconds 44 * except where indicated otherwise. 45 * @hide 46 */ 47public abstract class BatteryStats implements Parcelable { 48 49 private static final boolean LOCAL_LOGV = false; 50 51 /** @hide */ 52 public static final String SERVICE_NAME = "batterystats"; 53 54 /** 55 * A constant indicating a partial wake lock timer. 56 */ 57 public static final int WAKE_TYPE_PARTIAL = 0; 58 59 /** 60 * A constant indicating a full wake lock timer. 61 */ 62 public static final int WAKE_TYPE_FULL = 1; 63 64 /** 65 * A constant indicating a window wake lock timer. 66 */ 67 public static final int WAKE_TYPE_WINDOW = 2; 68 69 /** 70 * A constant indicating a sensor timer. 71 */ 72 public static final int SENSOR = 3; 73 74 /** 75 * A constant indicating a a wifi running timer 76 */ 77 public static final int WIFI_RUNNING = 4; 78 79 /** 80 * A constant indicating a full wifi lock timer 81 */ 82 public static final int FULL_WIFI_LOCK = 5; 83 84 /** 85 * A constant indicating a wifi scan 86 */ 87 public static final int WIFI_SCAN = 6; 88 89 /** 90 * A constant indicating a wifi multicast timer 91 */ 92 public static final int WIFI_MULTICAST_ENABLED = 7; 93 94 /** 95 * A constant indicating a video turn on timer 96 */ 97 public static final int VIDEO_TURNED_ON = 8; 98 99 /** 100 * A constant indicating a vibrator on timer 101 */ 102 public static final int VIBRATOR_ON = 9; 103 104 /** 105 * A constant indicating a foreground activity timer 106 */ 107 public static final int FOREGROUND_ACTIVITY = 10; 108 109 /** 110 * A constant indicating a wifi batched scan is active 111 */ 112 public static final int WIFI_BATCHED_SCAN = 11; 113 114 /** 115 * A constant indicating a process state timer 116 */ 117 public static final int PROCESS_STATE = 12; 118 119 /** 120 * A constant indicating a sync timer 121 */ 122 public static final int SYNC = 13; 123 124 /** 125 * A constant indicating a job timer 126 */ 127 public static final int JOB = 14; 128 129 /** 130 * A constant indicating an audio turn on timer 131 */ 132 public static final int AUDIO_TURNED_ON = 15; 133 134 /** 135 * Include all of the data in the stats, including previously saved data. 136 */ 137 public static final int STATS_SINCE_CHARGED = 0; 138 139 /** 140 * Include only the current run in the stats. 141 */ 142 public static final int STATS_CURRENT = 1; 143 144 /** 145 * Include only the run since the last time the device was unplugged in the stats. 146 */ 147 public static final int STATS_SINCE_UNPLUGGED = 2; 148 149 // NOTE: Update this list if you add/change any stats above. 150 // These characters are supposed to represent "total", "last", "current", 151 // and "unplugged". They were shortened for efficiency sake. 152 private static final String[] STAT_NAMES = { "l", "c", "u" }; 153 154 /** 155 * Current version of checkin data format. 156 */ 157 static final String CHECKIN_VERSION = "14"; 158 159 /** 160 * Old version, we hit 9 and ran out of room, need to remove. 161 */ 162 private static final int BATTERY_STATS_CHECKIN_VERSION = 9; 163 164 private static final long BYTES_PER_KB = 1024; 165 private static final long BYTES_PER_MB = 1048576; // 1024^2 166 private static final long BYTES_PER_GB = 1073741824; //1024^3 167 168 private static final String VERSION_DATA = "vers"; 169 private static final String UID_DATA = "uid"; 170 private static final String APK_DATA = "apk"; 171 private static final String PROCESS_DATA = "pr"; 172 private static final String SENSOR_DATA = "sr"; 173 private static final String VIBRATOR_DATA = "vib"; 174 private static final String FOREGROUND_DATA = "fg"; 175 private static final String STATE_TIME_DATA = "st"; 176 private static final String WAKELOCK_DATA = "wl"; 177 private static final String SYNC_DATA = "sy"; 178 private static final String JOB_DATA = "jb"; 179 private static final String KERNEL_WAKELOCK_DATA = "kwl"; 180 private static final String WAKEUP_REASON_DATA = "wr"; 181 private static final String NETWORK_DATA = "nt"; 182 private static final String USER_ACTIVITY_DATA = "ua"; 183 private static final String BATTERY_DATA = "bt"; 184 private static final String BATTERY_DISCHARGE_DATA = "dc"; 185 private static final String BATTERY_LEVEL_DATA = "lv"; 186 private static final String WIFI_DATA = "wfl"; 187 private static final String MISC_DATA = "m"; 188 private static final String GLOBAL_NETWORK_DATA = "gn"; 189 private static final String HISTORY_STRING_POOL = "hsp"; 190 private static final String HISTORY_DATA = "h"; 191 private static final String SCREEN_BRIGHTNESS_DATA = "br"; 192 private static final String SIGNAL_STRENGTH_TIME_DATA = "sgt"; 193 private static final String SIGNAL_SCANNING_TIME_DATA = "sst"; 194 private static final String SIGNAL_STRENGTH_COUNT_DATA = "sgc"; 195 private static final String DATA_CONNECTION_TIME_DATA = "dct"; 196 private static final String DATA_CONNECTION_COUNT_DATA = "dcc"; 197 private static final String WIFI_STATE_TIME_DATA = "wst"; 198 private static final String WIFI_STATE_COUNT_DATA = "wsc"; 199 private static final String WIFI_SUPPL_STATE_TIME_DATA = "wsst"; 200 private static final String WIFI_SUPPL_STATE_COUNT_DATA = "wssc"; 201 private static final String WIFI_SIGNAL_STRENGTH_TIME_DATA = "wsgt"; 202 private static final String WIFI_SIGNAL_STRENGTH_COUNT_DATA = "wsgc"; 203 private static final String BLUETOOTH_STATE_TIME_DATA = "bst"; 204 private static final String BLUETOOTH_STATE_COUNT_DATA = "bsc"; 205 private static final String POWER_USE_SUMMARY_DATA = "pws"; 206 private static final String POWER_USE_ITEM_DATA = "pwi"; 207 private static final String DISCHARGE_STEP_DATA = "dsd"; 208 private static final String CHARGE_STEP_DATA = "csd"; 209 private static final String DISCHARGE_TIME_REMAIN_DATA = "dtr"; 210 private static final String CHARGE_TIME_REMAIN_DATA = "ctr"; 211 212 private final StringBuilder mFormatBuilder = new StringBuilder(32); 213 private final Formatter mFormatter = new Formatter(mFormatBuilder); 214 215 /** 216 * State for keeping track of counting information. 217 */ 218 public static abstract class Counter { 219 220 /** 221 * Returns the count associated with this Counter for the 222 * selected type of statistics. 223 * 224 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT 225 */ 226 public abstract int getCountLocked(int which); 227 228 /** 229 * Temporary for debugging. 230 */ 231 public abstract void logState(Printer pw, String prefix); 232 } 233 234 /** 235 * State for keeping track of long counting information. 236 */ 237 public static abstract class LongCounter { 238 239 /** 240 * Returns the count associated with this Counter for the 241 * selected type of statistics. 242 * 243 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT 244 */ 245 public abstract long getCountLocked(int which); 246 247 /** 248 * Temporary for debugging. 249 */ 250 public abstract void logState(Printer pw, String prefix); 251 } 252 253 /** 254 * State for keeping track of timing information. 255 */ 256 public static abstract class Timer { 257 258 /** 259 * Returns the count associated with this Timer for the 260 * selected type of statistics. 261 * 262 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT 263 */ 264 public abstract int getCountLocked(int which); 265 266 /** 267 * Returns the total time in microseconds associated with this Timer for the 268 * selected type of statistics. 269 * 270 * @param elapsedRealtimeUs current elapsed realtime of system in microseconds 271 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT 272 * @return a time in microseconds 273 */ 274 public abstract long getTotalTimeLocked(long elapsedRealtimeUs, int which); 275 276 /** 277 * Returns the total time in microseconds associated with this Timer since the 278 * 'mark' was last set. 279 * 280 * @param elapsedRealtimeUs current elapsed realtime of system in microseconds 281 * @return a time in microseconds 282 */ 283 public abstract long getTimeSinceMarkLocked(long elapsedRealtimeUs); 284 285 /** 286 * Temporary for debugging. 287 */ 288 public abstract void logState(Printer pw, String prefix); 289 } 290 291 /** 292 * The statistics associated with a particular uid. 293 */ 294 public static abstract class Uid { 295 296 /** 297 * Returns a mapping containing wakelock statistics. 298 * 299 * @return a Map from Strings to Uid.Wakelock objects. 300 */ 301 public abstract ArrayMap<String, ? extends Wakelock> getWakelockStats(); 302 303 /** 304 * Returns a mapping containing sync statistics. 305 * 306 * @return a Map from Strings to Timer objects. 307 */ 308 public abstract ArrayMap<String, ? extends Timer> getSyncStats(); 309 310 /** 311 * Returns a mapping containing scheduled job statistics. 312 * 313 * @return a Map from Strings to Timer objects. 314 */ 315 public abstract ArrayMap<String, ? extends Timer> getJobStats(); 316 317 /** 318 * The statistics associated with a particular wake lock. 319 */ 320 public static abstract class Wakelock { 321 public abstract Timer getWakeTime(int type); 322 } 323 324 /** 325 * Returns a mapping containing sensor statistics. 326 * 327 * @return a Map from Integer sensor ids to Uid.Sensor objects. 328 */ 329 public abstract SparseArray<? extends Sensor> getSensorStats(); 330 331 /** 332 * Returns a mapping containing active process data. 333 */ 334 public abstract SparseArray<? extends Pid> getPidStats(); 335 336 /** 337 * Returns a mapping containing process statistics. 338 * 339 * @return a Map from Strings to Uid.Proc objects. 340 */ 341 public abstract ArrayMap<String, ? extends Proc> getProcessStats(); 342 343 /** 344 * Returns a mapping containing package statistics. 345 * 346 * @return a Map from Strings to Uid.Pkg objects. 347 */ 348 public abstract ArrayMap<String, ? extends Pkg> getPackageStats(); 349 350 /** 351 * Returns the time in milliseconds that this app kept the WiFi controller in the 352 * specified state <code>type</code>. 353 * @param type one of {@link #CONTROLLER_IDLE_TIME}, {@link #CONTROLLER_RX_TIME}, or 354 * {@link #CONTROLLER_TX_TIME}. 355 * @param which one of {@link #STATS_CURRENT}, {@link #STATS_SINCE_CHARGED}, or 356 * {@link #STATS_SINCE_UNPLUGGED}. 357 */ 358 public abstract long getWifiControllerActivity(int type, int which); 359 360 /** 361 * {@hide} 362 */ 363 public abstract int getUid(); 364 365 public abstract void noteWifiRunningLocked(long elapsedRealtime); 366 public abstract void noteWifiStoppedLocked(long elapsedRealtime); 367 public abstract void noteFullWifiLockAcquiredLocked(long elapsedRealtime); 368 public abstract void noteFullWifiLockReleasedLocked(long elapsedRealtime); 369 public abstract void noteWifiScanStartedLocked(long elapsedRealtime); 370 public abstract void noteWifiScanStoppedLocked(long elapsedRealtime); 371 public abstract void noteWifiBatchedScanStartedLocked(int csph, long elapsedRealtime); 372 public abstract void noteWifiBatchedScanStoppedLocked(long elapsedRealtime); 373 public abstract void noteWifiMulticastEnabledLocked(long elapsedRealtime); 374 public abstract void noteWifiMulticastDisabledLocked(long elapsedRealtime); 375 public abstract void noteActivityResumedLocked(long elapsedRealtime); 376 public abstract void noteActivityPausedLocked(long elapsedRealtime); 377 public abstract long getWifiRunningTime(long elapsedRealtimeUs, int which); 378 public abstract long getFullWifiLockTime(long elapsedRealtimeUs, int which); 379 public abstract long getWifiScanTime(long elapsedRealtimeUs, int which); 380 public abstract int getWifiScanCount(int which); 381 public abstract long getWifiBatchedScanTime(int csphBin, long elapsedRealtimeUs, int which); 382 public abstract int getWifiBatchedScanCount(int csphBin, int which); 383 public abstract long getWifiMulticastTime(long elapsedRealtimeUs, int which); 384 public abstract long getAudioTurnedOnTime(long elapsedRealtimeUs, int which); 385 public abstract long getVideoTurnedOnTime(long elapsedRealtimeUs, int which); 386 public abstract Timer getForegroundActivityTimer(); 387 388 // Time this uid has any processes in foreground state. 389 public static final int PROCESS_STATE_FOREGROUND = 0; 390 // Time this uid has any process in active state (not cached). 391 public static final int PROCESS_STATE_ACTIVE = 1; 392 // Time this uid has any processes running at all. 393 public static final int PROCESS_STATE_RUNNING = 2; 394 // Total number of process states we track. 395 public static final int NUM_PROCESS_STATE = 3; 396 397 static final String[] PROCESS_STATE_NAMES = { 398 "Foreground", "Active", "Running" 399 }; 400 401 public abstract long getProcessStateTime(int state, long elapsedRealtimeUs, int which); 402 403 public abstract Timer getVibratorOnTimer(); 404 405 public static final int NUM_WIFI_BATCHED_SCAN_BINS = 5; 406 407 /** 408 * Note that these must match the constants in android.os.PowerManager. 409 * Also, if the user activity types change, the BatteryStatsImpl.VERSION must 410 * also be bumped. 411 */ 412 static final String[] USER_ACTIVITY_TYPES = { 413 "other", "button", "touch" 414 }; 415 416 public static final int NUM_USER_ACTIVITY_TYPES = 3; 417 418 public abstract void noteUserActivityLocked(int type); 419 public abstract boolean hasUserActivity(); 420 public abstract int getUserActivityCount(int type, int which); 421 422 public abstract boolean hasNetworkActivity(); 423 public abstract long getNetworkActivityBytes(int type, int which); 424 public abstract long getNetworkActivityPackets(int type, int which); 425 public abstract long getMobileRadioActiveTime(int which); 426 public abstract int getMobileRadioActiveCount(int which); 427 428 public static abstract class Sensor { 429 /* 430 * FIXME: it's not correct to use this magic value because it 431 * could clash with a sensor handle (which are defined by 432 * the sensor HAL, and therefore out of our control 433 */ 434 // Magic sensor number for the GPS. 435 public static final int GPS = -10000; 436 437 public abstract int getHandle(); 438 439 public abstract Timer getSensorTime(); 440 } 441 442 public class Pid { 443 public int mWakeNesting; 444 public long mWakeSumMs; 445 public long mWakeStartMs; 446 } 447 448 /** 449 * The statistics associated with a particular process. 450 */ 451 public static abstract class Proc { 452 453 public static class ExcessivePower { 454 public static final int TYPE_WAKE = 1; 455 public static final int TYPE_CPU = 2; 456 457 public int type; 458 public long overTime; 459 public long usedTime; 460 } 461 462 /** 463 * Returns true if this process is still active in the battery stats. 464 */ 465 public abstract boolean isActive(); 466 467 /** 468 * Returns the total time (in milliseconds) spent executing in user code. 469 * 470 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 471 */ 472 public abstract long getUserTime(int which); 473 474 /** 475 * Returns the total time (in milliseconds) spent executing in system code. 476 * 477 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 478 */ 479 public abstract long getSystemTime(int which); 480 481 /** 482 * Returns the number of times the process has been started. 483 * 484 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 485 */ 486 public abstract int getStarts(int which); 487 488 /** 489 * Returns the number of times the process has crashed. 490 * 491 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 492 */ 493 public abstract int getNumCrashes(int which); 494 495 /** 496 * Returns the number of times the process has ANRed. 497 * 498 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 499 */ 500 public abstract int getNumAnrs(int which); 501 502 /** 503 * Returns the cpu time (milliseconds) spent while the process was in the foreground. 504 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 505 * @return foreground cpu time in microseconds 506 */ 507 public abstract long getForegroundTime(int which); 508 509 /** 510 * Returns the approximate cpu time (in milliseconds) spent at a certain CPU speed. 511 * @param speedStep the index of the CPU speed. This is not the actual speed of the 512 * CPU. 513 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 514 * @see BatteryStats#getCpuSpeedSteps() 515 */ 516 public abstract long getTimeAtCpuSpeedStep(int speedStep, int which); 517 518 public abstract int countExcessivePowers(); 519 520 public abstract ExcessivePower getExcessivePower(int i); 521 } 522 523 /** 524 * The statistics associated with a particular package. 525 */ 526 public static abstract class Pkg { 527 528 /** 529 * Returns information about all wakeup alarms that have been triggered for this 530 * package. The mapping keys are tag names for the alarms, the counter contains 531 * the number of times the alarm was triggered while on battery. 532 */ 533 public abstract ArrayMap<String, ? extends Counter> getWakeupAlarmStats(); 534 535 /** 536 * Returns a mapping containing service statistics. 537 */ 538 public abstract ArrayMap<String, ? extends Serv> getServiceStats(); 539 540 /** 541 * The statistics associated with a particular service. 542 */ 543 public abstract class Serv { 544 545 /** 546 * Returns the amount of time spent started. 547 * 548 * @param batteryUptime elapsed uptime on battery in microseconds. 549 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 550 * @return 551 */ 552 public abstract long getStartTime(long batteryUptime, int which); 553 554 /** 555 * Returns the total number of times startService() has been called. 556 * 557 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 558 */ 559 public abstract int getStarts(int which); 560 561 /** 562 * Returns the total number times the service has been launched. 563 * 564 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 565 */ 566 public abstract int getLaunches(int which); 567 } 568 } 569 } 570 571 public static final class LevelStepTracker { 572 public long mLastStepTime = -1; 573 public int mNumStepDurations; 574 public final long[] mStepDurations; 575 576 public LevelStepTracker(int maxLevelSteps) { 577 mStepDurations = new long[maxLevelSteps]; 578 } 579 580 public LevelStepTracker(int numSteps, long[] steps) { 581 mNumStepDurations = numSteps; 582 mStepDurations = new long[numSteps]; 583 System.arraycopy(steps, 0, mStepDurations, 0, numSteps); 584 } 585 586 public long getDurationAt(int index) { 587 return mStepDurations[index] & STEP_LEVEL_TIME_MASK; 588 } 589 590 public int getLevelAt(int index) { 591 return (int)((mStepDurations[index] & STEP_LEVEL_LEVEL_MASK) 592 >> STEP_LEVEL_LEVEL_SHIFT); 593 } 594 595 public int getInitModeAt(int index) { 596 return (int)((mStepDurations[index] & STEP_LEVEL_INITIAL_MODE_MASK) 597 >> STEP_LEVEL_INITIAL_MODE_SHIFT); 598 } 599 600 public int getModModeAt(int index) { 601 return (int)((mStepDurations[index] & STEP_LEVEL_MODIFIED_MODE_MASK) 602 >> STEP_LEVEL_MODIFIED_MODE_SHIFT); 603 } 604 605 private void appendHex(long val, int topOffset, StringBuilder out) { 606 boolean hasData = false; 607 while (topOffset >= 0) { 608 int digit = (int)( (val>>topOffset) & 0xf ); 609 topOffset -= 4; 610 if (!hasData && digit == 0) { 611 continue; 612 } 613 hasData = true; 614 if (digit >= 0 && digit <= 9) { 615 out.append((char)('0' + digit)); 616 } else { 617 out.append((char)('a' + digit - 10)); 618 } 619 } 620 } 621 622 public void encodeEntryAt(int index, StringBuilder out) { 623 long item = mStepDurations[index]; 624 long duration = item & STEP_LEVEL_TIME_MASK; 625 int level = (int)((item & STEP_LEVEL_LEVEL_MASK) 626 >> STEP_LEVEL_LEVEL_SHIFT); 627 int initMode = (int)((item & STEP_LEVEL_INITIAL_MODE_MASK) 628 >> STEP_LEVEL_INITIAL_MODE_SHIFT); 629 int modMode = (int)((item & STEP_LEVEL_MODIFIED_MODE_MASK) 630 >> STEP_LEVEL_MODIFIED_MODE_SHIFT); 631 switch ((initMode&STEP_LEVEL_MODE_SCREEN_STATE) + 1) { 632 case Display.STATE_OFF: out.append('f'); break; 633 case Display.STATE_ON: out.append('o'); break; 634 case Display.STATE_DOZE: out.append('d'); break; 635 case Display.STATE_DOZE_SUSPEND: out.append('z'); break; 636 } 637 if ((initMode&STEP_LEVEL_MODE_POWER_SAVE) != 0) { 638 out.append('p'); 639 } 640 if ((initMode&STEP_LEVEL_MODE_DEVICE_IDLE) != 0) { 641 out.append('i'); 642 } 643 switch ((modMode&STEP_LEVEL_MODE_SCREEN_STATE) + 1) { 644 case Display.STATE_OFF: out.append('F'); break; 645 case Display.STATE_ON: out.append('O'); break; 646 case Display.STATE_DOZE: out.append('D'); break; 647 case Display.STATE_DOZE_SUSPEND: out.append('Z'); break; 648 } 649 if ((modMode&STEP_LEVEL_MODE_POWER_SAVE) != 0) { 650 out.append('P'); 651 } 652 if ((modMode&STEP_LEVEL_MODE_DEVICE_IDLE) != 0) { 653 out.append('I'); 654 } 655 out.append('-'); 656 appendHex(level, 4, out); 657 out.append('-'); 658 appendHex(duration, STEP_LEVEL_LEVEL_SHIFT-4, out); 659 } 660 661 public void decodeEntryAt(int index, String value) { 662 final int N = value.length(); 663 int i = 0; 664 char c; 665 long out = 0; 666 while (i < N && (c=value.charAt(i)) != '-') { 667 i++; 668 switch (c) { 669 case 'f': out |= (((long)Display.STATE_OFF-1)<<STEP_LEVEL_INITIAL_MODE_SHIFT); 670 break; 671 case 'o': out |= (((long)Display.STATE_ON-1)<<STEP_LEVEL_INITIAL_MODE_SHIFT); 672 break; 673 case 'd': out |= (((long)Display.STATE_DOZE-1)<<STEP_LEVEL_INITIAL_MODE_SHIFT); 674 break; 675 case 'z': out |= (((long)Display.STATE_DOZE_SUSPEND-1) 676 << STEP_LEVEL_INITIAL_MODE_SHIFT); 677 break; 678 case 'p': out |= (((long)STEP_LEVEL_MODE_POWER_SAVE) 679 << STEP_LEVEL_INITIAL_MODE_SHIFT); 680 break; 681 case 'i': out |= (((long)STEP_LEVEL_MODE_DEVICE_IDLE) 682 << STEP_LEVEL_INITIAL_MODE_SHIFT); 683 break; 684 case 'F': out |= (((long)Display.STATE_OFF-1)<<STEP_LEVEL_MODIFIED_MODE_SHIFT); 685 break; 686 case 'O': out |= (((long)Display.STATE_ON-1)<<STEP_LEVEL_MODIFIED_MODE_SHIFT); 687 break; 688 case 'D': out |= (((long)Display.STATE_DOZE-1)<<STEP_LEVEL_MODIFIED_MODE_SHIFT); 689 break; 690 case 'Z': out |= (((long)Display.STATE_DOZE_SUSPEND-1) 691 << STEP_LEVEL_MODIFIED_MODE_SHIFT); 692 break; 693 case 'P': out |= (((long)STEP_LEVEL_MODE_POWER_SAVE) 694 << STEP_LEVEL_MODIFIED_MODE_SHIFT); 695 break; 696 case 'I': out |= (((long)STEP_LEVEL_MODE_DEVICE_IDLE) 697 << STEP_LEVEL_MODIFIED_MODE_SHIFT); 698 break; 699 } 700 } 701 i++; 702 long level = 0; 703 while (i < N && (c=value.charAt(i)) != '-') { 704 i++; 705 level <<= 4; 706 if (c >= '0' && c <= '9') { 707 level += c - '0'; 708 } else if (c >= 'a' && c <= 'f') { 709 level += c - 'a' + 10; 710 } else if (c >= 'A' && c <= 'F') { 711 level += c - 'A' + 10; 712 } 713 } 714 i++; 715 out |= (level << STEP_LEVEL_LEVEL_SHIFT) & STEP_LEVEL_LEVEL_MASK; 716 long duration = 0; 717 while (i < N && (c=value.charAt(i)) != '-') { 718 i++; 719 duration <<= 4; 720 if (c >= '0' && c <= '9') { 721 duration += c - '0'; 722 } else if (c >= 'a' && c <= 'f') { 723 duration += c - 'a' + 10; 724 } else if (c >= 'A' && c <= 'F') { 725 duration += c - 'A' + 10; 726 } 727 } 728 mStepDurations[index] = out | (duration & STEP_LEVEL_TIME_MASK); 729 } 730 731 public void init() { 732 mLastStepTime = -1; 733 mNumStepDurations = 0; 734 } 735 736 public void clearTime() { 737 mLastStepTime = -1; 738 } 739 740 public long computeTimePerLevel() { 741 final long[] steps = mStepDurations; 742 final int numSteps = mNumStepDurations; 743 744 // For now we'll do a simple average across all steps. 745 if (numSteps <= 0) { 746 return -1; 747 } 748 long total = 0; 749 for (int i=0; i<numSteps; i++) { 750 total += steps[i] & STEP_LEVEL_TIME_MASK; 751 } 752 return total / numSteps; 753 /* 754 long[] buckets = new long[numSteps]; 755 int numBuckets = 0; 756 int numToAverage = 4; 757 int i = 0; 758 while (i < numSteps) { 759 long totalTime = 0; 760 int num = 0; 761 for (int j=0; j<numToAverage && (i+j)<numSteps; j++) { 762 totalTime += steps[i+j] & STEP_LEVEL_TIME_MASK; 763 num++; 764 } 765 buckets[numBuckets] = totalTime / num; 766 numBuckets++; 767 numToAverage *= 2; 768 i += num; 769 } 770 if (numBuckets < 1) { 771 return -1; 772 } 773 long averageTime = buckets[numBuckets-1]; 774 for (i=numBuckets-2; i>=0; i--) { 775 averageTime = (averageTime + buckets[i]) / 2; 776 } 777 return averageTime; 778 */ 779 } 780 781 public long computeTimeEstimate(long modesOfInterest, long modeValues, 782 int[] outNumOfInterest) { 783 final long[] steps = mStepDurations; 784 final int count = mNumStepDurations; 785 if (count <= 0) { 786 return -1; 787 } 788 long total = 0; 789 int numOfInterest = 0; 790 for (int i=0; i<count; i++) { 791 long initMode = (steps[i] & STEP_LEVEL_INITIAL_MODE_MASK) 792 >> STEP_LEVEL_INITIAL_MODE_SHIFT; 793 long modMode = (steps[i] & STEP_LEVEL_MODIFIED_MODE_MASK) 794 >> STEP_LEVEL_MODIFIED_MODE_SHIFT; 795 // If the modes of interest didn't change during this step period... 796 if ((modMode&modesOfInterest) == 0) { 797 // And the mode values during this period match those we are measuring... 798 if ((initMode&modesOfInterest) == modeValues) { 799 // Then this can be used to estimate the total time! 800 numOfInterest++; 801 total += steps[i] & STEP_LEVEL_TIME_MASK; 802 } 803 } 804 } 805 if (numOfInterest <= 0) { 806 return -1; 807 } 808 809 if (outNumOfInterest != null) { 810 outNumOfInterest[0] = numOfInterest; 811 } 812 813 // The estimated time is the average time we spend in each level, multipled 814 // by 100 -- the total number of battery levels 815 return (total / numOfInterest) * 100; 816 } 817 818 public void addLevelSteps(int numStepLevels, long modeBits, long elapsedRealtime) { 819 int stepCount = mNumStepDurations; 820 final long lastStepTime = mLastStepTime; 821 if (lastStepTime >= 0 && numStepLevels > 0) { 822 final long[] steps = mStepDurations; 823 long duration = elapsedRealtime - lastStepTime; 824 for (int i=0; i<numStepLevels; i++) { 825 System.arraycopy(steps, 0, steps, 1, steps.length-1); 826 long thisDuration = duration / (numStepLevels-i); 827 duration -= thisDuration; 828 if (thisDuration > STEP_LEVEL_TIME_MASK) { 829 thisDuration = STEP_LEVEL_TIME_MASK; 830 } 831 steps[0] = thisDuration | modeBits; 832 } 833 stepCount += numStepLevels; 834 if (stepCount > steps.length) { 835 stepCount = steps.length; 836 } 837 } 838 mNumStepDurations = stepCount; 839 mLastStepTime = elapsedRealtime; 840 } 841 842 public void readFromParcel(Parcel in) { 843 final int N = in.readInt(); 844 mNumStepDurations = N; 845 for (int i=0; i<N; i++) { 846 mStepDurations[i] = in.readLong(); 847 } 848 } 849 850 public void writeToParcel(Parcel out) { 851 final int N = mNumStepDurations; 852 out.writeInt(N); 853 for (int i=0; i<N; i++) { 854 out.writeLong(mStepDurations[i]); 855 } 856 } 857 } 858 859 public static final class PackageChange { 860 public String mPackageName; 861 public boolean mUpdate; 862 public int mVersionCode; 863 } 864 865 public static final class DailyItem { 866 public long mStartTime; 867 public long mEndTime; 868 public LevelStepTracker mDischargeSteps; 869 public LevelStepTracker mChargeSteps; 870 public ArrayList<PackageChange> mPackageChanges; 871 } 872 873 public abstract DailyItem getDailyItemLocked(int daysAgo); 874 875 public abstract long getCurrentDailyStartTime(); 876 877 public abstract long getNextMinDailyDeadline(); 878 879 public abstract long getNextMaxDailyDeadline(); 880 881 public final static class HistoryTag { 882 public String string; 883 public int uid; 884 885 public int poolIdx; 886 887 public void setTo(HistoryTag o) { 888 string = o.string; 889 uid = o.uid; 890 poolIdx = o.poolIdx; 891 } 892 893 public void setTo(String _string, int _uid) { 894 string = _string; 895 uid = _uid; 896 poolIdx = -1; 897 } 898 899 public void writeToParcel(Parcel dest, int flags) { 900 dest.writeString(string); 901 dest.writeInt(uid); 902 } 903 904 public void readFromParcel(Parcel src) { 905 string = src.readString(); 906 uid = src.readInt(); 907 poolIdx = -1; 908 } 909 910 @Override 911 public boolean equals(Object o) { 912 if (this == o) return true; 913 if (o == null || getClass() != o.getClass()) return false; 914 915 HistoryTag that = (HistoryTag) o; 916 917 if (uid != that.uid) return false; 918 if (!string.equals(that.string)) return false; 919 920 return true; 921 } 922 923 @Override 924 public int hashCode() { 925 int result = string.hashCode(); 926 result = 31 * result + uid; 927 return result; 928 } 929 } 930 931 /** 932 * Optional detailed information that can go into a history step. This is typically 933 * generated each time the battery level changes. 934 */ 935 public final static class HistoryStepDetails { 936 // Time (in 1/100 second) spent in user space and the kernel since the last step. 937 public int userTime; 938 public int systemTime; 939 940 // Top three apps using CPU in the last step, with times in 1/100 second. 941 public int appCpuUid1; 942 public int appCpuUTime1; 943 public int appCpuSTime1; 944 public int appCpuUid2; 945 public int appCpuUTime2; 946 public int appCpuSTime2; 947 public int appCpuUid3; 948 public int appCpuUTime3; 949 public int appCpuSTime3; 950 951 // Information from /proc/stat 952 public int statUserTime; 953 public int statSystemTime; 954 public int statIOWaitTime; 955 public int statIrqTime; 956 public int statSoftIrqTime; 957 public int statIdlTime; 958 959 public HistoryStepDetails() { 960 clear(); 961 } 962 963 public void clear() { 964 userTime = systemTime = 0; 965 appCpuUid1 = appCpuUid2 = appCpuUid3 = -1; 966 appCpuUTime1 = appCpuSTime1 = appCpuUTime2 = appCpuSTime2 967 = appCpuUTime3 = appCpuSTime3 = 0; 968 } 969 970 public void writeToParcel(Parcel out) { 971 out.writeInt(userTime); 972 out.writeInt(systemTime); 973 out.writeInt(appCpuUid1); 974 out.writeInt(appCpuUTime1); 975 out.writeInt(appCpuSTime1); 976 out.writeInt(appCpuUid2); 977 out.writeInt(appCpuUTime2); 978 out.writeInt(appCpuSTime2); 979 out.writeInt(appCpuUid3); 980 out.writeInt(appCpuUTime3); 981 out.writeInt(appCpuSTime3); 982 out.writeInt(statUserTime); 983 out.writeInt(statSystemTime); 984 out.writeInt(statIOWaitTime); 985 out.writeInt(statIrqTime); 986 out.writeInt(statSoftIrqTime); 987 out.writeInt(statIdlTime); 988 } 989 990 public void readFromParcel(Parcel in) { 991 userTime = in.readInt(); 992 systemTime = in.readInt(); 993 appCpuUid1 = in.readInt(); 994 appCpuUTime1 = in.readInt(); 995 appCpuSTime1 = in.readInt(); 996 appCpuUid2 = in.readInt(); 997 appCpuUTime2 = in.readInt(); 998 appCpuSTime2 = in.readInt(); 999 appCpuUid3 = in.readInt(); 1000 appCpuUTime3 = in.readInt(); 1001 appCpuSTime3 = in.readInt(); 1002 statUserTime = in.readInt(); 1003 statSystemTime = in.readInt(); 1004 statIOWaitTime = in.readInt(); 1005 statIrqTime = in.readInt(); 1006 statSoftIrqTime = in.readInt(); 1007 statIdlTime = in.readInt(); 1008 } 1009 } 1010 1011 public final static class HistoryItem implements Parcelable { 1012 public HistoryItem next; 1013 1014 // The time of this event in milliseconds, as per SystemClock.elapsedRealtime(). 1015 public long time; 1016 1017 public static final byte CMD_UPDATE = 0; // These can be written as deltas 1018 public static final byte CMD_NULL = -1; 1019 public static final byte CMD_START = 4; 1020 public static final byte CMD_CURRENT_TIME = 5; 1021 public static final byte CMD_OVERFLOW = 6; 1022 public static final byte CMD_RESET = 7; 1023 public static final byte CMD_SHUTDOWN = 8; 1024 1025 public byte cmd = CMD_NULL; 1026 1027 /** 1028 * Return whether the command code is a delta data update. 1029 */ 1030 public boolean isDeltaData() { 1031 return cmd == CMD_UPDATE; 1032 } 1033 1034 public byte batteryLevel; 1035 public byte batteryStatus; 1036 public byte batteryHealth; 1037 public byte batteryPlugType; 1038 1039 public short batteryTemperature; 1040 public char batteryVoltage; 1041 1042 // Constants from SCREEN_BRIGHTNESS_* 1043 public static final int STATE_BRIGHTNESS_SHIFT = 0; 1044 public static final int STATE_BRIGHTNESS_MASK = 0x7; 1045 // Constants from SIGNAL_STRENGTH_* 1046 public static final int STATE_PHONE_SIGNAL_STRENGTH_SHIFT = 3; 1047 public static final int STATE_PHONE_SIGNAL_STRENGTH_MASK = 0x7 << STATE_PHONE_SIGNAL_STRENGTH_SHIFT; 1048 // Constants from ServiceState.STATE_* 1049 public static final int STATE_PHONE_STATE_SHIFT = 6; 1050 public static final int STATE_PHONE_STATE_MASK = 0x7 << STATE_PHONE_STATE_SHIFT; 1051 // Constants from DATA_CONNECTION_* 1052 public static final int STATE_DATA_CONNECTION_SHIFT = 9; 1053 public static final int STATE_DATA_CONNECTION_MASK = 0x1f << STATE_DATA_CONNECTION_SHIFT; 1054 1055 // These states always appear directly in the first int token 1056 // of a delta change; they should be ones that change relatively 1057 // frequently. 1058 public static final int STATE_CPU_RUNNING_FLAG = 1<<31; 1059 public static final int STATE_WAKE_LOCK_FLAG = 1<<30; 1060 public static final int STATE_GPS_ON_FLAG = 1<<29; 1061 public static final int STATE_WIFI_FULL_LOCK_FLAG = 1<<28; 1062 public static final int STATE_WIFI_SCAN_FLAG = 1<<27; 1063 public static final int STATE_WIFI_RADIO_ACTIVE_FLAG = 1<<26; 1064 public static final int STATE_MOBILE_RADIO_ACTIVE_FLAG = 1<<25; 1065 // These are on the lower bits used for the command; if they change 1066 // we need to write another int of data. 1067 public static final int STATE_SENSOR_ON_FLAG = 1<<23; 1068 public static final int STATE_AUDIO_ON_FLAG = 1<<22; 1069 public static final int STATE_PHONE_SCANNING_FLAG = 1<<21; 1070 public static final int STATE_SCREEN_ON_FLAG = 1<<20; // consider moving to states2 1071 public static final int STATE_BATTERY_PLUGGED_FLAG = 1<<19; // consider moving to states2 1072 // empty slot 1073 // empty slot 1074 public static final int STATE_WIFI_MULTICAST_ON_FLAG = 1<<16; 1075 1076 public static final int MOST_INTERESTING_STATES = 1077 STATE_BATTERY_PLUGGED_FLAG | STATE_SCREEN_ON_FLAG; 1078 1079 public static final int SETTLE_TO_ZERO_STATES = 0xffff0000 & ~MOST_INTERESTING_STATES; 1080 1081 public int states; 1082 1083 // Constants from WIFI_SUPPL_STATE_* 1084 public static final int STATE2_WIFI_SUPPL_STATE_SHIFT = 0; 1085 public static final int STATE2_WIFI_SUPPL_STATE_MASK = 0xf; 1086 // Values for NUM_WIFI_SIGNAL_STRENGTH_BINS 1087 public static final int STATE2_WIFI_SIGNAL_STRENGTH_SHIFT = 4; 1088 public static final int STATE2_WIFI_SIGNAL_STRENGTH_MASK = 1089 0x7 << STATE2_WIFI_SIGNAL_STRENGTH_SHIFT; 1090 1091 public static final int STATE2_POWER_SAVE_FLAG = 1<<31; 1092 public static final int STATE2_VIDEO_ON_FLAG = 1<<30; 1093 public static final int STATE2_WIFI_RUNNING_FLAG = 1<<29; 1094 public static final int STATE2_WIFI_ON_FLAG = 1<<28; 1095 public static final int STATE2_FLASHLIGHT_FLAG = 1<<27; 1096 public static final int STATE2_DEVICE_IDLE_FLAG = 1<<26; 1097 public static final int STATE2_CHARGING_FLAG = 1<<25; 1098 public static final int STATE2_PHONE_IN_CALL_FLAG = 1<<24; 1099 public static final int STATE2_BLUETOOTH_ON_FLAG = 1<<23; 1100 1101 public static final int MOST_INTERESTING_STATES2 = 1102 STATE2_POWER_SAVE_FLAG | STATE2_WIFI_ON_FLAG | STATE2_DEVICE_IDLE_FLAG 1103 | STATE2_CHARGING_FLAG | STATE2_PHONE_IN_CALL_FLAG | STATE2_BLUETOOTH_ON_FLAG; 1104 1105 public static final int SETTLE_TO_ZERO_STATES2 = 0xffff0000 & ~MOST_INTERESTING_STATES2; 1106 1107 public int states2; 1108 1109 // The wake lock that was acquired at this point. 1110 public HistoryTag wakelockTag; 1111 1112 // Kernel wakeup reason at this point. 1113 public HistoryTag wakeReasonTag; 1114 1115 // Non-null when there is more detailed information at this step. 1116 public HistoryStepDetails stepDetails; 1117 1118 public static final int EVENT_FLAG_START = 0x8000; 1119 public static final int EVENT_FLAG_FINISH = 0x4000; 1120 1121 // No event in this item. 1122 public static final int EVENT_NONE = 0x0000; 1123 // Event is about a process that is running. 1124 public static final int EVENT_PROC = 0x0001; 1125 // Event is about an application package that is in the foreground. 1126 public static final int EVENT_FOREGROUND = 0x0002; 1127 // Event is about an application package that is at the top of the screen. 1128 public static final int EVENT_TOP = 0x0003; 1129 // Event is about active sync operations. 1130 public static final int EVENT_SYNC = 0x0004; 1131 // Events for all additional wake locks aquired/release within a wake block. 1132 // These are not generated by default. 1133 public static final int EVENT_WAKE_LOCK = 0x0005; 1134 // Event is about an application executing a scheduled job. 1135 public static final int EVENT_JOB = 0x0006; 1136 // Events for users running. 1137 public static final int EVENT_USER_RUNNING = 0x0007; 1138 // Events for foreground user. 1139 public static final int EVENT_USER_FOREGROUND = 0x0008; 1140 // Event for connectivity changed. 1141 public static final int EVENT_CONNECTIVITY_CHANGED = 0x0009; 1142 // Event for significant motion taking us out of idle mode. 1143 public static final int EVENT_SIGNIFICANT_MOTION = 0x000a; 1144 // Event for becoming active taking us out of idle mode. 1145 public static final int EVENT_ACTIVE = 0x000b; 1146 // Event for a package being installed. 1147 public static final int EVENT_PACKAGE_INSTALLED = 0x000c; 1148 // Event for a package being uninstalled. 1149 public static final int EVENT_PACKAGE_UNINSTALLED = 0x000d; 1150 // Event for a package being uninstalled. 1151 public static final int EVENT_ALARM = 0x000e; 1152 // Record that we have decided we need to collect new stats data. 1153 public static final int EVENT_COLLECT_EXTERNAL_STATS = 0x000f; 1154 // Number of event types. 1155 public static final int EVENT_COUNT = 0x0010; 1156 // Mask to extract out only the type part of the event. 1157 public static final int EVENT_TYPE_MASK = ~(EVENT_FLAG_START|EVENT_FLAG_FINISH); 1158 1159 public static final int EVENT_PROC_START = EVENT_PROC | EVENT_FLAG_START; 1160 public static final int EVENT_PROC_FINISH = EVENT_PROC | EVENT_FLAG_FINISH; 1161 public static final int EVENT_FOREGROUND_START = EVENT_FOREGROUND | EVENT_FLAG_START; 1162 public static final int EVENT_FOREGROUND_FINISH = EVENT_FOREGROUND | EVENT_FLAG_FINISH; 1163 public static final int EVENT_TOP_START = EVENT_TOP | EVENT_FLAG_START; 1164 public static final int EVENT_TOP_FINISH = EVENT_TOP | EVENT_FLAG_FINISH; 1165 public static final int EVENT_SYNC_START = EVENT_SYNC | EVENT_FLAG_START; 1166 public static final int EVENT_SYNC_FINISH = EVENT_SYNC | EVENT_FLAG_FINISH; 1167 public static final int EVENT_WAKE_LOCK_START = EVENT_WAKE_LOCK | EVENT_FLAG_START; 1168 public static final int EVENT_WAKE_LOCK_FINISH = EVENT_WAKE_LOCK | EVENT_FLAG_FINISH; 1169 public static final int EVENT_JOB_START = EVENT_JOB | EVENT_FLAG_START; 1170 public static final int EVENT_JOB_FINISH = EVENT_JOB | EVENT_FLAG_FINISH; 1171 public static final int EVENT_USER_RUNNING_START = EVENT_USER_RUNNING | EVENT_FLAG_START; 1172 public static final int EVENT_USER_RUNNING_FINISH = EVENT_USER_RUNNING | EVENT_FLAG_FINISH; 1173 public static final int EVENT_USER_FOREGROUND_START = 1174 EVENT_USER_FOREGROUND | EVENT_FLAG_START; 1175 public static final int EVENT_USER_FOREGROUND_FINISH = 1176 EVENT_USER_FOREGROUND | EVENT_FLAG_FINISH; 1177 public static final int EVENT_ALARM_START = EVENT_ALARM | EVENT_FLAG_START; 1178 public static final int EVENT_ALARM_FINISH = EVENT_ALARM | EVENT_FLAG_FINISH; 1179 1180 // For CMD_EVENT. 1181 public int eventCode; 1182 public HistoryTag eventTag; 1183 1184 // Only set for CMD_CURRENT_TIME or CMD_RESET, as per System.currentTimeMillis(). 1185 public long currentTime; 1186 1187 // Meta-data when reading. 1188 public int numReadInts; 1189 1190 // Pre-allocated objects. 1191 public final HistoryTag localWakelockTag = new HistoryTag(); 1192 public final HistoryTag localWakeReasonTag = new HistoryTag(); 1193 public final HistoryTag localEventTag = new HistoryTag(); 1194 1195 public HistoryItem() { 1196 } 1197 1198 public HistoryItem(long time, Parcel src) { 1199 this.time = time; 1200 numReadInts = 2; 1201 readFromParcel(src); 1202 } 1203 1204 public int describeContents() { 1205 return 0; 1206 } 1207 1208 public void writeToParcel(Parcel dest, int flags) { 1209 dest.writeLong(time); 1210 int bat = (((int)cmd)&0xff) 1211 | ((((int)batteryLevel)<<8)&0xff00) 1212 | ((((int)batteryStatus)<<16)&0xf0000) 1213 | ((((int)batteryHealth)<<20)&0xf00000) 1214 | ((((int)batteryPlugType)<<24)&0xf000000) 1215 | (wakelockTag != null ? 0x10000000 : 0) 1216 | (wakeReasonTag != null ? 0x20000000 : 0) 1217 | (eventCode != EVENT_NONE ? 0x40000000 : 0); 1218 dest.writeInt(bat); 1219 bat = (((int)batteryTemperature)&0xffff) 1220 | ((((int)batteryVoltage)<<16)&0xffff0000); 1221 dest.writeInt(bat); 1222 dest.writeInt(states); 1223 dest.writeInt(states2); 1224 if (wakelockTag != null) { 1225 wakelockTag.writeToParcel(dest, flags); 1226 } 1227 if (wakeReasonTag != null) { 1228 wakeReasonTag.writeToParcel(dest, flags); 1229 } 1230 if (eventCode != EVENT_NONE) { 1231 dest.writeInt(eventCode); 1232 eventTag.writeToParcel(dest, flags); 1233 } 1234 if (cmd == CMD_CURRENT_TIME || cmd == CMD_RESET) { 1235 dest.writeLong(currentTime); 1236 } 1237 } 1238 1239 public void readFromParcel(Parcel src) { 1240 int start = src.dataPosition(); 1241 int bat = src.readInt(); 1242 cmd = (byte)(bat&0xff); 1243 batteryLevel = (byte)((bat>>8)&0xff); 1244 batteryStatus = (byte)((bat>>16)&0xf); 1245 batteryHealth = (byte)((bat>>20)&0xf); 1246 batteryPlugType = (byte)((bat>>24)&0xf); 1247 int bat2 = src.readInt(); 1248 batteryTemperature = (short)(bat2&0xffff); 1249 batteryVoltage = (char)((bat2>>16)&0xffff); 1250 states = src.readInt(); 1251 states2 = src.readInt(); 1252 if ((bat&0x10000000) != 0) { 1253 wakelockTag = localWakelockTag; 1254 wakelockTag.readFromParcel(src); 1255 } else { 1256 wakelockTag = null; 1257 } 1258 if ((bat&0x20000000) != 0) { 1259 wakeReasonTag = localWakeReasonTag; 1260 wakeReasonTag.readFromParcel(src); 1261 } else { 1262 wakeReasonTag = null; 1263 } 1264 if ((bat&0x40000000) != 0) { 1265 eventCode = src.readInt(); 1266 eventTag = localEventTag; 1267 eventTag.readFromParcel(src); 1268 } else { 1269 eventCode = EVENT_NONE; 1270 eventTag = null; 1271 } 1272 if (cmd == CMD_CURRENT_TIME || cmd == CMD_RESET) { 1273 currentTime = src.readLong(); 1274 } else { 1275 currentTime = 0; 1276 } 1277 numReadInts += (src.dataPosition()-start)/4; 1278 } 1279 1280 public void clear() { 1281 time = 0; 1282 cmd = CMD_NULL; 1283 batteryLevel = 0; 1284 batteryStatus = 0; 1285 batteryHealth = 0; 1286 batteryPlugType = 0; 1287 batteryTemperature = 0; 1288 batteryVoltage = 0; 1289 states = 0; 1290 states2 = 0; 1291 wakelockTag = null; 1292 wakeReasonTag = null; 1293 eventCode = EVENT_NONE; 1294 eventTag = null; 1295 } 1296 1297 public void setTo(HistoryItem o) { 1298 time = o.time; 1299 cmd = o.cmd; 1300 setToCommon(o); 1301 } 1302 1303 public void setTo(long time, byte cmd, HistoryItem o) { 1304 this.time = time; 1305 this.cmd = cmd; 1306 setToCommon(o); 1307 } 1308 1309 private void setToCommon(HistoryItem o) { 1310 batteryLevel = o.batteryLevel; 1311 batteryStatus = o.batteryStatus; 1312 batteryHealth = o.batteryHealth; 1313 batteryPlugType = o.batteryPlugType; 1314 batteryTemperature = o.batteryTemperature; 1315 batteryVoltage = o.batteryVoltage; 1316 states = o.states; 1317 states2 = o.states2; 1318 if (o.wakelockTag != null) { 1319 wakelockTag = localWakelockTag; 1320 wakelockTag.setTo(o.wakelockTag); 1321 } else { 1322 wakelockTag = null; 1323 } 1324 if (o.wakeReasonTag != null) { 1325 wakeReasonTag = localWakeReasonTag; 1326 wakeReasonTag.setTo(o.wakeReasonTag); 1327 } else { 1328 wakeReasonTag = null; 1329 } 1330 eventCode = o.eventCode; 1331 if (o.eventTag != null) { 1332 eventTag = localEventTag; 1333 eventTag.setTo(o.eventTag); 1334 } else { 1335 eventTag = null; 1336 } 1337 currentTime = o.currentTime; 1338 } 1339 1340 public boolean sameNonEvent(HistoryItem o) { 1341 return batteryLevel == o.batteryLevel 1342 && batteryStatus == o.batteryStatus 1343 && batteryHealth == o.batteryHealth 1344 && batteryPlugType == o.batteryPlugType 1345 && batteryTemperature == o.batteryTemperature 1346 && batteryVoltage == o.batteryVoltage 1347 && states == o.states 1348 && states2 == o.states2 1349 && currentTime == o.currentTime; 1350 } 1351 1352 public boolean same(HistoryItem o) { 1353 if (!sameNonEvent(o) || eventCode != o.eventCode) { 1354 return false; 1355 } 1356 if (wakelockTag != o.wakelockTag) { 1357 if (wakelockTag == null || o.wakelockTag == null) { 1358 return false; 1359 } 1360 if (!wakelockTag.equals(o.wakelockTag)) { 1361 return false; 1362 } 1363 } 1364 if (wakeReasonTag != o.wakeReasonTag) { 1365 if (wakeReasonTag == null || o.wakeReasonTag == null) { 1366 return false; 1367 } 1368 if (!wakeReasonTag.equals(o.wakeReasonTag)) { 1369 return false; 1370 } 1371 } 1372 if (eventTag != o.eventTag) { 1373 if (eventTag == null || o.eventTag == null) { 1374 return false; 1375 } 1376 if (!eventTag.equals(o.eventTag)) { 1377 return false; 1378 } 1379 } 1380 return true; 1381 } 1382 } 1383 1384 public final static class HistoryEventTracker { 1385 private final HashMap<String, SparseIntArray>[] mActiveEvents 1386 = (HashMap<String, SparseIntArray>[]) new HashMap[HistoryItem.EVENT_COUNT]; 1387 1388 public boolean updateState(int code, String name, int uid, int poolIdx) { 1389 if ((code&HistoryItem.EVENT_FLAG_START) != 0) { 1390 int idx = code&HistoryItem.EVENT_TYPE_MASK; 1391 HashMap<String, SparseIntArray> active = mActiveEvents[idx]; 1392 if (active == null) { 1393 active = new HashMap<>(); 1394 mActiveEvents[idx] = active; 1395 } 1396 SparseIntArray uids = active.get(name); 1397 if (uids == null) { 1398 uids = new SparseIntArray(); 1399 active.put(name, uids); 1400 } 1401 if (uids.indexOfKey(uid) >= 0) { 1402 // Already set, nothing to do! 1403 return false; 1404 } 1405 uids.put(uid, poolIdx); 1406 } else if ((code&HistoryItem.EVENT_FLAG_FINISH) != 0) { 1407 int idx = code&HistoryItem.EVENT_TYPE_MASK; 1408 HashMap<String, SparseIntArray> active = mActiveEvents[idx]; 1409 if (active == null) { 1410 // not currently active, nothing to do. 1411 return false; 1412 } 1413 SparseIntArray uids = active.get(name); 1414 if (uids == null) { 1415 // not currently active, nothing to do. 1416 return false; 1417 } 1418 idx = uids.indexOfKey(uid); 1419 if (idx < 0) { 1420 // not currently active, nothing to do. 1421 return false; 1422 } 1423 uids.removeAt(idx); 1424 if (uids.size() <= 0) { 1425 active.remove(name); 1426 } 1427 } 1428 return true; 1429 } 1430 1431 public void removeEvents(int code) { 1432 int idx = code&HistoryItem.EVENT_TYPE_MASK; 1433 mActiveEvents[idx] = null; 1434 } 1435 1436 public HashMap<String, SparseIntArray> getStateForEvent(int code) { 1437 return mActiveEvents[code]; 1438 } 1439 } 1440 1441 public static final class BitDescription { 1442 public final int mask; 1443 public final int shift; 1444 public final String name; 1445 public final String shortName; 1446 public final String[] values; 1447 public final String[] shortValues; 1448 1449 public BitDescription(int mask, String name, String shortName) { 1450 this.mask = mask; 1451 this.shift = -1; 1452 this.name = name; 1453 this.shortName = shortName; 1454 this.values = null; 1455 this.shortValues = null; 1456 } 1457 1458 public BitDescription(int mask, int shift, String name, String shortName, 1459 String[] values, String[] shortValues) { 1460 this.mask = mask; 1461 this.shift = shift; 1462 this.name = name; 1463 this.shortName = shortName; 1464 this.values = values; 1465 this.shortValues = shortValues; 1466 } 1467 } 1468 1469 /** 1470 * Don't allow any more batching in to the current history event. This 1471 * is called when printing partial histories, so to ensure that the next 1472 * history event will go in to a new batch after what was printed in the 1473 * last partial history. 1474 */ 1475 public abstract void commitCurrentHistoryBatchLocked(); 1476 1477 public abstract int getHistoryTotalSize(); 1478 1479 public abstract int getHistoryUsedSize(); 1480 1481 public abstract boolean startIteratingHistoryLocked(); 1482 1483 public abstract int getHistoryStringPoolSize(); 1484 1485 public abstract int getHistoryStringPoolBytes(); 1486 1487 public abstract String getHistoryTagPoolString(int index); 1488 1489 public abstract int getHistoryTagPoolUid(int index); 1490 1491 public abstract boolean getNextHistoryLocked(HistoryItem out); 1492 1493 public abstract void finishIteratingHistoryLocked(); 1494 1495 public abstract boolean startIteratingOldHistoryLocked(); 1496 1497 public abstract boolean getNextOldHistoryLocked(HistoryItem out); 1498 1499 public abstract void finishIteratingOldHistoryLocked(); 1500 1501 /** 1502 * Return the base time offset for the battery history. 1503 */ 1504 public abstract long getHistoryBaseTime(); 1505 1506 /** 1507 * Returns the number of times the device has been started. 1508 */ 1509 public abstract int getStartCount(); 1510 1511 /** 1512 * Returns the time in microseconds that the screen has been on while the device was 1513 * running on battery. 1514 * 1515 * {@hide} 1516 */ 1517 public abstract long getScreenOnTime(long elapsedRealtimeUs, int which); 1518 1519 /** 1520 * Returns the number of times the screen was turned on. 1521 * 1522 * {@hide} 1523 */ 1524 public abstract int getScreenOnCount(int which); 1525 1526 public abstract long getInteractiveTime(long elapsedRealtimeUs, int which); 1527 1528 public static final int SCREEN_BRIGHTNESS_DARK = 0; 1529 public static final int SCREEN_BRIGHTNESS_DIM = 1; 1530 public static final int SCREEN_BRIGHTNESS_MEDIUM = 2; 1531 public static final int SCREEN_BRIGHTNESS_LIGHT = 3; 1532 public static final int SCREEN_BRIGHTNESS_BRIGHT = 4; 1533 1534 static final String[] SCREEN_BRIGHTNESS_NAMES = { 1535 "dark", "dim", "medium", "light", "bright" 1536 }; 1537 1538 static final String[] SCREEN_BRIGHTNESS_SHORT_NAMES = { 1539 "0", "1", "2", "3", "4" 1540 }; 1541 1542 public static final int NUM_SCREEN_BRIGHTNESS_BINS = 5; 1543 1544 /** 1545 * Returns the time in microseconds that the screen has been on with 1546 * the given brightness 1547 * 1548 * {@hide} 1549 */ 1550 public abstract long getScreenBrightnessTime(int brightnessBin, 1551 long elapsedRealtimeUs, int which); 1552 1553 /** 1554 * Returns the time in microseconds that power save mode has been enabled while the device was 1555 * running on battery. 1556 * 1557 * {@hide} 1558 */ 1559 public abstract long getPowerSaveModeEnabledTime(long elapsedRealtimeUs, int which); 1560 1561 /** 1562 * Returns the number of times that power save mode was enabled. 1563 * 1564 * {@hide} 1565 */ 1566 public abstract int getPowerSaveModeEnabledCount(int which); 1567 1568 /** 1569 * Returns the time in microseconds that device has been in idle mode while 1570 * running on battery. 1571 * 1572 * {@hide} 1573 */ 1574 public abstract long getDeviceIdleModeEnabledTime(long elapsedRealtimeUs, int which); 1575 1576 /** 1577 * Returns the number of times that the devie has gone in to idle mode. 1578 * 1579 * {@hide} 1580 */ 1581 public abstract int getDeviceIdleModeEnabledCount(int which); 1582 1583 /** 1584 * Returns the time in microseconds that device has been in idling while on 1585 * battery. This is broader than {@link #getDeviceIdleModeEnabledTime} -- it 1586 * counts all of the time that we consider the device to be idle, whether or not 1587 * it is currently in the actual device idle mode. 1588 * 1589 * {@hide} 1590 */ 1591 public abstract long getDeviceIdlingTime(long elapsedRealtimeUs, int which); 1592 1593 /** 1594 * Returns the number of times that the devie has started idling. 1595 * 1596 * {@hide} 1597 */ 1598 public abstract int getDeviceIdlingCount(int which); 1599 1600 /** 1601 * Returns the number of times that connectivity state changed. 1602 * 1603 * {@hide} 1604 */ 1605 public abstract int getNumConnectivityChange(int which); 1606 1607 /** 1608 * Returns the time in microseconds that the phone has been on while the device was 1609 * running on battery. 1610 * 1611 * {@hide} 1612 */ 1613 public abstract long getPhoneOnTime(long elapsedRealtimeUs, int which); 1614 1615 /** 1616 * Returns the number of times a phone call was activated. 1617 * 1618 * {@hide} 1619 */ 1620 public abstract int getPhoneOnCount(int which); 1621 1622 /** 1623 * Returns the time in microseconds that the phone has been running with 1624 * the given signal strength. 1625 * 1626 * {@hide} 1627 */ 1628 public abstract long getPhoneSignalStrengthTime(int strengthBin, 1629 long elapsedRealtimeUs, int which); 1630 1631 /** 1632 * Returns the time in microseconds that the phone has been trying to 1633 * acquire a signal. 1634 * 1635 * {@hide} 1636 */ 1637 public abstract long getPhoneSignalScanningTime( 1638 long elapsedRealtimeUs, int which); 1639 1640 /** 1641 * Returns the number of times the phone has entered the given signal strength. 1642 * 1643 * {@hide} 1644 */ 1645 public abstract int getPhoneSignalStrengthCount(int strengthBin, int which); 1646 1647 /** 1648 * Returns the time in microseconds that the mobile network has been active 1649 * (in a high power state). 1650 * 1651 * {@hide} 1652 */ 1653 public abstract long getMobileRadioActiveTime(long elapsedRealtimeUs, int which); 1654 1655 /** 1656 * Returns the number of times that the mobile network has transitioned to the 1657 * active state. 1658 * 1659 * {@hide} 1660 */ 1661 public abstract int getMobileRadioActiveCount(int which); 1662 1663 /** 1664 * Returns the time in microseconds that is the difference between the mobile radio 1665 * time we saw based on the elapsed timestamp when going down vs. the given time stamp 1666 * from the radio. 1667 * 1668 * {@hide} 1669 */ 1670 public abstract long getMobileRadioActiveAdjustedTime(int which); 1671 1672 /** 1673 * Returns the time in microseconds that the mobile network has been active 1674 * (in a high power state) but not being able to blame on an app. 1675 * 1676 * {@hide} 1677 */ 1678 public abstract long getMobileRadioActiveUnknownTime(int which); 1679 1680 /** 1681 * Return count of number of times radio was up that could not be blamed on apps. 1682 * 1683 * {@hide} 1684 */ 1685 public abstract int getMobileRadioActiveUnknownCount(int which); 1686 1687 public static final int DATA_CONNECTION_NONE = 0; 1688 public static final int DATA_CONNECTION_GPRS = 1; 1689 public static final int DATA_CONNECTION_EDGE = 2; 1690 public static final int DATA_CONNECTION_UMTS = 3; 1691 public static final int DATA_CONNECTION_CDMA = 4; 1692 public static final int DATA_CONNECTION_EVDO_0 = 5; 1693 public static final int DATA_CONNECTION_EVDO_A = 6; 1694 public static final int DATA_CONNECTION_1xRTT = 7; 1695 public static final int DATA_CONNECTION_HSDPA = 8; 1696 public static final int DATA_CONNECTION_HSUPA = 9; 1697 public static final int DATA_CONNECTION_HSPA = 10; 1698 public static final int DATA_CONNECTION_IDEN = 11; 1699 public static final int DATA_CONNECTION_EVDO_B = 12; 1700 public static final int DATA_CONNECTION_LTE = 13; 1701 public static final int DATA_CONNECTION_EHRPD = 14; 1702 public static final int DATA_CONNECTION_HSPAP = 15; 1703 public static final int DATA_CONNECTION_OTHER = 16; 1704 1705 static final String[] DATA_CONNECTION_NAMES = { 1706 "none", "gprs", "edge", "umts", "cdma", "evdo_0", "evdo_A", 1707 "1xrtt", "hsdpa", "hsupa", "hspa", "iden", "evdo_b", "lte", 1708 "ehrpd", "hspap", "other" 1709 }; 1710 1711 public static final int NUM_DATA_CONNECTION_TYPES = DATA_CONNECTION_OTHER+1; 1712 1713 /** 1714 * Returns the time in microseconds that the phone has been running with 1715 * the given data connection. 1716 * 1717 * {@hide} 1718 */ 1719 public abstract long getPhoneDataConnectionTime(int dataType, 1720 long elapsedRealtimeUs, int which); 1721 1722 /** 1723 * Returns the number of times the phone has entered the given data 1724 * connection type. 1725 * 1726 * {@hide} 1727 */ 1728 public abstract int getPhoneDataConnectionCount(int dataType, int which); 1729 1730 public static final int WIFI_SUPPL_STATE_INVALID = 0; 1731 public static final int WIFI_SUPPL_STATE_DISCONNECTED = 1; 1732 public static final int WIFI_SUPPL_STATE_INTERFACE_DISABLED = 2; 1733 public static final int WIFI_SUPPL_STATE_INACTIVE = 3; 1734 public static final int WIFI_SUPPL_STATE_SCANNING = 4; 1735 public static final int WIFI_SUPPL_STATE_AUTHENTICATING = 5; 1736 public static final int WIFI_SUPPL_STATE_ASSOCIATING = 6; 1737 public static final int WIFI_SUPPL_STATE_ASSOCIATED = 7; 1738 public static final int WIFI_SUPPL_STATE_FOUR_WAY_HANDSHAKE = 8; 1739 public static final int WIFI_SUPPL_STATE_GROUP_HANDSHAKE = 9; 1740 public static final int WIFI_SUPPL_STATE_COMPLETED = 10; 1741 public static final int WIFI_SUPPL_STATE_DORMANT = 11; 1742 public static final int WIFI_SUPPL_STATE_UNINITIALIZED = 12; 1743 1744 public static final int NUM_WIFI_SUPPL_STATES = WIFI_SUPPL_STATE_UNINITIALIZED+1; 1745 1746 static final String[] WIFI_SUPPL_STATE_NAMES = { 1747 "invalid", "disconn", "disabled", "inactive", "scanning", 1748 "authenticating", "associating", "associated", "4-way-handshake", 1749 "group-handshake", "completed", "dormant", "uninit" 1750 }; 1751 1752 static final String[] WIFI_SUPPL_STATE_SHORT_NAMES = { 1753 "inv", "dsc", "dis", "inact", "scan", 1754 "auth", "ascing", "asced", "4-way", 1755 "group", "compl", "dorm", "uninit" 1756 }; 1757 1758 public static final BitDescription[] HISTORY_STATE_DESCRIPTIONS 1759 = new BitDescription[] { 1760 new BitDescription(HistoryItem.STATE_CPU_RUNNING_FLAG, "running", "r"), 1761 new BitDescription(HistoryItem.STATE_WAKE_LOCK_FLAG, "wake_lock", "w"), 1762 new BitDescription(HistoryItem.STATE_SENSOR_ON_FLAG, "sensor", "s"), 1763 new BitDescription(HistoryItem.STATE_GPS_ON_FLAG, "gps", "g"), 1764 new BitDescription(HistoryItem.STATE_WIFI_FULL_LOCK_FLAG, "wifi_full_lock", "Wl"), 1765 new BitDescription(HistoryItem.STATE_WIFI_SCAN_FLAG, "wifi_scan", "Ws"), 1766 new BitDescription(HistoryItem.STATE_WIFI_MULTICAST_ON_FLAG, "wifi_multicast", "Wm"), 1767 new BitDescription(HistoryItem.STATE_WIFI_RADIO_ACTIVE_FLAG, "wifi_radio", "Wr"), 1768 new BitDescription(HistoryItem.STATE_MOBILE_RADIO_ACTIVE_FLAG, "mobile_radio", "Pr"), 1769 new BitDescription(HistoryItem.STATE_PHONE_SCANNING_FLAG, "phone_scanning", "Psc"), 1770 new BitDescription(HistoryItem.STATE_AUDIO_ON_FLAG, "audio", "a"), 1771 new BitDescription(HistoryItem.STATE_SCREEN_ON_FLAG, "screen", "S"), 1772 new BitDescription(HistoryItem.STATE_BATTERY_PLUGGED_FLAG, "plugged", "BP"), 1773 new BitDescription(HistoryItem.STATE_DATA_CONNECTION_MASK, 1774 HistoryItem.STATE_DATA_CONNECTION_SHIFT, "data_conn", "Pcn", 1775 DATA_CONNECTION_NAMES, DATA_CONNECTION_NAMES), 1776 new BitDescription(HistoryItem.STATE_PHONE_STATE_MASK, 1777 HistoryItem.STATE_PHONE_STATE_SHIFT, "phone_state", "Pst", 1778 new String[] {"in", "out", "emergency", "off"}, 1779 new String[] {"in", "out", "em", "off"}), 1780 new BitDescription(HistoryItem.STATE_PHONE_SIGNAL_STRENGTH_MASK, 1781 HistoryItem.STATE_PHONE_SIGNAL_STRENGTH_SHIFT, "phone_signal_strength", "Pss", 1782 SignalStrength.SIGNAL_STRENGTH_NAMES, 1783 new String[] { "0", "1", "2", "3", "4" }), 1784 new BitDescription(HistoryItem.STATE_BRIGHTNESS_MASK, 1785 HistoryItem.STATE_BRIGHTNESS_SHIFT, "brightness", "Sb", 1786 SCREEN_BRIGHTNESS_NAMES, SCREEN_BRIGHTNESS_SHORT_NAMES), 1787 }; 1788 1789 public static final BitDescription[] HISTORY_STATE2_DESCRIPTIONS 1790 = new BitDescription[] { 1791 new BitDescription(HistoryItem.STATE2_POWER_SAVE_FLAG, "power_save", "ps"), 1792 new BitDescription(HistoryItem.STATE2_VIDEO_ON_FLAG, "video", "v"), 1793 new BitDescription(HistoryItem.STATE2_WIFI_RUNNING_FLAG, "wifi_running", "Ww"), 1794 new BitDescription(HistoryItem.STATE2_WIFI_ON_FLAG, "wifi", "W"), 1795 new BitDescription(HistoryItem.STATE2_FLASHLIGHT_FLAG, "flashlight", "fl"), 1796 new BitDescription(HistoryItem.STATE2_DEVICE_IDLE_FLAG, "device_idle", "di"), 1797 new BitDescription(HistoryItem.STATE2_CHARGING_FLAG, "charging", "ch"), 1798 new BitDescription(HistoryItem.STATE2_PHONE_IN_CALL_FLAG, "phone_in_call", "Pcl"), 1799 new BitDescription(HistoryItem.STATE2_BLUETOOTH_ON_FLAG, "bluetooth", "b"), 1800 new BitDescription(HistoryItem.STATE2_WIFI_SIGNAL_STRENGTH_MASK, 1801 HistoryItem.STATE2_WIFI_SIGNAL_STRENGTH_SHIFT, "wifi_signal_strength", "Wss", 1802 new String[] { "0", "1", "2", "3", "4" }, 1803 new String[] { "0", "1", "2", "3", "4" }), 1804 new BitDescription(HistoryItem.STATE2_WIFI_SUPPL_STATE_MASK, 1805 HistoryItem.STATE2_WIFI_SUPPL_STATE_SHIFT, "wifi_suppl", "Wsp", 1806 WIFI_SUPPL_STATE_NAMES, WIFI_SUPPL_STATE_SHORT_NAMES), 1807 }; 1808 1809 public static final String[] HISTORY_EVENT_NAMES = new String[] { 1810 "null", "proc", "fg", "top", "sync", "wake_lock_in", "job", "user", "userfg", "conn", 1811 "motion", "active", "pkginst", "pkgunin", "alarm", "stats" 1812 }; 1813 1814 public static final String[] HISTORY_EVENT_CHECKIN_NAMES = new String[] { 1815 "Enl", "Epr", "Efg", "Etp", "Esy", "Ewl", "Ejb", "Eur", "Euf", "Ecn", 1816 "Esm", "Eac", "Epi", "Epu", "Eal", "Est" 1817 }; 1818 1819 /** 1820 * Returns the time in microseconds that wifi has been on while the device was 1821 * running on battery. 1822 * 1823 * {@hide} 1824 */ 1825 public abstract long getWifiOnTime(long elapsedRealtimeUs, int which); 1826 1827 /** 1828 * Returns the time in microseconds that wifi has been on and the driver has 1829 * been in the running state while the device was running on battery. 1830 * 1831 * {@hide} 1832 */ 1833 public abstract long getGlobalWifiRunningTime(long elapsedRealtimeUs, int which); 1834 1835 public static final int WIFI_STATE_OFF = 0; 1836 public static final int WIFI_STATE_OFF_SCANNING = 1; 1837 public static final int WIFI_STATE_ON_NO_NETWORKS = 2; 1838 public static final int WIFI_STATE_ON_DISCONNECTED = 3; 1839 public static final int WIFI_STATE_ON_CONNECTED_STA = 4; 1840 public static final int WIFI_STATE_ON_CONNECTED_P2P = 5; 1841 public static final int WIFI_STATE_ON_CONNECTED_STA_P2P = 6; 1842 public static final int WIFI_STATE_SOFT_AP = 7; 1843 1844 static final String[] WIFI_STATE_NAMES = { 1845 "off", "scanning", "no_net", "disconn", 1846 "sta", "p2p", "sta_p2p", "soft_ap" 1847 }; 1848 1849 public static final int NUM_WIFI_STATES = WIFI_STATE_SOFT_AP+1; 1850 1851 /** 1852 * Returns the time in microseconds that WiFi has been running in the given state. 1853 * 1854 * {@hide} 1855 */ 1856 public abstract long getWifiStateTime(int wifiState, 1857 long elapsedRealtimeUs, int which); 1858 1859 /** 1860 * Returns the number of times that WiFi has entered the given state. 1861 * 1862 * {@hide} 1863 */ 1864 public abstract int getWifiStateCount(int wifiState, int which); 1865 1866 /** 1867 * Returns the time in microseconds that the wifi supplicant has been 1868 * in a given state. 1869 * 1870 * {@hide} 1871 */ 1872 public abstract long getWifiSupplStateTime(int state, long elapsedRealtimeUs, int which); 1873 1874 /** 1875 * Returns the number of times that the wifi supplicant has transitioned 1876 * to a given state. 1877 * 1878 * {@hide} 1879 */ 1880 public abstract int getWifiSupplStateCount(int state, int which); 1881 1882 public static final int NUM_WIFI_SIGNAL_STRENGTH_BINS = 5; 1883 1884 /** 1885 * Returns the time in microseconds that WIFI has been running with 1886 * the given signal strength. 1887 * 1888 * {@hide} 1889 */ 1890 public abstract long getWifiSignalStrengthTime(int strengthBin, 1891 long elapsedRealtimeUs, int which); 1892 1893 /** 1894 * Returns the number of times WIFI has entered the given signal strength. 1895 * 1896 * {@hide} 1897 */ 1898 public abstract int getWifiSignalStrengthCount(int strengthBin, int which); 1899 1900 /** 1901 * Returns the time in microseconds that bluetooth has been on while the device was 1902 * running on battery. 1903 * 1904 * {@hide} 1905 */ 1906 public abstract long getBluetoothOnTime(long elapsedRealtimeUs, int which); 1907 1908 public abstract int getBluetoothPingCount(); 1909 1910 public static final int BLUETOOTH_STATE_INACTIVE = 0; 1911 public static final int BLUETOOTH_STATE_LOW = 1; 1912 public static final int BLUETOOTH_STATE_MEDIUM = 2; 1913 public static final int BLUETOOTH_STATE_HIGH = 3; 1914 1915 static final String[] BLUETOOTH_STATE_NAMES = { 1916 "inactive", "low", "med", "high" 1917 }; 1918 1919 public static final int NUM_BLUETOOTH_STATES = BLUETOOTH_STATE_HIGH +1; 1920 1921 /** 1922 * Returns the time in microseconds that Bluetooth has been running in the 1923 * given active state. 1924 * 1925 * {@hide} 1926 */ 1927 public abstract long getBluetoothStateTime(int bluetoothState, 1928 long elapsedRealtimeUs, int which); 1929 1930 /** 1931 * Returns the number of times that Bluetooth has entered the given active state. 1932 * 1933 * {@hide} 1934 */ 1935 public abstract int getBluetoothStateCount(int bluetoothState, int which); 1936 1937 /** 1938 * Returns the time in microseconds that the flashlight has been on while the device was 1939 * running on battery. 1940 * 1941 * {@hide} 1942 */ 1943 public abstract long getFlashlightOnTime(long elapsedRealtimeUs, int which); 1944 1945 /** 1946 * Returns the number of times that the flashlight has been turned on while the device was 1947 * running on battery. 1948 * 1949 * {@hide} 1950 */ 1951 public abstract long getFlashlightOnCount(int which); 1952 1953 public static final int NETWORK_MOBILE_RX_DATA = 0; 1954 public static final int NETWORK_MOBILE_TX_DATA = 1; 1955 public static final int NETWORK_WIFI_RX_DATA = 2; 1956 public static final int NETWORK_WIFI_TX_DATA = 3; 1957 public static final int NUM_NETWORK_ACTIVITY_TYPES = NETWORK_WIFI_TX_DATA + 1; 1958 1959 public abstract long getNetworkActivityBytes(int type, int which); 1960 public abstract long getNetworkActivityPackets(int type, int which); 1961 1962 public static final int CONTROLLER_IDLE_TIME = 0; 1963 public static final int CONTROLLER_RX_TIME = 1; 1964 public static final int CONTROLLER_TX_TIME = 2; 1965 public static final int CONTROLLER_POWER_DRAIN = 3; 1966 public static final int NUM_CONTROLLER_ACTIVITY_TYPES = CONTROLLER_POWER_DRAIN + 1; 1967 1968 /** 1969 * Returns true if the BatteryStats object has detailed bluetooth power reports. 1970 * When true, calling {@link #getBluetoothControllerActivity(int, int)} will yield the 1971 * actual power data. 1972 */ 1973 public abstract boolean hasBluetoothActivityReporting(); 1974 1975 /** 1976 * For {@link #CONTROLLER_IDLE_TIME}, {@link #CONTROLLER_RX_TIME}, and 1977 * {@link #CONTROLLER_TX_TIME}, returns the time spent (in milliseconds) in the 1978 * respective state. 1979 * For {@link #CONTROLLER_POWER_DRAIN}, returns the power used by the controller in 1980 * milli-ampere-milliseconds (mAms). 1981 */ 1982 public abstract long getBluetoothControllerActivity(int type, int which); 1983 1984 /** 1985 * Returns true if the BatteryStats object has detailed WiFi power reports. 1986 * When true, calling {@link #getWifiControllerActivity(int, int)} will yield the 1987 * actual power data. 1988 */ 1989 public abstract boolean hasWifiActivityReporting(); 1990 1991 /** 1992 * For {@link #CONTROLLER_IDLE_TIME}, {@link #CONTROLLER_RX_TIME}, and 1993 * {@link #CONTROLLER_TX_TIME}, returns the time spent (in milliseconds) in the 1994 * respective state. 1995 * For {@link #CONTROLLER_POWER_DRAIN}, returns the power used by the controller in 1996 * milli-ampere-milliseconds (mAms). 1997 */ 1998 public abstract long getWifiControllerActivity(int type, int which); 1999 2000 /** 2001 * Return the wall clock time when battery stats data collection started. 2002 */ 2003 public abstract long getStartClockTime(); 2004 2005 /** 2006 * Return platform version tag that we were running in when the battery stats started. 2007 */ 2008 public abstract String getStartPlatformVersion(); 2009 2010 /** 2011 * Return platform version tag that we were running in when the battery stats ended. 2012 */ 2013 public abstract String getEndPlatformVersion(); 2014 2015 /** 2016 * Return the internal version code of the parcelled format. 2017 */ 2018 public abstract int getParcelVersion(); 2019 2020 /** 2021 * Return whether we are currently running on battery. 2022 */ 2023 public abstract boolean getIsOnBattery(); 2024 2025 /** 2026 * Returns a SparseArray containing the statistics for each uid. 2027 */ 2028 public abstract SparseArray<? extends Uid> getUidStats(); 2029 2030 /** 2031 * Returns the current battery uptime in microseconds. 2032 * 2033 * @param curTime the amount of elapsed realtime in microseconds. 2034 */ 2035 public abstract long getBatteryUptime(long curTime); 2036 2037 /** 2038 * Returns the current battery realtime in microseconds. 2039 * 2040 * @param curTime the amount of elapsed realtime in microseconds. 2041 */ 2042 public abstract long getBatteryRealtime(long curTime); 2043 2044 /** 2045 * Returns the battery percentage level at the last time the device was unplugged from power, or 2046 * the last time it booted on battery power. 2047 */ 2048 public abstract int getDischargeStartLevel(); 2049 2050 /** 2051 * Returns the current battery percentage level if we are in a discharge cycle, otherwise 2052 * returns the level at the last plug event. 2053 */ 2054 public abstract int getDischargeCurrentLevel(); 2055 2056 /** 2057 * Get the amount the battery has discharged since the stats were 2058 * last reset after charging, as a lower-end approximation. 2059 */ 2060 public abstract int getLowDischargeAmountSinceCharge(); 2061 2062 /** 2063 * Get the amount the battery has discharged since the stats were 2064 * last reset after charging, as an upper-end approximation. 2065 */ 2066 public abstract int getHighDischargeAmountSinceCharge(); 2067 2068 /** 2069 * Retrieve the discharge amount over the selected discharge period <var>which</var>. 2070 */ 2071 public abstract int getDischargeAmount(int which); 2072 2073 /** 2074 * Get the amount the battery has discharged while the screen was on, 2075 * since the last time power was unplugged. 2076 */ 2077 public abstract int getDischargeAmountScreenOn(); 2078 2079 /** 2080 * Get the amount the battery has discharged while the screen was on, 2081 * since the last time the device was charged. 2082 */ 2083 public abstract int getDischargeAmountScreenOnSinceCharge(); 2084 2085 /** 2086 * Get the amount the battery has discharged while the screen was off, 2087 * since the last time power was unplugged. 2088 */ 2089 public abstract int getDischargeAmountScreenOff(); 2090 2091 /** 2092 * Get the amount the battery has discharged while the screen was off, 2093 * since the last time the device was charged. 2094 */ 2095 public abstract int getDischargeAmountScreenOffSinceCharge(); 2096 2097 /** 2098 * Returns the total, last, or current battery uptime in microseconds. 2099 * 2100 * @param curTime the elapsed realtime in microseconds. 2101 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2102 */ 2103 public abstract long computeBatteryUptime(long curTime, int which); 2104 2105 /** 2106 * Returns the total, last, or current battery realtime in microseconds. 2107 * 2108 * @param curTime the current elapsed realtime in microseconds. 2109 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2110 */ 2111 public abstract long computeBatteryRealtime(long curTime, int which); 2112 2113 /** 2114 * Returns the total, last, or current battery screen off uptime in microseconds. 2115 * 2116 * @param curTime the elapsed realtime in microseconds. 2117 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2118 */ 2119 public abstract long computeBatteryScreenOffUptime(long curTime, int which); 2120 2121 /** 2122 * Returns the total, last, or current battery screen off realtime in microseconds. 2123 * 2124 * @param curTime the current elapsed realtime in microseconds. 2125 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2126 */ 2127 public abstract long computeBatteryScreenOffRealtime(long curTime, int which); 2128 2129 /** 2130 * Returns the total, last, or current uptime in microseconds. 2131 * 2132 * @param curTime the current elapsed realtime in microseconds. 2133 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2134 */ 2135 public abstract long computeUptime(long curTime, int which); 2136 2137 /** 2138 * Returns the total, last, or current realtime in microseconds. 2139 * 2140 * @param curTime the current elapsed realtime in microseconds. 2141 * @param which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2142 */ 2143 public abstract long computeRealtime(long curTime, int which); 2144 2145 /** 2146 * Compute an approximation for how much run time (in microseconds) is remaining on 2147 * the battery. Returns -1 if no time can be computed: either there is not 2148 * enough current data to make a decision, or the battery is currently 2149 * charging. 2150 * 2151 * @param curTime The current elepsed realtime in microseconds. 2152 */ 2153 public abstract long computeBatteryTimeRemaining(long curTime); 2154 2155 // The part of a step duration that is the actual time. 2156 public static final long STEP_LEVEL_TIME_MASK = 0x000000ffffffffffL; 2157 2158 // Bits in a step duration that are the new battery level we are at. 2159 public static final long STEP_LEVEL_LEVEL_MASK = 0x0000ff0000000000L; 2160 public static final int STEP_LEVEL_LEVEL_SHIFT = 40; 2161 2162 // Bits in a step duration that are the initial mode we were in at that step. 2163 public static final long STEP_LEVEL_INITIAL_MODE_MASK = 0x00ff000000000000L; 2164 public static final int STEP_LEVEL_INITIAL_MODE_SHIFT = 48; 2165 2166 // Bits in a step duration that indicate which modes changed during that step. 2167 public static final long STEP_LEVEL_MODIFIED_MODE_MASK = 0xff00000000000000L; 2168 public static final int STEP_LEVEL_MODIFIED_MODE_SHIFT = 56; 2169 2170 // Step duration mode: the screen is on, off, dozed, etc; value is Display.STATE_* - 1. 2171 public static final int STEP_LEVEL_MODE_SCREEN_STATE = 0x03; 2172 2173 // Step duration mode: power save is on. 2174 public static final int STEP_LEVEL_MODE_POWER_SAVE = 0x04; 2175 2176 // Step duration mode: device is currently in idle mode. 2177 public static final int STEP_LEVEL_MODE_DEVICE_IDLE = 0x08; 2178 2179 public static final int[] STEP_LEVEL_MODES_OF_INTEREST = new int[] { 2180 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE, 2181 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE|STEP_LEVEL_MODE_DEVICE_IDLE, 2182 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_DEVICE_IDLE, 2183 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE, 2184 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE, 2185 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE, 2186 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE, 2187 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE, 2188 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_POWER_SAVE|STEP_LEVEL_MODE_DEVICE_IDLE, 2189 STEP_LEVEL_MODE_SCREEN_STATE|STEP_LEVEL_MODE_DEVICE_IDLE, 2190 }; 2191 public static final int[] STEP_LEVEL_MODE_VALUES = new int[] { 2192 (Display.STATE_OFF-1), 2193 (Display.STATE_OFF-1)|STEP_LEVEL_MODE_POWER_SAVE, 2194 (Display.STATE_OFF-1)|STEP_LEVEL_MODE_DEVICE_IDLE, 2195 (Display.STATE_ON-1), 2196 (Display.STATE_ON-1)|STEP_LEVEL_MODE_POWER_SAVE, 2197 (Display.STATE_DOZE-1), 2198 (Display.STATE_DOZE-1)|STEP_LEVEL_MODE_POWER_SAVE, 2199 (Display.STATE_DOZE_SUSPEND-1), 2200 (Display.STATE_DOZE_SUSPEND-1)|STEP_LEVEL_MODE_POWER_SAVE, 2201 (Display.STATE_DOZE_SUSPEND-1)|STEP_LEVEL_MODE_DEVICE_IDLE, 2202 }; 2203 public static final String[] STEP_LEVEL_MODE_LABELS = new String[] { 2204 "screen off", 2205 "screen off power save", 2206 "screen off device idle", 2207 "screen on", 2208 "screen on power save", 2209 "screen doze", 2210 "screen doze power save", 2211 "screen doze-suspend", 2212 "screen doze-suspend power save", 2213 "screen doze-suspend device idle", 2214 }; 2215 2216 /** 2217 * Return the array of discharge step durations. 2218 */ 2219 public abstract LevelStepTracker getDischargeLevelStepTracker(); 2220 2221 /** 2222 * Return the array of daily discharge step durations. 2223 */ 2224 public abstract LevelStepTracker getDailyDischargeLevelStepTracker(); 2225 2226 /** 2227 * Compute an approximation for how much time (in microseconds) remains until the battery 2228 * is fully charged. Returns -1 if no time can be computed: either there is not 2229 * enough current data to make a decision, or the battery is currently 2230 * discharging. 2231 * 2232 * @param curTime The current elepsed realtime in microseconds. 2233 */ 2234 public abstract long computeChargeTimeRemaining(long curTime); 2235 2236 /** 2237 * Return the array of charge step durations. 2238 */ 2239 public abstract LevelStepTracker getChargeLevelStepTracker(); 2240 2241 /** 2242 * Return the array of daily charge step durations. 2243 */ 2244 public abstract LevelStepTracker getDailyChargeLevelStepTracker(); 2245 2246 public abstract ArrayList<PackageChange> getDailyPackageChanges(); 2247 2248 public abstract Map<String, ? extends Timer> getWakeupReasonStats(); 2249 2250 public abstract Map<String, ? extends Timer> getKernelWakelockStats(); 2251 2252 /** Returns the number of different speeds that the CPU can run at */ 2253 public abstract int getCpuSpeedSteps(); 2254 2255 public abstract void writeToParcelWithoutUids(Parcel out, int flags); 2256 2257 private final static void formatTimeRaw(StringBuilder out, long seconds) { 2258 long days = seconds / (60 * 60 * 24); 2259 if (days != 0) { 2260 out.append(days); 2261 out.append("d "); 2262 } 2263 long used = days * 60 * 60 * 24; 2264 2265 long hours = (seconds - used) / (60 * 60); 2266 if (hours != 0 || used != 0) { 2267 out.append(hours); 2268 out.append("h "); 2269 } 2270 used += hours * 60 * 60; 2271 2272 long mins = (seconds-used) / 60; 2273 if (mins != 0 || used != 0) { 2274 out.append(mins); 2275 out.append("m "); 2276 } 2277 used += mins * 60; 2278 2279 if (seconds != 0 || used != 0) { 2280 out.append(seconds-used); 2281 out.append("s "); 2282 } 2283 } 2284 2285 public final static void formatTimeMs(StringBuilder sb, long time) { 2286 long sec = time / 1000; 2287 formatTimeRaw(sb, sec); 2288 sb.append(time - (sec * 1000)); 2289 sb.append("ms "); 2290 } 2291 2292 public final static void formatTimeMsNoSpace(StringBuilder sb, long time) { 2293 long sec = time / 1000; 2294 formatTimeRaw(sb, sec); 2295 sb.append(time - (sec * 1000)); 2296 sb.append("ms"); 2297 } 2298 2299 public final String formatRatioLocked(long num, long den) { 2300 if (den == 0L) { 2301 return "--%"; 2302 } 2303 float perc = ((float)num) / ((float)den) * 100; 2304 mFormatBuilder.setLength(0); 2305 mFormatter.format("%.1f%%", perc); 2306 return mFormatBuilder.toString(); 2307 } 2308 2309 final String formatBytesLocked(long bytes) { 2310 mFormatBuilder.setLength(0); 2311 2312 if (bytes < BYTES_PER_KB) { 2313 return bytes + "B"; 2314 } else if (bytes < BYTES_PER_MB) { 2315 mFormatter.format("%.2fKB", bytes / (double) BYTES_PER_KB); 2316 return mFormatBuilder.toString(); 2317 } else if (bytes < BYTES_PER_GB){ 2318 mFormatter.format("%.2fMB", bytes / (double) BYTES_PER_MB); 2319 return mFormatBuilder.toString(); 2320 } else { 2321 mFormatter.format("%.2fGB", bytes / (double) BYTES_PER_GB); 2322 return mFormatBuilder.toString(); 2323 } 2324 } 2325 2326 private static long computeWakeLock(Timer timer, long elapsedRealtimeUs, int which) { 2327 if (timer != null) { 2328 // Convert from microseconds to milliseconds with rounding 2329 long totalTimeMicros = timer.getTotalTimeLocked(elapsedRealtimeUs, which); 2330 long totalTimeMillis = (totalTimeMicros + 500) / 1000; 2331 return totalTimeMillis; 2332 } 2333 return 0; 2334 } 2335 2336 /** 2337 * 2338 * @param sb a StringBuilder object. 2339 * @param timer a Timer object contining the wakelock times. 2340 * @param elapsedRealtimeUs the current on-battery time in microseconds. 2341 * @param name the name of the wakelock. 2342 * @param which which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2343 * @param linePrefix a String to be prepended to each line of output. 2344 * @return the line prefix 2345 */ 2346 private static final String printWakeLock(StringBuilder sb, Timer timer, 2347 long elapsedRealtimeUs, String name, int which, String linePrefix) { 2348 2349 if (timer != null) { 2350 long totalTimeMillis = computeWakeLock(timer, elapsedRealtimeUs, which); 2351 2352 int count = timer.getCountLocked(which); 2353 if (totalTimeMillis != 0) { 2354 sb.append(linePrefix); 2355 formatTimeMs(sb, totalTimeMillis); 2356 if (name != null) { 2357 sb.append(name); 2358 sb.append(' '); 2359 } 2360 sb.append('('); 2361 sb.append(count); 2362 sb.append(" times)"); 2363 return ", "; 2364 } 2365 } 2366 return linePrefix; 2367 } 2368 2369 /** 2370 * Checkin version of wakelock printer. Prints simple comma-separated list. 2371 * 2372 * @param sb a StringBuilder object. 2373 * @param timer a Timer object contining the wakelock times. 2374 * @param elapsedRealtimeUs the current time in microseconds. 2375 * @param name the name of the wakelock. 2376 * @param which which one of STATS_SINCE_CHARGED, STATS_SINCE_UNPLUGGED, or STATS_CURRENT. 2377 * @param linePrefix a String to be prepended to each line of output. 2378 * @return the line prefix 2379 */ 2380 private static final String printWakeLockCheckin(StringBuilder sb, Timer timer, 2381 long elapsedRealtimeUs, String name, int which, String linePrefix) { 2382 long totalTimeMicros = 0; 2383 int count = 0; 2384 if (timer != null) { 2385 totalTimeMicros = timer.getTotalTimeLocked(elapsedRealtimeUs, which); 2386 count = timer.getCountLocked(which); 2387 } 2388 sb.append(linePrefix); 2389 sb.append((totalTimeMicros + 500) / 1000); // microseconds to milliseconds with rounding 2390 sb.append(','); 2391 sb.append(name != null ? name + "," : ""); 2392 sb.append(count); 2393 return ","; 2394 } 2395 2396 /** 2397 * Dump a comma-separated line of values for terse checkin mode. 2398 * 2399 * @param pw the PageWriter to dump log to 2400 * @param category category of data (e.g. "total", "last", "unplugged", "current" ) 2401 * @param type type of data (e.g. "wakelock", "sensor", "process", "apk" , "process", "network") 2402 * @param args type-dependent data arguments 2403 */ 2404 private static final void dumpLine(PrintWriter pw, int uid, String category, String type, 2405 Object... args ) { 2406 pw.print(BATTERY_STATS_CHECKIN_VERSION); pw.print(','); 2407 pw.print(uid); pw.print(','); 2408 pw.print(category); pw.print(','); 2409 pw.print(type); 2410 2411 for (Object arg : args) { 2412 pw.print(','); 2413 pw.print(arg); 2414 } 2415 pw.println(); 2416 } 2417 2418 /** 2419 * Temporary for settings. 2420 */ 2421 public final void dumpCheckinLocked(Context context, PrintWriter pw, int which, int reqUid) { 2422 dumpCheckinLocked(context, pw, which, reqUid, BatteryStatsHelper.checkWifiOnly(context)); 2423 } 2424 2425 /** 2426 * Checkin server version of dump to produce more compact, computer-readable log. 2427 * 2428 * NOTE: all times are expressed in 'ms'. 2429 */ 2430 public final void dumpCheckinLocked(Context context, PrintWriter pw, int which, int reqUid, 2431 boolean wifiOnly) { 2432 final long rawUptime = SystemClock.uptimeMillis() * 1000; 2433 final long rawRealtime = SystemClock.elapsedRealtime() * 1000; 2434 final long batteryUptime = getBatteryUptime(rawUptime); 2435 final long whichBatteryUptime = computeBatteryUptime(rawUptime, which); 2436 final long whichBatteryRealtime = computeBatteryRealtime(rawRealtime, which); 2437 final long whichBatteryScreenOffUptime = computeBatteryScreenOffUptime(rawUptime, which); 2438 final long whichBatteryScreenOffRealtime = computeBatteryScreenOffRealtime(rawRealtime, 2439 which); 2440 final long totalRealtime = computeRealtime(rawRealtime, which); 2441 final long totalUptime = computeUptime(rawUptime, which); 2442 final long screenOnTime = getScreenOnTime(rawRealtime, which); 2443 final long interactiveTime = getInteractiveTime(rawRealtime, which); 2444 final long powerSaveModeEnabledTime = getPowerSaveModeEnabledTime(rawRealtime, which); 2445 final long deviceIdleModeEnabledTime = getDeviceIdleModeEnabledTime(rawRealtime, which); 2446 final long deviceIdlingTime = getDeviceIdlingTime(rawRealtime, which); 2447 final int connChanges = getNumConnectivityChange(which); 2448 final long phoneOnTime = getPhoneOnTime(rawRealtime, which); 2449 final long wifiOnTime = getWifiOnTime(rawRealtime, which); 2450 final long wifiRunningTime = getGlobalWifiRunningTime(rawRealtime, which); 2451 final long bluetoothOnTime = getBluetoothOnTime(rawRealtime, which); 2452 2453 final StringBuilder sb = new StringBuilder(128); 2454 2455 final SparseArray<? extends Uid> uidStats = getUidStats(); 2456 final int NU = uidStats.size(); 2457 2458 final String category = STAT_NAMES[which]; 2459 2460 // Dump "battery" stat 2461 dumpLine(pw, 0 /* uid */, category, BATTERY_DATA, 2462 which == STATS_SINCE_CHARGED ? getStartCount() : "N/A", 2463 whichBatteryRealtime / 1000, whichBatteryUptime / 1000, 2464 totalRealtime / 1000, totalUptime / 1000, 2465 getStartClockTime(), 2466 whichBatteryScreenOffRealtime / 1000, whichBatteryScreenOffUptime / 1000); 2467 2468 // Calculate wakelock times across all uids. 2469 long fullWakeLockTimeTotal = 0; 2470 long partialWakeLockTimeTotal = 0; 2471 2472 for (int iu = 0; iu < NU; iu++) { 2473 final Uid u = uidStats.valueAt(iu); 2474 2475 final ArrayMap<String, ? extends BatteryStats.Uid.Wakelock> wakelocks 2476 = u.getWakelockStats(); 2477 for (int iw=wakelocks.size()-1; iw>=0; iw--) { 2478 final Uid.Wakelock wl = wakelocks.valueAt(iw); 2479 2480 final Timer fullWakeTimer = wl.getWakeTime(WAKE_TYPE_FULL); 2481 if (fullWakeTimer != null) { 2482 fullWakeLockTimeTotal += fullWakeTimer.getTotalTimeLocked(rawRealtime, 2483 which); 2484 } 2485 2486 final Timer partialWakeTimer = wl.getWakeTime(WAKE_TYPE_PARTIAL); 2487 if (partialWakeTimer != null) { 2488 partialWakeLockTimeTotal += partialWakeTimer.getTotalTimeLocked( 2489 rawRealtime, which); 2490 } 2491 } 2492 } 2493 2494 final long mobileRxTotalBytes = getNetworkActivityBytes(NETWORK_MOBILE_RX_DATA, which); 2495 final long mobileTxTotalBytes = getNetworkActivityBytes(NETWORK_MOBILE_TX_DATA, which); 2496 final long wifiRxTotalBytes = getNetworkActivityBytes(NETWORK_WIFI_RX_DATA, which); 2497 final long wifiTxTotalBytes = getNetworkActivityBytes(NETWORK_WIFI_TX_DATA, which); 2498 final long mobileRxTotalPackets = getNetworkActivityPackets(NETWORK_MOBILE_RX_DATA, which); 2499 final long mobileTxTotalPackets = getNetworkActivityPackets(NETWORK_MOBILE_TX_DATA, which); 2500 final long wifiRxTotalPackets = getNetworkActivityPackets(NETWORK_WIFI_RX_DATA, which); 2501 final long wifiTxTotalPackets = getNetworkActivityPackets(NETWORK_WIFI_TX_DATA, which); 2502 2503 // Dump network stats 2504 dumpLine(pw, 0 /* uid */, category, GLOBAL_NETWORK_DATA, 2505 mobileRxTotalBytes, mobileTxTotalBytes, wifiRxTotalBytes, wifiTxTotalBytes, 2506 mobileRxTotalPackets, mobileTxTotalPackets, wifiRxTotalPackets, wifiTxTotalPackets); 2507 2508 // Dump misc stats 2509 dumpLine(pw, 0 /* uid */, category, MISC_DATA, 2510 screenOnTime / 1000, phoneOnTime / 1000, wifiOnTime / 1000, 2511 wifiRunningTime / 1000, bluetoothOnTime / 1000, 2512 mobileRxTotalBytes, mobileTxTotalBytes, wifiRxTotalBytes, wifiTxTotalBytes, 2513 fullWakeLockTimeTotal / 1000, partialWakeLockTimeTotal / 1000, 2514 0 /*legacy input event count*/, getMobileRadioActiveTime(rawRealtime, which) / 1000, 2515 getMobileRadioActiveAdjustedTime(which) / 1000, interactiveTime / 1000, 2516 powerSaveModeEnabledTime / 1000, connChanges, deviceIdleModeEnabledTime / 1000, 2517 getDeviceIdleModeEnabledCount(which), deviceIdlingTime / 1000, 2518 getDeviceIdlingCount(which)); 2519 2520 // Dump screen brightness stats 2521 Object[] args = new Object[NUM_SCREEN_BRIGHTNESS_BINS]; 2522 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) { 2523 args[i] = getScreenBrightnessTime(i, rawRealtime, which) / 1000; 2524 } 2525 dumpLine(pw, 0 /* uid */, category, SCREEN_BRIGHTNESS_DATA, args); 2526 2527 // Dump signal strength stats 2528 args = new Object[SignalStrength.NUM_SIGNAL_STRENGTH_BINS]; 2529 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) { 2530 args[i] = getPhoneSignalStrengthTime(i, rawRealtime, which) / 1000; 2531 } 2532 dumpLine(pw, 0 /* uid */, category, SIGNAL_STRENGTH_TIME_DATA, args); 2533 dumpLine(pw, 0 /* uid */, category, SIGNAL_SCANNING_TIME_DATA, 2534 getPhoneSignalScanningTime(rawRealtime, which) / 1000); 2535 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) { 2536 args[i] = getPhoneSignalStrengthCount(i, which); 2537 } 2538 dumpLine(pw, 0 /* uid */, category, SIGNAL_STRENGTH_COUNT_DATA, args); 2539 2540 // Dump network type stats 2541 args = new Object[NUM_DATA_CONNECTION_TYPES]; 2542 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) { 2543 args[i] = getPhoneDataConnectionTime(i, rawRealtime, which) / 1000; 2544 } 2545 dumpLine(pw, 0 /* uid */, category, DATA_CONNECTION_TIME_DATA, args); 2546 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) { 2547 args[i] = getPhoneDataConnectionCount(i, which); 2548 } 2549 dumpLine(pw, 0 /* uid */, category, DATA_CONNECTION_COUNT_DATA, args); 2550 2551 // Dump wifi state stats 2552 args = new Object[NUM_WIFI_STATES]; 2553 for (int i=0; i<NUM_WIFI_STATES; i++) { 2554 args[i] = getWifiStateTime(i, rawRealtime, which) / 1000; 2555 } 2556 dumpLine(pw, 0 /* uid */, category, WIFI_STATE_TIME_DATA, args); 2557 for (int i=0; i<NUM_WIFI_STATES; i++) { 2558 args[i] = getWifiStateCount(i, which); 2559 } 2560 dumpLine(pw, 0 /* uid */, category, WIFI_STATE_COUNT_DATA, args); 2561 2562 // Dump wifi suppl state stats 2563 args = new Object[NUM_WIFI_SUPPL_STATES]; 2564 for (int i=0; i<NUM_WIFI_SUPPL_STATES; i++) { 2565 args[i] = getWifiSupplStateTime(i, rawRealtime, which) / 1000; 2566 } 2567 dumpLine(pw, 0 /* uid */, category, WIFI_SUPPL_STATE_TIME_DATA, args); 2568 for (int i=0; i<NUM_WIFI_SUPPL_STATES; i++) { 2569 args[i] = getWifiSupplStateCount(i, which); 2570 } 2571 dumpLine(pw, 0 /* uid */, category, WIFI_SUPPL_STATE_COUNT_DATA, args); 2572 2573 // Dump wifi signal strength stats 2574 args = new Object[NUM_WIFI_SIGNAL_STRENGTH_BINS]; 2575 for (int i=0; i<NUM_WIFI_SIGNAL_STRENGTH_BINS; i++) { 2576 args[i] = getWifiSignalStrengthTime(i, rawRealtime, which) / 1000; 2577 } 2578 dumpLine(pw, 0 /* uid */, category, WIFI_SIGNAL_STRENGTH_TIME_DATA, args); 2579 for (int i=0; i<NUM_WIFI_SIGNAL_STRENGTH_BINS; i++) { 2580 args[i] = getWifiSignalStrengthCount(i, which); 2581 } 2582 dumpLine(pw, 0 /* uid */, category, WIFI_SIGNAL_STRENGTH_COUNT_DATA, args); 2583 2584 // Dump bluetooth state stats 2585 args = new Object[NUM_BLUETOOTH_STATES]; 2586 for (int i=0; i<NUM_BLUETOOTH_STATES; i++) { 2587 args[i] = getBluetoothStateTime(i, rawRealtime, which) / 1000; 2588 } 2589 dumpLine(pw, 0 /* uid */, category, BLUETOOTH_STATE_TIME_DATA, args); 2590 for (int i=0; i<NUM_BLUETOOTH_STATES; i++) { 2591 args[i] = getBluetoothStateCount(i, which); 2592 } 2593 dumpLine(pw, 0 /* uid */, category, BLUETOOTH_STATE_COUNT_DATA, args); 2594 2595 if (which == STATS_SINCE_UNPLUGGED) { 2596 dumpLine(pw, 0 /* uid */, category, BATTERY_LEVEL_DATA, getDischargeStartLevel(), 2597 getDischargeCurrentLevel()); 2598 } 2599 2600 if (which == STATS_SINCE_UNPLUGGED) { 2601 dumpLine(pw, 0 /* uid */, category, BATTERY_DISCHARGE_DATA, 2602 getDischargeStartLevel()-getDischargeCurrentLevel(), 2603 getDischargeStartLevel()-getDischargeCurrentLevel(), 2604 getDischargeAmountScreenOn(), getDischargeAmountScreenOff()); 2605 } else { 2606 dumpLine(pw, 0 /* uid */, category, BATTERY_DISCHARGE_DATA, 2607 getLowDischargeAmountSinceCharge(), getHighDischargeAmountSinceCharge(), 2608 getDischargeAmountScreenOnSinceCharge(), 2609 getDischargeAmountScreenOffSinceCharge()); 2610 } 2611 2612 if (reqUid < 0) { 2613 final Map<String, ? extends Timer> kernelWakelocks = getKernelWakelockStats(); 2614 if (kernelWakelocks.size() > 0) { 2615 for (Map.Entry<String, ? extends Timer> ent : kernelWakelocks.entrySet()) { 2616 sb.setLength(0); 2617 printWakeLockCheckin(sb, ent.getValue(), rawRealtime, null, which, ""); 2618 dumpLine(pw, 0 /* uid */, category, KERNEL_WAKELOCK_DATA, ent.getKey(), 2619 sb.toString()); 2620 } 2621 } 2622 final Map<String, ? extends Timer> wakeupReasons = getWakeupReasonStats(); 2623 if (wakeupReasons.size() > 0) { 2624 for (Map.Entry<String, ? extends Timer> ent : wakeupReasons.entrySet()) { 2625 // Not doing the regular wake lock formatting to remain compatible 2626 // with the old checkin format. 2627 long totalTimeMicros = ent.getValue().getTotalTimeLocked(rawRealtime, which); 2628 int count = ent.getValue().getCountLocked(which); 2629 dumpLine(pw, 0 /* uid */, category, WAKEUP_REASON_DATA, 2630 "\"" + ent.getKey() + "\"", (totalTimeMicros + 500) / 1000, count); 2631 } 2632 } 2633 } 2634 2635 final BatteryStatsHelper helper = new BatteryStatsHelper(context, false, wifiOnly); 2636 helper.create(this); 2637 helper.refreshStats(which, UserHandle.USER_ALL); 2638 final List<BatterySipper> sippers = helper.getUsageList(); 2639 if (sippers != null && sippers.size() > 0) { 2640 dumpLine(pw, 0 /* uid */, category, POWER_USE_SUMMARY_DATA, 2641 BatteryStatsHelper.makemAh(helper.getPowerProfile().getBatteryCapacity()), 2642 BatteryStatsHelper.makemAh(helper.getComputedPower()), 2643 BatteryStatsHelper.makemAh(helper.getMinDrainedPower()), 2644 BatteryStatsHelper.makemAh(helper.getMaxDrainedPower())); 2645 for (int i=0; i<sippers.size(); i++) { 2646 final BatterySipper bs = sippers.get(i); 2647 int uid = 0; 2648 String label; 2649 switch (bs.drainType) { 2650 case IDLE: 2651 label="idle"; 2652 break; 2653 case CELL: 2654 label="cell"; 2655 break; 2656 case PHONE: 2657 label="phone"; 2658 break; 2659 case WIFI: 2660 label="wifi"; 2661 break; 2662 case BLUETOOTH: 2663 label="blue"; 2664 break; 2665 case SCREEN: 2666 label="scrn"; 2667 break; 2668 case FLASHLIGHT: 2669 label="flashlight"; 2670 break; 2671 case APP: 2672 uid = bs.uidObj.getUid(); 2673 label = "uid"; 2674 break; 2675 case USER: 2676 uid = UserHandle.getUid(bs.userId, 0); 2677 label = "user"; 2678 break; 2679 case UNACCOUNTED: 2680 label = "unacc"; 2681 break; 2682 case OVERCOUNTED: 2683 label = "over"; 2684 break; 2685 default: 2686 label = "???"; 2687 } 2688 dumpLine(pw, uid, category, POWER_USE_ITEM_DATA, label, 2689 BatteryStatsHelper.makemAh(bs.totalPowerMah)); 2690 } 2691 } 2692 2693 for (int iu = 0; iu < NU; iu++) { 2694 final int uid = uidStats.keyAt(iu); 2695 if (reqUid >= 0 && uid != reqUid) { 2696 continue; 2697 } 2698 final Uid u = uidStats.valueAt(iu); 2699 // Dump Network stats per uid, if any 2700 final long mobileBytesRx = u.getNetworkActivityBytes(NETWORK_MOBILE_RX_DATA, which); 2701 final long mobileBytesTx = u.getNetworkActivityBytes(NETWORK_MOBILE_TX_DATA, which); 2702 final long wifiBytesRx = u.getNetworkActivityBytes(NETWORK_WIFI_RX_DATA, which); 2703 final long wifiBytesTx = u.getNetworkActivityBytes(NETWORK_WIFI_TX_DATA, which); 2704 final long mobilePacketsRx = u.getNetworkActivityPackets(NETWORK_MOBILE_RX_DATA, which); 2705 final long mobilePacketsTx = u.getNetworkActivityPackets(NETWORK_MOBILE_TX_DATA, which); 2706 final long mobileActiveTime = u.getMobileRadioActiveTime(which); 2707 final int mobileActiveCount = u.getMobileRadioActiveCount(which); 2708 final long wifiPacketsRx = u.getNetworkActivityPackets(NETWORK_WIFI_RX_DATA, which); 2709 final long wifiPacketsTx = u.getNetworkActivityPackets(NETWORK_WIFI_TX_DATA, which); 2710 final long fullWifiLockOnTime = u.getFullWifiLockTime(rawRealtime, which); 2711 final long wifiScanTime = u.getWifiScanTime(rawRealtime, which); 2712 final int wifiScanCount = u.getWifiScanCount(which); 2713 final long uidWifiRunningTime = u.getWifiRunningTime(rawRealtime, which); 2714 2715 if (mobileBytesRx > 0 || mobileBytesTx > 0 || wifiBytesRx > 0 || wifiBytesTx > 0 2716 || mobilePacketsRx > 0 || mobilePacketsTx > 0 || wifiPacketsRx > 0 2717 || wifiPacketsTx > 0 || mobileActiveTime > 0 || mobileActiveCount > 0) { 2718 dumpLine(pw, uid, category, NETWORK_DATA, mobileBytesRx, mobileBytesTx, 2719 wifiBytesRx, wifiBytesTx, 2720 mobilePacketsRx, mobilePacketsTx, 2721 wifiPacketsRx, wifiPacketsTx, 2722 mobileActiveTime, mobileActiveCount); 2723 } 2724 2725 if (fullWifiLockOnTime != 0 || wifiScanTime != 0 || wifiScanCount != 0 2726 || uidWifiRunningTime != 0) { 2727 dumpLine(pw, uid, category, WIFI_DATA, 2728 fullWifiLockOnTime, wifiScanTime, uidWifiRunningTime, wifiScanCount); 2729 } 2730 2731 if (u.hasUserActivity()) { 2732 args = new Object[Uid.NUM_USER_ACTIVITY_TYPES]; 2733 boolean hasData = false; 2734 for (int i=0; i<Uid.NUM_USER_ACTIVITY_TYPES; i++) { 2735 int val = u.getUserActivityCount(i, which); 2736 args[i] = val; 2737 if (val != 0) hasData = true; 2738 } 2739 if (hasData) { 2740 dumpLine(pw, uid /* uid */, category, USER_ACTIVITY_DATA, args); 2741 } 2742 } 2743 2744 final ArrayMap<String, ? extends Uid.Wakelock> wakelocks = u.getWakelockStats(); 2745 for (int iw=wakelocks.size()-1; iw>=0; iw--) { 2746 final Uid.Wakelock wl = wakelocks.valueAt(iw); 2747 String linePrefix = ""; 2748 sb.setLength(0); 2749 linePrefix = printWakeLockCheckin(sb, wl.getWakeTime(WAKE_TYPE_FULL), 2750 rawRealtime, "f", which, linePrefix); 2751 linePrefix = printWakeLockCheckin(sb, wl.getWakeTime(WAKE_TYPE_PARTIAL), 2752 rawRealtime, "p", which, linePrefix); 2753 linePrefix = printWakeLockCheckin(sb, wl.getWakeTime(WAKE_TYPE_WINDOW), 2754 rawRealtime, "w", which, linePrefix); 2755 2756 // Only log if we had at lease one wakelock... 2757 if (sb.length() > 0) { 2758 String name = wakelocks.keyAt(iw); 2759 if (name.indexOf(',') >= 0) { 2760 name = name.replace(',', '_'); 2761 } 2762 dumpLine(pw, uid, category, WAKELOCK_DATA, name, sb.toString()); 2763 } 2764 } 2765 2766 final ArrayMap<String, ? extends Timer> syncs = u.getSyncStats(); 2767 for (int isy=syncs.size()-1; isy>=0; isy--) { 2768 final Timer timer = syncs.valueAt(isy); 2769 // Convert from microseconds to milliseconds with rounding 2770 final long totalTime = (timer.getTotalTimeLocked(rawRealtime, which) + 500) / 1000; 2771 final int count = timer.getCountLocked(which); 2772 if (totalTime != 0) { 2773 dumpLine(pw, uid, category, SYNC_DATA, syncs.keyAt(isy), totalTime, count); 2774 } 2775 } 2776 2777 final ArrayMap<String, ? extends Timer> jobs = u.getJobStats(); 2778 for (int ij=jobs.size()-1; ij>=0; ij--) { 2779 final Timer timer = jobs.valueAt(ij); 2780 // Convert from microseconds to milliseconds with rounding 2781 final long totalTime = (timer.getTotalTimeLocked(rawRealtime, which) + 500) / 1000; 2782 final int count = timer.getCountLocked(which); 2783 if (totalTime != 0) { 2784 dumpLine(pw, uid, category, JOB_DATA, jobs.keyAt(ij), totalTime, count); 2785 } 2786 } 2787 2788 final SparseArray<? extends BatteryStats.Uid.Sensor> sensors = u.getSensorStats(); 2789 final int NSE = sensors.size(); 2790 for (int ise=0; ise<NSE; ise++) { 2791 final Uid.Sensor se = sensors.valueAt(ise); 2792 final int sensorNumber = sensors.keyAt(ise); 2793 final Timer timer = se.getSensorTime(); 2794 if (timer != null) { 2795 // Convert from microseconds to milliseconds with rounding 2796 final long totalTime = (timer.getTotalTimeLocked(rawRealtime, which) + 500) 2797 / 1000; 2798 final int count = timer.getCountLocked(which); 2799 if (totalTime != 0) { 2800 dumpLine(pw, uid, category, SENSOR_DATA, sensorNumber, totalTime, count); 2801 } 2802 } 2803 } 2804 2805 final Timer vibTimer = u.getVibratorOnTimer(); 2806 if (vibTimer != null) { 2807 // Convert from microseconds to milliseconds with rounding 2808 final long totalTime = (vibTimer.getTotalTimeLocked(rawRealtime, which) + 500) 2809 / 1000; 2810 final int count = vibTimer.getCountLocked(which); 2811 if (totalTime != 0) { 2812 dumpLine(pw, uid, category, VIBRATOR_DATA, totalTime, count); 2813 } 2814 } 2815 2816 final Timer fgTimer = u.getForegroundActivityTimer(); 2817 if (fgTimer != null) { 2818 // Convert from microseconds to milliseconds with rounding 2819 final long totalTime = (fgTimer.getTotalTimeLocked(rawRealtime, which) + 500) 2820 / 1000; 2821 final int count = fgTimer.getCountLocked(which); 2822 if (totalTime != 0) { 2823 dumpLine(pw, uid, category, FOREGROUND_DATA, totalTime, count); 2824 } 2825 } 2826 2827 final Object[] stateTimes = new Object[Uid.NUM_PROCESS_STATE]; 2828 long totalStateTime = 0; 2829 for (int ips=0; ips<Uid.NUM_PROCESS_STATE; ips++) { 2830 totalStateTime += u.getProcessStateTime(ips, rawRealtime, which); 2831 stateTimes[ips] = (totalStateTime + 500) / 1000; 2832 } 2833 if (totalStateTime > 0) { 2834 dumpLine(pw, uid, category, STATE_TIME_DATA, stateTimes); 2835 } 2836 2837 final ArrayMap<String, ? extends BatteryStats.Uid.Proc> processStats 2838 = u.getProcessStats(); 2839 for (int ipr=processStats.size()-1; ipr>=0; ipr--) { 2840 final Uid.Proc ps = processStats.valueAt(ipr); 2841 2842 final long userMillis = ps.getUserTime(which); 2843 final long systemMillis = ps.getSystemTime(which); 2844 final long foregroundMillis = ps.getForegroundTime(which); 2845 final int starts = ps.getStarts(which); 2846 final int numCrashes = ps.getNumCrashes(which); 2847 final int numAnrs = ps.getNumAnrs(which); 2848 2849 if (userMillis != 0 || systemMillis != 0 || foregroundMillis != 0 2850 || starts != 0 || numAnrs != 0 || numCrashes != 0) { 2851 dumpLine(pw, uid, category, PROCESS_DATA, processStats.keyAt(ipr), userMillis, 2852 systemMillis, foregroundMillis, starts, numAnrs, numCrashes); 2853 } 2854 } 2855 2856 final ArrayMap<String, ? extends BatteryStats.Uid.Pkg> packageStats 2857 = u.getPackageStats(); 2858 for (int ipkg=packageStats.size()-1; ipkg>=0; ipkg--) { 2859 final Uid.Pkg ps = packageStats.valueAt(ipkg); 2860 int wakeups = 0; 2861 final ArrayMap<String, ? extends Counter> alarms = ps.getWakeupAlarmStats(); 2862 for (int iwa=alarms.size()-1; iwa>=0; iwa--) { 2863 wakeups += alarms.valueAt(iwa).getCountLocked(which); 2864 } 2865 final ArrayMap<String, ? extends Uid.Pkg.Serv> serviceStats = ps.getServiceStats(); 2866 for (int isvc=serviceStats.size()-1; isvc>=0; isvc--) { 2867 final BatteryStats.Uid.Pkg.Serv ss = serviceStats.valueAt(isvc); 2868 final long startTime = ss.getStartTime(batteryUptime, which); 2869 final int starts = ss.getStarts(which); 2870 final int launches = ss.getLaunches(which); 2871 if (startTime != 0 || starts != 0 || launches != 0) { 2872 dumpLine(pw, uid, category, APK_DATA, 2873 wakeups, // wakeup alarms 2874 packageStats.keyAt(ipkg), // Apk 2875 serviceStats.keyAt(isvc), // service 2876 startTime / 1000, // time spent started, in ms 2877 starts, 2878 launches); 2879 } 2880 } 2881 } 2882 } 2883 } 2884 2885 static final class TimerEntry { 2886 final String mName; 2887 final int mId; 2888 final BatteryStats.Timer mTimer; 2889 final long mTime; 2890 TimerEntry(String name, int id, BatteryStats.Timer timer, long time) { 2891 mName = name; 2892 mId = id; 2893 mTimer = timer; 2894 mTime = time; 2895 } 2896 } 2897 2898 private void printmAh(PrintWriter printer, double power) { 2899 printer.print(BatteryStatsHelper.makemAh(power)); 2900 } 2901 2902 /** 2903 * Temporary for settings. 2904 */ 2905 public final void dumpLocked(Context context, PrintWriter pw, String prefix, int which, 2906 int reqUid) { 2907 dumpLocked(context, pw, prefix, which, reqUid, BatteryStatsHelper.checkWifiOnly(context)); 2908 } 2909 2910 @SuppressWarnings("unused") 2911 public final void dumpLocked(Context context, PrintWriter pw, String prefix, final int which, 2912 int reqUid, boolean wifiOnly) { 2913 final long rawUptime = SystemClock.uptimeMillis() * 1000; 2914 final long rawRealtime = SystemClock.elapsedRealtime() * 1000; 2915 final long batteryUptime = getBatteryUptime(rawUptime); 2916 2917 final long whichBatteryUptime = computeBatteryUptime(rawUptime, which); 2918 final long whichBatteryRealtime = computeBatteryRealtime(rawRealtime, which); 2919 final long totalRealtime = computeRealtime(rawRealtime, which); 2920 final long totalUptime = computeUptime(rawUptime, which); 2921 final long whichBatteryScreenOffUptime = computeBatteryScreenOffUptime(rawUptime, which); 2922 final long whichBatteryScreenOffRealtime = computeBatteryScreenOffRealtime(rawRealtime, 2923 which); 2924 final long batteryTimeRemaining = computeBatteryTimeRemaining(rawRealtime); 2925 final long chargeTimeRemaining = computeChargeTimeRemaining(rawRealtime); 2926 2927 final StringBuilder sb = new StringBuilder(128); 2928 2929 final SparseArray<? extends Uid> uidStats = getUidStats(); 2930 final int NU = uidStats.size(); 2931 2932 sb.setLength(0); 2933 sb.append(prefix); 2934 sb.append(" Time on battery: "); 2935 formatTimeMs(sb, whichBatteryRealtime / 1000); sb.append("("); 2936 sb.append(formatRatioLocked(whichBatteryRealtime, totalRealtime)); 2937 sb.append(") realtime, "); 2938 formatTimeMs(sb, whichBatteryUptime / 1000); 2939 sb.append("("); sb.append(formatRatioLocked(whichBatteryUptime, totalRealtime)); 2940 sb.append(") uptime"); 2941 pw.println(sb.toString()); 2942 sb.setLength(0); 2943 sb.append(prefix); 2944 sb.append(" Time on battery screen off: "); 2945 formatTimeMs(sb, whichBatteryScreenOffRealtime / 1000); sb.append("("); 2946 sb.append(formatRatioLocked(whichBatteryScreenOffRealtime, totalRealtime)); 2947 sb.append(") realtime, "); 2948 formatTimeMs(sb, whichBatteryScreenOffUptime / 1000); 2949 sb.append("("); 2950 sb.append(formatRatioLocked(whichBatteryScreenOffUptime, totalRealtime)); 2951 sb.append(") uptime"); 2952 pw.println(sb.toString()); 2953 sb.setLength(0); 2954 sb.append(prefix); 2955 sb.append(" Total run time: "); 2956 formatTimeMs(sb, totalRealtime / 1000); 2957 sb.append("realtime, "); 2958 formatTimeMs(sb, totalUptime / 1000); 2959 sb.append("uptime"); 2960 pw.println(sb.toString()); 2961 if (batteryTimeRemaining >= 0) { 2962 sb.setLength(0); 2963 sb.append(prefix); 2964 sb.append(" Battery time remaining: "); 2965 formatTimeMs(sb, batteryTimeRemaining / 1000); 2966 pw.println(sb.toString()); 2967 } 2968 if (chargeTimeRemaining >= 0) { 2969 sb.setLength(0); 2970 sb.append(prefix); 2971 sb.append(" Charge time remaining: "); 2972 formatTimeMs(sb, chargeTimeRemaining / 1000); 2973 pw.println(sb.toString()); 2974 } 2975 pw.print(" Start clock time: "); 2976 pw.println(DateFormat.format("yyyy-MM-dd-HH-mm-ss", getStartClockTime()).toString()); 2977 2978 final long screenOnTime = getScreenOnTime(rawRealtime, which); 2979 final long interactiveTime = getInteractiveTime(rawRealtime, which); 2980 final long powerSaveModeEnabledTime = getPowerSaveModeEnabledTime(rawRealtime, which); 2981 final long deviceIdleModeEnabledTime = getDeviceIdleModeEnabledTime(rawRealtime, which); 2982 final long deviceIdlingTime = getDeviceIdlingTime(rawRealtime, which); 2983 final long phoneOnTime = getPhoneOnTime(rawRealtime, which); 2984 final long wifiRunningTime = getGlobalWifiRunningTime(rawRealtime, which); 2985 final long wifiOnTime = getWifiOnTime(rawRealtime, which); 2986 final long bluetoothOnTime = getBluetoothOnTime(rawRealtime, which); 2987 sb.setLength(0); 2988 sb.append(prefix); 2989 sb.append(" Screen on: "); formatTimeMs(sb, screenOnTime / 1000); 2990 sb.append("("); sb.append(formatRatioLocked(screenOnTime, whichBatteryRealtime)); 2991 sb.append(") "); sb.append(getScreenOnCount(which)); 2992 sb.append("x, Interactive: "); formatTimeMs(sb, interactiveTime / 1000); 2993 sb.append("("); sb.append(formatRatioLocked(interactiveTime, whichBatteryRealtime)); 2994 sb.append(")"); 2995 pw.println(sb.toString()); 2996 sb.setLength(0); 2997 sb.append(prefix); 2998 sb.append(" Screen brightnesses:"); 2999 boolean didOne = false; 3000 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) { 3001 final long time = getScreenBrightnessTime(i, rawRealtime, which); 3002 if (time == 0) { 3003 continue; 3004 } 3005 sb.append("\n "); 3006 sb.append(prefix); 3007 didOne = true; 3008 sb.append(SCREEN_BRIGHTNESS_NAMES[i]); 3009 sb.append(" "); 3010 formatTimeMs(sb, time/1000); 3011 sb.append("("); 3012 sb.append(formatRatioLocked(time, screenOnTime)); 3013 sb.append(")"); 3014 } 3015 if (!didOne) sb.append(" (no activity)"); 3016 pw.println(sb.toString()); 3017 if (powerSaveModeEnabledTime != 0) { 3018 sb.setLength(0); 3019 sb.append(prefix); 3020 sb.append(" Power save mode enabled: "); 3021 formatTimeMs(sb, powerSaveModeEnabledTime / 1000); 3022 sb.append("("); 3023 sb.append(formatRatioLocked(powerSaveModeEnabledTime, whichBatteryRealtime)); 3024 sb.append(")"); 3025 pw.println(sb.toString()); 3026 } 3027 if (deviceIdlingTime != 0) { 3028 sb.setLength(0); 3029 sb.append(prefix); 3030 sb.append(" Device idling: "); 3031 formatTimeMs(sb, deviceIdlingTime / 1000); 3032 sb.append("("); 3033 sb.append(formatRatioLocked(deviceIdlingTime, whichBatteryRealtime)); 3034 sb.append(") "); sb.append(getDeviceIdlingCount(which)); 3035 sb.append("x"); 3036 pw.println(sb.toString()); 3037 } 3038 if (deviceIdleModeEnabledTime != 0) { 3039 sb.setLength(0); 3040 sb.append(prefix); 3041 sb.append(" Idle mode time: "); 3042 formatTimeMs(sb, deviceIdleModeEnabledTime / 1000); 3043 sb.append("("); 3044 sb.append(formatRatioLocked(deviceIdleModeEnabledTime, whichBatteryRealtime)); 3045 sb.append(") "); sb.append(getDeviceIdleModeEnabledCount(which)); 3046 sb.append("x"); 3047 pw.println(sb.toString()); 3048 } 3049 if (phoneOnTime != 0) { 3050 sb.setLength(0); 3051 sb.append(prefix); 3052 sb.append(" Active phone call: "); formatTimeMs(sb, phoneOnTime / 1000); 3053 sb.append("("); sb.append(formatRatioLocked(phoneOnTime, whichBatteryRealtime)); 3054 sb.append(") "); sb.append(getPhoneOnCount(which)); sb.append("x"); 3055 } 3056 final int connChanges = getNumConnectivityChange(which); 3057 if (connChanges != 0) { 3058 pw.print(prefix); 3059 pw.print(" Connectivity changes: "); pw.println(connChanges); 3060 } 3061 3062 // Calculate wakelock times across all uids. 3063 long fullWakeLockTimeTotalMicros = 0; 3064 long partialWakeLockTimeTotalMicros = 0; 3065 3066 final ArrayList<TimerEntry> timers = new ArrayList<>(); 3067 3068 for (int iu = 0; iu < NU; iu++) { 3069 final Uid u = uidStats.valueAt(iu); 3070 3071 final ArrayMap<String, ? extends BatteryStats.Uid.Wakelock> wakelocks 3072 = u.getWakelockStats(); 3073 for (int iw=wakelocks.size()-1; iw>=0; iw--) { 3074 final Uid.Wakelock wl = wakelocks.valueAt(iw); 3075 3076 final Timer fullWakeTimer = wl.getWakeTime(WAKE_TYPE_FULL); 3077 if (fullWakeTimer != null) { 3078 fullWakeLockTimeTotalMicros += fullWakeTimer.getTotalTimeLocked( 3079 rawRealtime, which); 3080 } 3081 3082 final Timer partialWakeTimer = wl.getWakeTime(WAKE_TYPE_PARTIAL); 3083 if (partialWakeTimer != null) { 3084 final long totalTimeMicros = partialWakeTimer.getTotalTimeLocked( 3085 rawRealtime, which); 3086 if (totalTimeMicros > 0) { 3087 if (reqUid < 0) { 3088 // Only show the ordered list of all wake 3089 // locks if the caller is not asking for data 3090 // about a specific uid. 3091 timers.add(new TimerEntry(wakelocks.keyAt(iw), u.getUid(), 3092 partialWakeTimer, totalTimeMicros)); 3093 } 3094 partialWakeLockTimeTotalMicros += totalTimeMicros; 3095 } 3096 } 3097 } 3098 } 3099 3100 final long mobileRxTotalBytes = getNetworkActivityBytes(NETWORK_MOBILE_RX_DATA, which); 3101 final long mobileTxTotalBytes = getNetworkActivityBytes(NETWORK_MOBILE_TX_DATA, which); 3102 final long wifiRxTotalBytes = getNetworkActivityBytes(NETWORK_WIFI_RX_DATA, which); 3103 final long wifiTxTotalBytes = getNetworkActivityBytes(NETWORK_WIFI_TX_DATA, which); 3104 final long mobileRxTotalPackets = getNetworkActivityPackets(NETWORK_MOBILE_RX_DATA, which); 3105 final long mobileTxTotalPackets = getNetworkActivityPackets(NETWORK_MOBILE_TX_DATA, which); 3106 final long wifiRxTotalPackets = getNetworkActivityPackets(NETWORK_WIFI_RX_DATA, which); 3107 final long wifiTxTotalPackets = getNetworkActivityPackets(NETWORK_WIFI_TX_DATA, which); 3108 3109 if (fullWakeLockTimeTotalMicros != 0) { 3110 sb.setLength(0); 3111 sb.append(prefix); 3112 sb.append(" Total full wakelock time: "); formatTimeMsNoSpace(sb, 3113 (fullWakeLockTimeTotalMicros + 500) / 1000); 3114 pw.println(sb.toString()); 3115 } 3116 3117 if (partialWakeLockTimeTotalMicros != 0) { 3118 sb.setLength(0); 3119 sb.append(prefix); 3120 sb.append(" Total partial wakelock time: "); formatTimeMsNoSpace(sb, 3121 (partialWakeLockTimeTotalMicros + 500) / 1000); 3122 pw.println(sb.toString()); 3123 } 3124 3125 pw.print(prefix); 3126 pw.print(" Mobile total received: "); pw.print(formatBytesLocked(mobileRxTotalBytes)); 3127 pw.print(", sent: "); pw.print(formatBytesLocked(mobileTxTotalBytes)); 3128 pw.print(" (packets received "); pw.print(mobileRxTotalPackets); 3129 pw.print(", sent "); pw.print(mobileTxTotalPackets); pw.println(")"); 3130 sb.setLength(0); 3131 sb.append(prefix); 3132 sb.append(" Phone signal levels:"); 3133 didOne = false; 3134 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) { 3135 final long time = getPhoneSignalStrengthTime(i, rawRealtime, which); 3136 if (time == 0) { 3137 continue; 3138 } 3139 sb.append("\n "); 3140 sb.append(prefix); 3141 didOne = true; 3142 sb.append(SignalStrength.SIGNAL_STRENGTH_NAMES[i]); 3143 sb.append(" "); 3144 formatTimeMs(sb, time/1000); 3145 sb.append("("); 3146 sb.append(formatRatioLocked(time, whichBatteryRealtime)); 3147 sb.append(") "); 3148 sb.append(getPhoneSignalStrengthCount(i, which)); 3149 sb.append("x"); 3150 } 3151 if (!didOne) sb.append(" (no activity)"); 3152 pw.println(sb.toString()); 3153 3154 sb.setLength(0); 3155 sb.append(prefix); 3156 sb.append(" Signal scanning time: "); 3157 formatTimeMsNoSpace(sb, getPhoneSignalScanningTime(rawRealtime, which) / 1000); 3158 pw.println(sb.toString()); 3159 3160 sb.setLength(0); 3161 sb.append(prefix); 3162 sb.append(" Radio types:"); 3163 didOne = false; 3164 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) { 3165 final long time = getPhoneDataConnectionTime(i, rawRealtime, which); 3166 if (time == 0) { 3167 continue; 3168 } 3169 sb.append("\n "); 3170 sb.append(prefix); 3171 didOne = true; 3172 sb.append(DATA_CONNECTION_NAMES[i]); 3173 sb.append(" "); 3174 formatTimeMs(sb, time/1000); 3175 sb.append("("); 3176 sb.append(formatRatioLocked(time, whichBatteryRealtime)); 3177 sb.append(") "); 3178 sb.append(getPhoneDataConnectionCount(i, which)); 3179 sb.append("x"); 3180 } 3181 if (!didOne) sb.append(" (no activity)"); 3182 pw.println(sb.toString()); 3183 3184 sb.setLength(0); 3185 sb.append(prefix); 3186 sb.append(" Mobile radio active time: "); 3187 final long mobileActiveTime = getMobileRadioActiveTime(rawRealtime, which); 3188 formatTimeMs(sb, mobileActiveTime / 1000); 3189 sb.append("("); sb.append(formatRatioLocked(mobileActiveTime, whichBatteryRealtime)); 3190 sb.append(") "); sb.append(getMobileRadioActiveCount(which)); 3191 sb.append("x"); 3192 pw.println(sb.toString()); 3193 3194 final long mobileActiveUnknownTime = getMobileRadioActiveUnknownTime(which); 3195 if (mobileActiveUnknownTime != 0) { 3196 sb.setLength(0); 3197 sb.append(prefix); 3198 sb.append(" Mobile radio active unknown time: "); 3199 formatTimeMs(sb, mobileActiveUnknownTime / 1000); 3200 sb.append("("); 3201 sb.append(formatRatioLocked(mobileActiveUnknownTime, whichBatteryRealtime)); 3202 sb.append(") "); sb.append(getMobileRadioActiveUnknownCount(which)); 3203 sb.append("x"); 3204 pw.println(sb.toString()); 3205 } 3206 3207 final long mobileActiveAdjustedTime = getMobileRadioActiveAdjustedTime(which); 3208 if (mobileActiveAdjustedTime != 0) { 3209 sb.setLength(0); 3210 sb.append(prefix); 3211 sb.append(" Mobile radio active adjusted time: "); 3212 formatTimeMs(sb, mobileActiveAdjustedTime / 1000); 3213 sb.append("("); 3214 sb.append(formatRatioLocked(mobileActiveAdjustedTime, whichBatteryRealtime)); 3215 sb.append(")"); 3216 pw.println(sb.toString()); 3217 } 3218 3219 pw.print(prefix); 3220 pw.print(" Wi-Fi total received: "); pw.print(formatBytesLocked(wifiRxTotalBytes)); 3221 pw.print(", sent: "); pw.print(formatBytesLocked(wifiTxTotalBytes)); 3222 pw.print(" (packets received "); pw.print(wifiRxTotalPackets); 3223 pw.print(", sent "); pw.print(wifiTxTotalPackets); pw.println(")"); 3224 sb.setLength(0); 3225 sb.append(prefix); 3226 sb.append(" Wifi on: "); formatTimeMs(sb, wifiOnTime / 1000); 3227 sb.append("("); sb.append(formatRatioLocked(wifiOnTime, whichBatteryRealtime)); 3228 sb.append("), Wifi running: "); formatTimeMs(sb, wifiRunningTime / 1000); 3229 sb.append("("); sb.append(formatRatioLocked(wifiRunningTime, whichBatteryRealtime)); 3230 sb.append(")"); 3231 pw.println(sb.toString()); 3232 3233 sb.setLength(0); 3234 sb.append(prefix); 3235 sb.append(" Wifi states:"); 3236 didOne = false; 3237 for (int i=0; i<NUM_WIFI_STATES; i++) { 3238 final long time = getWifiStateTime(i, rawRealtime, which); 3239 if (time == 0) { 3240 continue; 3241 } 3242 sb.append("\n "); 3243 didOne = true; 3244 sb.append(WIFI_STATE_NAMES[i]); 3245 sb.append(" "); 3246 formatTimeMs(sb, time/1000); 3247 sb.append("("); 3248 sb.append(formatRatioLocked(time, whichBatteryRealtime)); 3249 sb.append(") "); 3250 sb.append(getWifiStateCount(i, which)); 3251 sb.append("x"); 3252 } 3253 if (!didOne) sb.append(" (no activity)"); 3254 pw.println(sb.toString()); 3255 3256 sb.setLength(0); 3257 sb.append(prefix); 3258 sb.append(" Wifi supplicant states:"); 3259 didOne = false; 3260 for (int i=0; i<NUM_WIFI_SUPPL_STATES; i++) { 3261 final long time = getWifiSupplStateTime(i, rawRealtime, which); 3262 if (time == 0) { 3263 continue; 3264 } 3265 sb.append("\n "); 3266 didOne = true; 3267 sb.append(WIFI_SUPPL_STATE_NAMES[i]); 3268 sb.append(" "); 3269 formatTimeMs(sb, time/1000); 3270 sb.append("("); 3271 sb.append(formatRatioLocked(time, whichBatteryRealtime)); 3272 sb.append(") "); 3273 sb.append(getWifiSupplStateCount(i, which)); 3274 sb.append("x"); 3275 } 3276 if (!didOne) sb.append(" (no activity)"); 3277 pw.println(sb.toString()); 3278 3279 sb.setLength(0); 3280 sb.append(prefix); 3281 sb.append(" Wifi signal levels:"); 3282 didOne = false; 3283 for (int i=0; i<NUM_WIFI_SIGNAL_STRENGTH_BINS; i++) { 3284 final long time = getWifiSignalStrengthTime(i, rawRealtime, which); 3285 if (time == 0) { 3286 continue; 3287 } 3288 sb.append("\n "); 3289 sb.append(prefix); 3290 didOne = true; 3291 sb.append("level("); 3292 sb.append(i); 3293 sb.append(") "); 3294 formatTimeMs(sb, time/1000); 3295 sb.append("("); 3296 sb.append(formatRatioLocked(time, whichBatteryRealtime)); 3297 sb.append(") "); 3298 sb.append(getWifiSignalStrengthCount(i, which)); 3299 sb.append("x"); 3300 } 3301 if (!didOne) sb.append(" (no activity)"); 3302 pw.println(sb.toString()); 3303 3304 final long wifiIdleTimeMs = getWifiControllerActivity(CONTROLLER_IDLE_TIME, which); 3305 final long wifiRxTimeMs = getWifiControllerActivity(CONTROLLER_RX_TIME, which); 3306 final long wifiTxTimeMs = getWifiControllerActivity(CONTROLLER_TX_TIME, which); 3307 final long wifiTotalTimeMs = wifiIdleTimeMs + wifiRxTimeMs + wifiTxTimeMs; 3308 3309 sb.setLength(0); 3310 sb.append(prefix); 3311 sb.append(" WiFi Idle time: "); formatTimeMs(sb, wifiIdleTimeMs); 3312 sb.append(" ("); 3313 sb.append(formatRatioLocked(wifiIdleTimeMs, wifiTotalTimeMs)); 3314 sb.append(")"); 3315 pw.println(sb.toString()); 3316 3317 sb.setLength(0); 3318 sb.append(prefix); 3319 sb.append(" WiFi Rx time: "); formatTimeMs(sb, wifiRxTimeMs); 3320 sb.append(" ("); 3321 sb.append(formatRatioLocked(wifiRxTimeMs, wifiTotalTimeMs)); 3322 sb.append(")"); 3323 pw.println(sb.toString()); 3324 3325 sb.setLength(0); 3326 sb.append(prefix); 3327 sb.append(" WiFi Tx time: "); formatTimeMs(sb, wifiTxTimeMs); 3328 sb.append(" ("); 3329 sb.append(formatRatioLocked(wifiTxTimeMs, wifiTotalTimeMs)); 3330 sb.append(")"); 3331 pw.println(sb.toString()); 3332 3333 sb.setLength(0); 3334 sb.append(prefix); 3335 sb.append(" WiFi Energy use: ").append(BatteryStatsHelper.makemAh( 3336 getWifiControllerActivity(CONTROLLER_POWER_DRAIN, which) / (double)(1000*60*60))); 3337 sb.append(" mAh"); 3338 pw.println(sb.toString()); 3339 3340 sb.setLength(0); 3341 sb.append(prefix); 3342 sb.append(" Bluetooth on: "); formatTimeMs(sb, bluetoothOnTime / 1000); 3343 sb.append("("); sb.append(formatRatioLocked(bluetoothOnTime, whichBatteryRealtime)); 3344 sb.append(")"); 3345 pw.println(sb.toString()); 3346 3347 sb.setLength(0); 3348 sb.append(prefix); 3349 sb.append(" Bluetooth states:"); 3350 didOne = false; 3351 for (int i=0; i<NUM_BLUETOOTH_STATES; i++) { 3352 final long time = getBluetoothStateTime(i, rawRealtime, which); 3353 if (time == 0) { 3354 continue; 3355 } 3356 sb.append("\n "); 3357 didOne = true; 3358 sb.append(BLUETOOTH_STATE_NAMES[i]); 3359 sb.append(" "); 3360 formatTimeMs(sb, time/1000); 3361 sb.append("("); 3362 sb.append(formatRatioLocked(time, whichBatteryRealtime)); 3363 sb.append(") "); 3364 sb.append(getPhoneDataConnectionCount(i, which)); 3365 sb.append("x"); 3366 } 3367 3368 if (!didOne) sb.append(" (no activity)"); 3369 pw.println(sb.toString()); 3370 3371 final long bluetoothIdleTimeMs = 3372 getBluetoothControllerActivity(CONTROLLER_IDLE_TIME, which); 3373 final long bluetoothRxTimeMs = getBluetoothControllerActivity(CONTROLLER_RX_TIME, which); 3374 final long bluetoothTxTimeMs = getBluetoothControllerActivity(CONTROLLER_TX_TIME, which); 3375 final long bluetoothTotalTimeMs = bluetoothIdleTimeMs + bluetoothRxTimeMs + 3376 bluetoothTxTimeMs; 3377 3378 sb.setLength(0); 3379 sb.append(prefix); 3380 sb.append(" Bluetooth Idle time: "); formatTimeMs(sb, bluetoothIdleTimeMs); 3381 sb.append(" ("); 3382 sb.append(formatRatioLocked(bluetoothIdleTimeMs, bluetoothTotalTimeMs)); 3383 sb.append(")"); 3384 pw.println(sb.toString()); 3385 3386 sb.setLength(0); 3387 sb.append(prefix); 3388 sb.append(" Bluetooth Rx time: "); formatTimeMs(sb, bluetoothRxTimeMs); 3389 sb.append(" ("); 3390 sb.append(formatRatioLocked(bluetoothRxTimeMs, bluetoothTotalTimeMs)); 3391 sb.append(")"); 3392 pw.println(sb.toString()); 3393 3394 sb.setLength(0); 3395 sb.append(prefix); 3396 sb.append(" Bluetooth Tx time: "); formatTimeMs(sb, bluetoothTxTimeMs); 3397 sb.append(" ("); 3398 sb.append(formatRatioLocked(bluetoothTxTimeMs, bluetoothTotalTimeMs)); 3399 sb.append(")"); 3400 pw.println(sb.toString()); 3401 3402 pw.println(); 3403 3404 if (which == STATS_SINCE_UNPLUGGED) { 3405 if (getIsOnBattery()) { 3406 pw.print(prefix); pw.println(" Device is currently unplugged"); 3407 pw.print(prefix); pw.print(" Discharge cycle start level: "); 3408 pw.println(getDischargeStartLevel()); 3409 pw.print(prefix); pw.print(" Discharge cycle current level: "); 3410 pw.println(getDischargeCurrentLevel()); 3411 } else { 3412 pw.print(prefix); pw.println(" Device is currently plugged into power"); 3413 pw.print(prefix); pw.print(" Last discharge cycle start level: "); 3414 pw.println(getDischargeStartLevel()); 3415 pw.print(prefix); pw.print(" Last discharge cycle end level: "); 3416 pw.println(getDischargeCurrentLevel()); 3417 } 3418 pw.print(prefix); pw.print(" Amount discharged while screen on: "); 3419 pw.println(getDischargeAmountScreenOn()); 3420 pw.print(prefix); pw.print(" Amount discharged while screen off: "); 3421 pw.println(getDischargeAmountScreenOff()); 3422 pw.println(" "); 3423 } else { 3424 pw.print(prefix); pw.println(" Device battery use since last full charge"); 3425 pw.print(prefix); pw.print(" Amount discharged (lower bound): "); 3426 pw.println(getLowDischargeAmountSinceCharge()); 3427 pw.print(prefix); pw.print(" Amount discharged (upper bound): "); 3428 pw.println(getHighDischargeAmountSinceCharge()); 3429 pw.print(prefix); pw.print(" Amount discharged while screen on: "); 3430 pw.println(getDischargeAmountScreenOnSinceCharge()); 3431 pw.print(prefix); pw.print(" Amount discharged while screen off: "); 3432 pw.println(getDischargeAmountScreenOffSinceCharge()); 3433 pw.println(); 3434 } 3435 3436 final BatteryStatsHelper helper = new BatteryStatsHelper(context, false, wifiOnly); 3437 helper.create(this); 3438 helper.refreshStats(which, UserHandle.USER_ALL); 3439 List<BatterySipper> sippers = helper.getUsageList(); 3440 if (sippers != null && sippers.size() > 0) { 3441 pw.print(prefix); pw.println(" Estimated power use (mAh):"); 3442 pw.print(prefix); pw.print(" Capacity: "); 3443 printmAh(pw, helper.getPowerProfile().getBatteryCapacity()); 3444 pw.print(", Computed drain: "); printmAh(pw, helper.getComputedPower()); 3445 pw.print(", actual drain: "); printmAh(pw, helper.getMinDrainedPower()); 3446 if (helper.getMinDrainedPower() != helper.getMaxDrainedPower()) { 3447 pw.print("-"); printmAh(pw, helper.getMaxDrainedPower()); 3448 } 3449 pw.println(); 3450 for (int i=0; i<sippers.size(); i++) { 3451 final BatterySipper bs = sippers.get(i); 3452 switch (bs.drainType) { 3453 case IDLE: 3454 pw.print(prefix); pw.print(" Idle: "); printmAh(pw, bs.totalPowerMah); 3455 pw.println(); 3456 break; 3457 case CELL: 3458 pw.print(prefix); pw.print(" Cell standby: "); printmAh(pw, bs.totalPowerMah); 3459 pw.println(); 3460 break; 3461 case PHONE: 3462 pw.print(prefix); pw.print(" Phone calls: "); printmAh(pw, bs.totalPowerMah); 3463 pw.println(); 3464 break; 3465 case WIFI: 3466 pw.print(prefix); pw.print(" Wifi: "); printmAh(pw, bs.totalPowerMah); 3467 pw.println(); 3468 break; 3469 case BLUETOOTH: 3470 pw.print(prefix); pw.print(" Bluetooth: "); printmAh(pw, bs.totalPowerMah); 3471 pw.println(); 3472 break; 3473 case SCREEN: 3474 pw.print(prefix); pw.print(" Screen: "); printmAh(pw, bs.totalPowerMah); 3475 pw.println(); 3476 break; 3477 case FLASHLIGHT: 3478 pw.print(prefix); pw.print(" Flashlight: "); printmAh(pw, bs.totalPowerMah); 3479 pw.println(); 3480 break; 3481 case APP: 3482 pw.print(prefix); pw.print(" Uid "); 3483 UserHandle.formatUid(pw, bs.uidObj.getUid()); 3484 pw.print(": "); printmAh(pw, bs.totalPowerMah); pw.println(); 3485 break; 3486 case USER: 3487 pw.print(prefix); pw.print(" User "); pw.print(bs.userId); 3488 pw.print(": "); printmAh(pw, bs.totalPowerMah); pw.println(); 3489 break; 3490 case UNACCOUNTED: 3491 pw.print(prefix); pw.print(" Unaccounted: "); printmAh(pw, bs.totalPowerMah); 3492 pw.println(); 3493 break; 3494 case OVERCOUNTED: 3495 pw.print(prefix); pw.print(" Over-counted: "); printmAh(pw, bs.totalPowerMah); 3496 pw.println(); 3497 break; 3498 } 3499 } 3500 pw.println(); 3501 } 3502 3503 sippers = helper.getMobilemsppList(); 3504 if (sippers != null && sippers.size() > 0) { 3505 pw.print(prefix); pw.println(" Per-app mobile ms per packet:"); 3506 long totalTime = 0; 3507 for (int i=0; i<sippers.size(); i++) { 3508 final BatterySipper bs = sippers.get(i); 3509 sb.setLength(0); 3510 sb.append(prefix); sb.append(" Uid "); 3511 UserHandle.formatUid(sb, bs.uidObj.getUid()); 3512 sb.append(": "); sb.append(BatteryStatsHelper.makemAh(bs.mobilemspp)); 3513 sb.append(" ("); sb.append(bs.mobileRxPackets+bs.mobileTxPackets); 3514 sb.append(" packets over "); formatTimeMsNoSpace(sb, bs.mobileActive); 3515 sb.append(") "); sb.append(bs.mobileActiveCount); sb.append("x"); 3516 pw.println(sb.toString()); 3517 totalTime += bs.mobileActive; 3518 } 3519 sb.setLength(0); 3520 sb.append(prefix); 3521 sb.append(" TOTAL TIME: "); 3522 formatTimeMs(sb, totalTime); 3523 sb.append("("); sb.append(formatRatioLocked(totalTime, whichBatteryRealtime)); 3524 sb.append(")"); 3525 pw.println(sb.toString()); 3526 pw.println(); 3527 } 3528 3529 final Comparator<TimerEntry> timerComparator = new Comparator<TimerEntry>() { 3530 @Override 3531 public int compare(TimerEntry lhs, TimerEntry rhs) { 3532 long lhsTime = lhs.mTime; 3533 long rhsTime = rhs.mTime; 3534 if (lhsTime < rhsTime) { 3535 return 1; 3536 } 3537 if (lhsTime > rhsTime) { 3538 return -1; 3539 } 3540 return 0; 3541 } 3542 }; 3543 3544 if (reqUid < 0) { 3545 final Map<String, ? extends BatteryStats.Timer> kernelWakelocks 3546 = getKernelWakelockStats(); 3547 if (kernelWakelocks.size() > 0) { 3548 final ArrayList<TimerEntry> ktimers = new ArrayList<>(); 3549 for (Map.Entry<String, ? extends BatteryStats.Timer> ent 3550 : kernelWakelocks.entrySet()) { 3551 final BatteryStats.Timer timer = ent.getValue(); 3552 final long totalTimeMillis = computeWakeLock(timer, rawRealtime, which); 3553 if (totalTimeMillis > 0) { 3554 ktimers.add(new TimerEntry(ent.getKey(), 0, timer, totalTimeMillis)); 3555 } 3556 } 3557 if (ktimers.size() > 0) { 3558 Collections.sort(ktimers, timerComparator); 3559 pw.print(prefix); pw.println(" All kernel wake locks:"); 3560 for (int i=0; i<ktimers.size(); i++) { 3561 final TimerEntry timer = ktimers.get(i); 3562 String linePrefix = ": "; 3563 sb.setLength(0); 3564 sb.append(prefix); 3565 sb.append(" Kernel Wake lock "); 3566 sb.append(timer.mName); 3567 linePrefix = printWakeLock(sb, timer.mTimer, rawRealtime, null, 3568 which, linePrefix); 3569 if (!linePrefix.equals(": ")) { 3570 sb.append(" realtime"); 3571 // Only print out wake locks that were held 3572 pw.println(sb.toString()); 3573 } 3574 } 3575 pw.println(); 3576 } 3577 } 3578 3579 if (timers.size() > 0) { 3580 Collections.sort(timers, timerComparator); 3581 pw.print(prefix); pw.println(" All partial wake locks:"); 3582 for (int i=0; i<timers.size(); i++) { 3583 TimerEntry timer = timers.get(i); 3584 sb.setLength(0); 3585 sb.append(" Wake lock "); 3586 UserHandle.formatUid(sb, timer.mId); 3587 sb.append(" "); 3588 sb.append(timer.mName); 3589 printWakeLock(sb, timer.mTimer, rawRealtime, null, which, ": "); 3590 sb.append(" realtime"); 3591 pw.println(sb.toString()); 3592 } 3593 timers.clear(); 3594 pw.println(); 3595 } 3596 3597 final Map<String, ? extends Timer> wakeupReasons = getWakeupReasonStats(); 3598 if (wakeupReasons.size() > 0) { 3599 pw.print(prefix); pw.println(" All wakeup reasons:"); 3600 final ArrayList<TimerEntry> reasons = new ArrayList<>(); 3601 for (Map.Entry<String, ? extends Timer> ent : wakeupReasons.entrySet()) { 3602 final Timer timer = ent.getValue(); 3603 reasons.add(new TimerEntry(ent.getKey(), 0, timer, 3604 timer.getCountLocked(which))); 3605 } 3606 Collections.sort(reasons, timerComparator); 3607 for (int i=0; i<reasons.size(); i++) { 3608 TimerEntry timer = reasons.get(i); 3609 String linePrefix = ": "; 3610 sb.setLength(0); 3611 sb.append(prefix); 3612 sb.append(" Wakeup reason "); 3613 sb.append(timer.mName); 3614 printWakeLock(sb, timer.mTimer, rawRealtime, null, which, ": "); 3615 sb.append(" realtime"); 3616 pw.println(sb.toString()); 3617 } 3618 pw.println(); 3619 } 3620 } 3621 3622 for (int iu=0; iu<NU; iu++) { 3623 final int uid = uidStats.keyAt(iu); 3624 if (reqUid >= 0 && uid != reqUid && uid != Process.SYSTEM_UID) { 3625 continue; 3626 } 3627 3628 final Uid u = uidStats.valueAt(iu); 3629 3630 pw.print(prefix); 3631 pw.print(" "); 3632 UserHandle.formatUid(pw, uid); 3633 pw.println(":"); 3634 boolean uidActivity = false; 3635 3636 final long mobileRxBytes = u.getNetworkActivityBytes(NETWORK_MOBILE_RX_DATA, which); 3637 final long mobileTxBytes = u.getNetworkActivityBytes(NETWORK_MOBILE_TX_DATA, which); 3638 final long wifiRxBytes = u.getNetworkActivityBytes(NETWORK_WIFI_RX_DATA, which); 3639 final long wifiTxBytes = u.getNetworkActivityBytes(NETWORK_WIFI_TX_DATA, which); 3640 final long mobileRxPackets = u.getNetworkActivityPackets(NETWORK_MOBILE_RX_DATA, which); 3641 final long mobileTxPackets = u.getNetworkActivityPackets(NETWORK_MOBILE_TX_DATA, which); 3642 final long uidMobileActiveTime = u.getMobileRadioActiveTime(which); 3643 final int uidMobileActiveCount = u.getMobileRadioActiveCount(which); 3644 final long wifiRxPackets = u.getNetworkActivityPackets(NETWORK_WIFI_RX_DATA, which); 3645 final long wifiTxPackets = u.getNetworkActivityPackets(NETWORK_WIFI_TX_DATA, which); 3646 final long fullWifiLockOnTime = u.getFullWifiLockTime(rawRealtime, which); 3647 final long wifiScanTime = u.getWifiScanTime(rawRealtime, which); 3648 final int wifiScanCount = u.getWifiScanCount(which); 3649 final long uidWifiRunningTime = u.getWifiRunningTime(rawRealtime, which); 3650 3651 if (mobileRxBytes > 0 || mobileTxBytes > 0 3652 || mobileRxPackets > 0 || mobileTxPackets > 0) { 3653 pw.print(prefix); pw.print(" Mobile network: "); 3654 pw.print(formatBytesLocked(mobileRxBytes)); pw.print(" received, "); 3655 pw.print(formatBytesLocked(mobileTxBytes)); 3656 pw.print(" sent (packets "); pw.print(mobileRxPackets); 3657 pw.print(" received, "); pw.print(mobileTxPackets); pw.println(" sent)"); 3658 } 3659 if (uidMobileActiveTime > 0 || uidMobileActiveCount > 0) { 3660 sb.setLength(0); 3661 sb.append(prefix); sb.append(" Mobile radio active: "); 3662 formatTimeMs(sb, uidMobileActiveTime / 1000); 3663 sb.append("("); 3664 sb.append(formatRatioLocked(uidMobileActiveTime, mobileActiveTime)); 3665 sb.append(") "); sb.append(uidMobileActiveCount); sb.append("x"); 3666 long packets = mobileRxPackets + mobileTxPackets; 3667 if (packets == 0) { 3668 packets = 1; 3669 } 3670 sb.append(" @ "); 3671 sb.append(BatteryStatsHelper.makemAh(uidMobileActiveTime / 1000 / (double)packets)); 3672 sb.append(" mspp"); 3673 pw.println(sb.toString()); 3674 } 3675 3676 if (wifiRxBytes > 0 || wifiTxBytes > 0 || wifiRxPackets > 0 || wifiTxPackets > 0) { 3677 pw.print(prefix); pw.print(" Wi-Fi network: "); 3678 pw.print(formatBytesLocked(wifiRxBytes)); pw.print(" received, "); 3679 pw.print(formatBytesLocked(wifiTxBytes)); 3680 pw.print(" sent (packets "); pw.print(wifiRxPackets); 3681 pw.print(" received, "); pw.print(wifiTxPackets); pw.println(" sent)"); 3682 } 3683 3684 if (fullWifiLockOnTime != 0 || wifiScanTime != 0 || wifiScanCount != 0 3685 || uidWifiRunningTime != 0) { 3686 sb.setLength(0); 3687 sb.append(prefix); sb.append(" Wifi Running: "); 3688 formatTimeMs(sb, uidWifiRunningTime / 1000); 3689 sb.append("("); sb.append(formatRatioLocked(uidWifiRunningTime, 3690 whichBatteryRealtime)); sb.append(")\n"); 3691 sb.append(prefix); sb.append(" Full Wifi Lock: "); 3692 formatTimeMs(sb, fullWifiLockOnTime / 1000); 3693 sb.append("("); sb.append(formatRatioLocked(fullWifiLockOnTime, 3694 whichBatteryRealtime)); sb.append(")\n"); 3695 sb.append(prefix); sb.append(" Wifi Scan: "); 3696 formatTimeMs(sb, wifiScanTime / 1000); 3697 sb.append("("); sb.append(formatRatioLocked(wifiScanTime, 3698 whichBatteryRealtime)); sb.append(") "); 3699 sb.append(wifiScanCount); 3700 sb.append("x"); 3701 pw.println(sb.toString()); 3702 } 3703 3704 if (u.hasUserActivity()) { 3705 boolean hasData = false; 3706 for (int i=0; i<Uid.NUM_USER_ACTIVITY_TYPES; i++) { 3707 final int val = u.getUserActivityCount(i, which); 3708 if (val != 0) { 3709 if (!hasData) { 3710 sb.setLength(0); 3711 sb.append(" User activity: "); 3712 hasData = true; 3713 } else { 3714 sb.append(", "); 3715 } 3716 sb.append(val); 3717 sb.append(" "); 3718 sb.append(Uid.USER_ACTIVITY_TYPES[i]); 3719 } 3720 } 3721 if (hasData) { 3722 pw.println(sb.toString()); 3723 } 3724 } 3725 3726 final ArrayMap<String, ? extends BatteryStats.Uid.Wakelock> wakelocks 3727 = u.getWakelockStats(); 3728 long totalFullWakelock = 0, totalPartialWakelock = 0, totalWindowWakelock = 0; 3729 int countWakelock = 0; 3730 for (int iw=wakelocks.size()-1; iw>=0; iw--) { 3731 final Uid.Wakelock wl = wakelocks.valueAt(iw); 3732 String linePrefix = ": "; 3733 sb.setLength(0); 3734 sb.append(prefix); 3735 sb.append(" Wake lock "); 3736 sb.append(wakelocks.keyAt(iw)); 3737 linePrefix = printWakeLock(sb, wl.getWakeTime(WAKE_TYPE_FULL), rawRealtime, 3738 "full", which, linePrefix); 3739 linePrefix = printWakeLock(sb, wl.getWakeTime(WAKE_TYPE_PARTIAL), rawRealtime, 3740 "partial", which, linePrefix); 3741 linePrefix = printWakeLock(sb, wl.getWakeTime(WAKE_TYPE_WINDOW), rawRealtime, 3742 "window", which, linePrefix); 3743 if (true || !linePrefix.equals(": ")) { 3744 sb.append(" realtime"); 3745 // Only print out wake locks that were held 3746 pw.println(sb.toString()); 3747 uidActivity = true; 3748 countWakelock++; 3749 } 3750 totalFullWakelock += computeWakeLock(wl.getWakeTime(WAKE_TYPE_FULL), 3751 rawRealtime, which); 3752 totalPartialWakelock += computeWakeLock(wl.getWakeTime(WAKE_TYPE_PARTIAL), 3753 rawRealtime, which); 3754 totalWindowWakelock += computeWakeLock(wl.getWakeTime(WAKE_TYPE_WINDOW), 3755 rawRealtime, which); 3756 } 3757 if (countWakelock > 1) { 3758 if (totalFullWakelock != 0 || totalPartialWakelock != 0 3759 || totalWindowWakelock != 0) { 3760 sb.setLength(0); 3761 sb.append(prefix); 3762 sb.append(" TOTAL wake: "); 3763 boolean needComma = false; 3764 if (totalFullWakelock != 0) { 3765 needComma = true; 3766 formatTimeMs(sb, totalFullWakelock); 3767 sb.append("full"); 3768 } 3769 if (totalPartialWakelock != 0) { 3770 if (needComma) { 3771 sb.append(", "); 3772 } 3773 needComma = true; 3774 formatTimeMs(sb, totalPartialWakelock); 3775 sb.append("partial"); 3776 } 3777 if (totalWindowWakelock != 0) { 3778 if (needComma) { 3779 sb.append(", "); 3780 } 3781 needComma = true; 3782 formatTimeMs(sb, totalWindowWakelock); 3783 sb.append("window"); 3784 } 3785 sb.append(" realtime"); 3786 pw.println(sb.toString()); 3787 } 3788 } 3789 3790 final ArrayMap<String, ? extends Timer> syncs = u.getSyncStats(); 3791 for (int isy=syncs.size()-1; isy>=0; isy--) { 3792 final Timer timer = syncs.valueAt(isy); 3793 // Convert from microseconds to milliseconds with rounding 3794 final long totalTime = (timer.getTotalTimeLocked(rawRealtime, which) + 500) / 1000; 3795 final int count = timer.getCountLocked(which); 3796 sb.setLength(0); 3797 sb.append(prefix); 3798 sb.append(" Sync "); 3799 sb.append(syncs.keyAt(isy)); 3800 sb.append(": "); 3801 if (totalTime != 0) { 3802 formatTimeMs(sb, totalTime); 3803 sb.append("realtime ("); 3804 sb.append(count); 3805 sb.append(" times)"); 3806 } else { 3807 sb.append("(not used)"); 3808 } 3809 pw.println(sb.toString()); 3810 uidActivity = true; 3811 } 3812 3813 final ArrayMap<String, ? extends Timer> jobs = u.getJobStats(); 3814 for (int ij=jobs.size()-1; ij>=0; ij--) { 3815 final Timer timer = jobs.valueAt(ij); 3816 // Convert from microseconds to milliseconds with rounding 3817 final long totalTime = (timer.getTotalTimeLocked(rawRealtime, which) + 500) / 1000; 3818 final int count = timer.getCountLocked(which); 3819 sb.setLength(0); 3820 sb.append(prefix); 3821 sb.append(" Job "); 3822 sb.append(jobs.keyAt(ij)); 3823 sb.append(": "); 3824 if (totalTime != 0) { 3825 formatTimeMs(sb, totalTime); 3826 sb.append("realtime ("); 3827 sb.append(count); 3828 sb.append(" times)"); 3829 } else { 3830 sb.append("(not used)"); 3831 } 3832 pw.println(sb.toString()); 3833 uidActivity = true; 3834 } 3835 3836 final SparseArray<? extends BatteryStats.Uid.Sensor> sensors = u.getSensorStats(); 3837 final int NSE = sensors.size(); 3838 for (int ise=0; ise<NSE; ise++) { 3839 final Uid.Sensor se = sensors.valueAt(ise); 3840 final int sensorNumber = sensors.keyAt(ise); 3841 sb.setLength(0); 3842 sb.append(prefix); 3843 sb.append(" Sensor "); 3844 int handle = se.getHandle(); 3845 if (handle == Uid.Sensor.GPS) { 3846 sb.append("GPS"); 3847 } else { 3848 sb.append(handle); 3849 } 3850 sb.append(": "); 3851 3852 final Timer timer = se.getSensorTime(); 3853 if (timer != null) { 3854 // Convert from microseconds to milliseconds with rounding 3855 final long totalTime = (timer.getTotalTimeLocked( 3856 rawRealtime, which) + 500) / 1000; 3857 final int count = timer.getCountLocked(which); 3858 //timer.logState(); 3859 if (totalTime != 0) { 3860 formatTimeMs(sb, totalTime); 3861 sb.append("realtime ("); 3862 sb.append(count); 3863 sb.append(" times)"); 3864 } else { 3865 sb.append("(not used)"); 3866 } 3867 } else { 3868 sb.append("(not used)"); 3869 } 3870 3871 pw.println(sb.toString()); 3872 uidActivity = true; 3873 } 3874 3875 final Timer vibTimer = u.getVibratorOnTimer(); 3876 if (vibTimer != null) { 3877 // Convert from microseconds to milliseconds with rounding 3878 final long totalTime = (vibTimer.getTotalTimeLocked( 3879 rawRealtime, which) + 500) / 1000; 3880 final int count = vibTimer.getCountLocked(which); 3881 //timer.logState(); 3882 if (totalTime != 0) { 3883 sb.setLength(0); 3884 sb.append(prefix); 3885 sb.append(" Vibrator: "); 3886 formatTimeMs(sb, totalTime); 3887 sb.append("realtime ("); 3888 sb.append(count); 3889 sb.append(" times)"); 3890 pw.println(sb.toString()); 3891 uidActivity = true; 3892 } 3893 } 3894 3895 final Timer fgTimer = u.getForegroundActivityTimer(); 3896 if (fgTimer != null) { 3897 // Convert from microseconds to milliseconds with rounding 3898 final long totalTime = (fgTimer.getTotalTimeLocked(rawRealtime, which) + 500) 3899 / 1000; 3900 final int count = fgTimer.getCountLocked(which); 3901 if (totalTime != 0) { 3902 sb.setLength(0); 3903 sb.append(prefix); 3904 sb.append(" Foreground activities: "); 3905 formatTimeMs(sb, totalTime); 3906 sb.append("realtime ("); 3907 sb.append(count); 3908 sb.append(" times)"); 3909 pw.println(sb.toString()); 3910 uidActivity = true; 3911 } 3912 } 3913 3914 long totalStateTime = 0; 3915 for (int ips=0; ips<Uid.NUM_PROCESS_STATE; ips++) { 3916 long time = u.getProcessStateTime(ips, rawRealtime, which); 3917 if (time > 0) { 3918 totalStateTime += time; 3919 sb.setLength(0); 3920 sb.append(prefix); 3921 sb.append(" "); 3922 sb.append(Uid.PROCESS_STATE_NAMES[ips]); 3923 sb.append(" for: "); 3924 formatTimeMs(sb, (totalStateTime + 500) / 1000); 3925 pw.println(sb.toString()); 3926 uidActivity = true; 3927 } 3928 } 3929 3930 final ArrayMap<String, ? extends BatteryStats.Uid.Proc> processStats 3931 = u.getProcessStats(); 3932 for (int ipr=processStats.size()-1; ipr>=0; ipr--) { 3933 final Uid.Proc ps = processStats.valueAt(ipr); 3934 long userTime; 3935 long systemTime; 3936 long foregroundTime; 3937 int starts; 3938 int numExcessive; 3939 3940 userTime = ps.getUserTime(which); 3941 systemTime = ps.getSystemTime(which); 3942 foregroundTime = ps.getForegroundTime(which); 3943 starts = ps.getStarts(which); 3944 final int numCrashes = ps.getNumCrashes(which); 3945 final int numAnrs = ps.getNumAnrs(which); 3946 numExcessive = which == STATS_SINCE_CHARGED 3947 ? ps.countExcessivePowers() : 0; 3948 3949 if (userTime != 0 || systemTime != 0 || foregroundTime != 0 || starts != 0 3950 || numExcessive != 0 || numCrashes != 0 || numAnrs != 0) { 3951 sb.setLength(0); 3952 sb.append(prefix); sb.append(" Proc "); 3953 sb.append(processStats.keyAt(ipr)); sb.append(":\n"); 3954 sb.append(prefix); sb.append(" CPU: "); 3955 formatTimeMs(sb, userTime); sb.append("usr + "); 3956 formatTimeMs(sb, systemTime); sb.append("krn ; "); 3957 formatTimeMs(sb, foregroundTime); sb.append("fg"); 3958 if (starts != 0 || numCrashes != 0 || numAnrs != 0) { 3959 sb.append("\n"); sb.append(prefix); sb.append(" "); 3960 boolean hasOne = false; 3961 if (starts != 0) { 3962 hasOne = true; 3963 sb.append(starts); sb.append(" starts"); 3964 } 3965 if (numCrashes != 0) { 3966 if (hasOne) { 3967 sb.append(", "); 3968 } 3969 hasOne = true; 3970 sb.append(numCrashes); sb.append(" crashes"); 3971 } 3972 if (numAnrs != 0) { 3973 if (hasOne) { 3974 sb.append(", "); 3975 } 3976 sb.append(numAnrs); sb.append(" anrs"); 3977 } 3978 } 3979 pw.println(sb.toString()); 3980 for (int e=0; e<numExcessive; e++) { 3981 Uid.Proc.ExcessivePower ew = ps.getExcessivePower(e); 3982 if (ew != null) { 3983 pw.print(prefix); pw.print(" * Killed for "); 3984 if (ew.type == Uid.Proc.ExcessivePower.TYPE_WAKE) { 3985 pw.print("wake lock"); 3986 } else if (ew.type == Uid.Proc.ExcessivePower.TYPE_CPU) { 3987 pw.print("cpu"); 3988 } else { 3989 pw.print("unknown"); 3990 } 3991 pw.print(" use: "); 3992 TimeUtils.formatDuration(ew.usedTime, pw); 3993 pw.print(" over "); 3994 TimeUtils.formatDuration(ew.overTime, pw); 3995 if (ew.overTime != 0) { 3996 pw.print(" ("); 3997 pw.print((ew.usedTime*100)/ew.overTime); 3998 pw.println("%)"); 3999 } 4000 } 4001 } 4002 uidActivity = true; 4003 } 4004 } 4005 4006 final ArrayMap<String, ? extends BatteryStats.Uid.Pkg> packageStats 4007 = u.getPackageStats(); 4008 for (int ipkg=packageStats.size()-1; ipkg>=0; ipkg--) { 4009 pw.print(prefix); pw.print(" Apk "); pw.print(packageStats.keyAt(ipkg)); 4010 pw.println(":"); 4011 boolean apkActivity = false; 4012 final Uid.Pkg ps = packageStats.valueAt(ipkg); 4013 final ArrayMap<String, ? extends Counter> alarms = ps.getWakeupAlarmStats(); 4014 for (int iwa=alarms.size()-1; iwa>=0; iwa--) { 4015 pw.print(prefix); pw.print(" Wakeup alarm "); 4016 pw.print(alarms.keyAt(iwa)); pw.print(": "); 4017 pw.print(alarms.valueAt(iwa).getCountLocked(which)); 4018 pw.println(" times"); 4019 apkActivity = true; 4020 } 4021 final ArrayMap<String, ? extends Uid.Pkg.Serv> serviceStats = ps.getServiceStats(); 4022 for (int isvc=serviceStats.size()-1; isvc>=0; isvc--) { 4023 final BatteryStats.Uid.Pkg.Serv ss = serviceStats.valueAt(isvc); 4024 final long startTime = ss.getStartTime(batteryUptime, which); 4025 final int starts = ss.getStarts(which); 4026 final int launches = ss.getLaunches(which); 4027 if (startTime != 0 || starts != 0 || launches != 0) { 4028 sb.setLength(0); 4029 sb.append(prefix); sb.append(" Service "); 4030 sb.append(serviceStats.keyAt(isvc)); sb.append(":\n"); 4031 sb.append(prefix); sb.append(" Created for: "); 4032 formatTimeMs(sb, startTime / 1000); 4033 sb.append("uptime\n"); 4034 sb.append(prefix); sb.append(" Starts: "); 4035 sb.append(starts); 4036 sb.append(", launches: "); sb.append(launches); 4037 pw.println(sb.toString()); 4038 apkActivity = true; 4039 } 4040 } 4041 if (!apkActivity) { 4042 pw.print(prefix); pw.println(" (nothing executed)"); 4043 } 4044 uidActivity = true; 4045 } 4046 if (!uidActivity) { 4047 pw.print(prefix); pw.println(" (nothing executed)"); 4048 } 4049 } 4050 } 4051 4052 static void printBitDescriptions(PrintWriter pw, int oldval, int newval, HistoryTag wakelockTag, 4053 BitDescription[] descriptions, boolean longNames) { 4054 int diff = oldval ^ newval; 4055 if (diff == 0) return; 4056 boolean didWake = false; 4057 for (int i=0; i<descriptions.length; i++) { 4058 BitDescription bd = descriptions[i]; 4059 if ((diff&bd.mask) != 0) { 4060 pw.print(longNames ? " " : ","); 4061 if (bd.shift < 0) { 4062 pw.print((newval&bd.mask) != 0 ? "+" : "-"); 4063 pw.print(longNames ? bd.name : bd.shortName); 4064 if (bd.mask == HistoryItem.STATE_WAKE_LOCK_FLAG && wakelockTag != null) { 4065 didWake = true; 4066 pw.print("="); 4067 if (longNames) { 4068 UserHandle.formatUid(pw, wakelockTag.uid); 4069 pw.print(":\""); 4070 pw.print(wakelockTag.string); 4071 pw.print("\""); 4072 } else { 4073 pw.print(wakelockTag.poolIdx); 4074 } 4075 } 4076 } else { 4077 pw.print(longNames ? bd.name : bd.shortName); 4078 pw.print("="); 4079 int val = (newval&bd.mask)>>bd.shift; 4080 if (bd.values != null && val >= 0 && val < bd.values.length) { 4081 pw.print(longNames? bd.values[val] : bd.shortValues[val]); 4082 } else { 4083 pw.print(val); 4084 } 4085 } 4086 } 4087 } 4088 if (!didWake && wakelockTag != null) { 4089 pw.print(longNames ? " wake_lock=" : ",w="); 4090 if (longNames) { 4091 UserHandle.formatUid(pw, wakelockTag.uid); 4092 pw.print(":\""); 4093 pw.print(wakelockTag.string); 4094 pw.print("\""); 4095 } else { 4096 pw.print(wakelockTag.poolIdx); 4097 } 4098 } 4099 } 4100 4101 public void prepareForDumpLocked() { 4102 } 4103 4104 public static class HistoryPrinter { 4105 int oldState = 0; 4106 int oldState2 = 0; 4107 int oldLevel = -1; 4108 int oldStatus = -1; 4109 int oldHealth = -1; 4110 int oldPlug = -1; 4111 int oldTemp = -1; 4112 int oldVolt = -1; 4113 long lastTime = -1; 4114 4115 void reset() { 4116 oldState = oldState2 = 0; 4117 oldLevel = -1; 4118 oldStatus = -1; 4119 oldHealth = -1; 4120 oldPlug = -1; 4121 oldTemp = -1; 4122 oldVolt = -1; 4123 } 4124 4125 public void printNextItem(PrintWriter pw, HistoryItem rec, long baseTime, boolean checkin, 4126 boolean verbose) { 4127 if (!checkin) { 4128 pw.print(" "); 4129 TimeUtils.formatDuration(rec.time - baseTime, pw, TimeUtils.HUNDRED_DAY_FIELD_LEN); 4130 pw.print(" ("); 4131 pw.print(rec.numReadInts); 4132 pw.print(") "); 4133 } else { 4134 pw.print(BATTERY_STATS_CHECKIN_VERSION); pw.print(','); 4135 pw.print(HISTORY_DATA); pw.print(','); 4136 if (lastTime < 0) { 4137 pw.print(rec.time - baseTime); 4138 } else { 4139 pw.print(rec.time - lastTime); 4140 } 4141 lastTime = rec.time; 4142 } 4143 if (rec.cmd == HistoryItem.CMD_START) { 4144 if (checkin) { 4145 pw.print(":"); 4146 } 4147 pw.println("START"); 4148 reset(); 4149 } else if (rec.cmd == HistoryItem.CMD_CURRENT_TIME 4150 || rec.cmd == HistoryItem.CMD_RESET) { 4151 if (checkin) { 4152 pw.print(":"); 4153 } 4154 if (rec.cmd == HistoryItem.CMD_RESET) { 4155 pw.print("RESET:"); 4156 reset(); 4157 } 4158 pw.print("TIME:"); 4159 if (checkin) { 4160 pw.println(rec.currentTime); 4161 } else { 4162 pw.print(" "); 4163 pw.println(DateFormat.format("yyyy-MM-dd-HH-mm-ss", 4164 rec.currentTime).toString()); 4165 } 4166 } else if (rec.cmd == HistoryItem.CMD_SHUTDOWN) { 4167 if (checkin) { 4168 pw.print(":"); 4169 } 4170 pw.println("SHUTDOWN"); 4171 } else if (rec.cmd == HistoryItem.CMD_OVERFLOW) { 4172 if (checkin) { 4173 pw.print(":"); 4174 } 4175 pw.println("*OVERFLOW*"); 4176 } else { 4177 if (!checkin) { 4178 if (rec.batteryLevel < 10) pw.print("00"); 4179 else if (rec.batteryLevel < 100) pw.print("0"); 4180 pw.print(rec.batteryLevel); 4181 if (verbose) { 4182 pw.print(" "); 4183 if (rec.states < 0) ; 4184 else if (rec.states < 0x10) pw.print("0000000"); 4185 else if (rec.states < 0x100) pw.print("000000"); 4186 else if (rec.states < 0x1000) pw.print("00000"); 4187 else if (rec.states < 0x10000) pw.print("0000"); 4188 else if (rec.states < 0x100000) pw.print("000"); 4189 else if (rec.states < 0x1000000) pw.print("00"); 4190 else if (rec.states < 0x10000000) pw.print("0"); 4191 pw.print(Integer.toHexString(rec.states)); 4192 } 4193 } else { 4194 if (oldLevel != rec.batteryLevel) { 4195 oldLevel = rec.batteryLevel; 4196 pw.print(",Bl="); pw.print(rec.batteryLevel); 4197 } 4198 } 4199 if (oldStatus != rec.batteryStatus) { 4200 oldStatus = rec.batteryStatus; 4201 pw.print(checkin ? ",Bs=" : " status="); 4202 switch (oldStatus) { 4203 case BatteryManager.BATTERY_STATUS_UNKNOWN: 4204 pw.print(checkin ? "?" : "unknown"); 4205 break; 4206 case BatteryManager.BATTERY_STATUS_CHARGING: 4207 pw.print(checkin ? "c" : "charging"); 4208 break; 4209 case BatteryManager.BATTERY_STATUS_DISCHARGING: 4210 pw.print(checkin ? "d" : "discharging"); 4211 break; 4212 case BatteryManager.BATTERY_STATUS_NOT_CHARGING: 4213 pw.print(checkin ? "n" : "not-charging"); 4214 break; 4215 case BatteryManager.BATTERY_STATUS_FULL: 4216 pw.print(checkin ? "f" : "full"); 4217 break; 4218 default: 4219 pw.print(oldStatus); 4220 break; 4221 } 4222 } 4223 if (oldHealth != rec.batteryHealth) { 4224 oldHealth = rec.batteryHealth; 4225 pw.print(checkin ? ",Bh=" : " health="); 4226 switch (oldHealth) { 4227 case BatteryManager.BATTERY_HEALTH_UNKNOWN: 4228 pw.print(checkin ? "?" : "unknown"); 4229 break; 4230 case BatteryManager.BATTERY_HEALTH_GOOD: 4231 pw.print(checkin ? "g" : "good"); 4232 break; 4233 case BatteryManager.BATTERY_HEALTH_OVERHEAT: 4234 pw.print(checkin ? "h" : "overheat"); 4235 break; 4236 case BatteryManager.BATTERY_HEALTH_DEAD: 4237 pw.print(checkin ? "d" : "dead"); 4238 break; 4239 case BatteryManager.BATTERY_HEALTH_OVER_VOLTAGE: 4240 pw.print(checkin ? "v" : "over-voltage"); 4241 break; 4242 case BatteryManager.BATTERY_HEALTH_UNSPECIFIED_FAILURE: 4243 pw.print(checkin ? "f" : "failure"); 4244 break; 4245 case BatteryManager.BATTERY_HEALTH_COLD: 4246 pw.print(checkin ? "c" : "cold"); 4247 break; 4248 default: 4249 pw.print(oldHealth); 4250 break; 4251 } 4252 } 4253 if (oldPlug != rec.batteryPlugType) { 4254 oldPlug = rec.batteryPlugType; 4255 pw.print(checkin ? ",Bp=" : " plug="); 4256 switch (oldPlug) { 4257 case 0: 4258 pw.print(checkin ? "n" : "none"); 4259 break; 4260 case BatteryManager.BATTERY_PLUGGED_AC: 4261 pw.print(checkin ? "a" : "ac"); 4262 break; 4263 case BatteryManager.BATTERY_PLUGGED_USB: 4264 pw.print(checkin ? "u" : "usb"); 4265 break; 4266 case BatteryManager.BATTERY_PLUGGED_WIRELESS: 4267 pw.print(checkin ? "w" : "wireless"); 4268 break; 4269 default: 4270 pw.print(oldPlug); 4271 break; 4272 } 4273 } 4274 if (oldTemp != rec.batteryTemperature) { 4275 oldTemp = rec.batteryTemperature; 4276 pw.print(checkin ? ",Bt=" : " temp="); 4277 pw.print(oldTemp); 4278 } 4279 if (oldVolt != rec.batteryVoltage) { 4280 oldVolt = rec.batteryVoltage; 4281 pw.print(checkin ? ",Bv=" : " volt="); 4282 pw.print(oldVolt); 4283 } 4284 printBitDescriptions(pw, oldState, rec.states, rec.wakelockTag, 4285 HISTORY_STATE_DESCRIPTIONS, !checkin); 4286 printBitDescriptions(pw, oldState2, rec.states2, null, 4287 HISTORY_STATE2_DESCRIPTIONS, !checkin); 4288 if (rec.wakeReasonTag != null) { 4289 if (checkin) { 4290 pw.print(",wr="); 4291 pw.print(rec.wakeReasonTag.poolIdx); 4292 } else { 4293 pw.print(" wake_reason="); 4294 pw.print(rec.wakeReasonTag.uid); 4295 pw.print(":\""); 4296 pw.print(rec.wakeReasonTag.string); 4297 pw.print("\""); 4298 } 4299 } 4300 if (rec.eventCode != HistoryItem.EVENT_NONE) { 4301 pw.print(checkin ? "," : " "); 4302 if ((rec.eventCode&HistoryItem.EVENT_FLAG_START) != 0) { 4303 pw.print("+"); 4304 } else if ((rec.eventCode&HistoryItem.EVENT_FLAG_FINISH) != 0) { 4305 pw.print("-"); 4306 } 4307 String[] eventNames = checkin ? HISTORY_EVENT_CHECKIN_NAMES 4308 : HISTORY_EVENT_NAMES; 4309 int idx = rec.eventCode & ~(HistoryItem.EVENT_FLAG_START 4310 | HistoryItem.EVENT_FLAG_FINISH); 4311 if (idx >= 0 && idx < eventNames.length) { 4312 pw.print(eventNames[idx]); 4313 } else { 4314 pw.print(checkin ? "Ev" : "event"); 4315 pw.print(idx); 4316 } 4317 pw.print("="); 4318 if (checkin) { 4319 pw.print(rec.eventTag.poolIdx); 4320 } else { 4321 UserHandle.formatUid(pw, rec.eventTag.uid); 4322 pw.print(":\""); 4323 pw.print(rec.eventTag.string); 4324 pw.print("\""); 4325 } 4326 } 4327 pw.println(); 4328 if (rec.stepDetails != null) { 4329 if (!checkin) { 4330 pw.print(" Details: cpu="); 4331 pw.print(rec.stepDetails.userTime); 4332 pw.print("u+"); 4333 pw.print(rec.stepDetails.systemTime); 4334 pw.print("s"); 4335 if (rec.stepDetails.appCpuUid1 >= 0) { 4336 pw.print(" ("); 4337 printStepCpuUidDetails(pw, rec.stepDetails.appCpuUid1, 4338 rec.stepDetails.appCpuUTime1, rec.stepDetails.appCpuSTime1); 4339 if (rec.stepDetails.appCpuUid2 >= 0) { 4340 pw.print(", "); 4341 printStepCpuUidDetails(pw, rec.stepDetails.appCpuUid2, 4342 rec.stepDetails.appCpuUTime2, rec.stepDetails.appCpuSTime2); 4343 } 4344 if (rec.stepDetails.appCpuUid3 >= 0) { 4345 pw.print(", "); 4346 printStepCpuUidDetails(pw, rec.stepDetails.appCpuUid3, 4347 rec.stepDetails.appCpuUTime3, rec.stepDetails.appCpuSTime3); 4348 } 4349 pw.print(')'); 4350 } 4351 pw.println(); 4352 pw.print(" /proc/stat="); 4353 pw.print(rec.stepDetails.statUserTime); 4354 pw.print(" usr, "); 4355 pw.print(rec.stepDetails.statSystemTime); 4356 pw.print(" sys, "); 4357 pw.print(rec.stepDetails.statIOWaitTime); 4358 pw.print(" io, "); 4359 pw.print(rec.stepDetails.statIrqTime); 4360 pw.print(" irq, "); 4361 pw.print(rec.stepDetails.statSoftIrqTime); 4362 pw.print(" sirq, "); 4363 pw.print(rec.stepDetails.statIdlTime); 4364 pw.print(" idle"); 4365 int totalRun = rec.stepDetails.statUserTime + rec.stepDetails.statSystemTime 4366 + rec.stepDetails.statIOWaitTime + rec.stepDetails.statIrqTime 4367 + rec.stepDetails.statSoftIrqTime; 4368 int total = totalRun + rec.stepDetails.statIdlTime; 4369 if (total > 0) { 4370 pw.print(" ("); 4371 float perc = ((float)totalRun) / ((float)total) * 100; 4372 pw.print(String.format("%.1f%%", perc)); 4373 pw.print(" of "); 4374 StringBuilder sb = new StringBuilder(64); 4375 formatTimeMsNoSpace(sb, total*10); 4376 pw.print(sb); 4377 pw.print(")"); 4378 } 4379 pw.println(); 4380 } else { 4381 pw.print(BATTERY_STATS_CHECKIN_VERSION); pw.print(','); 4382 pw.print(HISTORY_DATA); pw.print(",0,Dcpu="); 4383 pw.print(rec.stepDetails.userTime); 4384 pw.print(":"); 4385 pw.print(rec.stepDetails.systemTime); 4386 if (rec.stepDetails.appCpuUid1 >= 0) { 4387 printStepCpuUidCheckinDetails(pw, rec.stepDetails.appCpuUid1, 4388 rec.stepDetails.appCpuUTime1, rec.stepDetails.appCpuSTime1); 4389 if (rec.stepDetails.appCpuUid2 >= 0) { 4390 printStepCpuUidCheckinDetails(pw, rec.stepDetails.appCpuUid2, 4391 rec.stepDetails.appCpuUTime2, rec.stepDetails.appCpuSTime2); 4392 } 4393 if (rec.stepDetails.appCpuUid3 >= 0) { 4394 printStepCpuUidCheckinDetails(pw, rec.stepDetails.appCpuUid3, 4395 rec.stepDetails.appCpuUTime3, rec.stepDetails.appCpuSTime3); 4396 } 4397 } 4398 pw.println(); 4399 pw.print(BATTERY_STATS_CHECKIN_VERSION); pw.print(','); 4400 pw.print(HISTORY_DATA); pw.print(",0,Dpst="); 4401 pw.print(rec.stepDetails.statUserTime); 4402 pw.print(','); 4403 pw.print(rec.stepDetails.statSystemTime); 4404 pw.print(','); 4405 pw.print(rec.stepDetails.statIOWaitTime); 4406 pw.print(','); 4407 pw.print(rec.stepDetails.statIrqTime); 4408 pw.print(','); 4409 pw.print(rec.stepDetails.statSoftIrqTime); 4410 pw.print(','); 4411 pw.print(rec.stepDetails.statIdlTime); 4412 pw.println(); 4413 } 4414 } 4415 oldState = rec.states; 4416 oldState2 = rec.states2; 4417 } 4418 } 4419 4420 private void printStepCpuUidDetails(PrintWriter pw, int uid, int utime, int stime) { 4421 UserHandle.formatUid(pw, uid); 4422 pw.print("="); 4423 pw.print(utime); 4424 pw.print("u+"); 4425 pw.print(stime); 4426 pw.print("s"); 4427 } 4428 4429 private void printStepCpuUidCheckinDetails(PrintWriter pw, int uid, int utime, int stime) { 4430 pw.print('/'); 4431 pw.print(uid); 4432 pw.print(":"); 4433 pw.print(utime); 4434 pw.print(":"); 4435 pw.print(stime); 4436 } 4437 } 4438 4439 private void printSizeValue(PrintWriter pw, long size) { 4440 float result = size; 4441 String suffix = ""; 4442 if (result >= 10*1024) { 4443 suffix = "KB"; 4444 result = result / 1024; 4445 } 4446 if (result >= 10*1024) { 4447 suffix = "MB"; 4448 result = result / 1024; 4449 } 4450 if (result >= 10*1024) { 4451 suffix = "GB"; 4452 result = result / 1024; 4453 } 4454 if (result >= 10*1024) { 4455 suffix = "TB"; 4456 result = result / 1024; 4457 } 4458 if (result >= 10*1024) { 4459 suffix = "PB"; 4460 result = result / 1024; 4461 } 4462 pw.print((int)result); 4463 pw.print(suffix); 4464 } 4465 4466 private static boolean dumpTimeEstimate(PrintWriter pw, String label1, String label2, 4467 String label3, long estimatedTime) { 4468 if (estimatedTime < 0) { 4469 return false; 4470 } 4471 pw.print(label1); 4472 pw.print(label2); 4473 pw.print(label3); 4474 StringBuilder sb = new StringBuilder(64); 4475 formatTimeMs(sb, estimatedTime); 4476 pw.print(sb); 4477 pw.println(); 4478 return true; 4479 } 4480 4481 private static boolean dumpDurationSteps(PrintWriter pw, String prefix, String header, 4482 LevelStepTracker steps, boolean checkin) { 4483 if (steps == null) { 4484 return false; 4485 } 4486 int count = steps.mNumStepDurations; 4487 if (count <= 0) { 4488 return false; 4489 } 4490 if (!checkin) { 4491 pw.println(header); 4492 } 4493 String[] lineArgs = new String[5]; 4494 for (int i=0; i<count; i++) { 4495 long duration = steps.getDurationAt(i); 4496 int level = steps.getLevelAt(i); 4497 long initMode = steps.getInitModeAt(i); 4498 long modMode = steps.getModModeAt(i); 4499 if (checkin) { 4500 lineArgs[0] = Long.toString(duration); 4501 lineArgs[1] = Integer.toString(level); 4502 if ((modMode&STEP_LEVEL_MODE_SCREEN_STATE) == 0) { 4503 switch ((int)(initMode&STEP_LEVEL_MODE_SCREEN_STATE) + 1) { 4504 case Display.STATE_OFF: lineArgs[2] = "s-"; break; 4505 case Display.STATE_ON: lineArgs[2] = "s+"; break; 4506 case Display.STATE_DOZE: lineArgs[2] = "sd"; break; 4507 case Display.STATE_DOZE_SUSPEND: lineArgs[2] = "sds"; break; 4508 default: lineArgs[2] = "?"; break; 4509 } 4510 } else { 4511 lineArgs[2] = ""; 4512 } 4513 if ((modMode&STEP_LEVEL_MODE_POWER_SAVE) == 0) { 4514 lineArgs[3] = (initMode&STEP_LEVEL_MODE_POWER_SAVE) != 0 ? "p+" : "p-"; 4515 } else { 4516 lineArgs[3] = ""; 4517 } 4518 if ((modMode&STEP_LEVEL_MODE_DEVICE_IDLE) == 0) { 4519 lineArgs[4] = (initMode&STEP_LEVEL_MODE_DEVICE_IDLE) != 0 ? "i+" : "i-"; 4520 } else { 4521 lineArgs[4] = ""; 4522 } 4523 dumpLine(pw, 0 /* uid */, "i" /* category */, header, (Object[])lineArgs); 4524 } else { 4525 pw.print(prefix); 4526 pw.print("#"); pw.print(i); pw.print(": "); 4527 TimeUtils.formatDuration(duration, pw); 4528 pw.print(" to "); pw.print(level); 4529 boolean haveModes = false; 4530 if ((modMode&STEP_LEVEL_MODE_SCREEN_STATE) == 0) { 4531 pw.print(" ("); 4532 switch ((int)(initMode&STEP_LEVEL_MODE_SCREEN_STATE) + 1) { 4533 case Display.STATE_OFF: pw.print("screen-off"); break; 4534 case Display.STATE_ON: pw.print("screen-on"); break; 4535 case Display.STATE_DOZE: pw.print("screen-doze"); break; 4536 case Display.STATE_DOZE_SUSPEND: pw.print("screen-doze-suspend"); break; 4537 default: pw.print("screen-?"); break; 4538 } 4539 haveModes = true; 4540 } 4541 if ((modMode&STEP_LEVEL_MODE_POWER_SAVE) == 0) { 4542 pw.print(haveModes ? ", " : " ("); 4543 pw.print((initMode&STEP_LEVEL_MODE_POWER_SAVE) != 0 4544 ? "power-save-on" : "power-save-off"); 4545 haveModes = true; 4546 } 4547 if ((modMode&STEP_LEVEL_MODE_DEVICE_IDLE) == 0) { 4548 pw.print(haveModes ? ", " : " ("); 4549 pw.print((initMode&STEP_LEVEL_MODE_DEVICE_IDLE) != 0 4550 ? "device-idle-on" : "device-idle-off"); 4551 haveModes = true; 4552 } 4553 if (haveModes) { 4554 pw.print(")"); 4555 } 4556 pw.println(); 4557 } 4558 } 4559 return true; 4560 } 4561 4562 public static final int DUMP_CHARGED_ONLY = 1<<1; 4563 public static final int DUMP_DAILY_ONLY = 1<<2; 4564 public static final int DUMP_HISTORY_ONLY = 1<<3; 4565 public static final int DUMP_INCLUDE_HISTORY = 1<<4; 4566 public static final int DUMP_VERBOSE = 1<<5; 4567 public static final int DUMP_DEVICE_WIFI_ONLY = 1<<6; 4568 4569 private void dumpHistoryLocked(PrintWriter pw, int flags, long histStart, boolean checkin) { 4570 final HistoryPrinter hprinter = new HistoryPrinter(); 4571 final HistoryItem rec = new HistoryItem(); 4572 long lastTime = -1; 4573 long baseTime = -1; 4574 boolean printed = false; 4575 HistoryEventTracker tracker = null; 4576 while (getNextHistoryLocked(rec)) { 4577 lastTime = rec.time; 4578 if (baseTime < 0) { 4579 baseTime = lastTime; 4580 } 4581 if (rec.time >= histStart) { 4582 if (histStart >= 0 && !printed) { 4583 if (rec.cmd == HistoryItem.CMD_CURRENT_TIME 4584 || rec.cmd == HistoryItem.CMD_RESET 4585 || rec.cmd == HistoryItem.CMD_START 4586 || rec.cmd == HistoryItem.CMD_SHUTDOWN) { 4587 printed = true; 4588 hprinter.printNextItem(pw, rec, baseTime, checkin, 4589 (flags&DUMP_VERBOSE) != 0); 4590 rec.cmd = HistoryItem.CMD_UPDATE; 4591 } else if (rec.currentTime != 0) { 4592 printed = true; 4593 byte cmd = rec.cmd; 4594 rec.cmd = HistoryItem.CMD_CURRENT_TIME; 4595 hprinter.printNextItem(pw, rec, baseTime, checkin, 4596 (flags&DUMP_VERBOSE) != 0); 4597 rec.cmd = cmd; 4598 } 4599 if (tracker != null) { 4600 if (rec.cmd != HistoryItem.CMD_UPDATE) { 4601 hprinter.printNextItem(pw, rec, baseTime, checkin, 4602 (flags&DUMP_VERBOSE) != 0); 4603 rec.cmd = HistoryItem.CMD_UPDATE; 4604 } 4605 int oldEventCode = rec.eventCode; 4606 HistoryTag oldEventTag = rec.eventTag; 4607 rec.eventTag = new HistoryTag(); 4608 for (int i=0; i<HistoryItem.EVENT_COUNT; i++) { 4609 HashMap<String, SparseIntArray> active 4610 = tracker.getStateForEvent(i); 4611 if (active == null) { 4612 continue; 4613 } 4614 for (HashMap.Entry<String, SparseIntArray> ent 4615 : active.entrySet()) { 4616 SparseIntArray uids = ent.getValue(); 4617 for (int j=0; j<uids.size(); j++) { 4618 rec.eventCode = i; 4619 rec.eventTag.string = ent.getKey(); 4620 rec.eventTag.uid = uids.keyAt(j); 4621 rec.eventTag.poolIdx = uids.valueAt(j); 4622 hprinter.printNextItem(pw, rec, baseTime, checkin, 4623 (flags&DUMP_VERBOSE) != 0); 4624 rec.wakeReasonTag = null; 4625 rec.wakelockTag = null; 4626 } 4627 } 4628 } 4629 rec.eventCode = oldEventCode; 4630 rec.eventTag = oldEventTag; 4631 tracker = null; 4632 } 4633 } 4634 hprinter.printNextItem(pw, rec, baseTime, checkin, 4635 (flags&DUMP_VERBOSE) != 0); 4636 } else if (false && rec.eventCode != HistoryItem.EVENT_NONE) { 4637 // This is an attempt to aggregate the previous state and generate 4638 // fake events to reflect that state at the point where we start 4639 // printing real events. It doesn't really work right, so is turned off. 4640 if (tracker == null) { 4641 tracker = new HistoryEventTracker(); 4642 } 4643 tracker.updateState(rec.eventCode, rec.eventTag.string, 4644 rec.eventTag.uid, rec.eventTag.poolIdx); 4645 } 4646 } 4647 if (histStart >= 0) { 4648 commitCurrentHistoryBatchLocked(); 4649 pw.print(checkin ? "NEXT: " : " NEXT: "); pw.println(lastTime+1); 4650 } 4651 } 4652 4653 private void dumpDailyLevelStepSummary(PrintWriter pw, String prefix, String label, 4654 LevelStepTracker steps, StringBuilder tmpSb, int[] tmpOutInt) { 4655 if (steps == null) { 4656 return; 4657 } 4658 long timeRemaining = steps.computeTimeEstimate(0, 0, tmpOutInt); 4659 if (timeRemaining >= 0) { 4660 pw.print(prefix); pw.print(label); pw.print(" total time: "); 4661 tmpSb.setLength(0); 4662 formatTimeMs(tmpSb, timeRemaining); 4663 pw.print(tmpSb); 4664 pw.print(" (from "); pw.print(tmpOutInt[0]); 4665 pw.println(" steps)"); 4666 } 4667 for (int i=0; i< STEP_LEVEL_MODES_OF_INTEREST.length; i++) { 4668 long estimatedTime = steps.computeTimeEstimate(STEP_LEVEL_MODES_OF_INTEREST[i], 4669 STEP_LEVEL_MODE_VALUES[i], tmpOutInt); 4670 if (estimatedTime > 0) { 4671 pw.print(prefix); pw.print(label); pw.print(" "); 4672 pw.print(STEP_LEVEL_MODE_LABELS[i]); 4673 pw.print(" time: "); 4674 tmpSb.setLength(0); 4675 formatTimeMs(tmpSb, estimatedTime); 4676 pw.print(tmpSb); 4677 pw.print(" (from "); pw.print(tmpOutInt[0]); 4678 pw.println(" steps)"); 4679 } 4680 } 4681 } 4682 4683 private void dumpDailyPackageChanges(PrintWriter pw, String prefix, 4684 ArrayList<PackageChange> changes) { 4685 if (changes == null) { 4686 return; 4687 } 4688 pw.print(prefix); pw.println("Package changes:"); 4689 for (int i=0; i<changes.size(); i++) { 4690 PackageChange pc = changes.get(i); 4691 if (pc.mUpdate) { 4692 pw.print(prefix); pw.print(" Update "); pw.print(pc.mPackageName); 4693 pw.print(" vers="); pw.println(pc.mVersionCode); 4694 } else { 4695 pw.print(prefix); pw.print(" Uninstall "); pw.println(pc.mPackageName); 4696 } 4697 } 4698 } 4699 4700 /** 4701 * Dumps a human-readable summary of the battery statistics to the given PrintWriter. 4702 * 4703 * @param pw a Printer to receive the dump output. 4704 */ 4705 @SuppressWarnings("unused") 4706 public void dumpLocked(Context context, PrintWriter pw, int flags, int reqUid, long histStart) { 4707 prepareForDumpLocked(); 4708 4709 final boolean filtering = (flags 4710 & (DUMP_HISTORY_ONLY|DUMP_CHARGED_ONLY|DUMP_DAILY_ONLY)) != 0; 4711 4712 if ((flags&DUMP_HISTORY_ONLY) != 0 || !filtering) { 4713 final long historyTotalSize = getHistoryTotalSize(); 4714 final long historyUsedSize = getHistoryUsedSize(); 4715 if (startIteratingHistoryLocked()) { 4716 try { 4717 pw.print("Battery History ("); 4718 pw.print((100*historyUsedSize)/historyTotalSize); 4719 pw.print("% used, "); 4720 printSizeValue(pw, historyUsedSize); 4721 pw.print(" used of "); 4722 printSizeValue(pw, historyTotalSize); 4723 pw.print(", "); 4724 pw.print(getHistoryStringPoolSize()); 4725 pw.print(" strings using "); 4726 printSizeValue(pw, getHistoryStringPoolBytes()); 4727 pw.println("):"); 4728 dumpHistoryLocked(pw, flags, histStart, false); 4729 pw.println(); 4730 } finally { 4731 finishIteratingHistoryLocked(); 4732 } 4733 } 4734 4735 if (startIteratingOldHistoryLocked()) { 4736 try { 4737 final HistoryItem rec = new HistoryItem(); 4738 pw.println("Old battery History:"); 4739 HistoryPrinter hprinter = new HistoryPrinter(); 4740 long baseTime = -1; 4741 while (getNextOldHistoryLocked(rec)) { 4742 if (baseTime < 0) { 4743 baseTime = rec.time; 4744 } 4745 hprinter.printNextItem(pw, rec, baseTime, false, (flags&DUMP_VERBOSE) != 0); 4746 } 4747 pw.println(); 4748 } finally { 4749 finishIteratingOldHistoryLocked(); 4750 } 4751 } 4752 } 4753 4754 if (filtering && (flags&(DUMP_CHARGED_ONLY|DUMP_DAILY_ONLY)) == 0) { 4755 return; 4756 } 4757 4758 if (!filtering) { 4759 SparseArray<? extends Uid> uidStats = getUidStats(); 4760 final int NU = uidStats.size(); 4761 boolean didPid = false; 4762 long nowRealtime = SystemClock.elapsedRealtime(); 4763 for (int i=0; i<NU; i++) { 4764 Uid uid = uidStats.valueAt(i); 4765 SparseArray<? extends Uid.Pid> pids = uid.getPidStats(); 4766 if (pids != null) { 4767 for (int j=0; j<pids.size(); j++) { 4768 Uid.Pid pid = pids.valueAt(j); 4769 if (!didPid) { 4770 pw.println("Per-PID Stats:"); 4771 didPid = true; 4772 } 4773 long time = pid.mWakeSumMs + (pid.mWakeNesting > 0 4774 ? (nowRealtime - pid.mWakeStartMs) : 0); 4775 pw.print(" PID "); pw.print(pids.keyAt(j)); 4776 pw.print(" wake time: "); 4777 TimeUtils.formatDuration(time, pw); 4778 pw.println(""); 4779 } 4780 } 4781 } 4782 if (didPid) { 4783 pw.println(); 4784 } 4785 } 4786 4787 if (!filtering || (flags&DUMP_CHARGED_ONLY) != 0) { 4788 if (dumpDurationSteps(pw, " ", "Discharge step durations:", 4789 getDischargeLevelStepTracker(), false)) { 4790 long timeRemaining = computeBatteryTimeRemaining(SystemClock.elapsedRealtime()); 4791 if (timeRemaining >= 0) { 4792 pw.print(" Estimated discharge time remaining: "); 4793 TimeUtils.formatDuration(timeRemaining / 1000, pw); 4794 pw.println(); 4795 } 4796 final LevelStepTracker steps = getDischargeLevelStepTracker(); 4797 for (int i=0; i< STEP_LEVEL_MODES_OF_INTEREST.length; i++) { 4798 dumpTimeEstimate(pw, " Estimated ", STEP_LEVEL_MODE_LABELS[i], " time: ", 4799 steps.computeTimeEstimate(STEP_LEVEL_MODES_OF_INTEREST[i], 4800 STEP_LEVEL_MODE_VALUES[i], null)); 4801 } 4802 pw.println(); 4803 } 4804 if (dumpDurationSteps(pw, " ", "Charge step durations:", 4805 getChargeLevelStepTracker(), false)) { 4806 long timeRemaining = computeChargeTimeRemaining(SystemClock.elapsedRealtime()); 4807 if (timeRemaining >= 0) { 4808 pw.print(" Estimated charge time remaining: "); 4809 TimeUtils.formatDuration(timeRemaining / 1000, pw); 4810 pw.println(); 4811 } 4812 pw.println(); 4813 } 4814 } 4815 if (!filtering || (flags&(DUMP_CHARGED_ONLY|DUMP_DAILY_ONLY)) != 0) { 4816 pw.println("Daily stats:"); 4817 pw.print(" Current start time: "); 4818 pw.println(DateFormat.format("yyyy-MM-dd-HH-mm-ss", 4819 getCurrentDailyStartTime()).toString()); 4820 pw.print(" Next min deadline: "); 4821 pw.println(DateFormat.format("yyyy-MM-dd-HH-mm-ss", 4822 getNextMinDailyDeadline()).toString()); 4823 pw.print(" Next max deadline: "); 4824 pw.println(DateFormat.format("yyyy-MM-dd-HH-mm-ss", 4825 getNextMaxDailyDeadline()).toString()); 4826 StringBuilder sb = new StringBuilder(64); 4827 int[] outInt = new int[1]; 4828 LevelStepTracker dsteps = getDailyDischargeLevelStepTracker(); 4829 LevelStepTracker csteps = getDailyChargeLevelStepTracker(); 4830 ArrayList<PackageChange> pkgc = getDailyPackageChanges(); 4831 if (dsteps.mNumStepDurations > 0 || csteps.mNumStepDurations > 0 || pkgc != null) { 4832 if ((flags&DUMP_DAILY_ONLY) != 0 || !filtering) { 4833 if (dumpDurationSteps(pw, " ", " Current daily discharge step durations:", 4834 dsteps, false)) { 4835 dumpDailyLevelStepSummary(pw, " ", "Discharge", dsteps, 4836 sb, outInt); 4837 } 4838 if (dumpDurationSteps(pw, " ", " Current daily charge step durations:", 4839 csteps, false)) { 4840 dumpDailyLevelStepSummary(pw, " ", "Charge", csteps, 4841 sb, outInt); 4842 } 4843 dumpDailyPackageChanges(pw, " ", pkgc); 4844 } else { 4845 pw.println(" Current daily steps:"); 4846 dumpDailyLevelStepSummary(pw, " ", "Discharge", dsteps, 4847 sb, outInt); 4848 dumpDailyLevelStepSummary(pw, " ", "Charge", csteps, 4849 sb, outInt); 4850 } 4851 } 4852 DailyItem dit; 4853 int curIndex = 0; 4854 while ((dit=getDailyItemLocked(curIndex)) != null) { 4855 curIndex++; 4856 if ((flags&DUMP_DAILY_ONLY) != 0) { 4857 pw.println(); 4858 } 4859 pw.print(" Daily from "); 4860 pw.print(DateFormat.format("yyyy-MM-dd-HH-mm-ss", dit.mStartTime).toString()); 4861 pw.print(" to "); 4862 pw.print(DateFormat.format("yyyy-MM-dd-HH-mm-ss", dit.mEndTime).toString()); 4863 pw.println(":"); 4864 if ((flags&DUMP_DAILY_ONLY) != 0 || !filtering) { 4865 if (dumpDurationSteps(pw, " ", 4866 " Discharge step durations:", dit.mDischargeSteps, false)) { 4867 dumpDailyLevelStepSummary(pw, " ", "Discharge", dit.mDischargeSteps, 4868 sb, outInt); 4869 } 4870 if (dumpDurationSteps(pw, " ", 4871 " Charge step durations:", dit.mChargeSteps, false)) { 4872 dumpDailyLevelStepSummary(pw, " ", "Charge", dit.mChargeSteps, 4873 sb, outInt); 4874 } 4875 dumpDailyPackageChanges(pw, " ", dit.mPackageChanges); 4876 } else { 4877 dumpDailyLevelStepSummary(pw, " ", "Discharge", dit.mDischargeSteps, 4878 sb, outInt); 4879 dumpDailyLevelStepSummary(pw, " ", "Charge", dit.mChargeSteps, 4880 sb, outInt); 4881 } 4882 } 4883 pw.println(); 4884 } 4885 if (!filtering || (flags&DUMP_CHARGED_ONLY) != 0) { 4886 pw.println("Statistics since last charge:"); 4887 pw.println(" System starts: " + getStartCount() 4888 + ", currently on battery: " + getIsOnBattery()); 4889 dumpLocked(context, pw, "", STATS_SINCE_CHARGED, reqUid, 4890 (flags&DUMP_DEVICE_WIFI_ONLY) != 0); 4891 pw.println(); 4892 } 4893 } 4894 4895 @SuppressWarnings("unused") 4896 public void dumpCheckinLocked(Context context, PrintWriter pw, 4897 List<ApplicationInfo> apps, int flags, long histStart) { 4898 prepareForDumpLocked(); 4899 4900 dumpLine(pw, 0 /* uid */, "i" /* category */, VERSION_DATA, 4901 CHECKIN_VERSION, getParcelVersion(), getStartPlatformVersion(), 4902 getEndPlatformVersion()); 4903 4904 long now = getHistoryBaseTime() + SystemClock.elapsedRealtime(); 4905 4906 final boolean filtering = (flags & 4907 (DUMP_HISTORY_ONLY|DUMP_CHARGED_ONLY|DUMP_DAILY_ONLY)) != 0; 4908 4909 if ((flags&DUMP_INCLUDE_HISTORY) != 0 || (flags&DUMP_HISTORY_ONLY) != 0) { 4910 if (startIteratingHistoryLocked()) { 4911 try { 4912 for (int i=0; i<getHistoryStringPoolSize(); i++) { 4913 pw.print(BATTERY_STATS_CHECKIN_VERSION); pw.print(','); 4914 pw.print(HISTORY_STRING_POOL); pw.print(','); 4915 pw.print(i); 4916 pw.print(","); 4917 pw.print(getHistoryTagPoolUid(i)); 4918 pw.print(",\""); 4919 String str = getHistoryTagPoolString(i); 4920 str = str.replace("\\", "\\\\"); 4921 str = str.replace("\"", "\\\""); 4922 pw.print(str); 4923 pw.print("\""); 4924 pw.println(); 4925 } 4926 dumpHistoryLocked(pw, flags, histStart, true); 4927 } finally { 4928 finishIteratingHistoryLocked(); 4929 } 4930 } 4931 } 4932 4933 if (filtering && (flags&(DUMP_CHARGED_ONLY|DUMP_DAILY_ONLY)) == 0) { 4934 return; 4935 } 4936 4937 if (apps != null) { 4938 SparseArray<ArrayList<String>> uids = new SparseArray<ArrayList<String>>(); 4939 for (int i=0; i<apps.size(); i++) { 4940 ApplicationInfo ai = apps.get(i); 4941 ArrayList<String> pkgs = uids.get(ai.uid); 4942 if (pkgs == null) { 4943 pkgs = new ArrayList<String>(); 4944 uids.put(ai.uid, pkgs); 4945 } 4946 pkgs.add(ai.packageName); 4947 } 4948 SparseArray<? extends Uid> uidStats = getUidStats(); 4949 final int NU = uidStats.size(); 4950 String[] lineArgs = new String[2]; 4951 for (int i=0; i<NU; i++) { 4952 int uid = uidStats.keyAt(i); 4953 ArrayList<String> pkgs = uids.get(uid); 4954 if (pkgs != null) { 4955 for (int j=0; j<pkgs.size(); j++) { 4956 lineArgs[0] = Integer.toString(uid); 4957 lineArgs[1] = pkgs.get(j); 4958 dumpLine(pw, 0 /* uid */, "i" /* category */, UID_DATA, 4959 (Object[])lineArgs); 4960 } 4961 } 4962 } 4963 } 4964 if (!filtering || (flags&DUMP_CHARGED_ONLY) != 0) { 4965 dumpDurationSteps(pw, "", DISCHARGE_STEP_DATA, getDischargeLevelStepTracker(), true); 4966 String[] lineArgs = new String[1]; 4967 long timeRemaining = computeBatteryTimeRemaining(SystemClock.elapsedRealtime()); 4968 if (timeRemaining >= 0) { 4969 lineArgs[0] = Long.toString(timeRemaining); 4970 dumpLine(pw, 0 /* uid */, "i" /* category */, DISCHARGE_TIME_REMAIN_DATA, 4971 (Object[])lineArgs); 4972 } 4973 dumpDurationSteps(pw, "", CHARGE_STEP_DATA, getChargeLevelStepTracker(), true); 4974 timeRemaining = computeChargeTimeRemaining(SystemClock.elapsedRealtime()); 4975 if (timeRemaining >= 0) { 4976 lineArgs[0] = Long.toString(timeRemaining); 4977 dumpLine(pw, 0 /* uid */, "i" /* category */, CHARGE_TIME_REMAIN_DATA, 4978 (Object[])lineArgs); 4979 } 4980 dumpCheckinLocked(context, pw, STATS_SINCE_CHARGED, -1, 4981 (flags&DUMP_DEVICE_WIFI_ONLY) != 0); 4982 } 4983 } 4984} 4985