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