summaryrefslogtreecommitdiffstats
path: root/core/java
diff options
context:
space:
mode:
authorDianne Hackborn <hackbod@google.com>2010-08-13 14:09:56 -0700
committerDianne Hackborn <hackbod@google.com>2010-08-13 15:17:49 -0700
commit9adb9c3b10991ef315c270993f4155709c8a232d (patch)
tree445c2437eeb4b3b5fa5597dc0538c04e0fdf490e /core/java
parent3f442ece257d416b48f7803a4cc263f0215faa0d (diff)
downloadframeworks_base-9adb9c3b10991ef315c270993f4155709c8a232d.zip
frameworks_base-9adb9c3b10991ef315c270993f4155709c8a232d.tar.gz
frameworks_base-9adb9c3b10991ef315c270993f4155709c8a232d.tar.bz2
Various battery info things:
- Now track wake locks in battery history. - Now track sensors in battery history. - Some filtering of sensory data. - Fixes to some data that wasn't cleared when resetting battery stats. - Print amount discharged since last charge. And the big part -- keep track of wake locks held per process, and kill processes that hold wake locks too much while they are in the background. This includes information in the battery stats about the process being killed, which will be available to the developer if the app is reported. Change-Id: I97202e94d00aafe0526ba2db74a03212e7539c54
Diffstat (limited to 'core/java')
-rw-r--r--core/java/android/app/ActivityManager.java6
-rw-r--r--core/java/android/os/BatteryStats.java47
-rw-r--r--core/java/com/android/internal/app/IBatteryStats.aidl4
-rw-r--r--core/java/com/android/internal/os/BatteryStatsImpl.java285
4 files changed, 305 insertions, 37 deletions
diff --git a/core/java/android/app/ActivityManager.java b/core/java/android/app/ActivityManager.java
index d66e98b..d5741fc 100644
--- a/core/java/android/app/ActivityManager.java
+++ b/core/java/android/app/ActivityManager.java
@@ -365,7 +365,8 @@ public class ActivityManager {
/**
* The time when the service was first made active, either by someone
- * starting or binding to it.
+ * starting or binding to it. This
+ * is in units of {@link android.os.SystemClock#elapsedRealtime()}.
*/
public long activeSince;
@@ -387,7 +388,8 @@ public class ActivityManager {
/**
* The time when there was last activity in the service (either
- * explicit requests to start it or clients binding to it).
+ * explicit requests to start it or clients binding to it). This
+ * is in units of {@link android.os.SystemClock#uptimeMillis()}.
*/
public long lastActivityTime;
diff --git a/core/java/android/os/BatteryStats.java b/core/java/android/os/BatteryStats.java
index a699388..a0a3bdf 100644
--- a/core/java/android/os/BatteryStats.java
+++ b/core/java/android/os/BatteryStats.java
@@ -290,6 +290,11 @@ public abstract class BatteryStats implements Parcelable {
*/
public static abstract class Proc {
+ public static class ExcessiveWake {
+ public long overTime;
+ public long usedTime;
+ }
+
/**
* Returns the total time (in 1/100 sec) spent executing in user code.
*
@@ -326,6 +331,10 @@ public abstract class BatteryStats implements Parcelable {
* @see BatteryStats#getCpuSpeedSteps()
*/
public abstract long getTimeAtCpuSpeedStep(int speedStep, int which);
+
+ public abstract int countExcessiveWakes();
+
+ public abstract ExcessiveWake getExcessiveWake(int i);
}
/**
@@ -421,6 +430,8 @@ public abstract class BatteryStats implements Parcelable {
public static final int STATE_BLUETOOTH_ON_FLAG = 1<<20;
public static final int STATE_AUDIO_ON_FLAG = 1<<19;
public static final int STATE_VIDEO_ON_FLAG = 1<<18;
+ public static final int STATE_WAKE_LOCK_FLAG = 1<<17;
+ public static final int STATE_SENSOR_ON_FLAG = 1<<16;
public int states;
@@ -470,6 +481,16 @@ public abstract class BatteryStats implements Parcelable {
batteryVoltage = o.batteryVoltage;
states = o.states;
}
+
+ public boolean same(HistoryItem o) {
+ return batteryLevel == o.batteryLevel
+ && batteryStatus == o.batteryStatus
+ && batteryHealth == o.batteryHealth
+ && batteryPlugType == o.batteryPlugType
+ && batteryTemperature == o.batteryTemperature
+ && batteryVoltage == o.batteryVoltage
+ && states == o.states;
+ }
}
public static final class BitDescription {
@@ -633,6 +654,8 @@ public abstract class BatteryStats implements Parcelable {
new BitDescription(HistoryItem.STATE_BLUETOOTH_ON_FLAG, "bluetooth"),
new BitDescription(HistoryItem.STATE_AUDIO_ON_FLAG, "audio"),
new BitDescription(HistoryItem.STATE_VIDEO_ON_FLAG, "video"),
+ new BitDescription(HistoryItem.STATE_WAKE_LOCK_FLAG, "wake_lock"),
+ new BitDescription(HistoryItem.STATE_SENSOR_ON_FLAG, "sensor"),
new BitDescription(HistoryItem.STATE_BRIGHTNESS_MASK,
HistoryItem.STATE_BRIGHTNESS_SHIFT, "brightness",
SCREEN_BRIGHTNESS_NAMES),
@@ -1376,7 +1399,6 @@ public abstract class BatteryStats implements Parcelable {
pw.println(getDischargeStartLevel());
pw.print(prefix); pw.print(" Discharge cycle current level: ");
pw.println(getDischargeCurrentLevel());
- } else {
pw.print(prefix); pw.println(" Device is currently plugged into power");
pw.print(prefix); pw.print(" Last discharge cycle start level: ");
pw.println(getDischargeStartLevel());
@@ -1384,6 +1406,13 @@ public abstract class BatteryStats implements Parcelable {
pw.println(getDischargeCurrentLevel());
}
pw.println(" ");
+ } else {
+ pw.print(prefix); pw.println(" Device battery use since last full charge");
+ pw.print(prefix); pw.print(" Amount discharged (lower bound): ");
+ pw.println(getLowDischargeAmountSinceCharge());
+ pw.print(prefix); pw.print(" Amount discharged (upper bound): ");
+ pw.println(getHighDischargeAmountSinceCharge());
+ pw.println(" ");
}
@@ -1524,12 +1553,16 @@ public abstract class BatteryStats implements Parcelable {
long userTime;
long systemTime;
int starts;
+ int numExcessive;
userTime = ps.getUserTime(which);
systemTime = ps.getSystemTime(which);
starts = ps.getStarts(which);
+ numExcessive = which == STATS_SINCE_CHARGED
+ ? ps.countExcessiveWakes() : 0;
- if (userTime != 0 || systemTime != 0 || starts != 0) {
+ if (userTime != 0 || systemTime != 0 || starts != 0
+ || numExcessive != 0) {
sb.setLength(0);
sb.append(prefix); sb.append(" Proc ");
sb.append(ent.getKey()); sb.append(":\n");
@@ -1539,6 +1572,16 @@ public abstract class BatteryStats implements Parcelable {
sb.append(prefix); sb.append(" "); sb.append(starts);
sb.append(" proc starts");
pw.println(sb.toString());
+ for (int e=0; e<numExcessive; e++) {
+ Uid.Proc.ExcessiveWake ew = ps.getExcessiveWake(e);
+ if (ew != null) {
+ pw.print(prefix); pw.print(" * Killed for wake lock use: ");
+ pw.print(ew.usedTime); pw.print("ms over ");
+ pw.print(ew.overTime); pw.print("ms (");
+ pw.print((ew.usedTime*100)/ew.overTime);
+ pw.println("%)");
+ }
+ }
uidActivity = true;
}
}
diff --git a/core/java/com/android/internal/app/IBatteryStats.aidl b/core/java/com/android/internal/app/IBatteryStats.aidl
index d040d3f..1620778 100644
--- a/core/java/com/android/internal/app/IBatteryStats.aidl
+++ b/core/java/com/android/internal/app/IBatteryStats.aidl
@@ -22,8 +22,8 @@ import android.telephony.SignalStrength;
interface IBatteryStats {
byte[] getStatistics();
- void noteStartWakelock(int uid, String name, int type);
- void noteStopWakelock(int uid, String name, int type);
+ void noteStartWakelock(int uid, int pid, String name, int type);
+ void noteStopWakelock(int uid, int pid, String name, int type);
/* DO NOT CHANGE the position of noteStartSensor without updating
SensorService.cpp */
diff --git a/core/java/com/android/internal/os/BatteryStatsImpl.java b/core/java/com/android/internal/os/BatteryStatsImpl.java
index b3323e9..2f26135 100644
--- a/core/java/com/android/internal/os/BatteryStatsImpl.java
+++ b/core/java/com/android/internal/os/BatteryStatsImpl.java
@@ -27,6 +27,7 @@ import android.os.ParcelFormatException;
import android.os.Parcelable;
import android.os.Process;
import android.os.SystemClock;
+import android.os.BatteryStats.Uid.Proc.ExcessiveWake;
import android.telephony.ServiceState;
import android.telephony.SignalStrength;
import android.telephony.TelephonyManager;
@@ -63,7 +64,7 @@ public final class BatteryStatsImpl extends BatteryStats {
private static final int MAGIC = 0xBA757475; // 'BATSTATS'
// Current on-disk Parcel version
- private static final int VERSION = 49;
+ private static final int VERSION = 50;
// Maximum number of items we will record in the history.
private static final int MAX_HISTORY_ITEMS = 1000;
@@ -107,6 +108,7 @@ public final class BatteryStatsImpl extends BatteryStats {
int mNumHistoryItems;
HistoryItem mHistory;
HistoryItem mHistoryEnd;
+ HistoryItem mHistoryLastEnd;
HistoryItem mHistoryCache;
final HistoryItem mHistoryCur = new HistoryItem();
@@ -451,7 +453,7 @@ public final class BatteryStatsImpl extends BatteryStats {
* Clear state of this timer. Returns true if the timer is inactive
* so can be completely dropped.
*/
- boolean reset(boolean detachIfReset) {
+ boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
mTotalTime = mLoadedTime = mLastTime = 0;
mCount = mLoadedCount = mLastCount = 0;
if (detachIfReset) {
@@ -713,8 +715,8 @@ public final class BatteryStatsImpl extends BatteryStats {
out.writeInt(mTrackingReportedValues ? 1 : 0);
}
- boolean reset(boolean detachIfReset) {
- super.reset(detachIfReset);
+ boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
+ super.reset(stats, detachIfReset);
setStale();
return true;
}
@@ -749,7 +751,7 @@ public final class BatteryStatsImpl extends BatteryStats {
long mUpdateTime;
/**
- * The total time at which the timer was acquired, to determine if
+ * The total time at which the timer was acquired, to determine if it
* was actually held for an interesting duration.
*/
long mAcquireTime;
@@ -890,9 +892,14 @@ public final class BatteryStatsImpl extends BatteryStats {
return mCount;
}
- boolean reset(boolean detachIfReset) {
+ boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
boolean canDetach = mNesting <= 0;
- super.reset(canDetach && detachIfReset);
+ super.reset(stats, canDetach && detachIfReset);
+ if (mNesting > 0) {
+ mUpdateTime = stats.getBatteryRealtimeLocked(
+ SystemClock.elapsedRealtime() * 1000);
+ }
+ mAcquireTime = mTotalTime;
return canDetach;
}
@@ -1113,6 +1120,26 @@ public final class BatteryStatsImpl extends BatteryStats {
if (!mHaveBatteryLevel || !mRecordingHistory) {
return;
}
+
+ // If the current time is basically the same as the last time,
+ // just collapse into one record.
+ if (mHistoryEnd != null && mHistoryEnd.cmd == HistoryItem.CMD_UPDATE
+ && (mHistoryBaseTime+curTime) < (mHistoryEnd.time+100)) {
+ // If the current is the same as the one before, then we no
+ // longer need the entry.
+ if (mHistoryLastEnd != null && mHistoryLastEnd.cmd == HistoryItem.CMD_UPDATE
+ && mHistoryLastEnd.same(mHistoryCur)) {
+ mHistoryLastEnd.next = null;
+ mHistoryEnd.next = mHistoryCache;
+ mHistoryCache = mHistoryEnd;
+ mHistoryEnd = mHistoryLastEnd;
+ mHistoryLastEnd = null;
+ } else {
+ mHistoryEnd.setTo(mHistoryEnd.time, HistoryItem.CMD_UPDATE, mHistoryCur);
+ }
+ return;
+ }
+
if (mNumHistoryItems >= MAX_HISTORY_ITEMS) {
// Once we've reached the maximum number of items, we only
// record changes to the battery level.
@@ -1121,6 +1148,7 @@ public final class BatteryStatsImpl extends BatteryStats {
return;
}
}
+
addHistoryRecordLocked(curTime, HistoryItem.CMD_UPDATE);
}
@@ -1139,6 +1167,7 @@ public final class BatteryStatsImpl extends BatteryStats {
void addHistoryRecordLocked(HistoryItem rec) {
mNumHistoryItems++;
rec.next = null;
+ mHistoryLastEnd = mHistoryEnd;
if (mHistoryEnd != null) {
mHistoryEnd.next = rec;
mHistoryEnd = rec;
@@ -1151,7 +1180,7 @@ public final class BatteryStatsImpl extends BatteryStats {
if (mHistory != null) {
mHistoryEnd.next = mHistoryCache;
mHistoryCache = mHistory;
- mHistory = mHistoryEnd = null;
+ mHistory = mHistoryLastEnd = mHistoryEnd = null;
}
mNumHistoryItems = 0;
mHistoryBaseTime = 0;
@@ -1209,6 +1238,83 @@ public final class BatteryStatsImpl extends BatteryStats {
mBluetoothPingStart = -1;
}
+ int mWakeLockNesting;
+
+ public void noteStartWakeLocked(int uid, int pid, String name, int type) {
+ if (mWakeLockNesting == 0) {
+ mHistoryCur.states |= HistoryItem.STATE_WAKE_LOCK_FLAG;
+ if (DEBUG_HISTORY) Slog.v(TAG, "Start wake lock to: "
+ + Integer.toHexString(mHistoryCur.states));
+ addHistoryRecordLocked(SystemClock.elapsedRealtime());
+ }
+ mWakeLockNesting++;
+ if (uid >= 0) {
+ getUidStatsLocked(uid).noteStartWakeLocked(pid, name, type);
+ }
+ }
+
+ public void noteStopWakeLocked(int uid, int pid, String name, int type) {
+ mWakeLockNesting--;
+ if (mWakeLockNesting == 0) {
+ mHistoryCur.states &= ~HistoryItem.STATE_WAKE_LOCK_FLAG;
+ if (DEBUG_HISTORY) Slog.v(TAG, "Stop wake lock to: "
+ + Integer.toHexString(mHistoryCur.states));
+ addHistoryRecordLocked(SystemClock.elapsedRealtime());
+ }
+ if (uid >= 0) {
+ getUidStatsLocked(uid).noteStopWakeLocked(pid, name, type);
+ }
+ }
+
+ public void noteProcessDiedLocked(int uid, int pid) {
+ Uid u = mUidStats.get(uid);
+ if (u != null) {
+ u.mPids.remove(pid);
+ }
+ }
+
+ public long getProcessWakeTime(int uid, int pid, long realtime) {
+ Uid u = mUidStats.get(uid);
+ if (u != null) {
+ Uid.Pid p = u.mPids.get(pid);
+ if (p != null) {
+ return p.mWakeSum + (p.mWakeStart != 0 ? (realtime - p.mWakeStart) : 0);
+ }
+ }
+ return 0;
+ }
+
+ public void reportExcessiveWakeLocked(int uid, String proc, long overTime, long usedTime) {
+ Uid u = mUidStats.get(uid);
+ if (u != null) {
+ u.reportExcessiveWakeLocked(proc, overTime, usedTime);
+ }
+ }
+
+ int mSensorNesting;
+
+ public void noteStartSensorLocked(int uid, int sensor) {
+ if (mSensorNesting == 0) {
+ mHistoryCur.states |= HistoryItem.STATE_SENSOR_ON_FLAG;
+ if (DEBUG_HISTORY) Slog.v(TAG, "Start sensor to: "
+ + Integer.toHexString(mHistoryCur.states));
+ addHistoryRecordLocked(SystemClock.elapsedRealtime());
+ }
+ mSensorNesting++;
+ getUidStatsLocked(uid).noteStartSensor(sensor);
+ }
+
+ public void noteStopSensorLocked(int uid, int sensor) {
+ mSensorNesting--;
+ if (mSensorNesting == 0) {
+ mHistoryCur.states &= ~HistoryItem.STATE_SENSOR_ON_FLAG;
+ if (DEBUG_HISTORY) Slog.v(TAG, "Stop sensor to: "
+ + Integer.toHexString(mHistoryCur.states));
+ addHistoryRecordLocked(SystemClock.elapsedRealtime());
+ }
+ getUidStatsLocked(uid).noteStopSensor(sensor);
+ }
+
int mGpsNesting;
public void noteStartGpsLocked(int uid) {
@@ -1244,6 +1350,10 @@ public final class BatteryStatsImpl extends BatteryStats {
if (mScreenBrightnessBin >= 0) {
mScreenBrightnessTimer[mScreenBrightnessBin].startRunningLocked(this);
}
+
+ // Fake a wake lock, so we consider the device waked as long
+ // as the screen is on.
+ noteStartWakeLocked(-1, -1, "dummy", 0);
}
}
@@ -1258,6 +1368,8 @@ public final class BatteryStatsImpl extends BatteryStats {
if (mScreenBrightnessBin >= 0) {
mScreenBrightnessTimer[mScreenBrightnessBin].stopRunningLocked(this);
}
+
+ noteStopWakeLocked(-1, -1, "dummy", 0);
}
}
@@ -1798,6 +1910,11 @@ public final class BatteryStatsImpl extends BatteryStats {
*/
final HashMap<String, Pkg> mPackageStats = new HashMap<String, Pkg>();
+ /**
+ * The transient wake stats we have collected for this uid's pids.
+ */
+ final SparseArray<Pid> mPids = new SparseArray<Pid>();
+
public Uid(int uid) {
mUid = uid;
mWifiTurnedOnTimer = new StopwatchTimer(WIFI_TURNED_ON, null, mUnpluggables);
@@ -2081,27 +2198,27 @@ public final class BatteryStatsImpl extends BatteryStats {
boolean active = false;
if (mWifiTurnedOnTimer != null) {
- active |= !mWifiTurnedOnTimer.reset(false);
+ active |= !mWifiTurnedOnTimer.reset(BatteryStatsImpl.this, false);
active |= mWifiTurnedOn;
}
if (mFullWifiLockTimer != null) {
- active |= !mFullWifiLockTimer.reset(false);
+ active |= !mFullWifiLockTimer.reset(BatteryStatsImpl.this, false);
active |= mFullWifiLockOut;
}
if (mScanWifiLockTimer != null) {
- active |= !mScanWifiLockTimer.reset(false);
+ active |= !mScanWifiLockTimer.reset(BatteryStatsImpl.this, false);
active |= mScanWifiLockOut;
}
if (mWifiMulticastTimer != null) {
- active |= !mWifiMulticastTimer.reset(false);
+ active |= !mWifiMulticastTimer.reset(BatteryStatsImpl.this, false);
active |= mWifiMulticastEnabled;
}
if (mAudioTurnedOnTimer != null) {
- active |= !mAudioTurnedOnTimer.reset(false);
+ active |= !mAudioTurnedOnTimer.reset(BatteryStatsImpl.this, false);
active |= mAudioTurnedOn;
}
if (mVideoTurnedOnTimer != null) {
- active |= !mVideoTurnedOnTimer.reset(false);
+ active |= !mVideoTurnedOnTimer.reset(BatteryStatsImpl.this, false);
active |= mVideoTurnedOn;
}
@@ -2146,6 +2263,14 @@ public final class BatteryStatsImpl extends BatteryStats {
}
mProcessStats.clear();
}
+ if (mPids.size() > 0) {
+ for (int i=0; !active && i<mPids.size(); i++) {
+ Pid pid = mPids.valueAt(i);
+ if (pid.mWakeStart != 0) {
+ active = true;
+ }
+ }
+ }
if (mPackageStats.size() > 0) {
Iterator<Map.Entry<String, Pkg>> it = mPackageStats.entrySet().iterator();
while (it.hasNext()) {
@@ -2164,6 +2289,8 @@ public final class BatteryStatsImpl extends BatteryStats {
mPackageStats.clear();
}
+ mPids.clear();
+
if (!active) {
if (mWifiTurnedOnTimer != null) {
mWifiTurnedOnTimer.detach();
@@ -2412,13 +2539,13 @@ public final class BatteryStatsImpl extends BatteryStats {
boolean reset() {
boolean wlactive = false;
if (mTimerFull != null) {
- wlactive |= !mTimerFull.reset(false);
+ wlactive |= !mTimerFull.reset(BatteryStatsImpl.this, false);
}
if (mTimerPartial != null) {
- wlactive |= !mTimerPartial.reset(false);
+ wlactive |= !mTimerPartial.reset(BatteryStatsImpl.this, false);
}
if (mTimerWindow != null) {
- wlactive |= !mTimerWindow.reset(false);
+ wlactive |= !mTimerWindow.reset(BatteryStatsImpl.this, false);
}
if (!wlactive) {
if (mTimerFull != null) {
@@ -2486,7 +2613,7 @@ public final class BatteryStatsImpl extends BatteryStats {
}
boolean reset() {
- if (mTimer.reset(true)) {
+ if (mTimer.reset(BatteryStatsImpl.this, true)) {
mTimer = null;
return true;
}
@@ -2598,6 +2725,8 @@ public final class BatteryStatsImpl extends BatteryStats {
SamplingCounter[] mSpeedBins;
+ ArrayList<ExcessiveWake> mExcessiveWake;
+
Proc() {
mUnpluggables.add(this);
mSpeedBins = new SamplingCounter[getCpuSpeedSteps()];
@@ -2624,6 +2753,58 @@ public final class BatteryStatsImpl extends BatteryStats {
}
}
+ public int countExcessiveWakes() {
+ return mExcessiveWake != null ? mExcessiveWake.size() : 0;
+ }
+
+ public ExcessiveWake getExcessiveWake(int i) {
+ if (mExcessiveWake != null) {
+ return mExcessiveWake.get(i);
+ }
+ return null;
+ }
+
+ public void addExcessiveWake(long overTime, long usedTime) {
+ if (mExcessiveWake == null) {
+ mExcessiveWake = new ArrayList<ExcessiveWake>();
+ }
+ ExcessiveWake ew = new ExcessiveWake();
+ ew.overTime = overTime;
+ ew.usedTime = usedTime;
+ mExcessiveWake.add(ew);
+ }
+
+ void writeExcessiveWakeToParcelLocked(Parcel out) {
+ if (mExcessiveWake == null) {
+ out.writeInt(0);
+ return;
+ }
+
+ final int N = mExcessiveWake.size();
+ out.writeInt(N);
+ for (int i=0; i<N; i++) {
+ ExcessiveWake ew = mExcessiveWake.get(i);
+ out.writeLong(ew.overTime);
+ out.writeLong(ew.usedTime);
+ }
+ }
+
+ void readExcessiveWakeFromParcelLocked(Parcel in) {
+ final int N = in.readInt();
+ if (N == 0) {
+ mExcessiveWake = null;
+ return;
+ }
+
+ mExcessiveWake = new ArrayList<ExcessiveWake>();
+ for (int i=0; i<N; i++) {
+ ExcessiveWake ew = new ExcessiveWake();
+ ew.overTime = in.readLong();
+ ew.usedTime = in.readLong();
+ mExcessiveWake.add(ew);
+ }
+ }
+
void writeToParcelLocked(Parcel out) {
out.writeLong(mUserTime);
out.writeLong(mSystemTime);
@@ -2648,6 +2829,8 @@ public final class BatteryStatsImpl extends BatteryStats {
out.writeInt(0);
}
}
+
+ writeExcessiveWakeToParcelLocked(out);
}
void readFromParcelLocked(Parcel in) {
@@ -2676,6 +2859,8 @@ public final class BatteryStatsImpl extends BatteryStats {
mSpeedBins[i] = new SamplingCounter(mUnpluggables, in);
}
}
+
+ readExcessiveWakeFromParcelLocked(in);
}
public BatteryStatsImpl getBatteryStats() {
@@ -3153,6 +3338,11 @@ public final class BatteryStatsImpl extends BatteryStats {
}
}
+ public class Pid {
+ long mWakeSum;
+ long mWakeStart;
+ }
+
/**
* Retrieve the statistics object for a particular process, creating
* if needed.
@@ -3167,6 +3357,15 @@ public final class BatteryStatsImpl extends BatteryStats {
return ps;
}
+ public Pid getPidStatsLocked(int pid) {
+ Pid p = mPids.get(pid);
+ if (p == null) {
+ p = new Pid();
+ mPids.put(pid, p);
+ }
+ return p;
+ }
+
/**
* Retrieve the statistics object for a particular service, creating
* if needed.
@@ -3259,18 +3458,36 @@ public final class BatteryStatsImpl extends BatteryStats {
return t;
}
- public void noteStartWakeLocked(String name, int type) {
+ public void noteStartWakeLocked(int pid, String name, int type) {
StopwatchTimer t = getWakeTimerLocked(name, type);
if (t != null) {
t.startRunningLocked(BatteryStatsImpl.this);
}
+ if (pid >= 0) {
+ Pid p = getPidStatsLocked(pid);
+ p.mWakeStart = SystemClock.elapsedRealtime();
+ }
}
- public void noteStopWakeLocked(String name, int type) {
+ public void noteStopWakeLocked(int pid, String name, int type) {
StopwatchTimer t = getWakeTimerLocked(name, type);
if (t != null) {
t.stopRunningLocked(BatteryStatsImpl.this);
}
+ if (pid >= 0) {
+ Pid p = mPids.get(pid);
+ if (p != null) {
+ p.mWakeSum += SystemClock.elapsedRealtime() - p.mWakeStart;
+ p.mWakeStart = 0;
+ }
+ }
+ }
+
+ public void reportExcessiveWakeLocked(String proc, long overTime, long usedTime) {
+ Proc p = getProcessStatsLocked(proc);
+ if (p != null) {
+ p.addExcessiveWake(overTime, usedTime);
+ }
}
public void noteStartSensor(int sensor) {
@@ -3372,6 +3589,10 @@ public final class BatteryStatsImpl extends BatteryStats {
return mOnBattery;
}
+ public boolean isScreenOn() {
+ return mScreenOn;
+ }
+
void initTimes() {
mBatteryRealtime = mTrackBatteryPastUptime = 0;
mBatteryUptime = mTrackBatteryPastRealtime = 0;
@@ -3384,24 +3605,24 @@ public final class BatteryStatsImpl extends BatteryStats {
public void resetAllStatsLocked() {
mStartCount = 0;
initTimes();
- mScreenOnTimer.reset(false);
+ mScreenOnTimer.reset(this, false);
for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
- mScreenBrightnessTimer[i].reset(false);
+ mScreenBrightnessTimer[i].reset(this, false);
}
mInputEventCounter.reset(false);
- mPhoneOnTimer.reset(false);
- mAudioOnTimer.reset(false);
- mVideoOnTimer.reset(false);
+ mPhoneOnTimer.reset(this, false);
+ mAudioOnTimer.reset(this, false);
+ mVideoOnTimer.reset(this, false);
for (int i=0; i<NUM_SIGNAL_STRENGTH_BINS; i++) {
- mPhoneSignalStrengthsTimer[i].reset(false);
+ mPhoneSignalStrengthsTimer[i].reset(this, false);
}
- mPhoneSignalScanningTimer.reset(false);
+ mPhoneSignalScanningTimer.reset(this, false);
for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
- mPhoneDataConnectionsTimer[i].reset(false);
+ mPhoneDataConnectionsTimer[i].reset(this, false);
}
- mWifiOnTimer.reset(false);
- mWifiRunningTimer.reset(false);
- mBluetoothOnTimer.reset(false);
+ mWifiOnTimer.reset(this, false);
+ mWifiRunningTimer.reset(this, false);
+ mBluetoothOnTimer.reset(this, false);
for (int i=0; i<mUidStats.size(); i++) {
if (mUidStats.valueAt(i).reset()) {
@@ -4083,6 +4304,7 @@ public final class BatteryStatsImpl extends BatteryStats {
p.mUserTime = p.mLoadedUserTime = in.readLong();
p.mSystemTime = p.mLoadedSystemTime = in.readLong();
p.mStarts = p.mLoadedStarts = in.readInt();
+ p.readExcessiveWakeFromParcelLocked(in);
}
NP = in.readInt();
@@ -4271,6 +4493,7 @@ public final class BatteryStatsImpl extends BatteryStats {
out.writeLong(ps.mUserTime);
out.writeLong(ps.mSystemTime);
out.writeInt(ps.mStarts);
+ ps.writeExcessiveWakeToParcelLocked(out);
}
}