blob: 82dcbdb90f909e28a2962a9a909b3cc16d12a0bd [file] [log] [blame]
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001/*
2 * Copyright (C) 2006-2007 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 com.android.internal.os;
18
Jeff Sharkey418d12d2011-12-13 15:38:03 -080019import static com.android.server.NetworkManagementSocketTagger.PROP_QTAGUID_ENABLED;
Dianne Hackborn1afd1c92010-03-18 22:47:17 -070020
Jaikumar Ganesh3f034962010-09-27 17:02:23 -070021import android.bluetooth.BluetoothDevice;
Amith Yamasani3f7e35c2009-07-13 16:02:45 -070022import android.bluetooth.BluetoothHeadset;
Dianne Hackborna7c837f2014-01-15 16:20:44 -080023import android.content.Context;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -070024import android.net.ConnectivityManager;
25import android.net.NetworkStats;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -070026import android.os.BatteryManager;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080027import android.os.BatteryStats;
Dianne Hackborn8bdf5932010-10-15 12:54:40 -070028import android.os.FileUtils;
Dianne Hackborn0d903a82010-09-07 23:51:03 -070029import android.os.Handler;
Jeff Brown6f357d32014-01-15 20:40:55 -080030import android.os.Looper;
Dianne Hackborn0d903a82010-09-07 23:51:03 -070031import android.os.Message;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080032import android.os.Parcel;
33import android.os.ParcelFormatException;
34import android.os.Parcelable;
Evan Millarc64edde2009-04-18 12:26:32 -070035import android.os.Process;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080036import android.os.SystemClock;
Jeff Sharkey418d12d2011-12-13 15:38:03 -080037import android.os.SystemProperties;
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -070038import android.os.WorkSource;
Amith Yamasanif37447b2009-10-08 18:28:01 -070039import android.telephony.ServiceState;
Wink Savillee9b06d72009-05-18 21:47:50 -070040import android.telephony.SignalStrength;
Dianne Hackborn627bba72009-03-24 22:32:56 -070041import android.telephony.TelephonyManager;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080042import android.util.Log;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -070043import android.util.LogWriter;
Dianne Hackborn1d442e02009-04-20 18:14:05 -070044import android.util.PrintWriterPrinter;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080045import android.util.Printer;
Dianne Hackborn1afd1c92010-03-18 22:47:17 -070046import android.util.Slog;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080047import android.util.SparseArray;
Dianne Hackborneaf2ac42014-02-07 13:01:07 -080048import android.util.SparseBooleanArray;
Dianne Hackborn099bc622014-01-22 13:39:16 -080049import android.util.SparseIntArray;
Dianne Hackbornae384452011-06-28 12:33:48 -070050import android.util.TimeUtils;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080051
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -070052import com.android.internal.annotations.GuardedBy;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -070053import com.android.internal.net.NetworkStatsFactory;
Dianne Hackborn8c841092013-06-24 13:46:13 -070054import com.android.internal.util.FastPrintWriter;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -070055import com.android.internal.util.JournaledFile;
56import com.google.android.collect.Sets;
57
Amith Yamasani3718aaa2009-06-09 06:32:35 -070058import java.io.BufferedReader;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080059import java.io.File;
60import java.io.FileInputStream;
61import java.io.FileOutputStream;
Amith Yamasani3718aaa2009-06-09 06:32:35 -070062import java.io.FileReader;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080063import java.io.IOException;
Dianne Hackborn1d442e02009-04-20 18:14:05 -070064import java.io.PrintWriter;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080065import java.util.ArrayList;
66import java.util.HashMap;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -070067import java.util.HashSet;
Evan Millarc64edde2009-04-18 12:26:32 -070068import java.util.Iterator;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -070069import java.util.List;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080070import java.util.Map;
Christopher Tate4cee7252010-03-19 14:50:40 -070071import java.util.concurrent.atomic.AtomicInteger;
Dianne Hackbornce2ef762010-09-20 11:39:14 -070072import java.util.concurrent.locks.ReentrantLock;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080073
74/**
75 * All information we are collecting about things that can happen that impact
76 * battery life. All times are represented in microseconds except where indicated
77 * otherwise.
78 */
79public final class BatteryStatsImpl extends BatteryStats {
80 private static final String TAG = "BatteryStatsImpl";
Dianne Hackborneaf2ac42014-02-07 13:01:07 -080081 private static final boolean DEBUG = false;
Dianne Hackborn32907cf2010-06-10 17:50:20 -070082 private static final boolean DEBUG_HISTORY = false;
Dianne Hackborne8c88e62011-08-17 19:09:09 -070083 private static final boolean USE_OLD_HISTORY = false; // for debugging.
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -070084
Jeff Sharkey1059c3c2011-10-04 16:54:49 -070085 // TODO: remove "tcp" from network methods, since we measure total stats.
86
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080087 // In-memory Parcel magic number, used to detect attempts to unmarshall bad data
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -070088 private static final int MAGIC = 0xBA757475; // 'BATSTATS'
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080089
90 // Current on-disk Parcel version
Dianne Hackborneaf2ac42014-02-07 13:01:07 -080091 private static final int VERSION = 79 + (USE_OLD_HISTORY ? 1000 : 0);
Amith Yamasanie43530a2009-08-21 13:11:37 -070092
Dianne Hackborn6b7b4842010-06-14 17:17:44 -070093 // Maximum number of items we will record in the history.
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -070094 private static final int MAX_HISTORY_ITEMS = 2000;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -070095
Dianne Hackbornf47d8f22010-10-08 10:46:55 -070096 // No, really, THIS is the maximum number of items we will record in the history.
97 private static final int MAX_MAX_HISTORY_ITEMS = 3000;
98
Dianne Hackborn9e0f5d92010-02-22 15:05:42 -080099 // The maximum number of names wakelocks we will keep track of
100 // per uid; once the limit is reached, we batch the remaining wakelocks
101 // in to one common name.
Dianne Hackbornaf17baa2013-05-09 15:27:47 -0700102 private static final int MAX_WAKELOCKS_PER_UID = 50;
Dianne Hackbornc24ab862011-10-18 15:55:03 -0700103
Dianne Hackborn9e0f5d92010-02-22 15:05:42 -0800104 private static final String BATCHED_WAKELOCK_NAME = "*overflow*";
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700105
Amith Yamasanie43530a2009-08-21 13:11:37 -0700106 private static int sNumSpeedSteps;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800107
Dianne Hackborn1afd1c92010-03-18 22:47:17 -0700108 private final JournaledFile mFile;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800109
Dianne Hackborn0d903a82010-09-07 23:51:03 -0700110 static final int MSG_UPDATE_WAKELOCKS = 1;
111 static final int MSG_REPORT_POWER_CHANGE = 2;
Dianne Hackborn287952c2010-09-22 22:34:31 -0700112 static final long DELAY_UPDATE_WAKELOCKS = 5*1000;
Dianne Hackborn0d903a82010-09-07 23:51:03 -0700113
114 public interface BatteryCallback {
115 public void batteryNeedsCpuUpdate();
116 public void batteryPowerChanged(boolean onBattery);
117 }
118
119 final class MyHandler extends Handler {
Jeff Brown6f357d32014-01-15 20:40:55 -0800120 public MyHandler(Looper looper) {
121 super(looper, null, true);
122 }
123
Dianne Hackborn0d903a82010-09-07 23:51:03 -0700124 @Override
125 public void handleMessage(Message msg) {
126 BatteryCallback cb = mCallback;
127 switch (msg.what) {
128 case MSG_UPDATE_WAKELOCKS:
129 if (cb != null) {
130 cb.batteryNeedsCpuUpdate();
131 }
132 break;
133 case MSG_REPORT_POWER_CHANGE:
134 if (cb != null) {
135 cb.batteryPowerChanged(msg.arg1 != 0);
136 }
137 break;
138 }
139 }
140 }
141
142 private final MyHandler mHandler;
143
144 private BatteryCallback mCallback;
145
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800146 /**
Dianne Hackborn099bc622014-01-22 13:39:16 -0800147 * Mapping isolated uids to the actual owning app uid.
148 */
149 final SparseIntArray mIsolatedUids = new SparseIntArray();
150
151 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800152 * The statistics we have collected organized by uids.
153 */
154 final SparseArray<BatteryStatsImpl.Uid> mUidStats =
155 new SparseArray<BatteryStatsImpl.Uid>();
156
157 // A set of pools of currently active timers. When a timer is queried, we will divide the
158 // elapsed time by the number of active timers to arrive at that timer's share of the time.
159 // In order to do this, we must refresh each timer whenever the number of active timers
160 // changes.
Evan Millarc64edde2009-04-18 12:26:32 -0700161 final ArrayList<StopwatchTimer> mPartialTimers = new ArrayList<StopwatchTimer>();
162 final ArrayList<StopwatchTimer> mFullTimers = new ArrayList<StopwatchTimer>();
163 final ArrayList<StopwatchTimer> mWindowTimers = new ArrayList<StopwatchTimer>();
164 final SparseArray<ArrayList<StopwatchTimer>> mSensorTimers
165 = new SparseArray<ArrayList<StopwatchTimer>>();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -0700166 final ArrayList<StopwatchTimer> mWifiRunningTimers = new ArrayList<StopwatchTimer>();
167 final ArrayList<StopwatchTimer> mFullWifiLockTimers = new ArrayList<StopwatchTimer>();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -0700168 final ArrayList<StopwatchTimer> mWifiMulticastTimers = new ArrayList<StopwatchTimer>();
Nick Pelly6ccaa542012-06-15 15:22:47 -0700169 final ArrayList<StopwatchTimer> mWifiScanTimers = new ArrayList<StopwatchTimer>();
Robert Greenwalta029ea12013-09-25 16:38:12 -0700170 final SparseArray<ArrayList<StopwatchTimer>> mWifiBatchedScanTimers =
171 new SparseArray<ArrayList<StopwatchTimer>>();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800172
Dianne Hackborn0d903a82010-09-07 23:51:03 -0700173 // Last partial timers we use for distributing CPU usage.
174 final ArrayList<StopwatchTimer> mLastPartialTimers = new ArrayList<StopwatchTimer>();
175
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800176 // These are the objects that will want to do something when the device
177 // is unplugged from power.
178 final ArrayList<Unpluggable> mUnpluggables = new ArrayList<Unpluggable>();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700179
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700180 boolean mShuttingDown;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700181
Dianne Hackborneaf2ac42014-02-07 13:01:07 -0800182 HashMap<String, SparseBooleanArray>[] mActiveEvents
183 = (HashMap<String, SparseBooleanArray>[]) new HashMap[HistoryItem.EVENT_COUNT];
184
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700185 long mHistoryBaseTime;
186 boolean mHaveBatteryLevel = false;
187 boolean mRecordingHistory = true;
188 int mNumHistoryItems;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -0700189
Dianne Hackborn1fadab52011-04-14 17:57:33 -0700190 static final int MAX_HISTORY_BUFFER = 128*1024; // 128KB
191 static final int MAX_MAX_HISTORY_BUFFER = 144*1024; // 144KB
Dianne Hackborn0ffc9882011-04-13 18:15:56 -0700192 final Parcel mHistoryBuffer = Parcel.obtain();
193 final HistoryItem mHistoryLastWritten = new HistoryItem();
194 final HistoryItem mHistoryLastLastWritten = new HistoryItem();
Dianne Hackborn1fadab52011-04-14 17:57:33 -0700195 final HistoryItem mHistoryReadTmp = new HistoryItem();
Dianne Hackborn71fc13e2014-02-03 10:50:53 -0800196 final HashMap<HistoryTag, Integer> mHistoryTagPool = new HashMap<HistoryTag, Integer>();
Dianne Hackborn099bc622014-01-22 13:39:16 -0800197 String[] mReadHistoryStrings;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -0800198 int[] mReadHistoryUids;
199 int mReadHistoryChars;
200 int mNextHistoryTagIdx = 0;
201 int mNumHistoryTagChars = 0;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -0700202 int mHistoryBufferLastPos = -1;
203 boolean mHistoryOverflow = false;
204 long mLastHistoryTime = 0;
205
206 final HistoryItem mHistoryCur = new HistoryItem();
207
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700208 HistoryItem mHistory;
209 HistoryItem mHistoryEnd;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -0700210 HistoryItem mHistoryLastEnd;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700211 HistoryItem mHistoryCache;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -0700212
213 private HistoryItem mHistoryIterator;
214 private boolean mReadOverflow;
215 private boolean mIteratingHistory;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700216
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800217 int mStartCount;
218
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -0800219 long mStartClockTime;
220
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800221 long mBatteryUptime;
222 long mBatteryLastUptime;
223 long mBatteryRealtime;
224 long mBatteryLastRealtime;
225
226 long mUptime;
227 long mUptimeStart;
228 long mLastUptime;
229 long mRealtime;
230 long mRealtimeStart;
231 long mLastRealtime;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700232
Dianne Hackborn3d658bf2014-02-05 13:38:56 -0800233 int mWakeLockNesting;
234 boolean mWakeLockImportant;
235
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800236 boolean mScreenOn;
Evan Millarc64edde2009-04-18 12:26:32 -0700237 StopwatchTimer mScreenOnTimer;
Amith Yamasani3718aaa2009-06-09 06:32:35 -0700238
Dianne Hackborn617f8772009-03-31 15:04:46 -0700239 int mScreenBrightnessBin = -1;
Evan Millarc64edde2009-04-18 12:26:32 -0700240 final StopwatchTimer[] mScreenBrightnessTimer = new StopwatchTimer[NUM_SCREEN_BRIGHTNESS_BINS];
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700241
Dianne Hackborn617f8772009-03-31 15:04:46 -0700242 Counter mInputEventCounter;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700243
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800244 boolean mPhoneOn;
Evan Millarc64edde2009-04-18 12:26:32 -0700245 StopwatchTimer mPhoneOnTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700246
Amith Yamasani244fa5c2009-05-22 14:36:07 -0700247 boolean mAudioOn;
248 StopwatchTimer mAudioOnTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700249
Amith Yamasani244fa5c2009-05-22 14:36:07 -0700250 boolean mVideoOn;
251 StopwatchTimer mVideoOnTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700252
Dianne Hackborn627bba72009-03-24 22:32:56 -0700253 int mPhoneSignalStrengthBin = -1;
Dianne Hackborne4a59512010-12-07 11:08:07 -0800254 int mPhoneSignalStrengthBinRaw = -1;
Evan Millarc64edde2009-04-18 12:26:32 -0700255 final StopwatchTimer[] mPhoneSignalStrengthsTimer =
Wink Saville52840902011-02-18 12:40:47 -0800256 new StopwatchTimer[SignalStrength.NUM_SIGNAL_STRENGTH_BINS];
Amith Yamasanif37447b2009-10-08 18:28:01 -0700257
258 StopwatchTimer mPhoneSignalScanningTimer;
259
Dianne Hackborn627bba72009-03-24 22:32:56 -0700260 int mPhoneDataConnectionType = -1;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700261 final StopwatchTimer[] mPhoneDataConnectionsTimer =
Evan Millarc64edde2009-04-18 12:26:32 -0700262 new StopwatchTimer[NUM_DATA_CONNECTION_TYPES];
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700263
Dianne Hackborn57ed6a62013-12-09 18:15:56 -0800264 final LongSamplingCounter[] mNetworkByteActivityCounters =
265 new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
266 final LongSamplingCounter[] mNetworkPacketActivityCounters =
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -0700267 new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
268
The Android Open Source Project10592532009-03-18 17:39:46 -0700269 boolean mWifiOn;
Evan Millarc64edde2009-04-18 12:26:32 -0700270 StopwatchTimer mWifiOnTimer;
Dianne Hackborn617f8772009-03-31 15:04:46 -0700271 int mWifiOnUid = -1;
Eric Shienbroodd4c5f892009-03-24 18:13:20 -0700272
Dianne Hackborn58e0eef2010-09-16 01:22:10 -0700273 boolean mGlobalWifiRunning;
274 StopwatchTimer mGlobalWifiRunningTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700275
The Android Open Source Project10592532009-03-18 17:39:46 -0700276 boolean mBluetoothOn;
Evan Millarc64edde2009-04-18 12:26:32 -0700277 StopwatchTimer mBluetoothOnTimer;
Amith Yamasani3f7e35c2009-07-13 16:02:45 -0700278
279 /** Bluetooth headset object */
280 BluetoothHeadset mBtHeadset;
281
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800282 /**
283 * These provide time bases that discount the time the device is plugged
284 * in to power.
285 */
286 boolean mOnBattery;
287 boolean mOnBatteryInternal;
288 long mTrackBatteryPastUptime;
289 long mTrackBatteryUptimeStart;
290 long mTrackBatteryPastRealtime;
291 long mTrackBatteryRealtimeStart;
Amith Yamasani3718aaa2009-06-09 06:32:35 -0700292
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800293 long mUnpluggedBatteryUptime;
294 long mUnpluggedBatteryRealtime;
Amith Yamasani3718aaa2009-06-09 06:32:35 -0700295
The Android Open Source Project10592532009-03-18 17:39:46 -0700296 /*
297 * These keep track of battery levels (1-100) at the last plug event and the last unplug event.
298 */
Evan Millar633a1742009-04-02 16:36:33 -0700299 int mDischargeStartLevel;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700300 int mDischargeUnplugLevel;
Evan Millar633a1742009-04-02 16:36:33 -0700301 int mDischargeCurrentLevel;
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700302 int mLowDischargeAmountSinceCharge;
303 int mHighDischargeAmountSinceCharge;
Dianne Hackbornc1b40e32011-01-05 18:27:40 -0800304 int mDischargeScreenOnUnplugLevel;
305 int mDischargeScreenOffUnplugLevel;
306 int mDischargeAmountScreenOn;
307 int mDischargeAmountScreenOnSinceCharge;
308 int mDischargeAmountScreenOff;
309 int mDischargeAmountScreenOffSinceCharge;
Amith Yamasani244fa5c2009-05-22 14:36:07 -0700310
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800311 long mLastWriteTime = 0; // Milliseconds
Amith Yamasani244fa5c2009-05-22 14:36:07 -0700312
Amith Yamasani3718aaa2009-06-09 06:32:35 -0700313 private long mRadioDataUptime;
314 private long mRadioDataStart;
315
Amith Yamasani3f7e35c2009-07-13 16:02:45 -0700316 private int mBluetoothPingCount;
317 private int mBluetoothPingStart = -1;
318
Amith Yamasanif37447b2009-10-08 18:28:01 -0700319 private int mPhoneServiceState = -1;
Dianne Hackborne4a59512010-12-07 11:08:07 -0800320 private int mPhoneServiceStateRaw = -1;
321 private int mPhoneSimStateRaw = -1;
Amith Yamasanif37447b2009-10-08 18:28:01 -0700322
Evan Millarc64edde2009-04-18 12:26:32 -0700323 /*
324 * Holds a SamplingTimer associated with each kernel wakelock name being tracked.
325 */
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700326 private final HashMap<String, SamplingTimer> mKernelWakelockStats =
Evan Millarc64edde2009-04-18 12:26:32 -0700327 new HashMap<String, SamplingTimer>();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700328
Evan Millarc64edde2009-04-18 12:26:32 -0700329 public Map<String, ? extends SamplingTimer> getKernelWakelockStats() {
330 return mKernelWakelockStats;
331 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700332
Evan Millarc64edde2009-04-18 12:26:32 -0700333 private static int sKernelWakelockUpdateVersion = 0;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700334
Evan Millarc64edde2009-04-18 12:26:32 -0700335 private static final int[] PROC_WAKELOCKS_FORMAT = new int[] {
Dianne Hackborn13ac0412013-06-25 19:34:49 -0700336 Process.PROC_TAB_TERM|Process.PROC_OUT_STRING| // 0: name
337 Process.PROC_QUOTES,
Evan Millarc64edde2009-04-18 12:26:32 -0700338 Process.PROC_TAB_TERM|Process.PROC_OUT_LONG, // 1: count
339 Process.PROC_TAB_TERM,
340 Process.PROC_TAB_TERM,
341 Process.PROC_TAB_TERM,
342 Process.PROC_TAB_TERM|Process.PROC_OUT_LONG, // 5: totalTime
343 };
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700344
Todd Poynor73f534a2012-06-19 11:07:26 -0700345 private static final int[] WAKEUP_SOURCES_FORMAT = new int[] {
346 Process.PROC_TAB_TERM|Process.PROC_OUT_STRING, // 0: name
347 Process.PROC_TAB_TERM|Process.PROC_COMBINE|
348 Process.PROC_OUT_LONG, // 1: count
349 Process.PROC_TAB_TERM|Process.PROC_COMBINE,
350 Process.PROC_TAB_TERM|Process.PROC_COMBINE,
351 Process.PROC_TAB_TERM|Process.PROC_COMBINE,
352 Process.PROC_TAB_TERM|Process.PROC_COMBINE,
353 Process.PROC_TAB_TERM|Process.PROC_COMBINE
354 |Process.PROC_OUT_LONG, // 6: totalTime
355 };
356
Evan Millarc64edde2009-04-18 12:26:32 -0700357 private final String[] mProcWakelocksName = new String[3];
358 private final long[] mProcWakelocksData = new long[3];
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700359
Evan Millarc64edde2009-04-18 12:26:32 -0700360 /*
361 * Used as a buffer for reading in data from /proc/wakelocks before it is processed and added
362 * to mKernelWakelockStats.
363 */
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700364 private final Map<String, KernelWakelockStats> mProcWakelockFileStats =
Evan Millarc64edde2009-04-18 12:26:32 -0700365 new HashMap<String, KernelWakelockStats>();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800366
Jeff Sharkey1059c3c2011-10-04 16:54:49 -0700367 private final NetworkStatsFactory mNetworkStatsFactory = new NetworkStatsFactory();
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -0700368 private NetworkStats mLastSnapshot;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -0700369
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -0700370 @GuardedBy("this")
Jeff Sharkey1059c3c2011-10-04 16:54:49 -0700371 private HashSet<String> mMobileIfaces = Sets.newHashSet();
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -0700372 @GuardedBy("this")
373 private HashSet<String> mWifiIfaces = Sets.newHashSet();
Jeff Sharkey1059c3c2011-10-04 16:54:49 -0700374
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800375 // For debugging
376 public BatteryStatsImpl() {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -0700377 mFile = null;
Dianne Hackborn0d903a82010-09-07 23:51:03 -0700378 mHandler = null;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800379 }
380
381 public static interface Unpluggable {
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800382 void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime);
383 void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800384 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700385
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800386 /**
Dianne Hackborn617f8772009-03-31 15:04:46 -0700387 * State for keeping track of counting information.
388 */
Amith Yamasanie43530a2009-08-21 13:11:37 -0700389 public static class Counter extends BatteryStats.Counter implements Unpluggable {
Christopher Tate4cee7252010-03-19 14:50:40 -0700390 final AtomicInteger mCount = new AtomicInteger();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700391 final ArrayList<Unpluggable> mUnpluggables;
Dianne Hackborn617f8772009-03-31 15:04:46 -0700392 int mLoadedCount;
393 int mLastCount;
394 int mUnpluggedCount;
395 int mPluggedCount;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700396
Dianne Hackborn617f8772009-03-31 15:04:46 -0700397 Counter(ArrayList<Unpluggable> unpluggables, Parcel in) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700398 mUnpluggables = unpluggables;
Christopher Tate4cee7252010-03-19 14:50:40 -0700399 mPluggedCount = in.readInt();
400 mCount.set(mPluggedCount);
Dianne Hackborn617f8772009-03-31 15:04:46 -0700401 mLoadedCount = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700402 mLastCount = 0;
Dianne Hackborn617f8772009-03-31 15:04:46 -0700403 mUnpluggedCount = in.readInt();
404 unpluggables.add(this);
405 }
406
407 Counter(ArrayList<Unpluggable> unpluggables) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700408 mUnpluggables = unpluggables;
Dianne Hackborn617f8772009-03-31 15:04:46 -0700409 unpluggables.add(this);
410 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700411
Dianne Hackborn617f8772009-03-31 15:04:46 -0700412 public void writeToParcel(Parcel out) {
Christopher Tate4cee7252010-03-19 14:50:40 -0700413 out.writeInt(mCount.get());
Dianne Hackborn617f8772009-03-31 15:04:46 -0700414 out.writeInt(mLoadedCount);
Dianne Hackborn617f8772009-03-31 15:04:46 -0700415 out.writeInt(mUnpluggedCount);
416 }
417
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800418 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
Christopher Tate4cee7252010-03-19 14:50:40 -0700419 mUnpluggedCount = mPluggedCount;
420 mCount.set(mPluggedCount);
Dianne Hackborn617f8772009-03-31 15:04:46 -0700421 }
422
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800423 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
Christopher Tate4cee7252010-03-19 14:50:40 -0700424 mPluggedCount = mCount.get();
Dianne Hackborn617f8772009-03-31 15:04:46 -0700425 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700426
Dianne Hackborn617f8772009-03-31 15:04:46 -0700427 /**
428 * Writes a possibly null Counter to a Parcel.
429 *
430 * @param out the Parcel to be written to.
431 * @param counter a Counter, or null.
432 */
433 public static void writeCounterToParcel(Parcel out, Counter counter) {
434 if (counter == null) {
435 out.writeInt(0); // indicates null
436 return;
437 }
438 out.writeInt(1); // indicates non-null
439
440 counter.writeToParcel(out);
441 }
442
443 @Override
Evan Millarc64edde2009-04-18 12:26:32 -0700444 public int getCountLocked(int which) {
Dianne Hackborn617f8772009-03-31 15:04:46 -0700445 int val;
446 if (which == STATS_LAST) {
447 val = mLastCount;
448 } else {
Christopher Tate4cee7252010-03-19 14:50:40 -0700449 val = mCount.get();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700450 if (which == STATS_SINCE_UNPLUGGED) {
Dianne Hackborn617f8772009-03-31 15:04:46 -0700451 val -= mUnpluggedCount;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700452 } else if (which != STATS_SINCE_CHARGED) {
Dianne Hackborn617f8772009-03-31 15:04:46 -0700453 val -= mLoadedCount;
454 }
455 }
456
457 return val;
458 }
459
460 public void logState(Printer pw, String prefix) {
Christopher Tate4cee7252010-03-19 14:50:40 -0700461 pw.println(prefix + "mCount=" + mCount.get()
Dianne Hackborn617f8772009-03-31 15:04:46 -0700462 + " mLoadedCount=" + mLoadedCount + " mLastCount=" + mLastCount
463 + " mUnpluggedCount=" + mUnpluggedCount
464 + " mPluggedCount=" + mPluggedCount);
465 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700466
Christopher Tate4cee7252010-03-19 14:50:40 -0700467 void stepAtomic() {
468 mCount.incrementAndGet();
Dianne Hackborn617f8772009-03-31 15:04:46 -0700469 }
470
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700471 /**
472 * Clear state of this counter.
473 */
474 void reset(boolean detachIfReset) {
475 mCount.set(0);
476 mLoadedCount = mLastCount = mPluggedCount = mUnpluggedCount = 0;
477 if (detachIfReset) {
478 detach();
479 }
480 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700481
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700482 void detach() {
483 mUnpluggables.remove(this);
484 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700485
Dianne Hackborn617f8772009-03-31 15:04:46 -0700486 void writeSummaryFromParcelLocked(Parcel out) {
Christopher Tate4cee7252010-03-19 14:50:40 -0700487 int count = mCount.get();
488 out.writeInt(count);
Dianne Hackborn617f8772009-03-31 15:04:46 -0700489 }
490
491 void readSummaryFromParcelLocked(Parcel in) {
Christopher Tate4cee7252010-03-19 14:50:40 -0700492 mLoadedCount = in.readInt();
493 mCount.set(mLoadedCount);
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700494 mLastCount = 0;
Christopher Tate4cee7252010-03-19 14:50:40 -0700495 mUnpluggedCount = mPluggedCount = mLoadedCount;
Dianne Hackborn617f8772009-03-31 15:04:46 -0700496 }
497 }
Amith Yamasanie43530a2009-08-21 13:11:37 -0700498
499 public static class SamplingCounter extends Counter {
Amith Yamasanie43530a2009-08-21 13:11:37 -0700500 SamplingCounter(ArrayList<Unpluggable> unpluggables, Parcel in) {
501 super(unpluggables, in);
502 }
503
504 SamplingCounter(ArrayList<Unpluggable> unpluggables) {
505 super(unpluggables);
506 }
507
Christopher Tate4cee7252010-03-19 14:50:40 -0700508 public void addCountAtomic(long count) {
509 mCount.addAndGet((int)count);
Amith Yamasanie43530a2009-08-21 13:11:37 -0700510 }
511 }
512
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -0700513 public static class LongSamplingCounter implements Unpluggable {
514 final ArrayList<Unpluggable> mUnpluggables;
515 long mCount;
516 long mLoadedCount;
517 long mLastCount;
518 long mUnpluggedCount;
519 long mPluggedCount;
520
521 LongSamplingCounter(ArrayList<Unpluggable> unpluggables, Parcel in) {
522 mUnpluggables = unpluggables;
523 mPluggedCount = in.readLong();
524 mCount = mPluggedCount;
525 mLoadedCount = in.readLong();
526 mLastCount = 0;
527 mUnpluggedCount = in.readLong();
528 unpluggables.add(this);
529 }
530
531 LongSamplingCounter(ArrayList<Unpluggable> unpluggables) {
532 mUnpluggables = unpluggables;
533 unpluggables.add(this);
534 }
535
536 public void writeToParcel(Parcel out) {
537 out.writeLong(mCount);
538 out.writeLong(mLoadedCount);
539 out.writeLong(mUnpluggedCount);
540 }
541
542 @Override
543 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
544 mUnpluggedCount = mPluggedCount;
545 mCount = mPluggedCount;
546 }
547
548 @Override
549 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
550 mPluggedCount = mCount;
551 }
552
553 public long getCountLocked(int which) {
554 long val;
555 if (which == STATS_LAST) {
556 val = mLastCount;
557 } else {
558 val = mCount;
559 if (which == STATS_SINCE_UNPLUGGED) {
560 val -= mUnpluggedCount;
561 } else if (which != STATS_SINCE_CHARGED) {
562 val -= mLoadedCount;
563 }
564 }
565
566 return val;
567 }
568
569 void addCountLocked(long count) {
570 mCount += count;
571 }
572
573 /**
574 * Clear state of this counter.
575 */
576 void reset(boolean detachIfReset) {
577 mCount = 0;
578 mLoadedCount = mLastCount = mPluggedCount = mUnpluggedCount = 0;
579 if (detachIfReset) {
580 detach();
581 }
582 }
583
584 void detach() {
585 mUnpluggables.remove(this);
586 }
587
588 void writeSummaryFromParcelLocked(Parcel out) {
589 out.writeLong(mCount);
590 }
591
592 void readSummaryFromParcelLocked(Parcel in) {
593 mLoadedCount = in.readLong();
594 mCount = mLoadedCount;
595 mLastCount = 0;
596 mUnpluggedCount = mPluggedCount = mLoadedCount;
597 }
598 }
599
Dianne Hackborn617f8772009-03-31 15:04:46 -0700600 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800601 * State for keeping track of timing information.
602 */
Evan Millarc64edde2009-04-18 12:26:32 -0700603 public static abstract class Timer extends BatteryStats.Timer implements Unpluggable {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800604 final int mType;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700605 final ArrayList<Unpluggable> mUnpluggables;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700606
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800607 int mCount;
608 int mLoadedCount;
609 int mLastCount;
610 int mUnpluggedCount;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700611
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800612 // Times are in microseconds for better accuracy when dividing by the
613 // lock count, and are in "battery realtime" units.
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700614
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800615 /**
616 * The total time we have accumulated since the start of the original
617 * boot, to the last time something interesting happened in the
618 * current run.
619 */
620 long mTotalTime;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700621
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800622 /**
623 * The total time we loaded for the previous runs. Subtract this from
624 * mTotalTime to find the time for the current run of the system.
625 */
626 long mLoadedTime;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700627
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800628 /**
629 * The run time of the last run of the system, as loaded from the
630 * saved data.
631 */
632 long mLastTime;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700633
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800634 /**
635 * The value of mTotalTime when unplug() was last called. Subtract
636 * this from mTotalTime to find the time since the last unplug from
637 * power.
638 */
639 long mUnpluggedTime;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700640
Amith Yamasani244fa5c2009-05-22 14:36:07 -0700641 /**
642 * Constructs from a parcel.
643 * @param type
644 * @param unpluggables
Amith Yamasani244fa5c2009-05-22 14:36:07 -0700645 * @param in
646 */
Evan Millarc64edde2009-04-18 12:26:32 -0700647 Timer(int type, ArrayList<Unpluggable> unpluggables, Parcel in) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800648 mType = type;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700649 mUnpluggables = unpluggables;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700650
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800651 mCount = in.readInt();
652 mLoadedCount = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700653 mLastCount = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800654 mUnpluggedCount = in.readInt();
655 mTotalTime = in.readLong();
656 mLoadedTime = in.readLong();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700657 mLastTime = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800658 mUnpluggedTime = in.readLong();
659 unpluggables.add(this);
660 }
661
Evan Millarc64edde2009-04-18 12:26:32 -0700662 Timer(int type, ArrayList<Unpluggable> unpluggables) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800663 mType = type;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700664 mUnpluggables = unpluggables;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800665 unpluggables.add(this);
666 }
Evan Millarc64edde2009-04-18 12:26:32 -0700667
668 protected abstract long computeRunTimeLocked(long curBatteryRealtime);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700669
Evan Millarc64edde2009-04-18 12:26:32 -0700670 protected abstract int computeCurrentCountLocked();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700671
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700672 /**
673 * Clear state of this timer. Returns true if the timer is inactive
674 * so can be completely dropped.
675 */
Dianne Hackborn9adb9c32010-08-13 14:09:56 -0700676 boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700677 mTotalTime = mLoadedTime = mLastTime = 0;
678 mCount = mLoadedCount = mLastCount = 0;
679 if (detachIfReset) {
680 detach();
681 }
682 return true;
683 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700684
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700685 void detach() {
686 mUnpluggables.remove(this);
687 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700688
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800689 public void writeToParcel(Parcel out, long batteryRealtime) {
690 out.writeInt(mCount);
691 out.writeInt(mLoadedCount);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800692 out.writeInt(mUnpluggedCount);
693 out.writeLong(computeRunTimeLocked(batteryRealtime));
694 out.writeLong(mLoadedTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800695 out.writeLong(mUnpluggedTime);
696 }
697
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800698 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800699 if (DEBUG && mType < 0) {
700 Log.v(TAG, "unplug #" + mType + ": realtime=" + batteryRealtime
701 + " old mUnpluggedTime=" + mUnpluggedTime
702 + " old mUnpluggedCount=" + mUnpluggedCount);
703 }
704 mUnpluggedTime = computeRunTimeLocked(batteryRealtime);
705 mUnpluggedCount = mCount;
706 if (DEBUG && mType < 0) {
707 Log.v(TAG, "unplug #" + mType
708 + ": new mUnpluggedTime=" + mUnpluggedTime
709 + " new mUnpluggedCount=" + mUnpluggedCount);
710 }
711 }
712
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800713 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
Evan Millarc64edde2009-04-18 12:26:32 -0700714 if (DEBUG && mType < 0) {
715 Log.v(TAG, "plug #" + mType + ": realtime=" + batteryRealtime
716 + " old mTotalTime=" + mTotalTime);
717 }
718 mTotalTime = computeRunTimeLocked(batteryRealtime);
719 mCount = computeCurrentCountLocked();
720 if (DEBUG && mType < 0) {
721 Log.v(TAG, "plug #" + mType
722 + ": new mTotalTime=" + mTotalTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800723 }
724 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700725
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800726 /**
727 * Writes a possibly null Timer to a Parcel.
728 *
729 * @param out the Parcel to be written to.
730 * @param timer a Timer, or null.
731 */
732 public static void writeTimerToParcel(Parcel out, Timer timer,
733 long batteryRealtime) {
734 if (timer == null) {
735 out.writeInt(0); // indicates null
736 return;
737 }
738 out.writeInt(1); // indicates non-null
739
740 timer.writeToParcel(out, batteryRealtime);
741 }
742
743 @Override
Evan Millarc64edde2009-04-18 12:26:32 -0700744 public long getTotalTimeLocked(long batteryRealtime, int which) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800745 long val;
746 if (which == STATS_LAST) {
747 val = mLastTime;
748 } else {
749 val = computeRunTimeLocked(batteryRealtime);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700750 if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800751 val -= mUnpluggedTime;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700752 } else if (which != STATS_SINCE_CHARGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800753 val -= mLoadedTime;
754 }
755 }
756
757 return val;
758 }
759
760 @Override
Evan Millarc64edde2009-04-18 12:26:32 -0700761 public int getCountLocked(int which) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800762 int val;
763 if (which == STATS_LAST) {
764 val = mLastCount;
765 } else {
Evan Millarc64edde2009-04-18 12:26:32 -0700766 val = computeCurrentCountLocked();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700767 if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800768 val -= mUnpluggedCount;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700769 } else if (which != STATS_SINCE_CHARGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800770 val -= mLoadedCount;
771 }
772 }
773
774 return val;
775 }
776
Dianne Hackborn627bba72009-03-24 22:32:56 -0700777 public void logState(Printer pw, String prefix) {
Jeff Sharkey3e013e82013-04-25 14:48:19 -0700778 pw.println(prefix + "mCount=" + mCount
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800779 + " mLoadedCount=" + mLoadedCount + " mLastCount=" + mLastCount
780 + " mUnpluggedCount=" + mUnpluggedCount);
Dianne Hackborn627bba72009-03-24 22:32:56 -0700781 pw.println(prefix + "mTotalTime=" + mTotalTime
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800782 + " mLoadedTime=" + mLoadedTime);
Dianne Hackborn627bba72009-03-24 22:32:56 -0700783 pw.println(prefix + "mLastTime=" + mLastTime
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800784 + " mUnpluggedTime=" + mUnpluggedTime);
Evan Millarc64edde2009-04-18 12:26:32 -0700785 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700786
787
Evan Millarc64edde2009-04-18 12:26:32 -0700788 void writeSummaryFromParcelLocked(Parcel out, long batteryRealtime) {
789 long runTime = computeRunTimeLocked(batteryRealtime);
790 // Divide by 1000 for backwards compatibility
791 out.writeLong((runTime + 500) / 1000);
Evan Millarc64edde2009-04-18 12:26:32 -0700792 out.writeInt(mCount);
Evan Millarc64edde2009-04-18 12:26:32 -0700793 }
794
795 void readSummaryFromParcelLocked(Parcel in) {
796 // Multiply by 1000 for backwards compatibility
797 mTotalTime = mLoadedTime = in.readLong() * 1000;
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700798 mLastTime = 0;
Evan Millarc64edde2009-04-18 12:26:32 -0700799 mUnpluggedTime = mTotalTime;
800 mCount = mLoadedCount = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -0700801 mLastCount = 0;
Evan Millarc64edde2009-04-18 12:26:32 -0700802 mUnpluggedCount = mCount;
803 }
804 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700805
Evan Millarc64edde2009-04-18 12:26:32 -0700806 public static final class SamplingTimer extends Timer {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700807
Evan Millarc64edde2009-04-18 12:26:32 -0700808 /**
809 * The most recent reported count from /proc/wakelocks.
810 */
811 int mCurrentReportedCount;
812
813 /**
814 * The reported count from /proc/wakelocks when unplug() was last
815 * called.
816 */
817 int mUnpluggedReportedCount;
818
819 /**
820 * The most recent reported total_time from /proc/wakelocks.
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700821 */
Evan Millarc64edde2009-04-18 12:26:32 -0700822 long mCurrentReportedTotalTime;
823
824
825 /**
826 * The reported total_time from /proc/wakelocks when unplug() was last
827 * called.
828 */
829 long mUnpluggedReportedTotalTime;
830
831 /**
832 * Whether we are currently in a discharge cycle.
833 */
834 boolean mInDischarge;
835
836 /**
837 * Whether we are currently recording reported values.
838 */
839 boolean mTrackingReportedValues;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700840
Evan Millarc64edde2009-04-18 12:26:32 -0700841 /*
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800842 * A sequence counter, incremented once for each update of the stats.
Evan Millarc64edde2009-04-18 12:26:32 -0700843 */
844 int mUpdateVersion;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700845
Evan Millarc64edde2009-04-18 12:26:32 -0700846 SamplingTimer(ArrayList<Unpluggable> unpluggables, boolean inDischarge, Parcel in) {
847 super(0, unpluggables, in);
848 mCurrentReportedCount = in.readInt();
849 mUnpluggedReportedCount = in.readInt();
850 mCurrentReportedTotalTime = in.readLong();
851 mUnpluggedReportedTotalTime = in.readLong();
852 mTrackingReportedValues = in.readInt() == 1;
853 mInDischarge = inDischarge;
854 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700855
856 SamplingTimer(ArrayList<Unpluggable> unpluggables, boolean inDischarge,
Evan Millarc64edde2009-04-18 12:26:32 -0700857 boolean trackReportedValues) {
858 super(0, unpluggables);
859 mTrackingReportedValues = trackReportedValues;
860 mInDischarge = inDischarge;
861 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700862
Evan Millarc64edde2009-04-18 12:26:32 -0700863 public void setStale() {
864 mTrackingReportedValues = false;
865 mUnpluggedReportedTotalTime = 0;
866 mUnpluggedReportedCount = 0;
867 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700868
Evan Millarc64edde2009-04-18 12:26:32 -0700869 public void setUpdateVersion(int version) {
870 mUpdateVersion = version;
871 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700872
Evan Millarc64edde2009-04-18 12:26:32 -0700873 public int getUpdateVersion() {
874 return mUpdateVersion;
875 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700876
Evan Millarc64edde2009-04-18 12:26:32 -0700877 public void updateCurrentReportedCount(int count) {
878 if (mInDischarge && mUnpluggedReportedCount == 0) {
879 // Updating the reported value for the first time.
880 mUnpluggedReportedCount = count;
881 // If we are receiving an update update mTrackingReportedValues;
882 mTrackingReportedValues = true;
883 }
884 mCurrentReportedCount = count;
885 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700886
Evan Millarc64edde2009-04-18 12:26:32 -0700887 public void updateCurrentReportedTotalTime(long totalTime) {
888 if (mInDischarge && mUnpluggedReportedTotalTime == 0) {
889 // Updating the reported value for the first time.
890 mUnpluggedReportedTotalTime = totalTime;
891 // If we are receiving an update update mTrackingReportedValues;
892 mTrackingReportedValues = true;
893 }
894 mCurrentReportedTotalTime = totalTime;
895 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700896
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800897 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
898 super.unplug(elapsedRealtime, batteryUptime, batteryRealtime);
Evan Millarc64edde2009-04-18 12:26:32 -0700899 if (mTrackingReportedValues) {
900 mUnpluggedReportedTotalTime = mCurrentReportedTotalTime;
901 mUnpluggedReportedCount = mCurrentReportedCount;
902 }
903 mInDischarge = true;
904 }
905
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800906 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
907 super.plug(elapsedRealtime, batteryUptime, batteryRealtime);
Evan Millarc64edde2009-04-18 12:26:32 -0700908 mInDischarge = false;
909 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700910
Evan Millarc64edde2009-04-18 12:26:32 -0700911 public void logState(Printer pw, String prefix) {
912 super.logState(pw, prefix);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700913 pw.println(prefix + "mCurrentReportedCount=" + mCurrentReportedCount
Evan Millarc64edde2009-04-18 12:26:32 -0700914 + " mUnpluggedReportedCount=" + mUnpluggedReportedCount
915 + " mCurrentReportedTotalTime=" + mCurrentReportedTotalTime
916 + " mUnpluggedReportedTotalTime=" + mUnpluggedReportedTotalTime);
917 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700918
Evan Millarc64edde2009-04-18 12:26:32 -0700919 protected long computeRunTimeLocked(long curBatteryRealtime) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700920 return mTotalTime + (mInDischarge && mTrackingReportedValues
Evan Millarc64edde2009-04-18 12:26:32 -0700921 ? mCurrentReportedTotalTime - mUnpluggedReportedTotalTime : 0);
922 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700923
Evan Millarc64edde2009-04-18 12:26:32 -0700924 protected int computeCurrentCountLocked() {
925 return mCount + (mInDischarge && mTrackingReportedValues
926 ? mCurrentReportedCount - mUnpluggedReportedCount : 0);
927 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700928
Evan Millarc64edde2009-04-18 12:26:32 -0700929 public void writeToParcel(Parcel out, long batteryRealtime) {
930 super.writeToParcel(out, batteryRealtime);
931 out.writeInt(mCurrentReportedCount);
932 out.writeInt(mUnpluggedReportedCount);
933 out.writeLong(mCurrentReportedTotalTime);
934 out.writeLong(mUnpluggedReportedTotalTime);
935 out.writeInt(mTrackingReportedValues ? 1 : 0);
936 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700937
Dianne Hackborn9adb9c32010-08-13 14:09:56 -0700938 boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
939 super.reset(stats, detachIfReset);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -0700940 setStale();
941 return true;
942 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700943
Evan Millarc64edde2009-04-18 12:26:32 -0700944 void writeSummaryFromParcelLocked(Parcel out, long batteryRealtime) {
945 super.writeSummaryFromParcelLocked(out, batteryRealtime);
946 out.writeLong(mCurrentReportedTotalTime);
947 out.writeInt(mCurrentReportedCount);
948 out.writeInt(mTrackingReportedValues ? 1 : 0);
949 }
950
951 void readSummaryFromParcelLocked(Parcel in) {
952 super.readSummaryFromParcelLocked(in);
953 mUnpluggedReportedTotalTime = mCurrentReportedTotalTime = in.readLong();
954 mUnpluggedReportedCount = mCurrentReportedCount = in.readInt();
955 mTrackingReportedValues = in.readInt() == 1;
956 }
957 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -0700958
Evan Millarc64edde2009-04-18 12:26:32 -0700959 /**
Dianne Hackborna06de0f2012-12-11 16:34:47 -0800960 * A timer that increments in batches. It does not run for durations, but just jumps
961 * for a pre-determined amount.
962 */
963 public static final class BatchTimer extends Timer {
964 final Uid mUid;
965
966 /**
967 * The last time at which we updated the timer. This is in elapsed realtime microseconds.
968 */
969 long mLastAddedTime;
970
971 /**
972 * The last duration that we added to the timer. This is in microseconds.
973 */
974 long mLastAddedDuration;
975
976 /**
977 * Whether we are currently in a discharge cycle.
978 */
979 boolean mInDischarge;
980
981 BatchTimer(Uid uid, int type, ArrayList<Unpluggable> unpluggables,
982 boolean inDischarge, Parcel in) {
983 super(type, unpluggables, in);
984 mUid = uid;
985 mLastAddedTime = in.readLong();
986 mLastAddedDuration = in.readLong();
987 mInDischarge = inDischarge;
988 }
989
990 BatchTimer(Uid uid, int type, ArrayList<Unpluggable> unpluggables,
991 boolean inDischarge) {
992 super(type, unpluggables);
993 mUid = uid;
994 mInDischarge = inDischarge;
995 }
996
997 @Override
998 public void writeToParcel(Parcel out, long batteryRealtime) {
999 super.writeToParcel(out, batteryRealtime);
1000 out.writeLong(mLastAddedTime);
1001 out.writeLong(mLastAddedDuration);
1002 }
1003
1004 @Override
1005 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
1006 recomputeLastDuration(SystemClock.elapsedRealtime() * 1000, false);
1007 mInDischarge = false;
1008 super.plug(elapsedRealtime, batteryUptime, batteryRealtime);
1009 }
1010
1011 @Override
1012 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
1013 recomputeLastDuration(elapsedRealtime, false);
1014 mInDischarge = true;
1015 // If we are still within the last added duration, then re-added whatever remains.
1016 if (mLastAddedTime == elapsedRealtime) {
1017 mTotalTime += mLastAddedDuration;
1018 }
1019 super.unplug(elapsedRealtime, batteryUptime, batteryRealtime);
1020 }
1021
1022 @Override
1023 public void logState(Printer pw, String prefix) {
1024 super.logState(pw, prefix);
1025 pw.println(prefix + "mLastAddedTime=" + mLastAddedTime
1026 + " mLastAddedDuration=" + mLastAddedDuration);
1027 }
1028
1029 private long computeOverage(long curTime) {
1030 if (mLastAddedTime > 0) {
1031 return mLastTime + mLastAddedDuration - curTime;
1032 }
1033 return 0;
1034 }
1035
1036 private void recomputeLastDuration(long curTime, boolean abort) {
1037 final long overage = computeOverage(curTime);
1038 if (overage > 0) {
1039 // Aborting before the duration ran out -- roll back the remaining
1040 // duration. Only do this if currently discharging; otherwise we didn't
1041 // actually add the time.
1042 if (mInDischarge) {
1043 mTotalTime -= overage;
1044 }
1045 if (abort) {
1046 mLastAddedTime = 0;
1047 } else {
1048 mLastAddedTime = curTime;
1049 mLastAddedDuration -= overage;
1050 }
1051 }
1052 }
1053
1054 public void addDuration(BatteryStatsImpl stats, long durationMillis) {
1055 final long now = SystemClock.elapsedRealtime() * 1000;
1056 recomputeLastDuration(now, true);
1057 mLastAddedTime = now;
1058 mLastAddedDuration = durationMillis * 1000;
1059 if (mInDischarge) {
1060 mTotalTime += mLastAddedDuration;
1061 mCount++;
1062 }
1063 }
1064
1065 public void abortLastDuration(BatteryStatsImpl stats) {
1066 final long now = SystemClock.elapsedRealtime() * 1000;
1067 recomputeLastDuration(now, true);
1068 }
1069
1070 @Override
1071 protected int computeCurrentCountLocked() {
1072 return mCount;
1073 }
1074
1075 @Override
1076 protected long computeRunTimeLocked(long curBatteryRealtime) {
1077 final long overage = computeOverage(SystemClock.elapsedRealtime() * 1000);
1078 if (overage > 0) {
1079 return mTotalTime = overage;
1080 }
1081 return mTotalTime;
1082 }
1083
1084 @Override
1085 boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
1086 final long now = SystemClock.elapsedRealtime() * 1000;
1087 recomputeLastDuration(now, true);
1088 boolean stillActive = mLastAddedTime == now;
1089 super.reset(stats, !stillActive && detachIfReset);
1090 return !stillActive;
1091 }
1092 }
1093
1094 /**
Evan Millarc64edde2009-04-18 12:26:32 -07001095 * State for keeping track of timing information.
1096 */
1097 public static final class StopwatchTimer extends Timer {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07001098 final Uid mUid;
Evan Millarc64edde2009-04-18 12:26:32 -07001099 final ArrayList<StopwatchTimer> mTimerPool;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07001100
Evan Millarc64edde2009-04-18 12:26:32 -07001101 int mNesting;
1102
Evan Millarc64edde2009-04-18 12:26:32 -07001103 /**
1104 * The last time at which we updated the timer. If mNesting is > 0,
1105 * subtract this from the current battery time to find the amount of
1106 * time we have been running since we last computed an update.
1107 */
1108 long mUpdateTime;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001109
Evan Millarc64edde2009-04-18 12:26:32 -07001110 /**
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001111 * The total time at which the timer was acquired, to determine if it
Evan Millarc64edde2009-04-18 12:26:32 -07001112 * was actually held for an interesting duration.
1113 */
1114 long mAcquireTime;
Evan Millarc64edde2009-04-18 12:26:32 -07001115
Amith Yamasanif37447b2009-10-08 18:28:01 -07001116 long mTimeout;
1117
Dianne Hackborn0d903a82010-09-07 23:51:03 -07001118 /**
1119 * For partial wake locks, keep track of whether we are in the list
1120 * to consume CPU cycles.
1121 */
1122 boolean mInList;
1123
1124 StopwatchTimer(Uid uid, int type, ArrayList<StopwatchTimer> timerPool,
Evan Millarc64edde2009-04-18 12:26:32 -07001125 ArrayList<Unpluggable> unpluggables, Parcel in) {
1126 super(type, unpluggables, in);
Dianne Hackborn0d903a82010-09-07 23:51:03 -07001127 mUid = uid;
Evan Millarc64edde2009-04-18 12:26:32 -07001128 mTimerPool = timerPool;
1129 mUpdateTime = in.readLong();
1130 }
1131
Dianne Hackborn0d903a82010-09-07 23:51:03 -07001132 StopwatchTimer(Uid uid, int type, ArrayList<StopwatchTimer> timerPool,
Evan Millarc64edde2009-04-18 12:26:32 -07001133 ArrayList<Unpluggable> unpluggables) {
1134 super(type, unpluggables);
Dianne Hackborn0d903a82010-09-07 23:51:03 -07001135 mUid = uid;
Evan Millarc64edde2009-04-18 12:26:32 -07001136 mTimerPool = timerPool;
1137 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001138
Amith Yamasanif37447b2009-10-08 18:28:01 -07001139 void setTimeout(long timeout) {
1140 mTimeout = timeout;
1141 }
1142
Evan Millarc64edde2009-04-18 12:26:32 -07001143 public void writeToParcel(Parcel out, long batteryRealtime) {
1144 super.writeToParcel(out, batteryRealtime);
1145 out.writeLong(mUpdateTime);
1146 }
1147
Dianne Hackborna06de0f2012-12-11 16:34:47 -08001148 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
Evan Millarc64edde2009-04-18 12:26:32 -07001149 if (mNesting > 0) {
1150 if (DEBUG && mType < 0) {
1151 Log.v(TAG, "old mUpdateTime=" + mUpdateTime);
1152 }
Dianne Hackborna06de0f2012-12-11 16:34:47 -08001153 super.plug(elapsedRealtime, batteryUptime, batteryRealtime);
Evan Millarc64edde2009-04-18 12:26:32 -07001154 mUpdateTime = batteryRealtime;
1155 if (DEBUG && mType < 0) {
1156 Log.v(TAG, "new mUpdateTime=" + mUpdateTime);
1157 }
1158 }
1159 }
1160
1161 public void logState(Printer pw, String prefix) {
1162 super.logState(pw, prefix);
Jeff Sharkey3e013e82013-04-25 14:48:19 -07001163 pw.println(prefix + "mNesting=" + mNesting + " mUpdateTime=" + mUpdateTime
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001164 + " mAcquireTime=" + mAcquireTime);
1165 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001166
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001167 void startRunningLocked(BatteryStatsImpl stats) {
1168 if (mNesting++ == 0) {
1169 mUpdateTime = stats.getBatteryRealtimeLocked(
1170 SystemClock.elapsedRealtime() * 1000);
1171 if (mTimerPool != null) {
1172 // Accumulate time to all currently active timers before adding
1173 // this new one to the pool.
1174 refreshTimersLocked(stats, mTimerPool);
1175 // Add this timer to the active pool
1176 mTimerPool.add(this);
1177 }
1178 // Increment the count
1179 mCount++;
1180 mAcquireTime = mTotalTime;
1181 if (DEBUG && mType < 0) {
1182 Log.v(TAG, "start #" + mType + ": mUpdateTime=" + mUpdateTime
1183 + " mTotalTime=" + mTotalTime + " mCount=" + mCount
1184 + " mAcquireTime=" + mAcquireTime);
1185 }
1186 }
1187 }
1188
Amith Yamasani32dbefd2009-06-19 09:21:17 -07001189 boolean isRunningLocked() {
1190 return mNesting > 0;
1191 }
1192
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001193 void stopRunningLocked(BatteryStatsImpl stats) {
1194 // Ignore attempt to stop a timer that isn't running
1195 if (mNesting == 0) {
1196 return;
1197 }
1198 if (--mNesting == 0) {
1199 if (mTimerPool != null) {
1200 // Accumulate time to all active counters, scaled by the total
1201 // active in the pool, before taking this one out of the pool.
1202 refreshTimersLocked(stats, mTimerPool);
1203 // Remove this timer from the active pool
1204 mTimerPool.remove(this);
1205 } else {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001206 final long realtime = SystemClock.elapsedRealtime() * 1000;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001207 final long batteryRealtime = stats.getBatteryRealtimeLocked(realtime);
1208 mNesting = 1;
1209 mTotalTime = computeRunTimeLocked(batteryRealtime);
1210 mNesting = 0;
1211 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001212
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001213 if (DEBUG && mType < 0) {
1214 Log.v(TAG, "stop #" + mType + ": mUpdateTime=" + mUpdateTime
1215 + " mTotalTime=" + mTotalTime + " mCount=" + mCount
1216 + " mAcquireTime=" + mAcquireTime);
1217 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001218
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001219 if (mTotalTime == mAcquireTime) {
1220 // If there was no change in the time, then discard this
1221 // count. A somewhat cheezy strategy, but hey.
1222 mCount--;
1223 }
1224 }
1225 }
1226
1227 // Update the total time for all other running Timers with the same type as this Timer
1228 // due to a change in timer count
1229 private static void refreshTimersLocked(final BatteryStatsImpl stats,
Evan Millarc64edde2009-04-18 12:26:32 -07001230 final ArrayList<StopwatchTimer> pool) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001231 final long realtime = SystemClock.elapsedRealtime() * 1000;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001232 final long batteryRealtime = stats.getBatteryRealtimeLocked(realtime);
1233 final int N = pool.size();
1234 for (int i=N-1; i>= 0; i--) {
Evan Millarc64edde2009-04-18 12:26:32 -07001235 final StopwatchTimer t = pool.get(i);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001236 long heldTime = batteryRealtime - t.mUpdateTime;
1237 if (heldTime > 0) {
1238 t.mTotalTime += heldTime / N;
1239 }
1240 t.mUpdateTime = batteryRealtime;
1241 }
1242 }
1243
Evan Millarc64edde2009-04-18 12:26:32 -07001244 @Override
1245 protected long computeRunTimeLocked(long curBatteryRealtime) {
Amith Yamasanif37447b2009-10-08 18:28:01 -07001246 if (mTimeout > 0 && curBatteryRealtime > mUpdateTime + mTimeout) {
1247 curBatteryRealtime = mUpdateTime + mTimeout;
1248 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001249 return mTotalTime + (mNesting > 0
1250 ? (curBatteryRealtime - mUpdateTime)
1251 / (mTimerPool != null ? mTimerPool.size() : 1)
1252 : 0);
1253 }
1254
Evan Millarc64edde2009-04-18 12:26:32 -07001255 @Override
1256 protected int computeCurrentCountLocked() {
1257 return mCount;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001258 }
1259
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001260 boolean reset(BatteryStatsImpl stats, boolean detachIfReset) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001261 boolean canDetach = mNesting <= 0;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001262 super.reset(stats, canDetach && detachIfReset);
1263 if (mNesting > 0) {
1264 mUpdateTime = stats.getBatteryRealtimeLocked(
1265 SystemClock.elapsedRealtime() * 1000);
1266 }
1267 mAcquireTime = mTotalTime;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001268 return canDetach;
1269 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001270
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001271 void detach() {
1272 super.detach();
1273 if (mTimerPool != null) {
1274 mTimerPool.remove(this);
1275 }
1276 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001277
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001278 void readSummaryFromParcelLocked(Parcel in) {
Evan Millarc64edde2009-04-18 12:26:32 -07001279 super.readSummaryFromParcelLocked(in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001280 mNesting = 0;
1281 }
1282 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001283
Evan Millarc64edde2009-04-18 12:26:32 -07001284 private final Map<String, KernelWakelockStats> readKernelWakelockStats() {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001285
Todd Poynor73f534a2012-06-19 11:07:26 -07001286 FileInputStream is;
Johannes Carlsson3372f2e2010-06-30 08:45:55 +02001287 byte[] buffer = new byte[8192];
Evan Millarc64edde2009-04-18 12:26:32 -07001288 int len;
Todd Poynor73f534a2012-06-19 11:07:26 -07001289 boolean wakeup_sources = false;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001290
Evan Millarc64edde2009-04-18 12:26:32 -07001291 try {
Todd Poynor73f534a2012-06-19 11:07:26 -07001292 try {
1293 is = new FileInputStream("/proc/wakelocks");
1294 } catch (java.io.FileNotFoundException e) {
1295 try {
1296 is = new FileInputStream("/d/wakeup_sources");
1297 wakeup_sources = true;
1298 } catch (java.io.FileNotFoundException e2) {
1299 return null;
Evan Millarc64edde2009-04-18 12:26:32 -07001300 }
1301 }
Todd Poynor73f534a2012-06-19 11:07:26 -07001302
1303 len = is.read(buffer);
1304 is.close();
Evan Millarc64edde2009-04-18 12:26:32 -07001305 } catch (java.io.IOException e) {
1306 return null;
1307 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001308
Todd Poynor73f534a2012-06-19 11:07:26 -07001309 if (len > 0) {
1310 int i;
1311 for (i=0; i<len; i++) {
1312 if (buffer[i] == '\0') {
1313 len = i;
1314 break;
1315 }
1316 }
1317 }
1318
1319 return parseProcWakelocks(buffer, len, wakeup_sources);
Evan Millarc64edde2009-04-18 12:26:32 -07001320 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001321
Evan Millarc64edde2009-04-18 12:26:32 -07001322 private final Map<String, KernelWakelockStats> parseProcWakelocks(
Todd Poynor73f534a2012-06-19 11:07:26 -07001323 byte[] wlBuffer, int len, boolean wakeup_sources) {
Evan Millarc64edde2009-04-18 12:26:32 -07001324 String name;
1325 int count;
1326 long totalTime;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -07001327 int startIndex;
1328 int endIndex;
Evan Millarc64edde2009-04-18 12:26:32 -07001329 int numUpdatedWlNames = 0;
1330
1331 // Advance past the first line.
1332 int i;
1333 for (i = 0; i < len && wlBuffer[i] != '\n' && wlBuffer[i] != '\0'; i++);
1334 startIndex = endIndex = i + 1;
1335
1336 synchronized(this) {
1337 Map<String, KernelWakelockStats> m = mProcWakelockFileStats;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001338
Evan Millarc64edde2009-04-18 12:26:32 -07001339 sKernelWakelockUpdateVersion++;
1340 while (endIndex < len) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001341 for (endIndex=startIndex;
1342 endIndex < len && wlBuffer[endIndex] != '\n' && wlBuffer[endIndex] != '\0';
Evan Millarc64edde2009-04-18 12:26:32 -07001343 endIndex++);
Johannes Carlsson3372f2e2010-06-30 08:45:55 +02001344 endIndex++; // endIndex is an exclusive upper bound.
1345 // Don't go over the end of the buffer, Process.parseProcLine might
1346 // write to wlBuffer[endIndex]
1347 if (endIndex >= (len - 1) ) {
1348 return m;
Amith Yamasanie5795612010-04-05 12:43:44 -07001349 }
Evan Millarc64edde2009-04-18 12:26:32 -07001350
1351 String[] nameStringArray = mProcWakelocksName;
1352 long[] wlData = mProcWakelocksData;
Amith Yamasani2098ead2010-04-02 13:46:49 -07001353 // Stomp out any bad characters since this is from a circular buffer
1354 // A corruption is seen sometimes that results in the vm crashing
1355 // This should prevent crashes and the line will probably fail to parse
1356 for (int j = startIndex; j < endIndex; j++) {
1357 if ((wlBuffer[j] & 0x80) != 0) wlBuffer[j] = (byte) '?';
1358 }
Amith Yamasani53b707b2009-09-30 11:05:30 -07001359 boolean parsed = Process.parseProcLine(wlBuffer, startIndex, endIndex,
Todd Poynor73f534a2012-06-19 11:07:26 -07001360 wakeup_sources ? WAKEUP_SOURCES_FORMAT :
1361 PROC_WAKELOCKS_FORMAT,
1362 nameStringArray, wlData, null);
Amith Yamasani2098ead2010-04-02 13:46:49 -07001363
Evan Millarc64edde2009-04-18 12:26:32 -07001364 name = nameStringArray[0];
1365 count = (int) wlData[1];
Todd Poynor73f534a2012-06-19 11:07:26 -07001366
1367 if (wakeup_sources) {
1368 // convert milliseconds to microseconds
1369 totalTime = wlData[2] * 1000;
1370 } else {
1371 // convert nanoseconds to microseconds with rounding.
1372 totalTime = (wlData[2] + 500) / 1000;
1373 }
Evan Millarc64edde2009-04-18 12:26:32 -07001374
Amith Yamasani53b707b2009-09-30 11:05:30 -07001375 if (parsed && name.length() > 0) {
Evan Millarc64edde2009-04-18 12:26:32 -07001376 if (!m.containsKey(name)) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001377 m.put(name, new KernelWakelockStats(count, totalTime,
Evan Millarc64edde2009-04-18 12:26:32 -07001378 sKernelWakelockUpdateVersion));
1379 numUpdatedWlNames++;
1380 } else {
1381 KernelWakelockStats kwlStats = m.get(name);
1382 if (kwlStats.mVersion == sKernelWakelockUpdateVersion) {
1383 kwlStats.mCount += count;
1384 kwlStats.mTotalTime += totalTime;
1385 } else {
1386 kwlStats.mCount = count;
1387 kwlStats.mTotalTime = totalTime;
1388 kwlStats.mVersion = sKernelWakelockUpdateVersion;
1389 numUpdatedWlNames++;
1390 }
1391 }
Amith Yamasani53b707b2009-09-30 11:05:30 -07001392 }
Evan Millarc64edde2009-04-18 12:26:32 -07001393 startIndex = endIndex;
1394 }
1395
1396 if (m.size() != numUpdatedWlNames) {
1397 // Don't report old data.
1398 Iterator<KernelWakelockStats> itr = m.values().iterator();
1399 while (itr.hasNext()) {
1400 if (itr.next().mVersion != sKernelWakelockUpdateVersion) {
1401 itr.remove();
1402 }
1403 }
1404 }
1405 return m;
1406 }
1407 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001408
Evan Millarc64edde2009-04-18 12:26:32 -07001409 private class KernelWakelockStats {
1410 public int mCount;
1411 public long mTotalTime;
1412 public int mVersion;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001413
Evan Millarc64edde2009-04-18 12:26:32 -07001414 KernelWakelockStats(int count, long totalTime, int version) {
1415 mCount = count;
1416 mTotalTime = totalTime;
1417 mVersion = version;
1418 }
1419 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001420
Evan Millarc64edde2009-04-18 12:26:32 -07001421 /*
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001422 * Get the KernelWakelockTimer associated with name, and create a new one if one
Evan Millarc64edde2009-04-18 12:26:32 -07001423 * doesn't already exist.
1424 */
1425 public SamplingTimer getKernelWakelockTimerLocked(String name) {
1426 SamplingTimer kwlt = mKernelWakelockStats.get(name);
1427 if (kwlt == null) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001428 kwlt = new SamplingTimer(mUnpluggables, mOnBatteryInternal,
Evan Millarc64edde2009-04-18 12:26:32 -07001429 true /* track reported values */);
1430 mKernelWakelockStats.put(name, kwlt);
1431 }
1432 return kwlt;
1433 }
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001434
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001435 /**
1436 * Radio uptime in microseconds when transferring data. This value is very approximate.
1437 * @return
1438 */
1439 private long getCurrentRadioDataUptime() {
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001440 try {
1441 File awakeTimeFile = new File("/sys/devices/virtual/net/rmnet0/awake_time_ms");
1442 if (!awakeTimeFile.exists()) return 0;
1443 BufferedReader br = new BufferedReader(new FileReader(awakeTimeFile));
1444 String line = br.readLine();
1445 br.close();
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001446 return Long.parseLong(line) * 1000;
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001447 } catch (NumberFormatException nfe) {
1448 // Nothing
1449 } catch (IOException ioe) {
1450 // Nothing
1451 }
1452 return 0;
1453 }
1454
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001455 /**
1456 * @deprecated use getRadioDataUptime
1457 */
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001458 public long getRadioDataUptimeMs() {
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001459 return getRadioDataUptime() / 1000;
1460 }
1461
1462 /**
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001463 * Returns the duration that the cell radio was up for data transfers.
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001464 */
1465 public long getRadioDataUptime() {
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001466 if (mRadioDataStart == -1) {
1467 return mRadioDataUptime;
1468 } else {
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001469 return getCurrentRadioDataUptime() - mRadioDataStart;
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001470 }
1471 }
1472
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001473 private int getCurrentBluetoothPingCount() {
1474 if (mBtHeadset != null) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001475 List<BluetoothDevice> deviceList = mBtHeadset.getConnectedDevices();
1476 if (deviceList.size() > 0) {
1477 return mBtHeadset.getBatteryUsageHint(deviceList.get(0));
Jaikumar Ganesh3f034962010-09-27 17:02:23 -07001478 }
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001479 }
1480 return -1;
1481 }
1482
1483 public int getBluetoothPingCount() {
1484 if (mBluetoothPingStart == -1) {
1485 return mBluetoothPingCount;
1486 } else if (mBtHeadset != null) {
1487 return getCurrentBluetoothPingCount() - mBluetoothPingStart;
1488 }
Amith Yamasani82cb0292009-08-18 11:29:28 -07001489 return 0;
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001490 }
1491
1492 public void setBtHeadset(BluetoothHeadset headset) {
Amith Yamasani82cb0292009-08-18 11:29:28 -07001493 if (headset != null && mBtHeadset == null && isOnBattery() && mBluetoothPingStart == -1) {
1494 mBluetoothPingStart = getCurrentBluetoothPingCount();
1495 }
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001496 mBtHeadset = headset;
1497 }
1498
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001499 private int writeHistoryTag(HistoryTag tag) {
1500 Integer idxObj = mHistoryTagPool.get(tag);
1501 int idx;
1502 if (idxObj != null) {
1503 idx = idxObj;
1504 } else {
1505 idx = mNextHistoryTagIdx;
1506 HistoryTag key = new HistoryTag();
1507 key.setTo(tag);
1508 tag.poolIdx = idx;
1509 mHistoryTagPool.put(key, idx);
1510 mNextHistoryTagIdx++;
1511 mNumHistoryTagChars += key.string.length() + 1;
1512 }
1513 return idx;
1514 }
1515
1516 private void readHistoryTag(int index, HistoryTag tag) {
1517 tag.string = mReadHistoryStrings[index];
1518 tag.uid = mReadHistoryUids[index];
1519 tag.poolIdx = index;
1520 }
1521
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001522 // Part of initial delta int that specifies the time delta.
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001523 static final int DELTA_TIME_MASK = 0xfffff;
1524 static final int DELTA_TIME_LONG = 0xfffff; // The delta is a following long
1525 static final int DELTA_TIME_INT = 0xffffe; // The delta is a following int
1526 static final int DELTA_TIME_ABS = 0xffffd; // Following is an entire abs update.
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001527 // Flag in delta int: a new battery level int follows.
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001528 static final int DELTA_BATTERY_LEVEL_FLAG = 0x00100000;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001529 // Flag in delta int: a new full state and battery status int follows.
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001530 static final int DELTA_STATE_FLAG = 0x00200000;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001531 // Flag in delta int: contains a wakelock tag.
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001532 static final int DELTA_WAKELOCK_FLAG = 0x00400000;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001533 // Flag in delta int: contains an event description.
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001534 static final int DELTA_EVENT_FLAG = 0x00800000;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001535 // These upper bits are the frequently changing state bits.
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001536 static final int DELTA_STATE_MASK = 0xff000000;
1537
1538 // These are the pieces of battery state that are packed in to the upper bits of
1539 // the state int that have been packed in to the first delta int. They must fit
1540 // in DELTA_STATE_MASK.
1541 static final int STATE_BATTERY_STATUS_MASK = 0x00000007;
1542 static final int STATE_BATTERY_STATUS_SHIFT = 29;
1543 static final int STATE_BATTERY_HEALTH_MASK = 0x00000007;
1544 static final int STATE_BATTERY_HEALTH_SHIFT = 26;
1545 static final int STATE_BATTERY_PLUG_MASK = 0x00000003;
1546 static final int STATE_BATTERY_PLUG_SHIFT = 24;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001547
1548 public void writeHistoryDelta(Parcel dest, HistoryItem cur, HistoryItem last) {
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001549 if (last == null || cur.cmd != HistoryItem.CMD_UPDATE) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001550 dest.writeInt(DELTA_TIME_ABS);
1551 cur.writeToParcel(dest, 0);
1552 return;
1553 }
1554
1555 final long deltaTime = cur.time - last.time;
1556 final int lastBatteryLevelInt = buildBatteryLevelInt(last);
1557 final int lastStateInt = buildStateInt(last);
1558
1559 int deltaTimeToken;
1560 if (deltaTime < 0 || deltaTime > Integer.MAX_VALUE) {
1561 deltaTimeToken = DELTA_TIME_LONG;
1562 } else if (deltaTime >= DELTA_TIME_ABS) {
1563 deltaTimeToken = DELTA_TIME_INT;
1564 } else {
1565 deltaTimeToken = (int)deltaTime;
1566 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001567 int firstToken = deltaTimeToken | (cur.states&DELTA_STATE_MASK);
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001568 final int batteryLevelInt = buildBatteryLevelInt(cur);
1569 final boolean batteryLevelIntChanged = batteryLevelInt != lastBatteryLevelInt;
1570 if (batteryLevelIntChanged) {
1571 firstToken |= DELTA_BATTERY_LEVEL_FLAG;
1572 }
1573 final int stateInt = buildStateInt(cur);
1574 final boolean stateIntChanged = stateInt != lastStateInt;
1575 if (stateIntChanged) {
1576 firstToken |= DELTA_STATE_FLAG;
1577 }
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001578 if (cur.wakelockTag != null) {
1579 firstToken |= DELTA_WAKELOCK_FLAG;
1580 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001581 if (cur.eventCode != HistoryItem.EVENT_NONE) {
1582 firstToken |= DELTA_EVENT_FLAG;
1583 }
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001584 dest.writeInt(firstToken);
1585 if (DEBUG) Slog.i(TAG, "WRITE DELTA: firstToken=0x" + Integer.toHexString(firstToken)
1586 + " deltaTime=" + deltaTime);
1587
1588 if (deltaTimeToken >= DELTA_TIME_INT) {
1589 if (deltaTimeToken == DELTA_TIME_INT) {
1590 if (DEBUG) Slog.i(TAG, "WRITE DELTA: int deltaTime=" + (int)deltaTime);
1591 dest.writeInt((int)deltaTime);
1592 } else {
1593 if (DEBUG) Slog.i(TAG, "WRITE DELTA: long deltaTime=" + deltaTime);
1594 dest.writeLong(deltaTime);
1595 }
1596 }
1597 if (batteryLevelIntChanged) {
1598 dest.writeInt(batteryLevelInt);
1599 if (DEBUG) Slog.i(TAG, "WRITE DELTA: batteryToken=0x"
1600 + Integer.toHexString(batteryLevelInt)
1601 + " batteryLevel=" + cur.batteryLevel
1602 + " batteryTemp=" + cur.batteryTemperature
1603 + " batteryVolt=" + (int)cur.batteryVoltage);
1604 }
1605 if (stateIntChanged) {
1606 dest.writeInt(stateInt);
1607 if (DEBUG) Slog.i(TAG, "WRITE DELTA: stateToken=0x"
1608 + Integer.toHexString(stateInt)
1609 + " batteryStatus=" + cur.batteryStatus
1610 + " batteryHealth=" + cur.batteryHealth
1611 + " batteryPlugType=" + cur.batteryPlugType
1612 + " states=0x" + Integer.toHexString(cur.states));
1613 }
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001614 if (cur.wakelockTag != null) {
1615 int index = writeHistoryTag(cur.wakelockTag);
1616 dest.writeInt(index);
1617 if (DEBUG) Slog.i(TAG, "WRITE DELTA: wakelockTag=#" + cur.wakelockTag.poolIdx
1618 + " " + cur.wakelockTag.uid + ":" + cur.wakelockTag.string);
1619 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001620 if (cur.eventCode != HistoryItem.EVENT_NONE) {
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001621 int index = writeHistoryTag(cur.eventTag);
1622 int codeAndIndex = (cur.eventCode&0xffff) | (index<<16);
Dianne Hackborn099bc622014-01-22 13:39:16 -08001623 dest.writeInt(codeAndIndex);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001624 if (DEBUG) Slog.i(TAG, "WRITE DELTA: event=" + cur.eventCode + " tag=#"
1625 + cur.eventTag.poolIdx + " " + cur.eventTag.uid + ":"
1626 + cur.eventTag.string);
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001627 }
1628 }
1629
1630 private int buildBatteryLevelInt(HistoryItem h) {
1631 return ((((int)h.batteryLevel)<<25)&0xfe000000)
1632 | ((((int)h.batteryTemperature)<<14)&0x01ffc000)
1633 | (((int)h.batteryVoltage)&0x00003fff);
1634 }
1635
1636 private int buildStateInt(HistoryItem h) {
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001637 int plugType = 0;
1638 if ((h.batteryPlugType&BatteryManager.BATTERY_PLUGGED_AC) != 0) {
1639 plugType = 1;
1640 } else if ((h.batteryPlugType&BatteryManager.BATTERY_PLUGGED_USB) != 0) {
1641 plugType = 2;
1642 } else if ((h.batteryPlugType&BatteryManager.BATTERY_PLUGGED_WIRELESS) != 0) {
1643 plugType = 3;
1644 }
1645 return ((h.batteryStatus&STATE_BATTERY_STATUS_MASK)<<STATE_BATTERY_STATUS_SHIFT)
1646 | ((h.batteryHealth&STATE_BATTERY_HEALTH_MASK)<<STATE_BATTERY_HEALTH_SHIFT)
1647 | ((plugType&STATE_BATTERY_PLUG_MASK)<<STATE_BATTERY_PLUG_SHIFT)
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001648 | (h.states&(~DELTA_STATE_MASK));
1649 }
1650
1651 public void readHistoryDelta(Parcel src, HistoryItem cur) {
1652 int firstToken = src.readInt();
1653 int deltaTimeToken = firstToken&DELTA_TIME_MASK;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001654 cur.cmd = HistoryItem.CMD_UPDATE;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001655 cur.numReadInts = 1;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001656 if (DEBUG) Slog.i(TAG, "READ DELTA: firstToken=0x" + Integer.toHexString(firstToken)
1657 + " deltaTimeToken=" + deltaTimeToken);
1658
1659 if (deltaTimeToken < DELTA_TIME_ABS) {
1660 cur.time += deltaTimeToken;
1661 } else if (deltaTimeToken == DELTA_TIME_ABS) {
1662 cur.time = src.readLong();
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001663 cur.numReadInts += 2;
1664 if (DEBUG) Slog.i(TAG, "READ DELTA: ABS time=" + cur.time);
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001665 cur.readFromParcel(src);
1666 return;
1667 } else if (deltaTimeToken == DELTA_TIME_INT) {
1668 int delta = src.readInt();
1669 cur.time += delta;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001670 cur.numReadInts += 1;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001671 if (DEBUG) Slog.i(TAG, "READ DELTA: time delta=" + delta + " new time=" + cur.time);
1672 } else {
1673 long delta = src.readLong();
1674 if (DEBUG) Slog.i(TAG, "READ DELTA: time delta=" + delta + " new time=" + cur.time);
1675 cur.time += delta;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001676 cur.numReadInts += 2;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001677 }
1678
1679 if ((firstToken&DELTA_BATTERY_LEVEL_FLAG) != 0) {
1680 int batteryLevelInt = src.readInt();
1681 cur.batteryLevel = (byte)((batteryLevelInt>>25)&0x7f);
1682 cur.batteryTemperature = (short)((batteryLevelInt<<7)>>21);
1683 cur.batteryVoltage = (char)(batteryLevelInt&0x3fff);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001684 cur.numReadInts += 1;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001685 if (DEBUG) Slog.i(TAG, "READ DELTA: batteryToken=0x"
1686 + Integer.toHexString(batteryLevelInt)
1687 + " batteryLevel=" + cur.batteryLevel
1688 + " batteryTemp=" + cur.batteryTemperature
1689 + " batteryVolt=" + (int)cur.batteryVoltage);
1690 }
1691
1692 if ((firstToken&DELTA_STATE_FLAG) != 0) {
1693 int stateInt = src.readInt();
1694 cur.states = (firstToken&DELTA_STATE_MASK) | (stateInt&(~DELTA_STATE_MASK));
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08001695 cur.batteryStatus = (byte)((stateInt>>STATE_BATTERY_STATUS_SHIFT)
1696 & STATE_BATTERY_STATUS_MASK);
1697 cur.batteryHealth = (byte)((stateInt>>STATE_BATTERY_HEALTH_SHIFT)
1698 & STATE_BATTERY_HEALTH_MASK);
1699 cur.batteryPlugType = (byte)((stateInt>>STATE_BATTERY_PLUG_SHIFT)
1700 & STATE_BATTERY_PLUG_MASK);
1701 switch (cur.batteryPlugType) {
1702 case 1:
1703 cur.batteryPlugType = BatteryManager.BATTERY_PLUGGED_AC;
1704 break;
1705 case 2:
1706 cur.batteryPlugType = BatteryManager.BATTERY_PLUGGED_USB;
1707 break;
1708 case 3:
1709 cur.batteryPlugType = BatteryManager.BATTERY_PLUGGED_WIRELESS;
1710 break;
1711 }
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001712 cur.numReadInts += 1;
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001713 if (DEBUG) Slog.i(TAG, "READ DELTA: stateToken=0x"
1714 + Integer.toHexString(stateInt)
1715 + " batteryStatus=" + cur.batteryStatus
1716 + " batteryHealth=" + cur.batteryHealth
1717 + " batteryPlugType=" + cur.batteryPlugType
1718 + " states=0x" + Integer.toHexString(cur.states));
1719 } else {
1720 cur.states = (firstToken&DELTA_STATE_MASK) | (cur.states&(~DELTA_STATE_MASK));
1721 }
1722
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001723 if ((firstToken&DELTA_WAKELOCK_FLAG) != 0) {
1724 cur.wakelockTag = cur.localWakelockTag;
1725 int index = src.readInt();
1726 readHistoryTag(index, cur.wakelockTag);
1727 cur.numReadInts += 1;
1728 if (DEBUG) Slog.i(TAG, "READ DELTA: wakelockTag=#" + cur.wakelockTag.poolIdx
1729 + " " + cur.wakelockTag.uid + ":" + cur.wakelockTag.string);
1730 } else {
1731 cur.wakelockTag = null;
1732 }
1733
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001734 if ((firstToken&DELTA_EVENT_FLAG) != 0) {
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001735 cur.eventTag = cur.localEventTag;
1736 final int codeAndIndex = src.readInt();
Dianne Hackborn099bc622014-01-22 13:39:16 -08001737 cur.eventCode = (codeAndIndex&0xffff);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001738 final int index = ((codeAndIndex>>16)&0xffff);
1739 readHistoryTag(index, cur.eventTag);
1740 cur.numReadInts += 1;
1741 if (DEBUG) Slog.i(TAG, "READ DELTA: event=" + cur.eventCode + " tag=#"
1742 + cur.eventTag.poolIdx + " " + cur.eventTag.uid + ":"
1743 + cur.eventTag.string);
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001744 } else {
1745 cur.eventCode = HistoryItem.EVENT_NONE;
1746 }
1747 }
1748
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001749 void addHistoryBufferLocked(long curTime) {
1750 if (!mHaveBatteryLevel || !mRecordingHistory) {
1751 return;
1752 }
1753
Dianne Hackborn1fadab52011-04-14 17:57:33 -07001754 final long timeDiff = (mHistoryBaseTime+curTime) - mHistoryLastWritten.time;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001755 final int diffStates = mHistoryLastWritten.states^mHistoryCur.states;
1756 final int lastDiffStates = mHistoryLastWritten.states^mHistoryLastLastWritten.states;
1757 if (DEBUG) Slog.i(TAG, "ADD: tdelta=" + timeDiff + " diff="
1758 + Integer.toHexString(diffStates) + " lastDiff="
1759 + Integer.toHexString(lastDiffStates));
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001760 if (mHistoryBufferLastPos >= 0 && mHistoryLastWritten.cmd == HistoryItem.CMD_UPDATE
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001761 && timeDiff < 1000 && (diffStates&lastDiffStates) == 0
1762 && (mHistoryLastWritten.wakelockTag == null || mHistoryCur.wakelockTag == null)
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001763 && (mHistoryLastWritten.eventCode == HistoryItem.EVENT_NONE
1764 || mHistoryCur.eventCode == HistoryItem.EVENT_NONE)
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001765 && mHistoryLastWritten.batteryLevel == mHistoryCur.batteryLevel
1766 && mHistoryLastWritten.batteryStatus == mHistoryCur.batteryStatus
1767 && mHistoryLastWritten.batteryHealth == mHistoryCur.batteryHealth
1768 && mHistoryLastWritten.batteryPlugType == mHistoryCur.batteryPlugType
1769 && mHistoryLastWritten.batteryTemperature == mHistoryCur.batteryTemperature
1770 && mHistoryLastWritten.batteryVoltage == mHistoryCur.batteryVoltage) {
1771 // We can merge this new change in with the last one. Merging is
1772 // allows as long as only the states have changed, and within those states
1773 // as long as no bit has changed both between now and the last entry, as
1774 // well as the last entry and the one before it (so we capture any toggles).
1775 if (DEBUG) Slog.i(TAG, "ADD: rewinding back to " + mHistoryBufferLastPos);
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001776 mHistoryBuffer.setDataSize(mHistoryBufferLastPos);
1777 mHistoryBuffer.setDataPosition(mHistoryBufferLastPos);
1778 mHistoryBufferLastPos = -1;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001779 curTime = mHistoryLastWritten.time - mHistoryBaseTime;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001780 // If the last written history had a wakelock tag, we need to retain it.
1781 // Note that the condition above made sure that we aren't in a case where
1782 // both it and the current history item have a wakelock tag.
1783 if (mHistoryLastWritten.wakelockTag != null) {
1784 mHistoryCur.wakelockTag = mHistoryCur.localWakelockTag;
1785 mHistoryCur.wakelockTag.setTo(mHistoryLastWritten.wakelockTag);
1786 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001787 // If the last written history had an event, we need to retain it.
1788 // Note that the condition above made sure that we aren't in a case where
1789 // both it and the current history item have an event.
1790 if (mHistoryLastWritten.eventCode != HistoryItem.EVENT_NONE) {
1791 mHistoryCur.eventCode = mHistoryLastWritten.eventCode;
1792 mHistoryCur.eventTag = mHistoryCur.localEventTag;
1793 mHistoryCur.eventTag.setTo(mHistoryLastWritten.eventTag);
1794 }
Dianne Hackborn1fadab52011-04-14 17:57:33 -07001795 mHistoryLastWritten.setTo(mHistoryLastLastWritten);
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001796 }
1797
1798 final int dataSize = mHistoryBuffer.dataSize();
1799 if (dataSize >= MAX_HISTORY_BUFFER) {
1800 if (!mHistoryOverflow) {
1801 mHistoryOverflow = true;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001802 addHistoryBufferLocked(curTime, HistoryItem.CMD_UPDATE);
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001803 addHistoryBufferLocked(curTime, HistoryItem.CMD_OVERFLOW);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001804 return;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001805 }
1806
1807 // Once we've reached the maximum number of items, we only
1808 // record changes to the battery level and the most interesting states.
1809 // Once we've reached the maximum maximum number of items, we only
1810 // record changes to the battery level.
1811 if (mHistoryLastWritten.batteryLevel == mHistoryCur.batteryLevel &&
1812 (dataSize >= MAX_MAX_HISTORY_BUFFER
Amith Yamasani45f06462011-11-21 16:08:34 -08001813 || ((mHistoryLastWritten.states^mHistoryCur.states)
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001814 & HistoryItem.MOST_INTERESTING_STATES) == 0)) {
1815 return;
1816 }
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001817
1818 addHistoryBufferLocked(curTime, HistoryItem.CMD_UPDATE);
1819 return;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001820 }
1821
1822 addHistoryBufferLocked(curTime, HistoryItem.CMD_UPDATE);
1823 }
1824
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001825 private void addHistoryBufferLocked(long curTime, byte cmd) {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001826 if (mIteratingHistory) {
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001827 throw new IllegalStateException("Can't do this while iterating history!");
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001828 }
1829 mHistoryBufferLastPos = mHistoryBuffer.dataPosition();
1830 mHistoryLastLastWritten.setTo(mHistoryLastWritten);
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001831 mHistoryLastWritten.setTo(mHistoryBaseTime + curTime, cmd, mHistoryCur);
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001832 writeHistoryDelta(mHistoryBuffer, mHistoryLastWritten, mHistoryLastLastWritten);
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001833 mLastHistoryTime = curTime;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001834 mHistoryCur.wakelockTag = null;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001835 mHistoryCur.eventCode = HistoryItem.EVENT_NONE;
1836 mHistoryCur.eventTag = null;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001837 if (DEBUG_HISTORY) Slog.i(TAG, "Writing history buffer: was " + mHistoryBufferLastPos
1838 + " now " + mHistoryBuffer.dataPosition()
1839 + " size is now " + mHistoryBuffer.dataSize());
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001840 }
1841
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001842 int mChangedStates = 0;
1843
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001844 void addHistoryRecordLocked(long curTime) {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001845 addHistoryBufferLocked(curTime);
1846
Dianne Hackborne8c88e62011-08-17 19:09:09 -07001847 if (!USE_OLD_HISTORY) {
1848 return;
1849 }
1850
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001851 if (!mHaveBatteryLevel || !mRecordingHistory) {
1852 return;
1853 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001854
1855 // If the current time is basically the same as the last time,
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001856 // and no states have since the last recorded entry changed and
1857 // are now resetting back to their original value, then just collapse
1858 // into one record.
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001859 if (mHistoryEnd != null && mHistoryEnd.cmd == HistoryItem.CMD_UPDATE
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001860 && (mHistoryBaseTime+curTime) < (mHistoryEnd.time+2000)
1861 && ((mHistoryEnd.states^mHistoryCur.states)&mChangedStates) == 0) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001862 // If the current is the same as the one before, then we no
1863 // longer need the entry.
1864 if (mHistoryLastEnd != null && mHistoryLastEnd.cmd == HistoryItem.CMD_UPDATE
Dianne Hackborn1fadab52011-04-14 17:57:33 -07001865 && (mHistoryBaseTime+curTime) < (mHistoryEnd.time+500)
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08001866 && mHistoryLastEnd.sameNonEvent(mHistoryCur)) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001867 mHistoryLastEnd.next = null;
1868 mHistoryEnd.next = mHistoryCache;
1869 mHistoryCache = mHistoryEnd;
1870 mHistoryEnd = mHistoryLastEnd;
1871 mHistoryLastEnd = null;
1872 } else {
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001873 mChangedStates |= mHistoryEnd.states^mHistoryCur.states;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001874 mHistoryEnd.setTo(mHistoryEnd.time, HistoryItem.CMD_UPDATE, mHistoryCur);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001875 }
1876 return;
1877 }
1878
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001879 mChangedStates = 0;
1880
1881 if (mNumHistoryItems == MAX_HISTORY_ITEMS
1882 || mNumHistoryItems == MAX_MAX_HISTORY_ITEMS) {
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07001883 addHistoryRecordLocked(curTime, HistoryItem.CMD_OVERFLOW);
1884 }
1885
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001886 if (mNumHistoryItems >= MAX_HISTORY_ITEMS) {
1887 // Once we've reached the maximum number of items, we only
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001888 // record changes to the battery level and the most interesting states.
1889 // Once we've reached the maximum maximum number of items, we only
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001890 // record changes to the battery level.
1891 if (mHistoryEnd != null && mHistoryEnd.batteryLevel
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07001892 == mHistoryCur.batteryLevel &&
1893 (mNumHistoryItems >= MAX_MAX_HISTORY_ITEMS
1894 || ((mHistoryEnd.states^mHistoryCur.states)
1895 & HistoryItem.MOST_INTERESTING_STATES) == 0)) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001896 return;
1897 }
1898 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001899
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001900 addHistoryRecordLocked(curTime, HistoryItem.CMD_UPDATE);
1901 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001902
Dianne Hackborn099bc622014-01-22 13:39:16 -08001903 void addHistoryEventLocked(long curTime, int code, String name, int uid) {
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001904 mHistoryCur.eventCode = code;
1905 mHistoryCur.eventTag = mHistoryCur.localEventTag;
1906 mHistoryCur.eventTag.string = name;
1907 mHistoryCur.eventTag.uid = uid;
1908 addHistoryBufferLocked(curTime);
Dianne Hackborn099bc622014-01-22 13:39:16 -08001909 }
1910
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001911 void addHistoryRecordLocked(long curTime, byte cmd) {
1912 HistoryItem rec = mHistoryCache;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001913 if (rec != null) {
1914 mHistoryCache = rec.next;
1915 } else {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001916 rec = new HistoryItem();
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001917 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001918 rec.setTo(mHistoryBaseTime + curTime, cmd, mHistoryCur);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001919
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001920 addHistoryRecordLocked(rec);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001921 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001922
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001923 void addHistoryRecordLocked(HistoryItem rec) {
1924 mNumHistoryItems++;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001925 rec.next = null;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07001926 mHistoryLastEnd = mHistoryEnd;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001927 if (mHistoryEnd != null) {
1928 mHistoryEnd.next = rec;
1929 mHistoryEnd = rec;
1930 } else {
1931 mHistory = mHistoryEnd = rec;
1932 }
1933 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001934
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001935 void clearHistoryLocked() {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001936 if (DEBUG_HISTORY) Slog.i(TAG, "********** CLEARING HISTORY!");
Dianne Hackborne8c88e62011-08-17 19:09:09 -07001937 if (USE_OLD_HISTORY) {
1938 if (mHistory != null) {
1939 mHistoryEnd.next = mHistoryCache;
1940 mHistoryCache = mHistory;
1941 mHistory = mHistoryLastEnd = mHistoryEnd = null;
1942 }
1943 mNumHistoryItems = 0;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001944 }
Dianne Hackborne8c88e62011-08-17 19:09:09 -07001945
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07001946 mHistoryBaseTime = 0;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001947 mLastHistoryTime = 0;
1948
1949 mHistoryBuffer.setDataSize(0);
1950 mHistoryBuffer.setDataPosition(0);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001951 mHistoryBuffer.setDataCapacity(MAX_HISTORY_BUFFER / 2);
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08001952 mHistoryLastLastWritten.clear();
1953 mHistoryLastWritten.clear();
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08001954 mHistoryTagPool.clear();
1955 mNextHistoryTagIdx = 0;
1956 mNumHistoryTagChars = 0;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07001957 mHistoryBufferLastPos = -1;
1958 mHistoryOverflow = false;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07001959 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07001960
Dianne Hackborna06de0f2012-12-11 16:34:47 -08001961 public void doUnplugLocked(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001962 for (int i = mUnpluggables.size() - 1; i >= 0; i--) {
Dianne Hackborna06de0f2012-12-11 16:34:47 -08001963 mUnpluggables.get(i).unplug(elapsedRealtime, batteryUptime, batteryRealtime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001964 }
Jeff Sharkey1059c3c2011-10-04 16:54:49 -07001965
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001966 // Track radio awake time
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001967 mRadioDataStart = getCurrentRadioDataUptime();
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001968 mRadioDataUptime = 0;
Jeff Sharkey1059c3c2011-10-04 16:54:49 -07001969
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001970 // Track bt headset ping count
1971 mBluetoothPingStart = getCurrentBluetoothPingCount();
1972 mBluetoothPingCount = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001973 }
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001974
Dianne Hackborna06de0f2012-12-11 16:34:47 -08001975 public void doPlugLocked(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001976 for (int i = mUnpluggables.size() - 1; i >= 0; i--) {
Dianne Hackborna06de0f2012-12-11 16:34:47 -08001977 mUnpluggables.get(i).plug(elapsedRealtime, batteryUptime, batteryRealtime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001978 }
Jeff Sharkey1059c3c2011-10-04 16:54:49 -07001979
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001980 // Track radio awake time
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001981 mRadioDataUptime = getRadioDataUptime();
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001982 mRadioDataStart = -1;
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07001983
1984 // Track bt headset ping count
1985 mBluetoothPingCount = getBluetoothPingCount();
1986 mBluetoothPingStart = -1;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001987 }
Amith Yamasani3718aaa2009-06-09 06:32:35 -07001988
Dianne Hackborn099bc622014-01-22 13:39:16 -08001989 public void addIsolatedUidLocked(int isolatedUid, int appUid) {
1990 mIsolatedUids.put(isolatedUid, appUid);
1991 }
1992
1993 public void removeIsolatedUidLocked(int isolatedUid, int appUid) {
1994 int curUid = mIsolatedUids.get(isolatedUid, -1);
1995 if (curUid == appUid) {
1996 mIsolatedUids.delete(isolatedUid);
1997 }
1998 }
1999
2000 public int mapUid(int uid) {
2001 int isolated = mIsolatedUids.get(uid, -1);
2002 return isolated > 0 ? isolated : uid;
2003 }
2004
2005 public void noteEventLocked(int code, String name, int uid) {
2006 uid = mapUid(uid);
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08002007 if ((code&HistoryItem.EVENT_FLAG_START) != 0) {
2008 int idx = code&~HistoryItem.EVENT_FLAG_START;
2009 HashMap<String, SparseBooleanArray> active = mActiveEvents[idx];
2010 if (active == null) {
2011 active = new HashMap<String, SparseBooleanArray>();
2012 mActiveEvents[idx] = active;
2013 }
2014 SparseBooleanArray uids = active.get(name);
2015 if (uids == null) {
2016 uids = new SparseBooleanArray();
2017 active.put(name, uids);
2018 }
2019 if (uids.get(uid)) {
2020 // Already set, nothing to do!
2021 return;
2022 }
2023 uids.put(uid, true);
2024 } else if ((code&HistoryItem.EVENT_FLAG_FINISH) != 0) {
2025 int idx = code&~HistoryItem.EVENT_FLAG_FINISH;
2026 HashMap<String, SparseBooleanArray> active = mActiveEvents[idx];
2027 if (active == null) {
2028 // not currently active, nothing to do.
2029 return;
2030 }
2031 SparseBooleanArray uids = active.get(name);
2032 if (uids == null) {
2033 // not currently active, nothing to do.
2034 return;
2035 }
2036 idx = uids.indexOfKey(uid);
2037 if (idx < 0 || !uids.valueAt(idx)) {
2038 // not currently active, nothing to do.
2039 return;
2040 }
2041 uids.removeAt(idx);
2042 if (uids.size() <= 0) {
2043 active.remove(name);
2044 }
2045 }
Dianne Hackborn099bc622014-01-22 13:39:16 -08002046 addHistoryEventLocked(SystemClock.elapsedRealtime(), code, name, uid);
2047 }
2048
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08002049 public void noteStartWakeLocked(int uid, int pid, String name, int type,
2050 boolean unimportantForLogging) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002051 uid = mapUid(uid);
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07002052 if (type == WAKE_TYPE_PARTIAL) {
2053 // Only care about partial wake locks, since full wake locks
2054 // will be canceled when the user puts the screen to sleep.
2055 if (mWakeLockNesting == 0) {
2056 mHistoryCur.states |= HistoryItem.STATE_WAKE_LOCK_FLAG;
2057 if (DEBUG_HISTORY) Slog.v(TAG, "Start wake lock to: "
2058 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08002059 mHistoryCur.wakelockTag = mHistoryCur.localWakelockTag;
2060 mHistoryCur.wakelockTag.string = name;
2061 mHistoryCur.wakelockTag.uid = uid;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08002062 mWakeLockImportant = !unimportantForLogging;
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07002063 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08002064 } else if (!mWakeLockImportant && !unimportantForLogging) {
2065 if (mHistoryLastWritten.wakelockTag != null) {
2066 // We'll try to update the last tag.
2067 mHistoryLastWritten.wakelockTag = null;
2068 mHistoryCur.wakelockTag = mHistoryCur.localWakelockTag;
2069 mHistoryCur.wakelockTag.string = name;
2070 mHistoryCur.wakelockTag.uid = uid;
2071 addHistoryRecordLocked(SystemClock.elapsedRealtime());
2072 }
2073 mWakeLockImportant = true;
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07002074 }
2075 mWakeLockNesting++;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002076 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002077 if (uid >= 0) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07002078 if (!mHandler.hasMessages(MSG_UPDATE_WAKELOCKS)) {
2079 Message m = mHandler.obtainMessage(MSG_UPDATE_WAKELOCKS);
2080 mHandler.sendMessageDelayed(m, DELAY_UPDATE_WAKELOCKS);
2081 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002082 getUidStatsLocked(uid).noteStartWakeLocked(pid, name, type);
2083 }
2084 }
2085
2086 public void noteStopWakeLocked(int uid, int pid, String name, int type) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002087 uid = mapUid(uid);
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07002088 if (type == WAKE_TYPE_PARTIAL) {
2089 mWakeLockNesting--;
2090 if (mWakeLockNesting == 0) {
2091 mHistoryCur.states &= ~HistoryItem.STATE_WAKE_LOCK_FLAG;
2092 if (DEBUG_HISTORY) Slog.v(TAG, "Stop wake lock to: "
2093 + Integer.toHexString(mHistoryCur.states));
2094 addHistoryRecordLocked(SystemClock.elapsedRealtime());
2095 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002096 }
2097 if (uid >= 0) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07002098 if (!mHandler.hasMessages(MSG_UPDATE_WAKELOCKS)) {
2099 Message m = mHandler.obtainMessage(MSG_UPDATE_WAKELOCKS);
2100 mHandler.sendMessageDelayed(m, DELAY_UPDATE_WAKELOCKS);
2101 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002102 getUidStatsLocked(uid).noteStopWakeLocked(pid, name, type);
2103 }
2104 }
2105
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08002106 public void noteStartWakeFromSourceLocked(WorkSource ws, int pid, String name, int type,
2107 boolean unimportantForLogging) {
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002108 int N = ws.size();
2109 for (int i=0; i<N; i++) {
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08002110 noteStartWakeLocked(ws.get(i), pid, name, type, unimportantForLogging);
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002111 }
2112 }
2113
2114 public void noteStopWakeFromSourceLocked(WorkSource ws, int pid, String name, int type) {
2115 int N = ws.size();
2116 for (int i=0; i<N; i++) {
2117 noteStopWakeLocked(ws.get(i), pid, name, type);
2118 }
2119 }
2120
Dianne Hackborn0d903a82010-09-07 23:51:03 -07002121 public int startAddingCpuLocked() {
2122 mHandler.removeMessages(MSG_UPDATE_WAKELOCKS);
2123
2124 if (mScreenOn) {
2125 return 0;
2126 }
2127
2128 final int N = mPartialTimers.size();
2129 if (N == 0) {
2130 mLastPartialTimers.clear();
2131 return 0;
2132 }
2133
2134 // How many timers should consume CPU? Only want to include ones
2135 // that have already been in the list.
2136 for (int i=0; i<N; i++) {
2137 StopwatchTimer st = mPartialTimers.get(i);
2138 if (st.mInList) {
2139 Uid uid = st.mUid;
2140 // We don't include the system UID, because it so often
2141 // holds wake locks at one request or another of an app.
2142 if (uid != null && uid.mUid != Process.SYSTEM_UID) {
2143 return 50;
2144 }
2145 }
2146 }
2147
2148 return 0;
2149 }
2150
2151 public void finishAddingCpuLocked(int perc, int utime, int stime, long[] cpuSpeedTimes) {
2152 final int N = mPartialTimers.size();
2153 if (perc != 0) {
2154 int num = 0;
2155 for (int i=0; i<N; i++) {
2156 StopwatchTimer st = mPartialTimers.get(i);
2157 if (st.mInList) {
2158 Uid uid = st.mUid;
2159 // We don't include the system UID, because it so often
2160 // holds wake locks at one request or another of an app.
2161 if (uid != null && uid.mUid != Process.SYSTEM_UID) {
2162 num++;
2163 }
2164 }
2165 }
2166 if (num != 0) {
2167 for (int i=0; i<N; i++) {
2168 StopwatchTimer st = mPartialTimers.get(i);
2169 if (st.mInList) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07002170 Uid uid = st.mUid;
2171 if (uid != null && uid.mUid != Process.SYSTEM_UID) {
Dianne Hackborn618b8c12010-09-09 23:10:38 -07002172 int myUTime = utime/num;
2173 int mySTime = stime/num;
2174 utime -= myUTime;
2175 stime -= mySTime;
2176 num--;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07002177 Uid.Proc proc = uid.getProcessStatsLocked("*wakelock*");
2178 proc.addCpuTimeLocked(myUTime, mySTime);
2179 proc.addSpeedStepTimes(cpuSpeedTimes);
2180 }
2181 }
2182 }
2183 }
2184
2185 // Just in case, collect any lost CPU time.
2186 if (utime != 0 || stime != 0) {
2187 Uid uid = getUidStatsLocked(Process.SYSTEM_UID);
2188 if (uid != null) {
2189 Uid.Proc proc = uid.getProcessStatsLocked("*lost*");
2190 proc.addCpuTimeLocked(utime, stime);
2191 proc.addSpeedStepTimes(cpuSpeedTimes);
2192 }
2193 }
2194 }
2195
2196 final int NL = mLastPartialTimers.size();
2197 boolean diff = N != NL;
2198 for (int i=0; i<NL && !diff; i++) {
2199 diff |= mPartialTimers.get(i) != mLastPartialTimers.get(i);
2200 }
2201 if (!diff) {
2202 for (int i=0; i<NL; i++) {
2203 mPartialTimers.get(i).mInList = true;
2204 }
2205 return;
2206 }
2207
2208 for (int i=0; i<NL; i++) {
2209 mLastPartialTimers.get(i).mInList = false;
2210 }
2211 mLastPartialTimers.clear();
2212 for (int i=0; i<N; i++) {
2213 StopwatchTimer st = mPartialTimers.get(i);
2214 st.mInList = true;
2215 mLastPartialTimers.add(st);
2216 }
2217 }
2218
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002219 public void noteProcessDiedLocked(int uid, int pid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002220 uid = mapUid(uid);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002221 Uid u = mUidStats.get(uid);
2222 if (u != null) {
2223 u.mPids.remove(pid);
2224 }
2225 }
2226
2227 public long getProcessWakeTime(int uid, int pid, long realtime) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002228 uid = mapUid(uid);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002229 Uid u = mUidStats.get(uid);
2230 if (u != null) {
2231 Uid.Pid p = u.mPids.get(pid);
2232 if (p != null) {
2233 return p.mWakeSum + (p.mWakeStart != 0 ? (realtime - p.mWakeStart) : 0);
2234 }
2235 }
2236 return 0;
2237 }
2238
2239 public void reportExcessiveWakeLocked(int uid, String proc, long overTime, long usedTime) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002240 uid = mapUid(uid);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002241 Uid u = mUidStats.get(uid);
2242 if (u != null) {
2243 u.reportExcessiveWakeLocked(proc, overTime, usedTime);
2244 }
2245 }
2246
Dianne Hackborn287952c2010-09-22 22:34:31 -07002247 public void reportExcessiveCpuLocked(int uid, String proc, long overTime, long usedTime) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002248 uid = mapUid(uid);
Dianne Hackborn287952c2010-09-22 22:34:31 -07002249 Uid u = mUidStats.get(uid);
2250 if (u != null) {
2251 u.reportExcessiveCpuLocked(proc, overTime, usedTime);
2252 }
2253 }
2254
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002255 int mSensorNesting;
2256
2257 public void noteStartSensorLocked(int uid, int sensor) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002258 uid = mapUid(uid);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002259 if (mSensorNesting == 0) {
2260 mHistoryCur.states |= HistoryItem.STATE_SENSOR_ON_FLAG;
2261 if (DEBUG_HISTORY) Slog.v(TAG, "Start sensor to: "
2262 + Integer.toHexString(mHistoryCur.states));
2263 addHistoryRecordLocked(SystemClock.elapsedRealtime());
2264 }
2265 mSensorNesting++;
2266 getUidStatsLocked(uid).noteStartSensor(sensor);
2267 }
2268
2269 public void noteStopSensorLocked(int uid, int sensor) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002270 uid = mapUid(uid);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002271 mSensorNesting--;
2272 if (mSensorNesting == 0) {
2273 mHistoryCur.states &= ~HistoryItem.STATE_SENSOR_ON_FLAG;
2274 if (DEBUG_HISTORY) Slog.v(TAG, "Stop sensor to: "
2275 + Integer.toHexString(mHistoryCur.states));
2276 addHistoryRecordLocked(SystemClock.elapsedRealtime());
2277 }
2278 getUidStatsLocked(uid).noteStopSensor(sensor);
2279 }
2280
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002281 int mGpsNesting;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002282
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002283 public void noteStartGpsLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002284 uid = mapUid(uid);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002285 if (mGpsNesting == 0) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002286 mHistoryCur.states |= HistoryItem.STATE_GPS_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002287 if (DEBUG_HISTORY) Slog.v(TAG, "Start GPS to: "
2288 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002289 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002290 }
2291 mGpsNesting++;
Dianne Hackborn2e418422009-06-22 20:00:17 -07002292 getUidStatsLocked(uid).noteStartGps();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002293 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002294
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002295 public void noteStopGpsLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002296 uid = mapUid(uid);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002297 mGpsNesting--;
2298 if (mGpsNesting == 0) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002299 mHistoryCur.states &= ~HistoryItem.STATE_GPS_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002300 if (DEBUG_HISTORY) Slog.v(TAG, "Stop GPS to: "
2301 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002302 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002303 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002304 getUidStatsLocked(uid).noteStopGps();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002305 }
Amith Yamasani3718aaa2009-06-09 06:32:35 -07002306
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002307 public void noteScreenOnLocked() {
2308 if (!mScreenOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002309 mHistoryCur.states |= HistoryItem.STATE_SCREEN_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002310 if (DEBUG_HISTORY) Slog.v(TAG, "Screen on to: "
2311 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002312 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002313 mScreenOn = true;
2314 mScreenOnTimer.startRunningLocked(this);
Dianne Hackborn617f8772009-03-31 15:04:46 -07002315 if (mScreenBrightnessBin >= 0) {
2316 mScreenBrightnessTimer[mScreenBrightnessBin].startRunningLocked(this);
2317 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002318
2319 // Fake a wake lock, so we consider the device waked as long
2320 // as the screen is on.
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08002321 noteStartWakeLocked(-1, -1, "screen", WAKE_TYPE_PARTIAL, false);
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08002322
2323 // Update discharge amounts.
2324 if (mOnBatteryInternal) {
Dianne Hackborn32de2f62011-03-09 14:03:35 -08002325 updateDischargeScreenLevelsLocked(false, true);
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08002326 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002327 }
2328 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002329
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002330 public void noteScreenOffLocked() {
2331 if (mScreenOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002332 mHistoryCur.states &= ~HistoryItem.STATE_SCREEN_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002333 if (DEBUG_HISTORY) Slog.v(TAG, "Screen off to: "
2334 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002335 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002336 mScreenOn = false;
2337 mScreenOnTimer.stopRunningLocked(this);
Dianne Hackborn617f8772009-03-31 15:04:46 -07002338 if (mScreenBrightnessBin >= 0) {
2339 mScreenBrightnessTimer[mScreenBrightnessBin].stopRunningLocked(this);
2340 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07002341
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07002342 noteStopWakeLocked(-1, -1, "dummy", WAKE_TYPE_PARTIAL);
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08002343
2344 // Update discharge amounts.
2345 if (mOnBatteryInternal) {
Dianne Hackborn32de2f62011-03-09 14:03:35 -08002346 updateDischargeScreenLevelsLocked(true, false);
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08002347 }
Dianne Hackborn617f8772009-03-31 15:04:46 -07002348 }
2349 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002350
Dianne Hackborn617f8772009-03-31 15:04:46 -07002351 public void noteScreenBrightnessLocked(int brightness) {
2352 // Bin the brightness.
2353 int bin = brightness / (256/NUM_SCREEN_BRIGHTNESS_BINS);
2354 if (bin < 0) bin = 0;
2355 else if (bin >= NUM_SCREEN_BRIGHTNESS_BINS) bin = NUM_SCREEN_BRIGHTNESS_BINS-1;
2356 if (mScreenBrightnessBin != bin) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002357 mHistoryCur.states = (mHistoryCur.states&~HistoryItem.STATE_BRIGHTNESS_MASK)
2358 | (bin << HistoryItem.STATE_BRIGHTNESS_SHIFT);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002359 if (DEBUG_HISTORY) Slog.v(TAG, "Screen brightness " + bin + " to: "
2360 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002361 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn617f8772009-03-31 15:04:46 -07002362 if (mScreenOn) {
2363 if (mScreenBrightnessBin >= 0) {
2364 mScreenBrightnessTimer[mScreenBrightnessBin].stopRunningLocked(this);
2365 }
2366 mScreenBrightnessTimer[bin].startRunningLocked(this);
2367 }
2368 mScreenBrightnessBin = bin;
2369 }
2370 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002371
Christopher Tate4cee7252010-03-19 14:50:40 -07002372 public void noteInputEventAtomic() {
2373 mInputEventCounter.stepAtomic();
Dianne Hackborn617f8772009-03-31 15:04:46 -07002374 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002375
Dianne Hackborn617f8772009-03-31 15:04:46 -07002376 public void noteUserActivityLocked(int uid, int event) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002377 uid = mapUid(uid);
Dianne Hackborn2e418422009-06-22 20:00:17 -07002378 getUidStatsLocked(uid).noteUserActivityLocked(event);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002379 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002380
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002381 public void notePhoneOnLocked() {
2382 if (!mPhoneOn) {
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002383 mHistoryCur.states |= HistoryItem.STATE_PHONE_IN_CALL_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002384 if (DEBUG_HISTORY) Slog.v(TAG, "Phone on to: "
2385 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002386 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002387 mPhoneOn = true;
2388 mPhoneOnTimer.startRunningLocked(this);
2389 }
2390 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002391
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002392 public void notePhoneOffLocked() {
2393 if (mPhoneOn) {
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002394 mHistoryCur.states &= ~HistoryItem.STATE_PHONE_IN_CALL_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002395 if (DEBUG_HISTORY) Slog.v(TAG, "Phone off to: "
2396 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002397 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002398 mPhoneOn = false;
2399 mPhoneOnTimer.stopRunningLocked(this);
2400 }
2401 }
Amith Yamasani32dbefd2009-06-19 09:21:17 -07002402
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002403 void stopAllSignalStrengthTimersLocked(int except) {
Wink Saville52840902011-02-18 12:40:47 -08002404 for (int i = 0; i < SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002405 if (i == except) {
2406 continue;
2407 }
2408 while (mPhoneSignalStrengthsTimer[i].isRunningLocked()) {
2409 mPhoneSignalStrengthsTimer[i].stopRunningLocked(this);
2410 }
2411 }
2412 }
2413
Dianne Hackborne4a59512010-12-07 11:08:07 -08002414 private int fixPhoneServiceState(int state, int signalBin) {
2415 if (mPhoneSimStateRaw == TelephonyManager.SIM_STATE_ABSENT) {
2416 // In this case we will always be STATE_OUT_OF_SERVICE, so need
2417 // to infer that we are scanning from other data.
2418 if (state == ServiceState.STATE_OUT_OF_SERVICE
Wink Saville52840902011-02-18 12:40:47 -08002419 && signalBin > SignalStrength.SIGNAL_STRENGTH_NONE_OR_UNKNOWN) {
Dianne Hackborne4a59512010-12-07 11:08:07 -08002420 state = ServiceState.STATE_IN_SERVICE;
2421 }
2422 }
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002423
Dianne Hackborne4a59512010-12-07 11:08:07 -08002424 return state;
2425 }
2426
2427 private void updateAllPhoneStateLocked(int state, int simState, int bin) {
2428 boolean scanning = false;
2429 boolean newHistory = false;
2430
2431 mPhoneServiceStateRaw = state;
2432 mPhoneSimStateRaw = simState;
2433 mPhoneSignalStrengthBinRaw = bin;
2434
2435 if (simState == TelephonyManager.SIM_STATE_ABSENT) {
2436 // In this case we will always be STATE_OUT_OF_SERVICE, so need
2437 // to infer that we are scanning from other data.
2438 if (state == ServiceState.STATE_OUT_OF_SERVICE
Wink Saville52840902011-02-18 12:40:47 -08002439 && bin > SignalStrength.SIGNAL_STRENGTH_NONE_OR_UNKNOWN) {
Dianne Hackborne4a59512010-12-07 11:08:07 -08002440 state = ServiceState.STATE_IN_SERVICE;
2441 }
2442 }
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002443
2444 // If the phone is powered off, stop all timers.
2445 if (state == ServiceState.STATE_POWER_OFF) {
Dianne Hackborne4a59512010-12-07 11:08:07 -08002446 bin = -1;
Amith Yamasanif37447b2009-10-08 18:28:01 -07002447
Dianne Hackborne4a59512010-12-07 11:08:07 -08002448 // If we are in service, make sure the correct signal string timer is running.
2449 } else if (state == ServiceState.STATE_IN_SERVICE) {
2450 // Bin will be changed below.
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002451
2452 // If we're out of service, we are in the lowest signal strength
2453 // bin and have the scanning bit set.
Amith Yamasanif37447b2009-10-08 18:28:01 -07002454 } else if (state == ServiceState.STATE_OUT_OF_SERVICE) {
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002455 scanning = true;
Wink Saville52840902011-02-18 12:40:47 -08002456 bin = SignalStrength.SIGNAL_STRENGTH_NONE_OR_UNKNOWN;
Amith Yamasanif37447b2009-10-08 18:28:01 -07002457 if (!mPhoneSignalScanningTimer.isRunningLocked()) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002458 mHistoryCur.states |= HistoryItem.STATE_PHONE_SCANNING_FLAG;
Dianne Hackborne4a59512010-12-07 11:08:07 -08002459 newHistory = true;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002460 if (DEBUG_HISTORY) Slog.v(TAG, "Phone started scanning to: "
2461 + Integer.toHexString(mHistoryCur.states));
Amith Yamasanif37447b2009-10-08 18:28:01 -07002462 mPhoneSignalScanningTimer.startRunningLocked(this);
2463 }
2464 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002465
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002466 if (!scanning) {
2467 // If we are no longer scanning, then stop the scanning timer.
2468 if (mPhoneSignalScanningTimer.isRunningLocked()) {
2469 mHistoryCur.states &= ~HistoryItem.STATE_PHONE_SCANNING_FLAG;
2470 if (DEBUG_HISTORY) Slog.v(TAG, "Phone stopped scanning to: "
2471 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborne4a59512010-12-07 11:08:07 -08002472 newHistory = true;
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07002473 mPhoneSignalScanningTimer.stopRunningLocked(this);
2474 }
2475 }
2476
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002477 if (mPhoneServiceState != state) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002478 mHistoryCur.states = (mHistoryCur.states&~HistoryItem.STATE_PHONE_STATE_MASK)
2479 | (state << HistoryItem.STATE_PHONE_STATE_SHIFT);
Dianne Hackborne4a59512010-12-07 11:08:07 -08002480 if (DEBUG_HISTORY) Slog.v(TAG, "Phone state " + state + " to: "
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002481 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborne4a59512010-12-07 11:08:07 -08002482 newHistory = true;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002483 mPhoneServiceState = state;
2484 }
Dianne Hackborne4a59512010-12-07 11:08:07 -08002485
2486 if (mPhoneSignalStrengthBin != bin) {
2487 if (mPhoneSignalStrengthBin >= 0) {
2488 mPhoneSignalStrengthsTimer[mPhoneSignalStrengthBin].stopRunningLocked(this);
2489 }
2490 if (bin >= 0) {
2491 if (!mPhoneSignalStrengthsTimer[bin].isRunningLocked()) {
2492 mPhoneSignalStrengthsTimer[bin].startRunningLocked(this);
2493 }
2494 mHistoryCur.states = (mHistoryCur.states&~HistoryItem.STATE_SIGNAL_STRENGTH_MASK)
2495 | (bin << HistoryItem.STATE_SIGNAL_STRENGTH_SHIFT);
2496 if (DEBUG_HISTORY) Slog.v(TAG, "Signal strength " + bin + " to: "
2497 + Integer.toHexString(mHistoryCur.states));
2498 newHistory = true;
2499 } else {
2500 stopAllSignalStrengthTimersLocked(-1);
2501 }
2502 mPhoneSignalStrengthBin = bin;
2503 }
2504
2505 if (newHistory) {
2506 addHistoryRecordLocked(SystemClock.elapsedRealtime());
2507 }
2508 }
2509
2510 /**
2511 * Telephony stack updates the phone state.
2512 * @param state phone state from ServiceState.getState()
2513 */
2514 public void notePhoneStateLocked(int state, int simState) {
2515 updateAllPhoneStateLocked(state, simState, mPhoneSignalStrengthBinRaw);
Amith Yamasani32dbefd2009-06-19 09:21:17 -07002516 }
2517
Wink Savillee9b06d72009-05-18 21:47:50 -07002518 public void notePhoneSignalStrengthLocked(SignalStrength signalStrength) {
Dianne Hackborn627bba72009-03-24 22:32:56 -07002519 // Bin the strength.
Wink Saville52840902011-02-18 12:40:47 -08002520 int bin = signalStrength.getLevel();
Dianne Hackborne4a59512010-12-07 11:08:07 -08002521 updateAllPhoneStateLocked(mPhoneServiceStateRaw, mPhoneSimStateRaw, bin);
Dianne Hackborn627bba72009-03-24 22:32:56 -07002522 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002523
Dianne Hackborn627bba72009-03-24 22:32:56 -07002524 public void notePhoneDataConnectionStateLocked(int dataType, boolean hasData) {
2525 int bin = DATA_CONNECTION_NONE;
2526 if (hasData) {
2527 switch (dataType) {
2528 case TelephonyManager.NETWORK_TYPE_EDGE:
2529 bin = DATA_CONNECTION_EDGE;
2530 break;
2531 case TelephonyManager.NETWORK_TYPE_GPRS:
2532 bin = DATA_CONNECTION_GPRS;
2533 break;
2534 case TelephonyManager.NETWORK_TYPE_UMTS:
2535 bin = DATA_CONNECTION_UMTS;
2536 break;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002537 case TelephonyManager.NETWORK_TYPE_CDMA:
2538 bin = DATA_CONNECTION_CDMA;
2539 break;
2540 case TelephonyManager.NETWORK_TYPE_EVDO_0:
2541 bin = DATA_CONNECTION_EVDO_0;
2542 break;
2543 case TelephonyManager.NETWORK_TYPE_EVDO_A:
2544 bin = DATA_CONNECTION_EVDO_A;
2545 break;
2546 case TelephonyManager.NETWORK_TYPE_1xRTT:
2547 bin = DATA_CONNECTION_1xRTT;
2548 break;
2549 case TelephonyManager.NETWORK_TYPE_HSDPA:
2550 bin = DATA_CONNECTION_HSDPA;
2551 break;
2552 case TelephonyManager.NETWORK_TYPE_HSUPA:
2553 bin = DATA_CONNECTION_HSUPA;
2554 break;
2555 case TelephonyManager.NETWORK_TYPE_HSPA:
2556 bin = DATA_CONNECTION_HSPA;
2557 break;
2558 case TelephonyManager.NETWORK_TYPE_IDEN:
2559 bin = DATA_CONNECTION_IDEN;
2560 break;
2561 case TelephonyManager.NETWORK_TYPE_EVDO_B:
2562 bin = DATA_CONNECTION_EVDO_B;
2563 break;
Robert Greenwalt962a9902010-11-02 11:10:25 -07002564 case TelephonyManager.NETWORK_TYPE_LTE:
2565 bin = DATA_CONNECTION_LTE;
2566 break;
2567 case TelephonyManager.NETWORK_TYPE_EHRPD:
2568 bin = DATA_CONNECTION_EHRPD;
2569 break;
Patrick Tjinb71703c2013-11-06 09:27:03 -08002570 case TelephonyManager.NETWORK_TYPE_HSPAP:
2571 bin = DATA_CONNECTION_HSPAP;
2572 break;
Dianne Hackborn627bba72009-03-24 22:32:56 -07002573 default:
2574 bin = DATA_CONNECTION_OTHER;
2575 break;
2576 }
2577 }
Amith Yamasani3718aaa2009-06-09 06:32:35 -07002578 if (DEBUG) Log.i(TAG, "Phone Data Connection -> " + dataType + " = " + hasData);
Dianne Hackborn627bba72009-03-24 22:32:56 -07002579 if (mPhoneDataConnectionType != bin) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002580 mHistoryCur.states = (mHistoryCur.states&~HistoryItem.STATE_DATA_CONNECTION_MASK)
2581 | (bin << HistoryItem.STATE_DATA_CONNECTION_SHIFT);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002582 if (DEBUG_HISTORY) Slog.v(TAG, "Data connection " + bin + " to: "
2583 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002584 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn627bba72009-03-24 22:32:56 -07002585 if (mPhoneDataConnectionType >= 0) {
2586 mPhoneDataConnectionsTimer[mPhoneDataConnectionType].stopRunningLocked(this);
2587 }
2588 mPhoneDataConnectionType = bin;
2589 mPhoneDataConnectionsTimer[bin].startRunningLocked(this);
2590 }
2591 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002592
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002593 public void noteWifiOnLocked() {
The Android Open Source Project10592532009-03-18 17:39:46 -07002594 if (!mWifiOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002595 mHistoryCur.states |= HistoryItem.STATE_WIFI_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002596 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI on to: "
2597 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002598 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project10592532009-03-18 17:39:46 -07002599 mWifiOn = true;
2600 mWifiOnTimer.startRunningLocked(this);
2601 }
2602 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002603
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002604 public void noteWifiOffLocked() {
The Android Open Source Project10592532009-03-18 17:39:46 -07002605 if (mWifiOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002606 mHistoryCur.states &= ~HistoryItem.STATE_WIFI_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002607 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI off to: "
2608 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002609 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project10592532009-03-18 17:39:46 -07002610 mWifiOn = false;
2611 mWifiOnTimer.stopRunningLocked(this);
2612 }
Dianne Hackborn617f8772009-03-31 15:04:46 -07002613 if (mWifiOnUid >= 0) {
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002614 getUidStatsLocked(mWifiOnUid).noteWifiStoppedLocked();
Dianne Hackborn617f8772009-03-31 15:04:46 -07002615 mWifiOnUid = -1;
2616 }
The Android Open Source Project10592532009-03-18 17:39:46 -07002617 }
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002618
2619 public void noteAudioOnLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002620 uid = mapUid(uid);
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002621 if (!mAudioOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002622 mHistoryCur.states |= HistoryItem.STATE_AUDIO_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002623 if (DEBUG_HISTORY) Slog.v(TAG, "Audio on to: "
2624 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002625 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002626 mAudioOn = true;
2627 mAudioOnTimer.startRunningLocked(this);
2628 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002629 getUidStatsLocked(uid).noteAudioTurnedOnLocked();
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002630 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002631
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002632 public void noteAudioOffLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002633 uid = mapUid(uid);
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002634 if (mAudioOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002635 mHistoryCur.states &= ~HistoryItem.STATE_AUDIO_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002636 if (DEBUG_HISTORY) Slog.v(TAG, "Audio off to: "
2637 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002638 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002639 mAudioOn = false;
2640 mAudioOnTimer.stopRunningLocked(this);
2641 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002642 getUidStatsLocked(uid).noteAudioTurnedOffLocked();
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002643 }
2644
2645 public void noteVideoOnLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002646 uid = mapUid(uid);
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002647 if (!mVideoOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002648 mHistoryCur.states |= HistoryItem.STATE_VIDEO_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002649 if (DEBUG_HISTORY) Slog.v(TAG, "Video on to: "
2650 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002651 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002652 mVideoOn = true;
2653 mVideoOnTimer.startRunningLocked(this);
2654 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002655 getUidStatsLocked(uid).noteVideoTurnedOnLocked();
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002656 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002657
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002658 public void noteVideoOffLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002659 uid = mapUid(uid);
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002660 if (mVideoOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002661 mHistoryCur.states &= ~HistoryItem.STATE_VIDEO_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002662 if (DEBUG_HISTORY) Slog.v(TAG, "Video off to: "
2663 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002664 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002665 mVideoOn = false;
2666 mVideoOnTimer.stopRunningLocked(this);
2667 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002668 getUidStatsLocked(uid).noteVideoTurnedOffLocked();
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002669 }
2670
Jeff Sharkey3e013e82013-04-25 14:48:19 -07002671 public void noteActivityResumedLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002672 uid = mapUid(uid);
Jeff Sharkey3e013e82013-04-25 14:48:19 -07002673 getUidStatsLocked(uid).noteActivityResumedLocked();
2674 }
2675
2676 public void noteActivityPausedLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002677 uid = mapUid(uid);
Jeff Sharkey3e013e82013-04-25 14:48:19 -07002678 getUidStatsLocked(uid).noteActivityPausedLocked();
2679 }
2680
Dianne Hackborna06de0f2012-12-11 16:34:47 -08002681 public void noteVibratorOnLocked(int uid, long durationMillis) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002682 uid = mapUid(uid);
Dianne Hackborna06de0f2012-12-11 16:34:47 -08002683 getUidStatsLocked(uid).noteVibratorOnLocked(durationMillis);
2684 }
2685
2686 public void noteVibratorOffLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002687 uid = mapUid(uid);
Dianne Hackborna06de0f2012-12-11 16:34:47 -08002688 getUidStatsLocked(uid).noteVibratorOffLocked();
2689 }
2690
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002691 public void noteWifiRunningLocked(WorkSource ws) {
2692 if (!mGlobalWifiRunning) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002693 mHistoryCur.states |= HistoryItem.STATE_WIFI_RUNNING_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002694 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI running to: "
2695 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002696 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002697 mGlobalWifiRunning = true;
2698 mGlobalWifiRunningTimer.startRunningLocked(this);
2699 int N = ws.size();
2700 for (int i=0; i<N; i++) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002701 int uid = mapUid(ws.get(i));
2702 getUidStatsLocked(uid).noteWifiRunningLocked();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002703 }
2704 } else {
2705 Log.w(TAG, "noteWifiRunningLocked -- called while WIFI running");
Eric Shienbroodd4c5f892009-03-24 18:13:20 -07002706 }
2707 }
2708
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002709 public void noteWifiRunningChangedLocked(WorkSource oldWs, WorkSource newWs) {
2710 if (mGlobalWifiRunning) {
2711 int N = oldWs.size();
2712 for (int i=0; i<N; i++) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002713 int uid = mapUid(oldWs.get(i));
2714 getUidStatsLocked(uid).noteWifiStoppedLocked();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002715 }
2716 N = newWs.size();
2717 for (int i=0; i<N; i++) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002718 int uid = mapUid(newWs.get(i));
2719 getUidStatsLocked(uid).noteWifiRunningLocked();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002720 }
2721 } else {
2722 Log.w(TAG, "noteWifiRunningChangedLocked -- called while WIFI not running");
2723 }
2724 }
2725
2726 public void noteWifiStoppedLocked(WorkSource ws) {
2727 if (mGlobalWifiRunning) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002728 mHistoryCur.states &= ~HistoryItem.STATE_WIFI_RUNNING_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002729 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI stopped to: "
2730 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002731 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002732 mGlobalWifiRunning = false;
2733 mGlobalWifiRunningTimer.stopRunningLocked(this);
2734 int N = ws.size();
2735 for (int i=0; i<N; i++) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002736 int uid = mapUid(ws.get(i));
2737 getUidStatsLocked(uid).noteWifiStoppedLocked();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002738 }
2739 } else {
2740 Log.w(TAG, "noteWifiStoppedLocked -- called while WIFI not running");
Eric Shienbroodd4c5f892009-03-24 18:13:20 -07002741 }
2742 }
2743
The Android Open Source Project10592532009-03-18 17:39:46 -07002744 public void noteBluetoothOnLocked() {
2745 if (!mBluetoothOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002746 mHistoryCur.states |= HistoryItem.STATE_BLUETOOTH_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002747 if (DEBUG_HISTORY) Slog.v(TAG, "Bluetooth on to: "
2748 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002749 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project10592532009-03-18 17:39:46 -07002750 mBluetoothOn = true;
2751 mBluetoothOnTimer.startRunningLocked(this);
2752 }
2753 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002754
The Android Open Source Project10592532009-03-18 17:39:46 -07002755 public void noteBluetoothOffLocked() {
2756 if (mBluetoothOn) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002757 mHistoryCur.states &= ~HistoryItem.STATE_BLUETOOTH_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002758 if (DEBUG_HISTORY) Slog.v(TAG, "Bluetooth off to: "
2759 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002760 addHistoryRecordLocked(SystemClock.elapsedRealtime());
The Android Open Source Project10592532009-03-18 17:39:46 -07002761 mBluetoothOn = false;
2762 mBluetoothOnTimer.stopRunningLocked(this);
2763 }
2764 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002765
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002766 int mWifiFullLockNesting = 0;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002767
The Android Open Source Project10592532009-03-18 17:39:46 -07002768 public void noteFullWifiLockAcquiredLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002769 uid = mapUid(uid);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002770 if (mWifiFullLockNesting == 0) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002771 mHistoryCur.states |= HistoryItem.STATE_WIFI_FULL_LOCK_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002772 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI full lock on to: "
2773 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002774 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002775 }
2776 mWifiFullLockNesting++;
Dianne Hackborn2e418422009-06-22 20:00:17 -07002777 getUidStatsLocked(uid).noteFullWifiLockAcquiredLocked();
The Android Open Source Project10592532009-03-18 17:39:46 -07002778 }
2779
2780 public void noteFullWifiLockReleasedLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002781 uid = mapUid(uid);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002782 mWifiFullLockNesting--;
2783 if (mWifiFullLockNesting == 0) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002784 mHistoryCur.states &= ~HistoryItem.STATE_WIFI_FULL_LOCK_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002785 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI full lock off to: "
2786 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002787 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002788 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002789 getUidStatsLocked(uid).noteFullWifiLockReleasedLocked();
The Android Open Source Project10592532009-03-18 17:39:46 -07002790 }
2791
Nick Pelly6ccaa542012-06-15 15:22:47 -07002792 int mWifiScanNesting = 0;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002793
Nick Pelly6ccaa542012-06-15 15:22:47 -07002794 public void noteWifiScanStartedLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002795 uid = mapUid(uid);
Nick Pelly6ccaa542012-06-15 15:22:47 -07002796 if (mWifiScanNesting == 0) {
2797 mHistoryCur.states |= HistoryItem.STATE_WIFI_SCAN_FLAG;
2798 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI scan started for: "
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002799 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002800 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002801 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07002802 mWifiScanNesting++;
2803 getUidStatsLocked(uid).noteWifiScanStartedLocked();
The Android Open Source Project10592532009-03-18 17:39:46 -07002804 }
2805
Nick Pelly6ccaa542012-06-15 15:22:47 -07002806 public void noteWifiScanStoppedLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002807 uid = mapUid(uid);
Nick Pelly6ccaa542012-06-15 15:22:47 -07002808 mWifiScanNesting--;
2809 if (mWifiScanNesting == 0) {
2810 mHistoryCur.states &= ~HistoryItem.STATE_WIFI_SCAN_FLAG;
2811 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI scan stopped for: "
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002812 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002813 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002814 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07002815 getUidStatsLocked(uid).noteWifiScanStoppedLocked();
The Android Open Source Project10592532009-03-18 17:39:46 -07002816 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07002817
Robert Greenwalta029ea12013-09-25 16:38:12 -07002818 public void noteWifiBatchedScanStartedLocked(int uid, int csph) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002819 uid = mapUid(uid);
Robert Greenwalta029ea12013-09-25 16:38:12 -07002820 getUidStatsLocked(uid).noteWifiBatchedScanStartedLocked(csph);
2821 }
2822
2823 public void noteWifiBatchedScanStoppedLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002824 uid = mapUid(uid);
Robert Greenwalta029ea12013-09-25 16:38:12 -07002825 getUidStatsLocked(uid).noteWifiBatchedScanStoppedLocked();
2826 }
2827
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002828 int mWifiMulticastNesting = 0;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002829
Robert Greenwalt5347bd42009-05-13 15:10:16 -07002830 public void noteWifiMulticastEnabledLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002831 uid = mapUid(uid);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002832 if (mWifiMulticastNesting == 0) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002833 mHistoryCur.states |= HistoryItem.STATE_WIFI_MULTICAST_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002834 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI multicast on to: "
2835 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002836 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002837 }
2838 mWifiMulticastNesting++;
Dianne Hackborn2e418422009-06-22 20:00:17 -07002839 getUidStatsLocked(uid).noteWifiMulticastEnabledLocked();
Robert Greenwalt5347bd42009-05-13 15:10:16 -07002840 }
2841
2842 public void noteWifiMulticastDisabledLocked(int uid) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08002843 uid = mapUid(uid);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002844 mWifiMulticastNesting--;
2845 if (mWifiMulticastNesting == 0) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002846 mHistoryCur.states &= ~HistoryItem.STATE_WIFI_MULTICAST_ON_FLAG;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002847 if (DEBUG_HISTORY) Slog.v(TAG, "WIFI multicast off to: "
2848 + Integer.toHexString(mHistoryCur.states));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07002849 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn32907cf2010-06-10 17:50:20 -07002850 }
Dianne Hackborn2e418422009-06-22 20:00:17 -07002851 getUidStatsLocked(uid).noteWifiMulticastDisabledLocked();
Robert Greenwalt5347bd42009-05-13 15:10:16 -07002852 }
2853
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002854 public void noteFullWifiLockAcquiredFromSourceLocked(WorkSource ws) {
2855 int N = ws.size();
2856 for (int i=0; i<N; i++) {
2857 noteFullWifiLockAcquiredLocked(ws.get(i));
2858 }
2859 }
2860
2861 public void noteFullWifiLockReleasedFromSourceLocked(WorkSource ws) {
2862 int N = ws.size();
2863 for (int i=0; i<N; i++) {
2864 noteFullWifiLockReleasedLocked(ws.get(i));
2865 }
2866 }
2867
Nick Pelly6ccaa542012-06-15 15:22:47 -07002868 public void noteWifiScanStartedFromSourceLocked(WorkSource ws) {
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002869 int N = ws.size();
2870 for (int i=0; i<N; i++) {
Nick Pelly6ccaa542012-06-15 15:22:47 -07002871 noteWifiScanStartedLocked(ws.get(i));
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002872 }
2873 }
2874
Nick Pelly6ccaa542012-06-15 15:22:47 -07002875 public void noteWifiScanStoppedFromSourceLocked(WorkSource ws) {
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002876 int N = ws.size();
2877 for (int i=0; i<N; i++) {
Nick Pelly6ccaa542012-06-15 15:22:47 -07002878 noteWifiScanStoppedLocked(ws.get(i));
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002879 }
2880 }
2881
Robert Greenwalta029ea12013-09-25 16:38:12 -07002882 public void noteWifiBatchedScanStartedFromSourceLocked(WorkSource ws, int csph) {
2883 int N = ws.size();
2884 for (int i=0; i<N; i++) {
2885 noteWifiBatchedScanStartedLocked(ws.get(i), csph);
2886 }
2887 }
2888
2889 public void noteWifiBatchedScanStoppedFromSourceLocked(WorkSource ws) {
2890 int N = ws.size();
2891 for (int i=0; i<N; i++) {
2892 noteWifiBatchedScanStoppedLocked(ws.get(i));
2893 }
2894 }
2895
Dianne Hackborn7e9f4eb2010-09-10 18:43:00 -07002896 public void noteWifiMulticastEnabledFromSourceLocked(WorkSource ws) {
2897 int N = ws.size();
2898 for (int i=0; i<N; i++) {
2899 noteWifiMulticastEnabledLocked(ws.get(i));
2900 }
2901 }
2902
2903 public void noteWifiMulticastDisabledFromSourceLocked(WorkSource ws) {
2904 int N = ws.size();
2905 for (int i=0; i<N; i++) {
2906 noteWifiMulticastDisabledLocked(ws.get(i));
2907 }
2908 }
2909
Jeff Sharkey1059c3c2011-10-04 16:54:49 -07002910 public void noteNetworkInterfaceTypeLocked(String iface, int networkType) {
2911 if (ConnectivityManager.isNetworkTypeMobile(networkType)) {
2912 mMobileIfaces.add(iface);
2913 } else {
2914 mMobileIfaces.remove(iface);
2915 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07002916 if (ConnectivityManager.isNetworkTypeWifi(networkType)) {
2917 mWifiIfaces.add(iface);
2918 } else {
2919 mWifiIfaces.remove(iface);
2920 }
2921 }
2922
2923 public void noteNetworkStatsEnabledLocked() {
2924 // During device boot, qtaguid isn't enabled until after the inital
2925 // loading of battery stats. Now that they're enabled, take our initial
2926 // snapshot for future delta calculation.
2927 updateNetworkActivityLocked();
Jeff Sharkey1059c3c2011-10-04 16:54:49 -07002928 }
2929
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002930 @Override public long getScreenOnTime(long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002931 return mScreenOnTimer.getTotalTimeLocked(batteryRealtime, which);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002932 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002933
Dianne Hackborn617f8772009-03-31 15:04:46 -07002934 @Override public long getScreenBrightnessTime(int brightnessBin,
2935 long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002936 return mScreenBrightnessTimer[brightnessBin].getTotalTimeLocked(
Dianne Hackborn617f8772009-03-31 15:04:46 -07002937 batteryRealtime, which);
2938 }
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002939
Dianne Hackborn617f8772009-03-31 15:04:46 -07002940 @Override public int getInputEventCount(int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002941 return mInputEventCounter.getCountLocked(which);
Dianne Hackborn617f8772009-03-31 15:04:46 -07002942 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002943
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002944 @Override public long getPhoneOnTime(long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002945 return mPhoneOnTimer.getTotalTimeLocked(batteryRealtime, which);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002946 }
Amith Yamasani244fa5c2009-05-22 14:36:07 -07002947
Dianne Hackborn627bba72009-03-24 22:32:56 -07002948 @Override public long getPhoneSignalStrengthTime(int strengthBin,
2949 long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002950 return mPhoneSignalStrengthsTimer[strengthBin].getTotalTimeLocked(
Dianne Hackborn627bba72009-03-24 22:32:56 -07002951 batteryRealtime, which);
2952 }
Amith Yamasanif37447b2009-10-08 18:28:01 -07002953
2954 @Override public long getPhoneSignalScanningTime(
2955 long batteryRealtime, int which) {
2956 return mPhoneSignalScanningTimer.getTotalTimeLocked(
2957 batteryRealtime, which);
2958 }
2959
Catherine Liufb900812012-07-17 14:12:56 -05002960 @Override public int getPhoneSignalStrengthCount(int strengthBin, int which) {
2961 return mPhoneSignalStrengthsTimer[strengthBin].getCountLocked(which);
Dianne Hackborn617f8772009-03-31 15:04:46 -07002962 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002963
Dianne Hackborn627bba72009-03-24 22:32:56 -07002964 @Override public long getPhoneDataConnectionTime(int dataType,
2965 long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002966 return mPhoneDataConnectionsTimer[dataType].getTotalTimeLocked(
Dianne Hackborn627bba72009-03-24 22:32:56 -07002967 batteryRealtime, which);
2968 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002969
Dianne Hackborn617f8772009-03-31 15:04:46 -07002970 @Override public int getPhoneDataConnectionCount(int dataType, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002971 return mPhoneDataConnectionsTimer[dataType].getCountLocked(which);
Dianne Hackborn617f8772009-03-31 15:04:46 -07002972 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002973
The Android Open Source Project10592532009-03-18 17:39:46 -07002974 @Override public long getWifiOnTime(long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002975 return mWifiOnTimer.getTotalTimeLocked(batteryRealtime, which);
The Android Open Source Project10592532009-03-18 17:39:46 -07002976 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002977
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07002978 @Override public long getGlobalWifiRunningTime(long batteryRealtime, int which) {
2979 return mGlobalWifiRunningTimer.getTotalTimeLocked(batteryRealtime, which);
Eric Shienbroodd4c5f892009-03-24 18:13:20 -07002980 }
2981
The Android Open Source Project10592532009-03-18 17:39:46 -07002982 @Override public long getBluetoothOnTime(long batteryRealtime, int which) {
Evan Millarc64edde2009-04-18 12:26:32 -07002983 return mBluetoothOnTimer.getTotalTimeLocked(batteryRealtime, which);
The Android Open Source Project10592532009-03-18 17:39:46 -07002984 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07002985
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07002986 @Override
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08002987 public long getNetworkActivityBytes(int type, int which) {
2988 if (type >= 0 && type < mNetworkByteActivityCounters.length) {
2989 return mNetworkByteActivityCounters[type].getCountLocked(which);
2990 } else {
2991 return 0;
2992 }
2993 }
2994
2995 @Override
2996 public long getNetworkActivityPackets(int type, int which) {
2997 if (type >= 0 && type < mNetworkPacketActivityCounters.length) {
2998 return mNetworkPacketActivityCounters[type].getCountLocked(which);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07002999 } else {
3000 return 0;
3001 }
3002 }
3003
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08003004 @Override public long getStartClockTime() {
3005 return mStartClockTime;
3006 }
3007
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003008 @Override public boolean getIsOnBattery() {
3009 return mOnBattery;
3010 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003011
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003012 @Override public SparseArray<? extends BatteryStats.Uid> getUidStats() {
3013 return mUidStats;
3014 }
3015
3016 /**
3017 * The statistics associated with a particular uid.
3018 */
3019 public final class Uid extends BatteryStats.Uid {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003020
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003021 final int mUid;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003022
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003023 boolean mWifiRunning;
3024 StopwatchTimer mWifiRunningTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003025
The Android Open Source Project10592532009-03-18 17:39:46 -07003026 boolean mFullWifiLockOut;
Evan Millarc64edde2009-04-18 12:26:32 -07003027 StopwatchTimer mFullWifiLockTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003028
Nick Pelly6ccaa542012-06-15 15:22:47 -07003029 boolean mWifiScanStarted;
3030 StopwatchTimer mWifiScanTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003031
Robert Greenwalta029ea12013-09-25 16:38:12 -07003032 private static final int NO_BATCHED_SCAN_STARTED = -1;
3033 int mWifiBatchedScanBinStarted = NO_BATCHED_SCAN_STARTED;
3034 StopwatchTimer[] mWifiBatchedScanTimer;
3035
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003036 boolean mWifiMulticastEnabled;
3037 StopwatchTimer mWifiMulticastTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003038
Amith Yamasani244fa5c2009-05-22 14:36:07 -07003039 boolean mAudioTurnedOn;
3040 StopwatchTimer mAudioTurnedOnTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003041
Amith Yamasani244fa5c2009-05-22 14:36:07 -07003042 boolean mVideoTurnedOn;
3043 StopwatchTimer mVideoTurnedOnTimer;
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003044
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003045 StopwatchTimer mForegroundActivityTimer;
3046
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003047 BatchTimer mVibratorOnTimer;
3048
Dianne Hackborn617f8772009-03-31 15:04:46 -07003049 Counter[] mUserActivityCounters;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003050
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003051 LongSamplingCounter[] mNetworkByteActivityCounters;
3052 LongSamplingCounter[] mNetworkPacketActivityCounters;
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003053
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003054 /**
3055 * The statistics we have collected for this uid's wake locks.
3056 */
3057 final HashMap<String, Wakelock> mWakelockStats = new HashMap<String, Wakelock>();
3058
3059 /**
3060 * The statistics we have collected for this uid's sensor activations.
3061 */
3062 final HashMap<Integer, Sensor> mSensorStats = new HashMap<Integer, Sensor>();
3063
3064 /**
3065 * The statistics we have collected for this uid's processes.
3066 */
3067 final HashMap<String, Proc> mProcessStats = new HashMap<String, Proc>();
3068
3069 /**
3070 * The statistics we have collected for this uid's processes.
3071 */
3072 final HashMap<String, Pkg> mPackageStats = new HashMap<String, Pkg>();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003073
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003074 /**
3075 * The transient wake stats we have collected for this uid's pids.
3076 */
3077 final SparseArray<Pid> mPids = new SparseArray<Pid>();
3078
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003079 public Uid(int uid) {
3080 mUid = uid;
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003081 mWifiRunningTimer = new StopwatchTimer(Uid.this, WIFI_RUNNING,
3082 mWifiRunningTimers, mUnpluggables);
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003083 mFullWifiLockTimer = new StopwatchTimer(Uid.this, FULL_WIFI_LOCK,
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003084 mFullWifiLockTimers, mUnpluggables);
Nick Pelly6ccaa542012-06-15 15:22:47 -07003085 mWifiScanTimer = new StopwatchTimer(Uid.this, WIFI_SCAN,
3086 mWifiScanTimers, mUnpluggables);
Robert Greenwalta029ea12013-09-25 16:38:12 -07003087 mWifiBatchedScanTimer = new StopwatchTimer[NUM_WIFI_BATCHED_SCAN_BINS];
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003088 mWifiMulticastTimer = new StopwatchTimer(Uid.this, WIFI_MULTICAST_ENABLED,
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003089 mWifiMulticastTimers, mUnpluggables);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003090 }
3091
3092 @Override
3093 public Map<String, ? extends BatteryStats.Uid.Wakelock> getWakelockStats() {
3094 return mWakelockStats;
3095 }
3096
3097 @Override
3098 public Map<Integer, ? extends BatteryStats.Uid.Sensor> getSensorStats() {
3099 return mSensorStats;
3100 }
3101
3102 @Override
3103 public Map<String, ? extends BatteryStats.Uid.Proc> getProcessStats() {
3104 return mProcessStats;
3105 }
3106
3107 @Override
3108 public Map<String, ? extends BatteryStats.Uid.Pkg> getPackageStats() {
3109 return mPackageStats;
3110 }
Amith Yamasanieaeb6632009-06-03 15:16:10 -07003111
3112 @Override
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003113 public int getUid() {
3114 return mUid;
3115 }
Amith Yamasanieaeb6632009-06-03 15:16:10 -07003116
3117 @Override
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003118 public void noteWifiRunningLocked() {
3119 if (!mWifiRunning) {
3120 mWifiRunning = true;
3121 if (mWifiRunningTimer == null) {
3122 mWifiRunningTimer = new StopwatchTimer(Uid.this, WIFI_RUNNING,
3123 mWifiRunningTimers, mUnpluggables);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003124 }
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003125 mWifiRunningTimer.startRunningLocked(BatteryStatsImpl.this);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003126 }
3127 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003128
Dianne Hackborn617f8772009-03-31 15:04:46 -07003129 @Override
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003130 public void noteWifiStoppedLocked() {
3131 if (mWifiRunning) {
3132 mWifiRunning = false;
3133 mWifiRunningTimer.stopRunningLocked(BatteryStatsImpl.this);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003134 }
3135 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003136
Dianne Hackborn617f8772009-03-31 15:04:46 -07003137 @Override
The Android Open Source Project10592532009-03-18 17:39:46 -07003138 public void noteFullWifiLockAcquiredLocked() {
3139 if (!mFullWifiLockOut) {
3140 mFullWifiLockOut = true;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003141 if (mFullWifiLockTimer == null) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003142 mFullWifiLockTimer = new StopwatchTimer(Uid.this, FULL_WIFI_LOCK,
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003143 mFullWifiLockTimers, mUnpluggables);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003144 }
The Android Open Source Project10592532009-03-18 17:39:46 -07003145 mFullWifiLockTimer.startRunningLocked(BatteryStatsImpl.this);
3146 }
3147 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003148
The Android Open Source Project10592532009-03-18 17:39:46 -07003149 @Override
3150 public void noteFullWifiLockReleasedLocked() {
3151 if (mFullWifiLockOut) {
3152 mFullWifiLockOut = false;
3153 mFullWifiLockTimer.stopRunningLocked(BatteryStatsImpl.this);
3154 }
3155 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003156
The Android Open Source Project10592532009-03-18 17:39:46 -07003157 @Override
Nick Pelly6ccaa542012-06-15 15:22:47 -07003158 public void noteWifiScanStartedLocked() {
3159 if (!mWifiScanStarted) {
3160 mWifiScanStarted = true;
3161 if (mWifiScanTimer == null) {
3162 mWifiScanTimer = new StopwatchTimer(Uid.this, WIFI_SCAN,
3163 mWifiScanTimers, mUnpluggables);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003164 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07003165 mWifiScanTimer.startRunningLocked(BatteryStatsImpl.this);
The Android Open Source Project10592532009-03-18 17:39:46 -07003166 }
3167 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003168
The Android Open Source Project10592532009-03-18 17:39:46 -07003169 @Override
Nick Pelly6ccaa542012-06-15 15:22:47 -07003170 public void noteWifiScanStoppedLocked() {
3171 if (mWifiScanStarted) {
3172 mWifiScanStarted = false;
3173 mWifiScanTimer.stopRunningLocked(BatteryStatsImpl.this);
The Android Open Source Project10592532009-03-18 17:39:46 -07003174 }
3175 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003176
3177 @Override
Robert Greenwalta029ea12013-09-25 16:38:12 -07003178 public void noteWifiBatchedScanStartedLocked(int csph) {
3179 int bin = 0;
3180 while (csph > 8 && bin < NUM_WIFI_BATCHED_SCAN_BINS) {
3181 csph = csph >> 3;
3182 bin++;
3183 }
3184
3185 if (mWifiBatchedScanBinStarted == bin) return;
3186
3187 if (mWifiBatchedScanBinStarted != NO_BATCHED_SCAN_STARTED) {
3188 mWifiBatchedScanTimer[mWifiBatchedScanBinStarted].
3189 stopRunningLocked(BatteryStatsImpl.this);
3190 }
3191 mWifiBatchedScanBinStarted = bin;
3192 if (mWifiBatchedScanTimer[bin] == null) {
3193 makeWifiBatchedScanBin(bin, null);
3194 }
3195 mWifiBatchedScanTimer[bin].startRunningLocked(BatteryStatsImpl.this);
3196 }
3197
3198 @Override
3199 public void noteWifiBatchedScanStoppedLocked() {
3200 if (mWifiBatchedScanBinStarted != NO_BATCHED_SCAN_STARTED) {
3201 mWifiBatchedScanTimer[mWifiBatchedScanBinStarted].
3202 stopRunningLocked(BatteryStatsImpl.this);
3203 mWifiBatchedScanBinStarted = NO_BATCHED_SCAN_STARTED;
3204 }
3205 }
3206
3207 @Override
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003208 public void noteWifiMulticastEnabledLocked() {
3209 if (!mWifiMulticastEnabled) {
3210 mWifiMulticastEnabled = true;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003211 if (mWifiMulticastTimer == null) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003212 mWifiMulticastTimer = new StopwatchTimer(Uid.this, WIFI_MULTICAST_ENABLED,
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003213 mWifiMulticastTimers, mUnpluggables);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003214 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003215 mWifiMulticastTimer.startRunningLocked(BatteryStatsImpl.this);
3216 }
3217 }
3218
3219 @Override
3220 public void noteWifiMulticastDisabledLocked() {
3221 if (mWifiMulticastEnabled) {
3222 mWifiMulticastEnabled = false;
3223 mWifiMulticastTimer.stopRunningLocked(BatteryStatsImpl.this);
3224 }
3225 }
3226
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003227 public StopwatchTimer createAudioTurnedOnTimerLocked() {
3228 if (mAudioTurnedOnTimer == null) {
3229 mAudioTurnedOnTimer = new StopwatchTimer(Uid.this, AUDIO_TURNED_ON,
3230 null, mUnpluggables);
3231 }
3232 return mAudioTurnedOnTimer;
3233 }
3234
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003235 @Override
3236 public void noteAudioTurnedOnLocked() {
3237 if (!mAudioTurnedOn) {
3238 mAudioTurnedOn = true;
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003239 createAudioTurnedOnTimerLocked().startRunningLocked(BatteryStatsImpl.this);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003240 }
3241 }
3242
3243 @Override
3244 public void noteAudioTurnedOffLocked() {
3245 if (mAudioTurnedOn) {
3246 mAudioTurnedOn = false;
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003247 if (mAudioTurnedOnTimer != null) {
3248 mAudioTurnedOnTimer.stopRunningLocked(BatteryStatsImpl.this);
3249 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003250 }
3251 }
3252
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003253 public StopwatchTimer createVideoTurnedOnTimerLocked() {
3254 if (mVideoTurnedOnTimer == null) {
3255 mVideoTurnedOnTimer = new StopwatchTimer(Uid.this, VIDEO_TURNED_ON,
3256 null, mUnpluggables);
3257 }
3258 return mVideoTurnedOnTimer;
3259 }
3260
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003261 @Override
3262 public void noteVideoTurnedOnLocked() {
3263 if (!mVideoTurnedOn) {
3264 mVideoTurnedOn = true;
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003265 createVideoTurnedOnTimerLocked().startRunningLocked(BatteryStatsImpl.this);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003266 }
3267 }
3268
3269 @Override
3270 public void noteVideoTurnedOffLocked() {
3271 if (mVideoTurnedOn) {
3272 mVideoTurnedOn = false;
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003273 if (mVideoTurnedOnTimer != null) {
3274 mVideoTurnedOnTimer.stopRunningLocked(BatteryStatsImpl.this);
3275 }
3276 }
3277 }
3278
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003279 public StopwatchTimer createForegroundActivityTimerLocked() {
3280 if (mForegroundActivityTimer == null) {
3281 mForegroundActivityTimer = new StopwatchTimer(
3282 Uid.this, FOREGROUND_ACTIVITY, null, mUnpluggables);
3283 }
3284 return mForegroundActivityTimer;
3285 }
3286
3287 @Override
3288 public void noteActivityResumedLocked() {
3289 // We always start, since we want multiple foreground PIDs to nest
3290 createForegroundActivityTimerLocked().startRunningLocked(BatteryStatsImpl.this);
3291 }
3292
3293 @Override
3294 public void noteActivityPausedLocked() {
3295 if (mForegroundActivityTimer != null) {
3296 mForegroundActivityTimer.stopRunningLocked(BatteryStatsImpl.this);
3297 }
3298 }
3299
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003300 public BatchTimer createVibratorOnTimerLocked() {
3301 if (mVibratorOnTimer == null) {
3302 mVibratorOnTimer = new BatchTimer(Uid.this, VIBRATOR_ON,
3303 mUnpluggables, BatteryStatsImpl.this.mOnBatteryInternal);
3304 }
3305 return mVibratorOnTimer;
3306 }
3307
3308 public void noteVibratorOnLocked(long durationMillis) {
3309 createVibratorOnTimerLocked().addDuration(BatteryStatsImpl.this, durationMillis);
3310 }
3311
3312 public void noteVibratorOffLocked() {
3313 if (mVibratorOnTimer != null) {
3314 mVibratorOnTimer.abortLastDuration(BatteryStatsImpl.this);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003315 }
3316 }
3317
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003318 @Override
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003319 public long getWifiRunningTime(long batteryRealtime, int which) {
3320 if (mWifiRunningTimer == null) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003321 return 0;
3322 }
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003323 return mWifiRunningTimer.getTotalTimeLocked(batteryRealtime, which);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003324 }
Amith Yamasani244fa5c2009-05-22 14:36:07 -07003325
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003326 @Override
The Android Open Source Project10592532009-03-18 17:39:46 -07003327 public long getFullWifiLockTime(long batteryRealtime, int which) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003328 if (mFullWifiLockTimer == null) {
3329 return 0;
3330 }
Evan Millarc64edde2009-04-18 12:26:32 -07003331 return mFullWifiLockTimer.getTotalTimeLocked(batteryRealtime, which);
The Android Open Source Project10592532009-03-18 17:39:46 -07003332 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003333
3334 @Override
Nick Pelly6ccaa542012-06-15 15:22:47 -07003335 public long getWifiScanTime(long batteryRealtime, int which) {
3336 if (mWifiScanTimer == null) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003337 return 0;
3338 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07003339 return mWifiScanTimer.getTotalTimeLocked(batteryRealtime, which);
The Android Open Source Project10592532009-03-18 17:39:46 -07003340 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003341
3342 @Override
Robert Greenwalta029ea12013-09-25 16:38:12 -07003343 public long getWifiBatchedScanTime(int csphBin, long batteryRealtime, int which) {
3344 if (csphBin < 0 || csphBin >= NUM_WIFI_BATCHED_SCAN_BINS) return 0;
3345 if (mWifiBatchedScanTimer[csphBin] == null) {
3346 return 0;
3347 }
3348 return mWifiBatchedScanTimer[csphBin].getTotalTimeLocked(batteryRealtime, which);
3349 }
3350
3351 @Override
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003352 public long getWifiMulticastTime(long batteryRealtime, int which) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003353 if (mWifiMulticastTimer == null) {
3354 return 0;
3355 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07003356 return mWifiMulticastTimer.getTotalTimeLocked(batteryRealtime,
3357 which);
3358 }
3359
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003360 @Override
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003361 public long getAudioTurnedOnTime(long batteryRealtime, int which) {
3362 if (mAudioTurnedOnTimer == null) {
3363 return 0;
3364 }
3365 return mAudioTurnedOnTimer.getTotalTimeLocked(batteryRealtime, which);
3366 }
3367
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003368 @Override
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003369 public long getVideoTurnedOnTime(long batteryRealtime, int which) {
3370 if (mVideoTurnedOnTimer == null) {
3371 return 0;
3372 }
3373 return mVideoTurnedOnTimer.getTotalTimeLocked(batteryRealtime, which);
3374 }
3375
Dianne Hackborn617f8772009-03-31 15:04:46 -07003376 @Override
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003377 public Timer getForegroundActivityTimer() {
3378 return mForegroundActivityTimer;
3379 }
3380
3381 @Override
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003382 public Timer getVibratorOnTimer() {
3383 return mVibratorOnTimer;
3384 }
3385
3386 @Override
Dianne Hackborn617f8772009-03-31 15:04:46 -07003387 public void noteUserActivityLocked(int type) {
3388 if (mUserActivityCounters == null) {
3389 initUserActivityLocked();
3390 }
Jeff Browndf693de2012-07-27 12:03:38 -07003391 if (type >= 0 && type < NUM_USER_ACTIVITY_TYPES) {
3392 mUserActivityCounters[type].stepAtomic();
3393 } else {
3394 Slog.w(TAG, "Unknown user activity type " + type + " was specified.",
3395 new Throwable());
3396 }
Dianne Hackborn617f8772009-03-31 15:04:46 -07003397 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003398
Dianne Hackborn617f8772009-03-31 15:04:46 -07003399 @Override
3400 public boolean hasUserActivity() {
3401 return mUserActivityCounters != null;
3402 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003403
Dianne Hackborn617f8772009-03-31 15:04:46 -07003404 @Override
3405 public int getUserActivityCount(int type, int which) {
3406 if (mUserActivityCounters == null) {
3407 return 0;
3408 }
Evan Millarc64edde2009-04-18 12:26:32 -07003409 return mUserActivityCounters[type].getCountLocked(which);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003410 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003411
Robert Greenwalta029ea12013-09-25 16:38:12 -07003412 void makeWifiBatchedScanBin(int i, Parcel in) {
3413 if (i < 0 || i >= NUM_WIFI_BATCHED_SCAN_BINS) return;
3414
3415 ArrayList<StopwatchTimer> collected = mWifiBatchedScanTimers.get(i);
3416 if (collected == null) {
3417 collected = new ArrayList<StopwatchTimer>();
3418 mWifiBatchedScanTimers.put(i, collected);
3419 }
3420 if (in == null) {
3421 mWifiBatchedScanTimer[i] = new StopwatchTimer(this, WIFI_BATCHED_SCAN, collected,
3422 mUnpluggables);
3423 } else {
3424 mWifiBatchedScanTimer[i] = new StopwatchTimer(this, WIFI_BATCHED_SCAN, collected,
3425 mUnpluggables, in);
3426 }
3427 }
3428
3429
Dianne Hackborn617f8772009-03-31 15:04:46 -07003430 void initUserActivityLocked() {
3431 mUserActivityCounters = new Counter[NUM_USER_ACTIVITY_TYPES];
3432 for (int i=0; i<NUM_USER_ACTIVITY_TYPES; i++) {
3433 mUserActivityCounters[i] = new Counter(mUnpluggables);
3434 }
3435 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003436
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003437 void noteNetworkActivityLocked(int type, long deltaBytes, long deltaPackets) {
3438 if (mNetworkByteActivityCounters == null) {
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003439 initNetworkActivityLocked();
3440 }
3441 if (type >= 0 && type < NUM_NETWORK_ACTIVITY_TYPES) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003442 mNetworkByteActivityCounters[type].addCountLocked(deltaBytes);
3443 mNetworkPacketActivityCounters[type].addCountLocked(deltaPackets);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003444 } else {
3445 Slog.w(TAG, "Unknown network activity type " + type + " was specified.",
3446 new Throwable());
3447 }
3448 }
3449
3450 @Override
3451 public boolean hasNetworkActivity() {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003452 return mNetworkByteActivityCounters != null;
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003453 }
3454
3455 @Override
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003456 public long getNetworkActivityBytes(int type, int which) {
3457 if (mNetworkByteActivityCounters != null && type >= 0
3458 && type < mNetworkByteActivityCounters.length) {
3459 return mNetworkByteActivityCounters[type].getCountLocked(which);
3460 } else {
3461 return 0;
3462 }
3463 }
3464
3465 @Override
3466 public long getNetworkActivityPackets(int type, int which) {
3467 if (mNetworkPacketActivityCounters != null && type >= 0
3468 && type < mNetworkPacketActivityCounters.length) {
3469 return mNetworkPacketActivityCounters[type].getCountLocked(which);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003470 } else {
3471 return 0;
3472 }
3473 }
3474
3475 void initNetworkActivityLocked() {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003476 mNetworkByteActivityCounters = new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
3477 mNetworkPacketActivityCounters = new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003478 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003479 mNetworkByteActivityCounters[i] = new LongSamplingCounter(mUnpluggables);
3480 mNetworkPacketActivityCounters[i] = new LongSamplingCounter(mUnpluggables);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003481 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003482 }
Amith Yamasani244fa5c2009-05-22 14:36:07 -07003483
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003484 /**
3485 * Clear all stats for this uid. Returns true if the uid is completely
3486 * inactive so can be dropped.
3487 */
3488 boolean reset() {
3489 boolean active = false;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003490
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003491 if (mWifiRunningTimer != null) {
3492 active |= !mWifiRunningTimer.reset(BatteryStatsImpl.this, false);
3493 active |= mWifiRunning;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003494 }
3495 if (mFullWifiLockTimer != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003496 active |= !mFullWifiLockTimer.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003497 active |= mFullWifiLockOut;
3498 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07003499 if (mWifiScanTimer != null) {
3500 active |= !mWifiScanTimer.reset(BatteryStatsImpl.this, false);
3501 active |= mWifiScanStarted;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003502 }
Robert Greenwalta029ea12013-09-25 16:38:12 -07003503 if (mWifiBatchedScanTimer != null) {
3504 for (int i = 0; i < NUM_WIFI_BATCHED_SCAN_BINS; i++) {
3505 if (mWifiBatchedScanTimer[i] != null) {
3506 active |= !mWifiBatchedScanTimer[i].reset(BatteryStatsImpl.this, false);
3507 }
3508 }
3509 active |= (mWifiBatchedScanBinStarted != NO_BATCHED_SCAN_STARTED);
3510 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003511 if (mWifiMulticastTimer != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003512 active |= !mWifiMulticastTimer.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003513 active |= mWifiMulticastEnabled;
3514 }
3515 if (mAudioTurnedOnTimer != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003516 active |= !mAudioTurnedOnTimer.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003517 active |= mAudioTurnedOn;
3518 }
3519 if (mVideoTurnedOnTimer != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003520 active |= !mVideoTurnedOnTimer.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003521 active |= mVideoTurnedOn;
3522 }
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003523 if (mForegroundActivityTimer != null) {
3524 active |= !mForegroundActivityTimer.reset(BatteryStatsImpl.this, false);
3525 }
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003526 if (mVibratorOnTimer != null) {
3527 if (mVibratorOnTimer.reset(BatteryStatsImpl.this, false)) {
3528 mVibratorOnTimer.detach();
3529 mVibratorOnTimer = null;
3530 } else {
3531 active = true;
3532 }
3533 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003534
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003535 if (mUserActivityCounters != null) {
3536 for (int i=0; i<NUM_USER_ACTIVITY_TYPES; i++) {
3537 mUserActivityCounters[i].reset(false);
3538 }
3539 }
3540
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003541 if (mNetworkByteActivityCounters != null) {
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003542 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003543 mNetworkByteActivityCounters[i].reset(false);
3544 mNetworkPacketActivityCounters[i].reset(false);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003545 }
3546 }
3547
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003548 if (mWakelockStats.size() > 0) {
3549 Iterator<Map.Entry<String, Wakelock>> it = mWakelockStats.entrySet().iterator();
3550 while (it.hasNext()) {
3551 Map.Entry<String, Wakelock> wakelockEntry = it.next();
3552 Wakelock wl = wakelockEntry.getValue();
3553 if (wl.reset()) {
3554 it.remove();
3555 } else {
3556 active = true;
3557 }
3558 }
3559 }
3560 if (mSensorStats.size() > 0) {
3561 Iterator<Map.Entry<Integer, Sensor>> it = mSensorStats.entrySet().iterator();
3562 while (it.hasNext()) {
3563 Map.Entry<Integer, Sensor> sensorEntry = it.next();
3564 Sensor s = sensorEntry.getValue();
3565 if (s.reset()) {
3566 it.remove();
3567 } else {
3568 active = true;
3569 }
3570 }
3571 }
3572 if (mProcessStats.size() > 0) {
3573 Iterator<Map.Entry<String, Proc>> it = mProcessStats.entrySet().iterator();
3574 while (it.hasNext()) {
3575 Map.Entry<String, Proc> procEntry = it.next();
3576 procEntry.getValue().detach();
3577 }
3578 mProcessStats.clear();
3579 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003580 if (mPids.size() > 0) {
3581 for (int i=0; !active && i<mPids.size(); i++) {
3582 Pid pid = mPids.valueAt(i);
3583 if (pid.mWakeStart != 0) {
3584 active = true;
3585 }
3586 }
3587 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003588 if (mPackageStats.size() > 0) {
3589 Iterator<Map.Entry<String, Pkg>> it = mPackageStats.entrySet().iterator();
3590 while (it.hasNext()) {
3591 Map.Entry<String, Pkg> pkgEntry = it.next();
3592 Pkg p = pkgEntry.getValue();
3593 p.detach();
3594 if (p.mServiceStats.size() > 0) {
3595 Iterator<Map.Entry<String, Pkg.Serv>> it2
3596 = p.mServiceStats.entrySet().iterator();
3597 while (it2.hasNext()) {
3598 Map.Entry<String, Pkg.Serv> servEntry = it2.next();
3599 servEntry.getValue().detach();
3600 }
3601 }
3602 }
3603 mPackageStats.clear();
3604 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003605
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003606 mPids.clear();
3607
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003608 if (!active) {
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003609 if (mWifiRunningTimer != null) {
3610 mWifiRunningTimer.detach();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003611 }
3612 if (mFullWifiLockTimer != null) {
3613 mFullWifiLockTimer.detach();
3614 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07003615 if (mWifiScanTimer != null) {
3616 mWifiScanTimer.detach();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003617 }
Robert Greenwalta029ea12013-09-25 16:38:12 -07003618 for (int i = 0; i < NUM_WIFI_BATCHED_SCAN_BINS; i++) {
3619 if (mWifiBatchedScanTimer[i] != null) {
3620 mWifiBatchedScanTimer[i].detach();
3621 }
3622 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003623 if (mWifiMulticastTimer != null) {
3624 mWifiMulticastTimer.detach();
3625 }
3626 if (mAudioTurnedOnTimer != null) {
3627 mAudioTurnedOnTimer.detach();
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003628 mAudioTurnedOnTimer = null;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003629 }
3630 if (mVideoTurnedOnTimer != null) {
3631 mVideoTurnedOnTimer.detach();
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003632 mVideoTurnedOnTimer = null;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003633 }
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003634 if (mForegroundActivityTimer != null) {
3635 mForegroundActivityTimer.detach();
3636 mForegroundActivityTimer = null;
3637 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003638 if (mUserActivityCounters != null) {
3639 for (int i=0; i<NUM_USER_ACTIVITY_TYPES; i++) {
3640 mUserActivityCounters[i].detach();
3641 }
3642 }
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003643 if (mNetworkByteActivityCounters != null) {
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003644 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003645 mNetworkByteActivityCounters[i].detach();
3646 mNetworkPacketActivityCounters[i].detach();
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003647 }
3648 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003649 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003650
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003651 return !active;
3652 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003653
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003654 void writeToParcelLocked(Parcel out, long batteryRealtime) {
3655 out.writeInt(mWakelockStats.size());
3656 for (Map.Entry<String, Uid.Wakelock> wakelockEntry : mWakelockStats.entrySet()) {
3657 out.writeString(wakelockEntry.getKey());
3658 Uid.Wakelock wakelock = wakelockEntry.getValue();
3659 wakelock.writeToParcelLocked(out, batteryRealtime);
3660 }
3661
3662 out.writeInt(mSensorStats.size());
3663 for (Map.Entry<Integer, Uid.Sensor> sensorEntry : mSensorStats.entrySet()) {
3664 out.writeInt(sensorEntry.getKey());
3665 Uid.Sensor sensor = sensorEntry.getValue();
3666 sensor.writeToParcelLocked(out, batteryRealtime);
3667 }
3668
3669 out.writeInt(mProcessStats.size());
3670 for (Map.Entry<String, Uid.Proc> procEntry : mProcessStats.entrySet()) {
3671 out.writeString(procEntry.getKey());
3672 Uid.Proc proc = procEntry.getValue();
3673 proc.writeToParcelLocked(out);
3674 }
3675
3676 out.writeInt(mPackageStats.size());
3677 for (Map.Entry<String, Uid.Pkg> pkgEntry : mPackageStats.entrySet()) {
3678 out.writeString(pkgEntry.getKey());
3679 Uid.Pkg pkg = pkgEntry.getValue();
3680 pkg.writeToParcelLocked(out);
3681 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003682
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003683 if (mWifiRunningTimer != null) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003684 out.writeInt(1);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003685 mWifiRunningTimer.writeToParcel(out, batteryRealtime);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003686 } else {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003687 out.writeInt(0);
3688 }
3689 if (mFullWifiLockTimer != null) {
3690 out.writeInt(1);
3691 mFullWifiLockTimer.writeToParcel(out, batteryRealtime);
3692 } else {
3693 out.writeInt(0);
3694 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07003695 if (mWifiScanTimer != null) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003696 out.writeInt(1);
Nick Pelly6ccaa542012-06-15 15:22:47 -07003697 mWifiScanTimer.writeToParcel(out, batteryRealtime);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003698 } else {
3699 out.writeInt(0);
3700 }
Robert Greenwalta029ea12013-09-25 16:38:12 -07003701 for (int i = 0; i < NUM_WIFI_BATCHED_SCAN_BINS; i++) {
3702 if (mWifiBatchedScanTimer[i] != null) {
3703 out.writeInt(1);
3704 mWifiBatchedScanTimer[i].writeToParcel(out, batteryRealtime);
3705 } else {
3706 out.writeInt(0);
3707 }
3708 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003709 if (mWifiMulticastTimer != null) {
3710 out.writeInt(1);
3711 mWifiMulticastTimer.writeToParcel(out, batteryRealtime);
3712 } else {
3713 out.writeInt(0);
3714 }
3715 if (mAudioTurnedOnTimer != null) {
3716 out.writeInt(1);
3717 mAudioTurnedOnTimer.writeToParcel(out, batteryRealtime);
3718 } else {
3719 out.writeInt(0);
3720 }
3721 if (mVideoTurnedOnTimer != null) {
3722 out.writeInt(1);
3723 mVideoTurnedOnTimer.writeToParcel(out, batteryRealtime);
3724 } else {
3725 out.writeInt(0);
3726 }
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003727 if (mForegroundActivityTimer != null) {
3728 out.writeInt(1);
3729 mForegroundActivityTimer.writeToParcel(out, batteryRealtime);
3730 } else {
3731 out.writeInt(0);
3732 }
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003733 if (mVibratorOnTimer != null) {
3734 out.writeInt(1);
3735 mVibratorOnTimer.writeToParcel(out, batteryRealtime);
3736 } else {
3737 out.writeInt(0);
3738 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003739 if (mUserActivityCounters != null) {
Dianne Hackborn617f8772009-03-31 15:04:46 -07003740 out.writeInt(1);
3741 for (int i=0; i<NUM_USER_ACTIVITY_TYPES; i++) {
3742 mUserActivityCounters[i].writeToParcel(out);
3743 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003744 } else {
3745 out.writeInt(0);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003746 }
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003747 if (mNetworkByteActivityCounters != null) {
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003748 out.writeInt(1);
3749 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003750 mNetworkByteActivityCounters[i].writeToParcel(out);
3751 mNetworkPacketActivityCounters[i].writeToParcel(out);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003752 }
3753 } else {
3754 out.writeInt(0);
3755 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003756 }
3757
3758 void readFromParcelLocked(ArrayList<Unpluggable> unpluggables, Parcel in) {
3759 int numWakelocks = in.readInt();
3760 mWakelockStats.clear();
3761 for (int j = 0; j < numWakelocks; j++) {
3762 String wakelockName = in.readString();
3763 Uid.Wakelock wakelock = new Wakelock();
3764 wakelock.readFromParcelLocked(unpluggables, in);
Dianne Hackbornc24ab862011-10-18 15:55:03 -07003765 // We will just drop some random set of wakelocks if
3766 // the previous run of the system was an older version
3767 // that didn't impose a limit.
3768 mWakelockStats.put(wakelockName, wakelock);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003769 }
3770
3771 int numSensors = in.readInt();
3772 mSensorStats.clear();
3773 for (int k = 0; k < numSensors; k++) {
3774 int sensorNumber = in.readInt();
3775 Uid.Sensor sensor = new Sensor(sensorNumber);
3776 sensor.readFromParcelLocked(mUnpluggables, in);
3777 mSensorStats.put(sensorNumber, sensor);
3778 }
3779
3780 int numProcs = in.readInt();
3781 mProcessStats.clear();
3782 for (int k = 0; k < numProcs; k++) {
3783 String processName = in.readString();
3784 Uid.Proc proc = new Proc();
3785 proc.readFromParcelLocked(in);
3786 mProcessStats.put(processName, proc);
3787 }
3788
3789 int numPkgs = in.readInt();
3790 mPackageStats.clear();
3791 for (int l = 0; l < numPkgs; l++) {
3792 String packageName = in.readString();
3793 Uid.Pkg pkg = new Pkg();
3794 pkg.readFromParcelLocked(in);
3795 mPackageStats.put(packageName, pkg);
3796 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003797
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003798 mWifiRunning = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003799 if (in.readInt() != 0) {
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003800 mWifiRunningTimer = new StopwatchTimer(Uid.this, WIFI_RUNNING,
3801 mWifiRunningTimers, mUnpluggables, in);
Dianne Hackborn617f8772009-03-31 15:04:46 -07003802 } else {
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003803 mWifiRunningTimer = null;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003804 }
3805 mFullWifiLockOut = false;
3806 if (in.readInt() != 0) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003807 mFullWifiLockTimer = new StopwatchTimer(Uid.this, FULL_WIFI_LOCK,
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003808 mFullWifiLockTimers, mUnpluggables, in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003809 } else {
3810 mFullWifiLockTimer = null;
3811 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07003812 mWifiScanStarted = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003813 if (in.readInt() != 0) {
Nick Pelly6ccaa542012-06-15 15:22:47 -07003814 mWifiScanTimer = new StopwatchTimer(Uid.this, WIFI_SCAN,
3815 mWifiScanTimers, mUnpluggables, in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003816 } else {
Nick Pelly6ccaa542012-06-15 15:22:47 -07003817 mWifiScanTimer = null;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003818 }
Robert Greenwalta029ea12013-09-25 16:38:12 -07003819 mWifiBatchedScanBinStarted = NO_BATCHED_SCAN_STARTED;
3820 for (int i = 0; i < NUM_WIFI_BATCHED_SCAN_BINS; i++) {
3821 if (in.readInt() != 0) {
3822 makeWifiBatchedScanBin(i, in);
3823 } else {
3824 mWifiBatchedScanTimer[i] = null;
3825 }
3826 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003827 mWifiMulticastEnabled = false;
3828 if (in.readInt() != 0) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003829 mWifiMulticastTimer = new StopwatchTimer(Uid.this, WIFI_MULTICAST_ENABLED,
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07003830 mWifiMulticastTimers, mUnpluggables, in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003831 } else {
3832 mWifiMulticastTimer = null;
3833 }
3834 mAudioTurnedOn = false;
3835 if (in.readInt() != 0) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003836 mAudioTurnedOnTimer = new StopwatchTimer(Uid.this, AUDIO_TURNED_ON,
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003837 null, mUnpluggables, in);
3838 } else {
3839 mAudioTurnedOnTimer = null;
3840 }
3841 mVideoTurnedOn = false;
3842 if (in.readInt() != 0) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003843 mVideoTurnedOnTimer = new StopwatchTimer(Uid.this, VIDEO_TURNED_ON,
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003844 null, mUnpluggables, in);
3845 } else {
3846 mVideoTurnedOnTimer = null;
3847 }
3848 if (in.readInt() != 0) {
Jeff Sharkey3e013e82013-04-25 14:48:19 -07003849 mForegroundActivityTimer = new StopwatchTimer(
3850 Uid.this, FOREGROUND_ACTIVITY, null, mUnpluggables, in);
3851 } else {
3852 mForegroundActivityTimer = null;
3853 }
3854 if (in.readInt() != 0) {
Dianne Hackborna06de0f2012-12-11 16:34:47 -08003855 mVibratorOnTimer = new BatchTimer(Uid.this, VIBRATOR_ON,
3856 mUnpluggables, BatteryStatsImpl.this.mOnBatteryInternal, in);
3857 } else {
3858 mVibratorOnTimer = null;
3859 }
3860 if (in.readInt() != 0) {
Dianne Hackborn617f8772009-03-31 15:04:46 -07003861 mUserActivityCounters = new Counter[NUM_USER_ACTIVITY_TYPES];
3862 for (int i=0; i<NUM_USER_ACTIVITY_TYPES; i++) {
3863 mUserActivityCounters[i] = new Counter(mUnpluggables, in);
3864 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003865 } else {
3866 mUserActivityCounters = null;
Dianne Hackborn617f8772009-03-31 15:04:46 -07003867 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003868 if (in.readInt() != 0) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003869 mNetworkByteActivityCounters = new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
3870 mNetworkPacketActivityCounters
3871 = new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003872 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003873 mNetworkByteActivityCounters[i] = new LongSamplingCounter(mUnpluggables, in);
3874 mNetworkPacketActivityCounters[i] = new LongSamplingCounter(mUnpluggables, in);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003875 }
3876 } else {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08003877 mNetworkByteActivityCounters = null;
3878 mNetworkPacketActivityCounters = null;
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07003879 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003880 }
3881
3882 /**
3883 * The statistics associated with a particular wake lock.
3884 */
3885 public final class Wakelock extends BatteryStats.Uid.Wakelock {
3886 /**
3887 * How long (in ms) this uid has been keeping the device partially awake.
3888 */
Evan Millarc64edde2009-04-18 12:26:32 -07003889 StopwatchTimer mTimerPartial;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003890
3891 /**
3892 * How long (in ms) this uid has been keeping the device fully awake.
3893 */
Evan Millarc64edde2009-04-18 12:26:32 -07003894 StopwatchTimer mTimerFull;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003895
3896 /**
3897 * How long (in ms) this uid has had a window keeping the device awake.
3898 */
Evan Millarc64edde2009-04-18 12:26:32 -07003899 StopwatchTimer mTimerWindow;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003900
3901 /**
3902 * Reads a possibly null Timer from a Parcel. The timer is associated with the
3903 * proper timer pool from the given BatteryStatsImpl object.
3904 *
3905 * @param in the Parcel to be read from.
3906 * return a new Timer, or null.
3907 */
Evan Millarc64edde2009-04-18 12:26:32 -07003908 private StopwatchTimer readTimerFromParcel(int type, ArrayList<StopwatchTimer> pool,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003909 ArrayList<Unpluggable> unpluggables, Parcel in) {
3910 if (in.readInt() == 0) {
3911 return null;
3912 }
3913
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003914 return new StopwatchTimer(Uid.this, type, pool, unpluggables, in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003915 }
3916
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003917 boolean reset() {
3918 boolean wlactive = false;
3919 if (mTimerFull != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003920 wlactive |= !mTimerFull.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003921 }
3922 if (mTimerPartial != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003923 wlactive |= !mTimerPartial.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003924 }
3925 if (mTimerWindow != null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003926 wlactive |= !mTimerWindow.reset(BatteryStatsImpl.this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003927 }
3928 if (!wlactive) {
3929 if (mTimerFull != null) {
3930 mTimerFull.detach();
3931 mTimerFull = null;
3932 }
3933 if (mTimerPartial != null) {
3934 mTimerPartial.detach();
3935 mTimerPartial = null;
3936 }
3937 if (mTimerWindow != null) {
3938 mTimerWindow.detach();
3939 mTimerWindow = null;
3940 }
3941 }
3942 return !wlactive;
3943 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003944
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003945 void readFromParcelLocked(ArrayList<Unpluggable> unpluggables, Parcel in) {
3946 mTimerPartial = readTimerFromParcel(WAKE_TYPE_PARTIAL,
3947 mPartialTimers, unpluggables, in);
3948 mTimerFull = readTimerFromParcel(WAKE_TYPE_FULL,
3949 mFullTimers, unpluggables, in);
3950 mTimerWindow = readTimerFromParcel(WAKE_TYPE_WINDOW,
3951 mWindowTimers, unpluggables, in);
3952 }
3953
3954 void writeToParcelLocked(Parcel out, long batteryRealtime) {
3955 Timer.writeTimerToParcel(out, mTimerPartial, batteryRealtime);
3956 Timer.writeTimerToParcel(out, mTimerFull, batteryRealtime);
3957 Timer.writeTimerToParcel(out, mTimerWindow, batteryRealtime);
3958 }
3959
3960 @Override
3961 public Timer getWakeTime(int type) {
3962 switch (type) {
3963 case WAKE_TYPE_FULL: return mTimerFull;
3964 case WAKE_TYPE_PARTIAL: return mTimerPartial;
3965 case WAKE_TYPE_WINDOW: return mTimerWindow;
3966 default: throw new IllegalArgumentException("type = " + type);
3967 }
3968 }
3969 }
3970
3971 public final class Sensor extends BatteryStats.Uid.Sensor {
3972 final int mHandle;
Evan Millarc64edde2009-04-18 12:26:32 -07003973 StopwatchTimer mTimer;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07003974
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003975 public Sensor(int handle) {
3976 mHandle = handle;
3977 }
3978
Evan Millarc64edde2009-04-18 12:26:32 -07003979 private StopwatchTimer readTimerFromParcel(ArrayList<Unpluggable> unpluggables,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003980 Parcel in) {
3981 if (in.readInt() == 0) {
3982 return null;
3983 }
3984
Evan Millarc64edde2009-04-18 12:26:32 -07003985 ArrayList<StopwatchTimer> pool = mSensorTimers.get(mHandle);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003986 if (pool == null) {
Evan Millarc64edde2009-04-18 12:26:32 -07003987 pool = new ArrayList<StopwatchTimer>();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003988 mSensorTimers.put(mHandle, pool);
3989 }
Dianne Hackborn0d903a82010-09-07 23:51:03 -07003990 return new StopwatchTimer(Uid.this, 0, pool, unpluggables, in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08003991 }
3992
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003993 boolean reset() {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07003994 if (mTimer.reset(BatteryStatsImpl.this, true)) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07003995 mTimer = null;
3996 return true;
3997 }
3998 return false;
3999 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004000
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004001 void readFromParcelLocked(ArrayList<Unpluggable> unpluggables, Parcel in) {
4002 mTimer = readTimerFromParcel(unpluggables, in);
4003 }
4004
4005 void writeToParcelLocked(Parcel out, long batteryRealtime) {
4006 Timer.writeTimerToParcel(out, mTimer, batteryRealtime);
4007 }
4008
4009 @Override
4010 public Timer getSensorTime() {
4011 return mTimer;
4012 }
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004013
4014 @Override
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004015 public int getHandle() {
4016 return mHandle;
4017 }
4018 }
4019
4020 /**
4021 * The statistics associated with a particular process.
4022 */
4023 public final class Proc extends BatteryStats.Uid.Proc implements Unpluggable {
4024 /**
Dianne Hackborn099bc622014-01-22 13:39:16 -08004025 * Remains true until removed from the stats.
4026 */
4027 boolean mActive = true;
4028
4029 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004030 * Total time (in 1/100 sec) spent executing in user code.
4031 */
4032 long mUserTime;
4033
4034 /**
4035 * Total time (in 1/100 sec) spent executing in kernel code.
4036 */
4037 long mSystemTime;
4038
4039 /**
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004040 * Amount of time the process was running in the foreground.
4041 */
4042 long mForegroundTime;
4043
4044 /**
Jeff Sharkey3e013e82013-04-25 14:48:19 -07004045 * Number of times the process has been started.
4046 */
4047 int mStarts;
4048
4049 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004050 * The amount of user time loaded from a previous save.
4051 */
4052 long mLoadedUserTime;
4053
4054 /**
4055 * The amount of system time loaded from a previous save.
4056 */
4057 long mLoadedSystemTime;
4058
4059 /**
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004060 * The amount of foreground time loaded from a previous save.
4061 */
4062 long mLoadedForegroundTime;
4063
4064 /**
Jeff Sharkey3e013e82013-04-25 14:48:19 -07004065 * The number of times the process has started from a previous save.
4066 */
4067 int mLoadedStarts;
4068
4069 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004070 * The amount of user time loaded from the previous run.
4071 */
4072 long mLastUserTime;
4073
4074 /**
4075 * The amount of system time loaded from the previous run.
4076 */
4077 long mLastSystemTime;
4078
4079 /**
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004080 * The amount of foreground time loaded from the previous run
4081 */
4082 long mLastForegroundTime;
4083
4084 /**
Jeff Sharkey3e013e82013-04-25 14:48:19 -07004085 * The number of times the process has started from the previous run.
4086 */
4087 int mLastStarts;
4088
4089 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004090 * The amount of user time when last unplugged.
4091 */
4092 long mUnpluggedUserTime;
4093
4094 /**
4095 * The amount of system time when last unplugged.
4096 */
4097 long mUnpluggedSystemTime;
4098
4099 /**
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004100 * The amount of foreground time since unplugged.
4101 */
4102 long mUnpluggedForegroundTime;
4103
Jeff Sharkey3e013e82013-04-25 14:48:19 -07004104 /**
4105 * The number of times the process has started before unplugged.
4106 */
4107 int mUnpluggedStarts;
4108
Amith Yamasanie43530a2009-08-21 13:11:37 -07004109 SamplingCounter[] mSpeedBins;
4110
Dianne Hackborn287952c2010-09-22 22:34:31 -07004111 ArrayList<ExcessivePower> mExcessivePower;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004112
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004113 Proc() {
4114 mUnpluggables.add(this);
Amith Yamasanie43530a2009-08-21 13:11:37 -07004115 mSpeedBins = new SamplingCounter[getCpuSpeedSteps()];
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004116 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07004117
Dianne Hackborna06de0f2012-12-11 16:34:47 -08004118 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004119 mUnpluggedUserTime = mUserTime;
4120 mUnpluggedSystemTime = mSystemTime;
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004121 mUnpluggedForegroundTime = mForegroundTime;
Jeff Sharkey3e013e82013-04-25 14:48:19 -07004122 mUnpluggedStarts = mStarts;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004123 }
4124
Dianne Hackborna06de0f2012-12-11 16:34:47 -08004125 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004126 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004127
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004128 void detach() {
Dianne Hackborn099bc622014-01-22 13:39:16 -08004129 mActive = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004130 mUnpluggables.remove(this);
4131 for (int i = 0; i < mSpeedBins.length; i++) {
4132 SamplingCounter c = mSpeedBins[i];
4133 if (c != null) {
4134 mUnpluggables.remove(c);
4135 mSpeedBins[i] = null;
4136 }
4137 }
4138 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004139
Dianne Hackborn287952c2010-09-22 22:34:31 -07004140 public int countExcessivePowers() {
4141 return mExcessivePower != null ? mExcessivePower.size() : 0;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004142 }
4143
Dianne Hackborn287952c2010-09-22 22:34:31 -07004144 public ExcessivePower getExcessivePower(int i) {
4145 if (mExcessivePower != null) {
4146 return mExcessivePower.get(i);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004147 }
4148 return null;
4149 }
4150
4151 public void addExcessiveWake(long overTime, long usedTime) {
Dianne Hackborn287952c2010-09-22 22:34:31 -07004152 if (mExcessivePower == null) {
4153 mExcessivePower = new ArrayList<ExcessivePower>();
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004154 }
Dianne Hackborn287952c2010-09-22 22:34:31 -07004155 ExcessivePower ew = new ExcessivePower();
4156 ew.type = ExcessivePower.TYPE_WAKE;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004157 ew.overTime = overTime;
4158 ew.usedTime = usedTime;
Dianne Hackborn287952c2010-09-22 22:34:31 -07004159 mExcessivePower.add(ew);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004160 }
4161
Dianne Hackborn287952c2010-09-22 22:34:31 -07004162 public void addExcessiveCpu(long overTime, long usedTime) {
4163 if (mExcessivePower == null) {
4164 mExcessivePower = new ArrayList<ExcessivePower>();
4165 }
4166 ExcessivePower ew = new ExcessivePower();
4167 ew.type = ExcessivePower.TYPE_CPU;
4168 ew.overTime = overTime;
4169 ew.usedTime = usedTime;
4170 mExcessivePower.add(ew);
4171 }
4172
4173 void writeExcessivePowerToParcelLocked(Parcel out) {
4174 if (mExcessivePower == null) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004175 out.writeInt(0);
4176 return;
4177 }
4178
Dianne Hackborn287952c2010-09-22 22:34:31 -07004179 final int N = mExcessivePower.size();
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004180 out.writeInt(N);
4181 for (int i=0; i<N; i++) {
Dianne Hackborn287952c2010-09-22 22:34:31 -07004182 ExcessivePower ew = mExcessivePower.get(i);
4183 out.writeInt(ew.type);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004184 out.writeLong(ew.overTime);
4185 out.writeLong(ew.usedTime);
4186 }
4187 }
4188
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08004189 boolean readExcessivePowerFromParcelLocked(Parcel in) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004190 final int N = in.readInt();
4191 if (N == 0) {
Dianne Hackborn287952c2010-09-22 22:34:31 -07004192 mExcessivePower = null;
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08004193 return true;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004194 }
4195
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08004196 if (N > 10000) {
4197 Slog.w(TAG, "File corrupt: too many excessive power entries " + N);
4198 return false;
4199 }
4200
Dianne Hackborn287952c2010-09-22 22:34:31 -07004201 mExcessivePower = new ArrayList<ExcessivePower>();
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004202 for (int i=0; i<N; i++) {
Dianne Hackborn287952c2010-09-22 22:34:31 -07004203 ExcessivePower ew = new ExcessivePower();
4204 ew.type = in.readInt();
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004205 ew.overTime = in.readLong();
4206 ew.usedTime = in.readLong();
Dianne Hackborn287952c2010-09-22 22:34:31 -07004207 mExcessivePower.add(ew);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004208 }
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08004209 return true;
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004210 }
4211
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004212 void writeToParcelLocked(Parcel out) {
4213 out.writeLong(mUserTime);
4214 out.writeLong(mSystemTime);
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004215 out.writeLong(mForegroundTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004216 out.writeInt(mStarts);
4217 out.writeLong(mLoadedUserTime);
4218 out.writeLong(mLoadedSystemTime);
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004219 out.writeLong(mLoadedForegroundTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004220 out.writeInt(mLoadedStarts);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004221 out.writeLong(mUnpluggedUserTime);
4222 out.writeLong(mUnpluggedSystemTime);
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004223 out.writeLong(mUnpluggedForegroundTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004224 out.writeInt(mUnpluggedStarts);
Amith Yamasanie43530a2009-08-21 13:11:37 -07004225
4226 out.writeInt(mSpeedBins.length);
4227 for (int i = 0; i < mSpeedBins.length; i++) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004228 SamplingCounter c = mSpeedBins[i];
4229 if (c != null) {
4230 out.writeInt(1);
4231 c.writeToParcel(out);
4232 } else {
4233 out.writeInt(0);
4234 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07004235 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004236
Dianne Hackborn287952c2010-09-22 22:34:31 -07004237 writeExcessivePowerToParcelLocked(out);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004238 }
4239
4240 void readFromParcelLocked(Parcel in) {
4241 mUserTime = in.readLong();
4242 mSystemTime = in.readLong();
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004243 mForegroundTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004244 mStarts = in.readInt();
4245 mLoadedUserTime = in.readLong();
4246 mLoadedSystemTime = in.readLong();
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004247 mLoadedForegroundTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004248 mLoadedStarts = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07004249 mLastUserTime = 0;
4250 mLastSystemTime = 0;
4251 mLastForegroundTime = 0;
4252 mLastStarts = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004253 mUnpluggedUserTime = in.readLong();
4254 mUnpluggedSystemTime = in.readLong();
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004255 mUnpluggedForegroundTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004256 mUnpluggedStarts = in.readInt();
Amith Yamasanie43530a2009-08-21 13:11:37 -07004257
4258 int bins = in.readInt();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004259 int steps = getCpuSpeedSteps();
4260 mSpeedBins = new SamplingCounter[bins >= steps ? bins : steps];
Amith Yamasanie43530a2009-08-21 13:11:37 -07004261 for (int i = 0; i < bins; i++) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004262 if (in.readInt() != 0) {
4263 mSpeedBins[i] = new SamplingCounter(mUnpluggables, in);
4264 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07004265 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004266
Dianne Hackborn287952c2010-09-22 22:34:31 -07004267 readExcessivePowerFromParcelLocked(in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004268 }
4269
4270 public BatteryStatsImpl getBatteryStats() {
4271 return BatteryStatsImpl.this;
4272 }
4273
4274 public void addCpuTimeLocked(int utime, int stime) {
4275 mUserTime += utime;
4276 mSystemTime += stime;
4277 }
4278
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004279 public void addForegroundTimeLocked(long ttime) {
4280 mForegroundTime += ttime;
4281 }
4282
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004283 public void incStartsLocked() {
4284 mStarts++;
4285 }
4286
4287 @Override
Dianne Hackborn099bc622014-01-22 13:39:16 -08004288 public boolean isActive() {
4289 return mActive;
4290 }
4291
4292 @Override
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004293 public long getUserTime(int which) {
4294 long val;
4295 if (which == STATS_LAST) {
4296 val = mLastUserTime;
4297 } else {
4298 val = mUserTime;
4299 if (which == STATS_CURRENT) {
4300 val -= mLoadedUserTime;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004301 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004302 val -= mUnpluggedUserTime;
4303 }
4304 }
4305 return val;
4306 }
4307
4308 @Override
4309 public long getSystemTime(int which) {
4310 long val;
4311 if (which == STATS_LAST) {
4312 val = mLastSystemTime;
4313 } else {
4314 val = mSystemTime;
4315 if (which == STATS_CURRENT) {
4316 val -= mLoadedSystemTime;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004317 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004318 val -= mUnpluggedSystemTime;
4319 }
4320 }
4321 return val;
4322 }
4323
4324 @Override
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004325 public long getForegroundTime(int which) {
4326 long val;
4327 if (which == STATS_LAST) {
4328 val = mLastForegroundTime;
4329 } else {
4330 val = mForegroundTime;
4331 if (which == STATS_CURRENT) {
4332 val -= mLoadedForegroundTime;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004333 } else if (which == STATS_SINCE_UNPLUGGED) {
Amith Yamasanieaeb6632009-06-03 15:16:10 -07004334 val -= mUnpluggedForegroundTime;
4335 }
4336 }
4337 return val;
4338 }
4339
4340 @Override
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004341 public int getStarts(int which) {
4342 int val;
4343 if (which == STATS_LAST) {
4344 val = mLastStarts;
4345 } else {
4346 val = mStarts;
4347 if (which == STATS_CURRENT) {
4348 val -= mLoadedStarts;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004349 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004350 val -= mUnpluggedStarts;
4351 }
4352 }
4353 return val;
4354 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07004355
4356 /* Called by ActivityManagerService when CPU times are updated. */
4357 public void addSpeedStepTimes(long[] values) {
4358 for (int i = 0; i < mSpeedBins.length && i < values.length; i++) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004359 long amt = values[i];
4360 if (amt != 0) {
4361 SamplingCounter c = mSpeedBins[i];
4362 if (c == null) {
4363 mSpeedBins[i] = c = new SamplingCounter(mUnpluggables);
4364 }
4365 c.addCountAtomic(values[i]);
4366 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07004367 }
4368 }
4369
4370 @Override
4371 public long getTimeAtCpuSpeedStep(int speedStep, int which) {
4372 if (speedStep < mSpeedBins.length) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004373 SamplingCounter c = mSpeedBins[speedStep];
4374 return c != null ? c.getCountLocked(which) : 0;
Amith Yamasanie43530a2009-08-21 13:11:37 -07004375 } else {
4376 return 0;
4377 }
4378 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004379 }
4380
4381 /**
4382 * The statistics associated with a particular package.
4383 */
4384 public final class Pkg extends BatteryStats.Uid.Pkg implements Unpluggable {
4385 /**
4386 * Number of times this package has done something that could wake up the
4387 * device from sleep.
4388 */
4389 int mWakeups;
4390
4391 /**
4392 * Number of things that could wake up the device loaded from a
4393 * previous save.
4394 */
4395 int mLoadedWakeups;
4396
4397 /**
4398 * Number of things that could wake up the device as of the
4399 * last run.
4400 */
4401 int mLastWakeups;
4402
4403 /**
4404 * Number of things that could wake up the device as of the
4405 * last run.
4406 */
4407 int mUnpluggedWakeups;
4408
4409 /**
4410 * The statics we have collected for this package's services.
4411 */
4412 final HashMap<String, Serv> mServiceStats = new HashMap<String, Serv>();
4413
4414 Pkg() {
4415 mUnpluggables.add(this);
4416 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004417
Dianne Hackborna06de0f2012-12-11 16:34:47 -08004418 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004419 mUnpluggedWakeups = mWakeups;
4420 }
4421
Dianne Hackborna06de0f2012-12-11 16:34:47 -08004422 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004423 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004424
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004425 void detach() {
4426 mUnpluggables.remove(this);
4427 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004428
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004429 void readFromParcelLocked(Parcel in) {
4430 mWakeups = in.readInt();
4431 mLoadedWakeups = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07004432 mLastWakeups = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004433 mUnpluggedWakeups = in.readInt();
4434
4435 int numServs = in.readInt();
4436 mServiceStats.clear();
4437 for (int m = 0; m < numServs; m++) {
4438 String serviceName = in.readString();
4439 Uid.Pkg.Serv serv = new Serv();
4440 mServiceStats.put(serviceName, serv);
4441
4442 serv.readFromParcelLocked(in);
4443 }
4444 }
4445
4446 void writeToParcelLocked(Parcel out) {
4447 out.writeInt(mWakeups);
4448 out.writeInt(mLoadedWakeups);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004449 out.writeInt(mUnpluggedWakeups);
4450
4451 out.writeInt(mServiceStats.size());
4452 for (Map.Entry<String, Uid.Pkg.Serv> servEntry : mServiceStats.entrySet()) {
4453 out.writeString(servEntry.getKey());
4454 Uid.Pkg.Serv serv = servEntry.getValue();
4455
4456 serv.writeToParcelLocked(out);
4457 }
4458 }
4459
4460 @Override
4461 public Map<String, ? extends BatteryStats.Uid.Pkg.Serv> getServiceStats() {
4462 return mServiceStats;
4463 }
4464
4465 @Override
4466 public int getWakeups(int which) {
4467 int val;
4468 if (which == STATS_LAST) {
4469 val = mLastWakeups;
4470 } else {
4471 val = mWakeups;
4472 if (which == STATS_CURRENT) {
4473 val -= mLoadedWakeups;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004474 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004475 val -= mUnpluggedWakeups;
4476 }
4477 }
4478
4479 return val;
4480 }
4481
4482 /**
4483 * The statistics associated with a particular service.
4484 */
4485 public final class Serv extends BatteryStats.Uid.Pkg.Serv implements Unpluggable {
4486 /**
4487 * Total time (ms in battery uptime) the service has been left started.
4488 */
4489 long mStartTime;
4490
4491 /**
4492 * If service has been started and not yet stopped, this is
4493 * when it was started.
4494 */
4495 long mRunningSince;
4496
4497 /**
4498 * True if we are currently running.
4499 */
4500 boolean mRunning;
4501
4502 /**
4503 * Total number of times startService() has been called.
4504 */
4505 int mStarts;
4506
4507 /**
4508 * Total time (ms in battery uptime) the service has been left launched.
4509 */
4510 long mLaunchedTime;
4511
4512 /**
4513 * If service has been launched and not yet exited, this is
4514 * when it was launched (ms in battery uptime).
4515 */
4516 long mLaunchedSince;
4517
4518 /**
4519 * True if we are currently launched.
4520 */
4521 boolean mLaunched;
4522
4523 /**
4524 * Total number times the service has been launched.
4525 */
4526 int mLaunches;
4527
4528 /**
4529 * The amount of time spent started loaded from a previous save
4530 * (ms in battery uptime).
4531 */
4532 long mLoadedStartTime;
4533
4534 /**
4535 * The number of starts loaded from a previous save.
4536 */
4537 int mLoadedStarts;
4538
4539 /**
4540 * The number of launches loaded from a previous save.
4541 */
4542 int mLoadedLaunches;
4543
4544 /**
4545 * The amount of time spent started as of the last run (ms
4546 * in battery uptime).
4547 */
4548 long mLastStartTime;
4549
4550 /**
4551 * The number of starts as of the last run.
4552 */
4553 int mLastStarts;
4554
4555 /**
4556 * The number of launches as of the last run.
4557 */
4558 int mLastLaunches;
4559
4560 /**
4561 * The amount of time spent started when last unplugged (ms
4562 * in battery uptime).
4563 */
4564 long mUnpluggedStartTime;
4565
4566 /**
4567 * The number of starts when last unplugged.
4568 */
4569 int mUnpluggedStarts;
4570
4571 /**
4572 * The number of launches when last unplugged.
4573 */
4574 int mUnpluggedLaunches;
4575
4576 Serv() {
4577 mUnpluggables.add(this);
4578 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004579
Dianne Hackborna06de0f2012-12-11 16:34:47 -08004580 public void unplug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004581 mUnpluggedStartTime = getStartTimeToNowLocked(batteryUptime);
4582 mUnpluggedStarts = mStarts;
4583 mUnpluggedLaunches = mLaunches;
4584 }
4585
Dianne Hackborna06de0f2012-12-11 16:34:47 -08004586 public void plug(long elapsedRealtime, long batteryUptime, long batteryRealtime) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004587 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004588
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004589 void detach() {
4590 mUnpluggables.remove(this);
4591 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004592
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004593 void readFromParcelLocked(Parcel in) {
4594 mStartTime = in.readLong();
4595 mRunningSince = in.readLong();
4596 mRunning = in.readInt() != 0;
4597 mStarts = in.readInt();
4598 mLaunchedTime = in.readLong();
4599 mLaunchedSince = in.readLong();
4600 mLaunched = in.readInt() != 0;
4601 mLaunches = in.readInt();
4602 mLoadedStartTime = in.readLong();
4603 mLoadedStarts = in.readInt();
4604 mLoadedLaunches = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07004605 mLastStartTime = 0;
4606 mLastStarts = 0;
4607 mLastLaunches = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004608 mUnpluggedStartTime = in.readLong();
4609 mUnpluggedStarts = in.readInt();
4610 mUnpluggedLaunches = in.readInt();
4611 }
4612
4613 void writeToParcelLocked(Parcel out) {
4614 out.writeLong(mStartTime);
4615 out.writeLong(mRunningSince);
4616 out.writeInt(mRunning ? 1 : 0);
4617 out.writeInt(mStarts);
4618 out.writeLong(mLaunchedTime);
4619 out.writeLong(mLaunchedSince);
4620 out.writeInt(mLaunched ? 1 : 0);
4621 out.writeInt(mLaunches);
4622 out.writeLong(mLoadedStartTime);
4623 out.writeInt(mLoadedStarts);
4624 out.writeInt(mLoadedLaunches);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004625 out.writeLong(mUnpluggedStartTime);
4626 out.writeInt(mUnpluggedStarts);
4627 out.writeInt(mUnpluggedLaunches);
4628 }
4629
4630 long getLaunchTimeToNowLocked(long batteryUptime) {
4631 if (!mLaunched) return mLaunchedTime;
4632 return mLaunchedTime + batteryUptime - mLaunchedSince;
4633 }
4634
4635 long getStartTimeToNowLocked(long batteryUptime) {
4636 if (!mRunning) return mStartTime;
4637 return mStartTime + batteryUptime - mRunningSince;
4638 }
4639
4640 public void startLaunchedLocked() {
4641 if (!mLaunched) {
4642 mLaunches++;
4643 mLaunchedSince = getBatteryUptimeLocked();
4644 mLaunched = true;
4645 }
4646 }
4647
4648 public void stopLaunchedLocked() {
4649 if (mLaunched) {
4650 long time = getBatteryUptimeLocked() - mLaunchedSince;
4651 if (time > 0) {
4652 mLaunchedTime += time;
4653 } else {
4654 mLaunches--;
4655 }
4656 mLaunched = false;
4657 }
4658 }
4659
4660 public void startRunningLocked() {
4661 if (!mRunning) {
4662 mStarts++;
4663 mRunningSince = getBatteryUptimeLocked();
4664 mRunning = true;
4665 }
4666 }
4667
4668 public void stopRunningLocked() {
4669 if (mRunning) {
4670 long time = getBatteryUptimeLocked() - mRunningSince;
4671 if (time > 0) {
4672 mStartTime += time;
4673 } else {
4674 mStarts--;
4675 }
4676 mRunning = false;
4677 }
4678 }
4679
4680 public BatteryStatsImpl getBatteryStats() {
4681 return BatteryStatsImpl.this;
4682 }
4683
4684 @Override
4685 public int getLaunches(int which) {
4686 int val;
4687
4688 if (which == STATS_LAST) {
4689 val = mLastLaunches;
4690 } else {
4691 val = mLaunches;
4692 if (which == STATS_CURRENT) {
4693 val -= mLoadedLaunches;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004694 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004695 val -= mUnpluggedLaunches;
4696 }
4697 }
4698
4699 return val;
4700 }
4701
4702 @Override
4703 public long getStartTime(long now, int which) {
4704 long val;
4705 if (which == STATS_LAST) {
4706 val = mLastStartTime;
4707 } else {
4708 val = getStartTimeToNowLocked(now);
4709 if (which == STATS_CURRENT) {
4710 val -= mLoadedStartTime;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004711 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004712 val -= mUnpluggedStartTime;
4713 }
4714 }
4715
4716 return val;
4717 }
4718
4719 @Override
4720 public int getStarts(int which) {
4721 int val;
4722 if (which == STATS_LAST) {
4723 val = mLastStarts;
4724 } else {
4725 val = mStarts;
4726 if (which == STATS_CURRENT) {
4727 val -= mLoadedStarts;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004728 } else if (which == STATS_SINCE_UNPLUGGED) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004729 val -= mUnpluggedStarts;
4730 }
4731 }
4732
4733 return val;
4734 }
4735 }
4736
4737 public BatteryStatsImpl getBatteryStats() {
4738 return BatteryStatsImpl.this;
4739 }
4740
4741 public void incWakeupsLocked() {
4742 mWakeups++;
4743 }
4744
4745 final Serv newServiceStatsLocked() {
4746 return new Serv();
4747 }
4748 }
4749
4750 /**
4751 * Retrieve the statistics object for a particular process, creating
4752 * if needed.
4753 */
4754 public Proc getProcessStatsLocked(String name) {
4755 Proc ps = mProcessStats.get(name);
4756 if (ps == null) {
4757 ps = new Proc();
4758 mProcessStats.put(name, ps);
4759 }
4760
4761 return ps;
4762 }
4763
Dianne Hackbornb5e31652010-09-07 12:13:55 -07004764 public SparseArray<? extends Pid> getPidStats() {
4765 return mPids;
4766 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004767
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004768 public Pid getPidStatsLocked(int pid) {
4769 Pid p = mPids.get(pid);
4770 if (p == null) {
4771 p = new Pid();
4772 mPids.put(pid, p);
4773 }
4774 return p;
4775 }
4776
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004777 /**
4778 * Retrieve the statistics object for a particular service, creating
4779 * if needed.
4780 */
4781 public Pkg getPackageStatsLocked(String name) {
4782 Pkg ps = mPackageStats.get(name);
4783 if (ps == null) {
4784 ps = new Pkg();
4785 mPackageStats.put(name, ps);
4786 }
4787
4788 return ps;
4789 }
4790
4791 /**
4792 * Retrieve the statistics object for a particular service, creating
4793 * if needed.
4794 */
4795 public Pkg.Serv getServiceStatsLocked(String pkg, String serv) {
4796 Pkg ps = getPackageStatsLocked(pkg);
4797 Pkg.Serv ss = ps.mServiceStats.get(serv);
4798 if (ss == null) {
4799 ss = ps.newServiceStatsLocked();
4800 ps.mServiceStats.put(serv, ss);
4801 }
4802
4803 return ss;
4804 }
4805
Evan Millarc64edde2009-04-18 12:26:32 -07004806 public StopwatchTimer getWakeTimerLocked(String name, int type) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004807 Wakelock wl = mWakelockStats.get(name);
4808 if (wl == null) {
Dianne Hackbornc24ab862011-10-18 15:55:03 -07004809 final int N = mWakelockStats.size();
Dianne Hackbornaf17baa2013-05-09 15:27:47 -07004810 if (N > MAX_WAKELOCKS_PER_UID) {
Dianne Hackborn9e0f5d92010-02-22 15:05:42 -08004811 name = BATCHED_WAKELOCK_NAME;
4812 wl = mWakelockStats.get(name);
4813 }
4814 if (wl == null) {
4815 wl = new Wakelock();
4816 mWakelockStats.put(name, wl);
4817 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004818 }
Evan Millarc64edde2009-04-18 12:26:32 -07004819 StopwatchTimer t = null;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004820 switch (type) {
4821 case WAKE_TYPE_PARTIAL:
4822 t = wl.mTimerPartial;
4823 if (t == null) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004824 t = new StopwatchTimer(Uid.this, WAKE_TYPE_PARTIAL,
4825 mPartialTimers, mUnpluggables);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004826 wl.mTimerPartial = t;
4827 }
4828 return t;
4829 case WAKE_TYPE_FULL:
4830 t = wl.mTimerFull;
4831 if (t == null) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004832 t = new StopwatchTimer(Uid.this, WAKE_TYPE_FULL,
4833 mFullTimers, mUnpluggables);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004834 wl.mTimerFull = t;
4835 }
4836 return t;
4837 case WAKE_TYPE_WINDOW:
4838 t = wl.mTimerWindow;
4839 if (t == null) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004840 t = new StopwatchTimer(Uid.this, WAKE_TYPE_WINDOW,
4841 mWindowTimers, mUnpluggables);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004842 wl.mTimerWindow = t;
4843 }
4844 return t;
4845 default:
4846 throw new IllegalArgumentException("type=" + type);
4847 }
4848 }
4849
Evan Millarc64edde2009-04-18 12:26:32 -07004850 public StopwatchTimer getSensorTimerLocked(int sensor, boolean create) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004851 Sensor se = mSensorStats.get(sensor);
4852 if (se == null) {
4853 if (!create) {
4854 return null;
4855 }
4856 se = new Sensor(sensor);
4857 mSensorStats.put(sensor, se);
4858 }
Evan Millarc64edde2009-04-18 12:26:32 -07004859 StopwatchTimer t = se.mTimer;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004860 if (t != null) {
4861 return t;
4862 }
Evan Millarc64edde2009-04-18 12:26:32 -07004863 ArrayList<StopwatchTimer> timers = mSensorTimers.get(sensor);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004864 if (timers == null) {
Evan Millarc64edde2009-04-18 12:26:32 -07004865 timers = new ArrayList<StopwatchTimer>();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004866 mSensorTimers.put(sensor, timers);
4867 }
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004868 t = new StopwatchTimer(Uid.this, BatteryStats.SENSOR, timers, mUnpluggables);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004869 se.mTimer = t;
4870 return t;
4871 }
4872
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004873 public void noteStartWakeLocked(int pid, String name, int type) {
Evan Millarc64edde2009-04-18 12:26:32 -07004874 StopwatchTimer t = getWakeTimerLocked(name, type);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004875 if (t != null) {
4876 t.startRunningLocked(BatteryStatsImpl.this);
4877 }
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07004878 if (pid >= 0 && type == WAKE_TYPE_PARTIAL) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004879 Pid p = getPidStatsLocked(pid);
Dianne Hackbornb8071d792010-09-09 16:45:15 -07004880 if (p.mWakeStart == 0) {
4881 p.mWakeStart = SystemClock.elapsedRealtime();
4882 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004883 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004884 }
4885
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004886 public void noteStopWakeLocked(int pid, String name, int type) {
Evan Millarc64edde2009-04-18 12:26:32 -07004887 StopwatchTimer t = getWakeTimerLocked(name, type);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004888 if (t != null) {
4889 t.stopRunningLocked(BatteryStatsImpl.this);
4890 }
Dianne Hackborn1ebccf52010-08-15 13:04:34 -07004891 if (pid >= 0 && type == WAKE_TYPE_PARTIAL) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004892 Pid p = mPids.get(pid);
Dianne Hackbornb8071d792010-09-09 16:45:15 -07004893 if (p != null && p.mWakeStart != 0) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07004894 p.mWakeSum += SystemClock.elapsedRealtime() - p.mWakeStart;
4895 p.mWakeStart = 0;
4896 }
4897 }
4898 }
4899
4900 public void reportExcessiveWakeLocked(String proc, long overTime, long usedTime) {
4901 Proc p = getProcessStatsLocked(proc);
4902 if (p != null) {
4903 p.addExcessiveWake(overTime, usedTime);
4904 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004905 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004906
Dianne Hackborn287952c2010-09-22 22:34:31 -07004907 public void reportExcessiveCpuLocked(String proc, long overTime, long usedTime) {
4908 Proc p = getProcessStatsLocked(proc);
4909 if (p != null) {
4910 p.addExcessiveCpu(overTime, usedTime);
4911 }
4912 }
4913
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004914 public void noteStartSensor(int sensor) {
Evan Millarc64edde2009-04-18 12:26:32 -07004915 StopwatchTimer t = getSensorTimerLocked(sensor, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004916 if (t != null) {
4917 t.startRunningLocked(BatteryStatsImpl.this);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004918 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004919 }
4920
4921 public void noteStopSensor(int sensor) {
4922 // Don't create a timer if one doesn't already exist
Evan Millarc64edde2009-04-18 12:26:32 -07004923 StopwatchTimer t = getSensorTimerLocked(sensor, false);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004924 if (t != null) {
4925 t.stopRunningLocked(BatteryStatsImpl.this);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004926 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004927 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004928
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004929 public void noteStartGps() {
Evan Millarc64edde2009-04-18 12:26:32 -07004930 StopwatchTimer t = getSensorTimerLocked(Sensor.GPS, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004931 if (t != null) {
4932 t.startRunningLocked(BatteryStatsImpl.this);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004933 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004934 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07004935
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004936 public void noteStopGps() {
Evan Millarc64edde2009-04-18 12:26:32 -07004937 StopwatchTimer t = getSensorTimerLocked(Sensor.GPS, false);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004938 if (t != null) {
4939 t.stopRunningLocked(BatteryStatsImpl.this);
Amith Yamasani244fa5c2009-05-22 14:36:07 -07004940 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004941 }
4942
4943 public BatteryStatsImpl getBatteryStats() {
4944 return BatteryStatsImpl.this;
4945 }
4946 }
4947
Jeff Brown6f357d32014-01-15 20:40:55 -08004948 public BatteryStatsImpl(String filename, Handler handler) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07004949 mFile = new JournaledFile(new File(filename), new File(filename + ".tmp"));
Jeff Brown6f357d32014-01-15 20:40:55 -08004950 mHandler = new MyHandler(handler.getLooper());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004951 mStartCount++;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004952 mScreenOnTimer = new StopwatchTimer(null, -1, null, mUnpluggables);
Dianne Hackborn617f8772009-03-31 15:04:46 -07004953 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004954 mScreenBrightnessTimer[i] = new StopwatchTimer(null, -100-i, null, mUnpluggables);
Dianne Hackborn617f8772009-03-31 15:04:46 -07004955 }
4956 mInputEventCounter = new Counter(mUnpluggables);
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004957 mPhoneOnTimer = new StopwatchTimer(null, -2, null, mUnpluggables);
Wink Saville52840902011-02-18 12:40:47 -08004958 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004959 mPhoneSignalStrengthsTimer[i] = new StopwatchTimer(null, -200-i, null, mUnpluggables);
Dianne Hackborn627bba72009-03-24 22:32:56 -07004960 }
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004961 mPhoneSignalScanningTimer = new StopwatchTimer(null, -200+1, null, mUnpluggables);
Dianne Hackborn627bba72009-03-24 22:32:56 -07004962 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004963 mPhoneDataConnectionsTimer[i] = new StopwatchTimer(null, -300-i, null, mUnpluggables);
Dianne Hackborn627bba72009-03-24 22:32:56 -07004964 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07004965 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08004966 mNetworkByteActivityCounters[i] = new LongSamplingCounter(mUnpluggables);
4967 mNetworkPacketActivityCounters[i] = new LongSamplingCounter(mUnpluggables);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07004968 }
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004969 mWifiOnTimer = new StopwatchTimer(null, -3, null, mUnpluggables);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07004970 mGlobalWifiRunningTimer = new StopwatchTimer(null, -4, null, mUnpluggables);
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004971 mBluetoothOnTimer = new StopwatchTimer(null, -5, null, mUnpluggables);
4972 mAudioOnTimer = new StopwatchTimer(null, -6, null, mUnpluggables);
4973 mVideoOnTimer = new StopwatchTimer(null, -7, null, mUnpluggables);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004974 mOnBattery = mOnBatteryInternal = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004975 initTimes();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004976 mTrackBatteryPastUptime = 0;
4977 mTrackBatteryPastRealtime = 0;
4978 mUptimeStart = mTrackBatteryUptimeStart = SystemClock.uptimeMillis() * 1000;
4979 mRealtimeStart = mTrackBatteryRealtimeStart = SystemClock.elapsedRealtime() * 1000;
4980 mUnpluggedBatteryUptime = getBatteryUptimeLocked(mUptimeStart);
4981 mUnpluggedBatteryRealtime = getBatteryRealtimeLocked(mRealtimeStart);
Evan Millar633a1742009-04-02 16:36:33 -07004982 mDischargeStartLevel = 0;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07004983 mDischargeUnplugLevel = 0;
Evan Millar633a1742009-04-02 16:36:33 -07004984 mDischargeCurrentLevel = 0;
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08004985 initDischarge();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07004986 clearHistoryLocked();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004987 }
4988
4989 public BatteryStatsImpl(Parcel p) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07004990 mFile = null;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004991 mHandler = null;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07004992 clearHistoryLocked();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08004993 readFromParcel(p);
4994 }
4995
Dianne Hackborn0d903a82010-09-07 23:51:03 -07004996 public void setCallback(BatteryCallback cb) {
4997 mCallback = cb;
4998 }
4999
Amith Yamasanie43530a2009-08-21 13:11:37 -07005000 public void setNumSpeedSteps(int steps) {
5001 if (sNumSpeedSteps == 0) sNumSpeedSteps = steps;
5002 }
5003
Amith Yamasanif37447b2009-10-08 18:28:01 -07005004 public void setRadioScanningTimeout(long timeout) {
5005 if (mPhoneSignalScanningTimer != null) {
5006 mPhoneSignalScanningTimer.setTimeout(timeout);
5007 }
5008 }
5009
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005010 @Override
5011 public boolean startIteratingOldHistoryLocked() {
5012 if (DEBUG_HISTORY) Slog.i(TAG, "ITERATING: buff size=" + mHistoryBuffer.dataSize()
5013 + " pos=" + mHistoryBuffer.dataPosition());
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005014 if ((mHistoryIterator = mHistory) == null) {
5015 return false;
5016 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005017 mHistoryBuffer.setDataPosition(0);
Dianne Hackborn1fadab52011-04-14 17:57:33 -07005018 mHistoryReadTmp.clear();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005019 mReadOverflow = false;
5020 mIteratingHistory = true;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005021 return true;
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005022 }
5023
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005024 @Override
5025 public boolean getNextOldHistoryLocked(HistoryItem out) {
5026 boolean end = mHistoryBuffer.dataPosition() >= mHistoryBuffer.dataSize();
5027 if (!end) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005028 readHistoryDelta(mHistoryBuffer, mHistoryReadTmp);
Dianne Hackborn1fadab52011-04-14 17:57:33 -07005029 mReadOverflow |= mHistoryReadTmp.cmd == HistoryItem.CMD_OVERFLOW;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005030 }
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005031 HistoryItem cur = mHistoryIterator;
5032 if (cur == null) {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005033 if (!mReadOverflow && !end) {
5034 Slog.w(TAG, "Old history ends before new history!");
5035 }
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005036 return false;
5037 }
5038 out.setTo(cur);
5039 mHistoryIterator = cur.next;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005040 if (!mReadOverflow) {
5041 if (end) {
5042 Slog.w(TAG, "New history ends before old history!");
Dianne Hackborn1fadab52011-04-14 17:57:33 -07005043 } else if (!out.same(mHistoryReadTmp)) {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005044 long now = getHistoryBaseTime() + SystemClock.elapsedRealtime();
Dianne Hackborn8c841092013-06-24 13:46:13 -07005045 PrintWriter pw = new FastPrintWriter(new LogWriter(android.util.Log.WARN, TAG));
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005046 pw.println("Histories differ!");
5047 pw.println("Old history:");
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005048 (new HistoryPrinter()).printNextItem(pw, out, now, false);
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005049 pw.println("New history:");
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005050 (new HistoryPrinter()).printNextItem(pw, mHistoryReadTmp, now, false);
Dianne Hackborn8c841092013-06-24 13:46:13 -07005051 pw.flush();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005052 }
5053 }
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005054 return true;
5055 }
5056
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005057 @Override
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005058 public void finishIteratingOldHistoryLocked() {
5059 mIteratingHistory = false;
5060 mHistoryBuffer.setDataPosition(mHistoryBuffer.dataSize());
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005061 mHistoryIterator = null;
5062 }
5063
5064 public int getHistoryTotalSize() {
5065 return MAX_HISTORY_BUFFER;
5066 }
5067
5068 public int getHistoryUsedSize() {
5069 return mHistoryBuffer.dataSize();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005070 }
5071
5072 @Override
5073 public boolean startIteratingHistoryLocked() {
5074 if (DEBUG_HISTORY) Slog.i(TAG, "ITERATING: buff size=" + mHistoryBuffer.dataSize()
5075 + " pos=" + mHistoryBuffer.dataPosition());
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08005076 if (mHistoryBuffer.dataSize() <= 0) {
5077 return false;
5078 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005079 mHistoryBuffer.setDataPosition(0);
5080 mReadOverflow = false;
5081 mIteratingHistory = true;
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005082 mReadHistoryStrings = new String[mHistoryTagPool.size()];
5083 mReadHistoryUids = new int[mHistoryTagPool.size()];
5084 mReadHistoryChars = 0;
5085 for (HashMap.Entry<HistoryTag, Integer> ent : mHistoryTagPool.entrySet()) {
5086 final HistoryTag tag = ent.getKey();
5087 final int idx = ent.getValue();
5088 mReadHistoryStrings[idx] = tag.string;
5089 mReadHistoryUids[idx] = tag.uid;
5090 mReadHistoryChars += tag.string.length() + 1;
Dianne Hackborn099bc622014-01-22 13:39:16 -08005091 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08005092 return true;
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005093 }
5094
5095 @Override
Dianne Hackborn099bc622014-01-22 13:39:16 -08005096 public int getHistoryStringPoolSize() {
5097 return mReadHistoryStrings.length;
5098 }
5099
5100 @Override
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005101 public int getHistoryStringPoolBytes() {
5102 // Each entry is a fixed 12 bytes: 4 for index, 4 for uid, 4 for string size
5103 // Each string character is 2 bytes.
5104 return (mReadHistoryStrings.length * 12) + (mReadHistoryChars * 2);
5105 }
5106
5107 @Override
5108 public String getHistoryTagPoolString(int index) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08005109 return mReadHistoryStrings[index];
5110 }
5111
5112 @Override
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005113 public int getHistoryTagPoolUid(int index) {
5114 return mReadHistoryUids[index];
5115 }
5116
5117 @Override
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005118 public boolean getNextHistoryLocked(HistoryItem out) {
Dianne Hackborn1fadab52011-04-14 17:57:33 -07005119 final int pos = mHistoryBuffer.dataPosition();
5120 if (pos == 0) {
5121 out.clear();
5122 }
5123 boolean end = pos >= mHistoryBuffer.dataSize();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005124 if (end) {
5125 return false;
5126 }
5127
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005128 readHistoryDelta(mHistoryBuffer, out);
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005129 return true;
5130 }
5131
5132 @Override
5133 public void finishIteratingHistoryLocked() {
5134 mIteratingHistory = false;
5135 mHistoryBuffer.setDataPosition(mHistoryBuffer.dataSize());
Dianne Hackborn099bc622014-01-22 13:39:16 -08005136 mReadHistoryStrings = null;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07005137 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005138
Dianne Hackborn32907cf2010-06-10 17:50:20 -07005139 @Override
Dianne Hackbornb5e31652010-09-07 12:13:55 -07005140 public long getHistoryBaseTime() {
5141 return mHistoryBaseTime;
5142 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005143
Dianne Hackbornb5e31652010-09-07 12:13:55 -07005144 @Override
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005145 public int getStartCount() {
5146 return mStartCount;
5147 }
5148
5149 public boolean isOnBattery() {
5150 return mOnBattery;
5151 }
5152
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005153 public boolean isScreenOn() {
5154 return mScreenOn;
5155 }
5156
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005157 void initTimes() {
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08005158 mStartClockTime = System.currentTimeMillis();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005159 mBatteryRealtime = mTrackBatteryPastUptime = 0;
5160 mBatteryUptime = mTrackBatteryPastRealtime = 0;
5161 mUptimeStart = mTrackBatteryUptimeStart = SystemClock.uptimeMillis() * 1000;
5162 mRealtimeStart = mTrackBatteryRealtimeStart = SystemClock.elapsedRealtime() * 1000;
5163 mUnpluggedBatteryUptime = getBatteryUptimeLocked(mUptimeStart);
5164 mUnpluggedBatteryRealtime = getBatteryRealtimeLocked(mRealtimeStart);
5165 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005166
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08005167 void initDischarge() {
5168 mLowDischargeAmountSinceCharge = 0;
5169 mHighDischargeAmountSinceCharge = 0;
5170 mDischargeAmountScreenOn = 0;
5171 mDischargeAmountScreenOnSinceCharge = 0;
5172 mDischargeAmountScreenOff = 0;
5173 mDischargeAmountScreenOffSinceCharge = 0;
5174 }
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08005175
5176 public void resetAllStatsCmdLocked() {
5177 resetAllStatsLocked();
5178 long uptime = SystemClock.uptimeMillis() * 1000;
5179 long mSecRealtime = SystemClock.elapsedRealtime();
5180 long realtime = mSecRealtime * 1000;
5181 mDischargeStartLevel = mHistoryCur.batteryLevel;
5182 pullPendingStateUpdatesLocked();
5183 addHistoryRecordLocked(mSecRealtime);
5184 mDischargeCurrentLevel = mDischargeUnplugLevel = mHistoryCur.batteryLevel;
5185 if ((mHistoryCur.states&HistoryItem.STATE_BATTERY_PLUGGED_FLAG) != 0) {
5186 mTrackBatteryPastUptime = 0;
5187 mTrackBatteryPastRealtime = 0;
5188 } else {
5189 mTrackBatteryUptimeStart = uptime;
5190 mTrackBatteryRealtimeStart = realtime;
5191 mUnpluggedBatteryUptime = getBatteryUptimeLocked(uptime);
5192 mUnpluggedBatteryRealtime = getBatteryRealtimeLocked(realtime);
5193 if (mScreenOn) {
5194 mDischargeScreenOnUnplugLevel = mHistoryCur.batteryLevel;
5195 mDischargeScreenOffUnplugLevel = 0;
5196 } else {
5197 mDischargeScreenOnUnplugLevel = 0;
5198 mDischargeScreenOffUnplugLevel = mHistoryCur.batteryLevel;
5199 }
5200 mDischargeAmountScreenOn = 0;
5201 mDischargeAmountScreenOff = 0;
5202 }
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08005203 initActiveHistoryEventsLocked(mSecRealtime);
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08005204 }
5205
5206 private void resetAllStatsLocked() {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005207 mStartCount = 0;
5208 initTimes();
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005209 mScreenOnTimer.reset(this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005210 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005211 mScreenBrightnessTimer[i].reset(this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005212 }
5213 mInputEventCounter.reset(false);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005214 mPhoneOnTimer.reset(this, false);
5215 mAudioOnTimer.reset(this, false);
5216 mVideoOnTimer.reset(this, false);
Wink Saville52840902011-02-18 12:40:47 -08005217 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005218 mPhoneSignalStrengthsTimer[i].reset(this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005219 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005220 mPhoneSignalScanningTimer.reset(this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005221 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005222 mPhoneDataConnectionsTimer[i].reset(this, false);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005223 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005224 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005225 mNetworkByteActivityCounters[i].reset(false);
5226 mNetworkPacketActivityCounters[i].reset(false);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005227 }
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005228 mWifiOnTimer.reset(this, false);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07005229 mGlobalWifiRunningTimer.reset(this, false);
Dianne Hackborn9adb9c32010-08-13 14:09:56 -07005230 mBluetoothOnTimer.reset(this, false);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005231
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005232 for (int i=0; i<mUidStats.size(); i++) {
5233 if (mUidStats.valueAt(i).reset()) {
5234 mUidStats.remove(mUidStats.keyAt(i));
5235 i--;
5236 }
5237 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005238
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005239 if (mKernelWakelockStats.size() > 0) {
5240 for (SamplingTimer timer : mKernelWakelockStats.values()) {
5241 mUnpluggables.remove(timer);
5242 }
5243 mKernelWakelockStats.clear();
5244 }
5245
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08005246 initDischarge();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005247
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005248 clearHistoryLocked();
5249 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005250
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08005251 private void initActiveHistoryEventsLocked(long nowRealtime) {
5252 for (int i=0; i<HistoryItem.EVENT_COUNT; i++) {
5253 HashMap<String, SparseBooleanArray> active = mActiveEvents[i];
5254 if (active == null) {
5255 continue;
5256 }
5257 for (HashMap.Entry<String, SparseBooleanArray> ent : active.entrySet()) {
5258 SparseBooleanArray uids = ent.getValue();
5259 for (int j=0; j<uids.size(); j++) {
5260 if (uids.valueAt(j)) {
5261 addHistoryEventLocked(nowRealtime, i, ent.getKey(), uids.keyAt(j));
5262 }
5263 }
5264 }
5265 }
5266 }
5267
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005268 void updateDischargeScreenLevelsLocked(boolean oldScreenOn, boolean newScreenOn) {
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08005269 if (oldScreenOn) {
5270 int diff = mDischargeScreenOnUnplugLevel - mDischargeCurrentLevel;
5271 if (diff > 0) {
5272 mDischargeAmountScreenOn += diff;
5273 mDischargeAmountScreenOnSinceCharge += diff;
5274 }
5275 } else {
5276 int diff = mDischargeScreenOffUnplugLevel - mDischargeCurrentLevel;
5277 if (diff > 0) {
5278 mDischargeAmountScreenOff += diff;
5279 mDischargeAmountScreenOffSinceCharge += diff;
5280 }
5281 }
5282 if (newScreenOn) {
5283 mDischargeScreenOnUnplugLevel = mDischargeCurrentLevel;
5284 mDischargeScreenOffUnplugLevel = 0;
5285 } else {
5286 mDischargeScreenOnUnplugLevel = 0;
5287 mDischargeScreenOffUnplugLevel = mDischargeCurrentLevel;
5288 }
5289 }
5290
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005291 void setOnBattery(boolean onBattery, int oldStatus, int level) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005292 synchronized(this) {
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005293 setOnBatteryLocked(onBattery, oldStatus, level);
5294 }
5295 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005296
Dianne Hackborna7c837f2014-01-15 16:20:44 -08005297 public void pullPendingStateUpdatesLocked() {
5298 updateKernelWakelocksLocked();
5299 updateNetworkActivityLocked();
5300 }
5301
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005302 void setOnBatteryLocked(boolean onBattery, int oldStatus, int level) {
5303 boolean doWrite = false;
5304 Message m = mHandler.obtainMessage(MSG_REPORT_POWER_CHANGE);
5305 m.arg1 = onBattery ? 1 : 0;
5306 mHandler.sendMessage(m);
5307 mOnBattery = mOnBatteryInternal = onBattery;
5308
5309 long uptime = SystemClock.uptimeMillis() * 1000;
5310 long mSecRealtime = SystemClock.elapsedRealtime();
5311 long realtime = mSecRealtime * 1000;
5312 if (onBattery) {
5313 // We will reset our status if we are unplugging after the
5314 // battery was last full, or the level is at 100, or
5315 // we have gone through a significant charge (from a very low
5316 // level to a now very high level).
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08005317 boolean reset = false;
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005318 if (oldStatus == BatteryManager.BATTERY_STATUS_FULL
5319 || level >= 90
5320 || (mDischargeCurrentLevel < 20 && level >= 80)) {
5321 doWrite = true;
5322 resetAllStatsLocked();
5323 mDischargeStartLevel = level;
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08005324 reset = true;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005325 }
Dianne Hackborna7c837f2014-01-15 16:20:44 -08005326 pullPendingStateUpdatesLocked();
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005327 mHistoryCur.batteryLevel = (byte)level;
5328 mHistoryCur.states &= ~HistoryItem.STATE_BATTERY_PLUGGED_FLAG;
5329 if (DEBUG_HISTORY) Slog.v(TAG, "Battery unplugged to: "
5330 + Integer.toHexString(mHistoryCur.states));
5331 addHistoryRecordLocked(mSecRealtime);
5332 mTrackBatteryUptimeStart = uptime;
5333 mTrackBatteryRealtimeStart = realtime;
5334 mUnpluggedBatteryUptime = getBatteryUptimeLocked(uptime);
5335 mUnpluggedBatteryRealtime = getBatteryRealtimeLocked(realtime);
5336 mDischargeCurrentLevel = mDischargeUnplugLevel = level;
5337 if (mScreenOn) {
5338 mDischargeScreenOnUnplugLevel = level;
5339 mDischargeScreenOffUnplugLevel = 0;
5340 } else {
5341 mDischargeScreenOnUnplugLevel = 0;
5342 mDischargeScreenOffUnplugLevel = level;
5343 }
5344 mDischargeAmountScreenOn = 0;
5345 mDischargeAmountScreenOff = 0;
Dianne Hackborna06de0f2012-12-11 16:34:47 -08005346 doUnplugLocked(realtime, mUnpluggedBatteryUptime, mUnpluggedBatteryRealtime);
Dianne Hackborneaf2ac42014-02-07 13:01:07 -08005347 if (reset) {
5348 initActiveHistoryEventsLocked(mSecRealtime);
5349 }
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005350 } else {
Dianne Hackborna7c837f2014-01-15 16:20:44 -08005351 pullPendingStateUpdatesLocked();
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005352 mHistoryCur.batteryLevel = (byte)level;
5353 mHistoryCur.states |= HistoryItem.STATE_BATTERY_PLUGGED_FLAG;
5354 if (DEBUG_HISTORY) Slog.v(TAG, "Battery plugged to: "
5355 + Integer.toHexString(mHistoryCur.states));
5356 addHistoryRecordLocked(mSecRealtime);
5357 mTrackBatteryPastUptime += uptime - mTrackBatteryUptimeStart;
5358 mTrackBatteryPastRealtime += realtime - mTrackBatteryRealtimeStart;
5359 mDischargeCurrentLevel = level;
5360 if (level < mDischargeUnplugLevel) {
5361 mLowDischargeAmountSinceCharge += mDischargeUnplugLevel-level-1;
5362 mHighDischargeAmountSinceCharge += mDischargeUnplugLevel-level;
5363 }
5364 updateDischargeScreenLevelsLocked(mScreenOn, mScreenOn);
Dianne Hackborna06de0f2012-12-11 16:34:47 -08005365 doPlugLocked(realtime, getBatteryUptimeLocked(uptime), getBatteryRealtimeLocked(realtime));
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005366 }
5367 if (doWrite || (mLastWriteTime + (60 * 1000)) < mSecRealtime) {
5368 if (mFile != null) {
5369 writeAsyncLocked();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005370 }
5371 }
5372 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005373
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005374 // This should probably be exposed in the API, though it's not critical
5375 private static final int BATTERY_PLUGGED_NONE = 0;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005376
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005377 public void setBatteryState(int status, int health, int plugType, int level,
5378 int temp, int volt) {
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005379 synchronized(this) {
5380 boolean onBattery = plugType == BATTERY_PLUGGED_NONE;
5381 int oldStatus = mHistoryCur.batteryStatus;
5382 if (!mHaveBatteryLevel) {
5383 mHaveBatteryLevel = true;
5384 // We start out assuming that the device is plugged in (not
5385 // on battery). If our first report is now that we are indeed
5386 // plugged in, then twiddle our state to correctly reflect that
5387 // since we won't be going through the full setOnBattery().
5388 if (onBattery == mOnBattery) {
5389 if (onBattery) {
5390 mHistoryCur.states &= ~HistoryItem.STATE_BATTERY_PLUGGED_FLAG;
5391 } else {
5392 mHistoryCur.states |= HistoryItem.STATE_BATTERY_PLUGGED_FLAG;
5393 }
5394 }
5395 oldStatus = status;
5396 }
5397 if (onBattery) {
5398 mDischargeCurrentLevel = level;
5399 mRecordingHistory = true;
5400 }
5401 if (onBattery != mOnBattery) {
5402 mHistoryCur.batteryLevel = (byte)level;
5403 mHistoryCur.batteryStatus = (byte)status;
5404 mHistoryCur.batteryHealth = (byte)health;
5405 mHistoryCur.batteryPlugType = (byte)plugType;
Sungmin Choic7e9e8b2013-01-16 12:57:36 +09005406 mHistoryCur.batteryTemperature = (short)temp;
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005407 mHistoryCur.batteryVoltage = (char)volt;
5408 setOnBatteryLocked(onBattery, oldStatus, level);
5409 } else {
5410 boolean changed = false;
5411 if (mHistoryCur.batteryLevel != level) {
5412 mHistoryCur.batteryLevel = (byte)level;
5413 changed = true;
5414 }
5415 if (mHistoryCur.batteryStatus != status) {
5416 mHistoryCur.batteryStatus = (byte)status;
5417 changed = true;
5418 }
5419 if (mHistoryCur.batteryHealth != health) {
5420 mHistoryCur.batteryHealth = (byte)health;
5421 changed = true;
5422 }
5423 if (mHistoryCur.batteryPlugType != plugType) {
5424 mHistoryCur.batteryPlugType = (byte)plugType;
5425 changed = true;
5426 }
5427 if (temp >= (mHistoryCur.batteryTemperature+10)
5428 || temp <= (mHistoryCur.batteryTemperature-10)) {
Sungmin Choic7e9e8b2013-01-16 12:57:36 +09005429 mHistoryCur.batteryTemperature = (short)temp;
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005430 changed = true;
5431 }
5432 if (volt > (mHistoryCur.batteryVoltage+20)
5433 || volt < (mHistoryCur.batteryVoltage-20)) {
5434 mHistoryCur.batteryVoltage = (char)volt;
5435 changed = true;
5436 }
5437 if (changed) {
5438 addHistoryRecordLocked(SystemClock.elapsedRealtime());
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005439 }
5440 }
Dianne Hackborn32de2f62011-03-09 14:03:35 -08005441 if (!onBattery && status == BatteryManager.BATTERY_STATUS_FULL) {
5442 // We don't record history while we are plugged in and fully charged.
5443 // The next time we are unplugged, history will be cleared.
Dianne Hackborn3d658bf2014-02-05 13:38:56 -08005444 mRecordingHistory = DEBUG;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005445 }
Dianne Hackborn32907cf2010-06-10 17:50:20 -07005446 }
Evan Millar633a1742009-04-02 16:36:33 -07005447 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005448
Evan Millarc64edde2009-04-18 12:26:32 -07005449 public void updateKernelWakelocksLocked() {
5450 Map<String, KernelWakelockStats> m = readKernelWakelockStats();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005451
Marco Nelissend8593312009-04-30 14:45:06 -07005452 if (m == null) {
5453 // Not crashing might make board bringup easier.
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005454 Slog.w(TAG, "Couldn't get kernel wake lock stats");
Marco Nelissend8593312009-04-30 14:45:06 -07005455 return;
5456 }
5457
Evan Millarc64edde2009-04-18 12:26:32 -07005458 for (Map.Entry<String, KernelWakelockStats> ent : m.entrySet()) {
5459 String name = ent.getKey();
5460 KernelWakelockStats kws = ent.getValue();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005461
Evan Millarc64edde2009-04-18 12:26:32 -07005462 SamplingTimer kwlt = mKernelWakelockStats.get(name);
5463 if (kwlt == null) {
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005464 kwlt = new SamplingTimer(mUnpluggables, mOnBatteryInternal,
Evan Millarc64edde2009-04-18 12:26:32 -07005465 true /* track reported values */);
5466 mKernelWakelockStats.put(name, kwlt);
5467 }
5468 kwlt.updateCurrentReportedCount(kws.mCount);
5469 kwlt.updateCurrentReportedTotalTime(kws.mTotalTime);
5470 kwlt.setUpdateVersion(sKernelWakelockUpdateVersion);
5471 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005472
Evan Millarc64edde2009-04-18 12:26:32 -07005473 if (m.size() != mKernelWakelockStats.size()) {
5474 // Set timers to stale if they didn't appear in /proc/wakelocks this time.
5475 for (Map.Entry<String, SamplingTimer> ent : mKernelWakelockStats.entrySet()) {
5476 SamplingTimer st = ent.getValue();
5477 if (st.getUpdateVersion() != sKernelWakelockUpdateVersion) {
5478 st.setStale();
5479 }
5480 }
5481 }
5482 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005483
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005484 private void updateNetworkActivityLocked() {
5485 if (!SystemProperties.getBoolean(PROP_QTAGUID_ENABLED, false)) return;
5486
5487 final NetworkStats snapshot;
5488 try {
5489 snapshot = mNetworkStatsFactory.readNetworkStatsDetail();
5490 } catch (IOException e) {
5491 Log.wtf(TAG, "Failed to read network stats", e);
5492 return;
5493 }
5494
5495 if (mLastSnapshot == null) {
5496 mLastSnapshot = snapshot;
5497 return;
5498 }
5499
5500 final NetworkStats delta = snapshot.subtract(mLastSnapshot);
5501 mLastSnapshot = snapshot;
5502
5503 NetworkStats.Entry entry = null;
5504 final int size = delta.size();
5505 for (int i = 0; i < size; i++) {
5506 entry = delta.getValues(i, entry);
5507
5508 if (entry.rxBytes == 0 || entry.txBytes == 0) continue;
5509 if (entry.tag != NetworkStats.TAG_NONE) continue;
5510
5511 final Uid u = getUidStatsLocked(entry.uid);
5512
5513 if (mMobileIfaces.contains(entry.iface)) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005514 u.noteNetworkActivityLocked(NETWORK_MOBILE_RX_DATA, entry.rxBytes,
5515 entry.rxPackets);
5516 u.noteNetworkActivityLocked(NETWORK_MOBILE_TX_DATA, entry.txBytes,
5517 entry.txPackets);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005518
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005519 mNetworkByteActivityCounters[NETWORK_MOBILE_RX_DATA].addCountLocked(entry.rxBytes);
5520 mNetworkByteActivityCounters[NETWORK_MOBILE_TX_DATA].addCountLocked(entry.txBytes);
5521 mNetworkPacketActivityCounters[NETWORK_MOBILE_RX_DATA].addCountLocked(
5522 entry.rxPackets);
5523 mNetworkPacketActivityCounters[NETWORK_MOBILE_TX_DATA].addCountLocked(
5524 entry.txPackets);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005525
5526 } else if (mWifiIfaces.contains(entry.iface)) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005527 u.noteNetworkActivityLocked(NETWORK_WIFI_RX_DATA, entry.rxBytes, entry.rxPackets);
5528 u.noteNetworkActivityLocked(NETWORK_WIFI_TX_DATA, entry.txBytes, entry.txPackets);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005529
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08005530 mNetworkByteActivityCounters[NETWORK_WIFI_RX_DATA].addCountLocked(entry.rxBytes);
5531 mNetworkByteActivityCounters[NETWORK_WIFI_TX_DATA].addCountLocked(entry.txBytes);
5532 mNetworkPacketActivityCounters[NETWORK_WIFI_RX_DATA].addCountLocked(
5533 entry.rxPackets);
5534 mNetworkPacketActivityCounters[NETWORK_WIFI_TX_DATA].addCountLocked(
5535 entry.txPackets);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07005536 }
5537 }
5538 }
5539
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005540 public long getAwakeTimeBattery() {
5541 return computeBatteryUptime(getBatteryUptimeLocked(), STATS_CURRENT);
5542 }
5543
5544 public long getAwakeTimePlugged() {
5545 return (SystemClock.uptimeMillis() * 1000) - getAwakeTimeBattery();
5546 }
5547
5548 @Override
5549 public long computeUptime(long curTime, int which) {
5550 switch (which) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005551 case STATS_SINCE_CHARGED: return mUptime + (curTime-mUptimeStart);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005552 case STATS_LAST: return mLastUptime;
5553 case STATS_CURRENT: return (curTime-mUptimeStart);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005554 case STATS_SINCE_UNPLUGGED: return (curTime-mTrackBatteryUptimeStart);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005555 }
5556 return 0;
5557 }
5558
5559 @Override
5560 public long computeRealtime(long curTime, int which) {
5561 switch (which) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005562 case STATS_SINCE_CHARGED: return mRealtime + (curTime-mRealtimeStart);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005563 case STATS_LAST: return mLastRealtime;
5564 case STATS_CURRENT: return (curTime-mRealtimeStart);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005565 case STATS_SINCE_UNPLUGGED: return (curTime-mTrackBatteryRealtimeStart);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005566 }
5567 return 0;
5568 }
5569
5570 @Override
5571 public long computeBatteryUptime(long curTime, int which) {
5572 switch (which) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005573 case STATS_SINCE_CHARGED:
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005574 return mBatteryUptime + getBatteryUptime(curTime);
5575 case STATS_LAST:
5576 return mBatteryLastUptime;
5577 case STATS_CURRENT:
5578 return getBatteryUptime(curTime);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005579 case STATS_SINCE_UNPLUGGED:
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005580 return getBatteryUptimeLocked(curTime) - mUnpluggedBatteryUptime;
5581 }
5582 return 0;
5583 }
5584
5585 @Override
5586 public long computeBatteryRealtime(long curTime, int which) {
5587 switch (which) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005588 case STATS_SINCE_CHARGED:
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005589 return mBatteryRealtime + getBatteryRealtimeLocked(curTime);
5590 case STATS_LAST:
5591 return mBatteryLastRealtime;
5592 case STATS_CURRENT:
5593 return getBatteryRealtimeLocked(curTime);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005594 case STATS_SINCE_UNPLUGGED:
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005595 return getBatteryRealtimeLocked(curTime) - mUnpluggedBatteryRealtime;
5596 }
5597 return 0;
5598 }
5599
5600 long getBatteryUptimeLocked(long curTime) {
5601 long time = mTrackBatteryPastUptime;
5602 if (mOnBatteryInternal) {
5603 time += curTime - mTrackBatteryUptimeStart;
5604 }
5605 return time;
5606 }
5607
5608 long getBatteryUptimeLocked() {
5609 return getBatteryUptime(SystemClock.uptimeMillis() * 1000);
5610 }
5611
5612 @Override
5613 public long getBatteryUptime(long curTime) {
5614 return getBatteryUptimeLocked(curTime);
5615 }
5616
5617 long getBatteryRealtimeLocked(long curTime) {
5618 long time = mTrackBatteryPastRealtime;
5619 if (mOnBatteryInternal) {
5620 time += curTime - mTrackBatteryRealtimeStart;
5621 }
5622 return time;
5623 }
5624
5625 @Override
5626 public long getBatteryRealtime(long curTime) {
5627 return getBatteryRealtimeLocked(curTime);
5628 }
Amith Yamasani3718aaa2009-06-09 06:32:35 -07005629
The Android Open Source Project10592532009-03-18 17:39:46 -07005630 @Override
Evan Millar633a1742009-04-02 16:36:33 -07005631 public int getDischargeStartLevel() {
The Android Open Source Project10592532009-03-18 17:39:46 -07005632 synchronized(this) {
Evan Millar633a1742009-04-02 16:36:33 -07005633 return getDischargeStartLevelLocked();
The Android Open Source Project10592532009-03-18 17:39:46 -07005634 }
5635 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005636
Evan Millar633a1742009-04-02 16:36:33 -07005637 public int getDischargeStartLevelLocked() {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005638 return mDischargeUnplugLevel;
The Android Open Source Project10592532009-03-18 17:39:46 -07005639 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005640
The Android Open Source Project10592532009-03-18 17:39:46 -07005641 @Override
Evan Millar633a1742009-04-02 16:36:33 -07005642 public int getDischargeCurrentLevel() {
The Android Open Source Project10592532009-03-18 17:39:46 -07005643 synchronized(this) {
Evan Millar633a1742009-04-02 16:36:33 -07005644 return getDischargeCurrentLevelLocked();
The Android Open Source Project10592532009-03-18 17:39:46 -07005645 }
5646 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005647
Evan Millar633a1742009-04-02 16:36:33 -07005648 public int getDischargeCurrentLevelLocked() {
Dianne Hackborne4a59512010-12-07 11:08:07 -08005649 return mDischargeCurrentLevel;
The Android Open Source Project10592532009-03-18 17:39:46 -07005650 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005651
Amith Yamasanie43530a2009-08-21 13:11:37 -07005652 @Override
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07005653 public int getLowDischargeAmountSinceCharge() {
5654 synchronized(this) {
Dianne Hackborne4a59512010-12-07 11:08:07 -08005655 int val = mLowDischargeAmountSinceCharge;
5656 if (mOnBattery && mDischargeCurrentLevel < mDischargeUnplugLevel) {
5657 val += mDischargeUnplugLevel-mDischargeCurrentLevel-1;
5658 }
5659 return val;
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07005660 }
5661 }
5662
5663 @Override
5664 public int getHighDischargeAmountSinceCharge() {
5665 synchronized(this) {
Dianne Hackborne4a59512010-12-07 11:08:07 -08005666 int val = mHighDischargeAmountSinceCharge;
5667 if (mOnBattery && mDischargeCurrentLevel < mDischargeUnplugLevel) {
5668 val += mDischargeUnplugLevel-mDischargeCurrentLevel;
5669 }
5670 return val;
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07005671 }
5672 }
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08005673
5674 public int getDischargeAmountScreenOn() {
5675 synchronized(this) {
5676 int val = mDischargeAmountScreenOn;
5677 if (mOnBattery && mScreenOn
5678 && mDischargeCurrentLevel < mDischargeScreenOnUnplugLevel) {
5679 val += mDischargeScreenOnUnplugLevel-mDischargeCurrentLevel;
5680 }
5681 return val;
5682 }
5683 }
5684
5685 public int getDischargeAmountScreenOnSinceCharge() {
5686 synchronized(this) {
5687 int val = mDischargeAmountScreenOnSinceCharge;
5688 if (mOnBattery && mScreenOn
5689 && mDischargeCurrentLevel < mDischargeScreenOnUnplugLevel) {
5690 val += mDischargeScreenOnUnplugLevel-mDischargeCurrentLevel;
5691 }
5692 return val;
5693 }
5694 }
5695
5696 public int getDischargeAmountScreenOff() {
5697 synchronized(this) {
5698 int val = mDischargeAmountScreenOff;
5699 if (mOnBattery && !mScreenOn
5700 && mDischargeCurrentLevel < mDischargeScreenOffUnplugLevel) {
5701 val += mDischargeScreenOffUnplugLevel-mDischargeCurrentLevel;
5702 }
5703 return val;
5704 }
5705 }
5706
5707 public int getDischargeAmountScreenOffSinceCharge() {
5708 synchronized(this) {
5709 int val = mDischargeAmountScreenOffSinceCharge;
5710 if (mOnBattery && !mScreenOn
5711 && mDischargeCurrentLevel < mDischargeScreenOffUnplugLevel) {
5712 val += mDischargeScreenOffUnplugLevel-mDischargeCurrentLevel;
5713 }
5714 return val;
5715 }
5716 }
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07005717
5718 @Override
Amith Yamasanie43530a2009-08-21 13:11:37 -07005719 public int getCpuSpeedSteps() {
5720 return sNumSpeedSteps;
5721 }
5722
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005723 /**
5724 * Retrieve the statistics object for a particular uid, creating if needed.
5725 */
5726 public Uid getUidStatsLocked(int uid) {
5727 Uid u = mUidStats.get(uid);
5728 if (u == null) {
5729 u = new Uid(uid);
5730 mUidStats.put(uid, u);
5731 }
5732 return u;
5733 }
5734
5735 /**
5736 * Remove the statistics object for a particular uid.
5737 */
5738 public void removeUidStatsLocked(int uid) {
5739 mUidStats.remove(uid);
5740 }
Amith Yamasani32dbefd2009-06-19 09:21:17 -07005741
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005742 /**
5743 * Retrieve the statistics object for a particular process, creating
5744 * if needed.
5745 */
5746 public Uid.Proc getProcessStatsLocked(int uid, String name) {
5747 Uid u = getUidStatsLocked(uid);
5748 return u.getProcessStatsLocked(name);
5749 }
5750
5751 /**
5752 * Retrieve the statistics object for a particular process, creating
5753 * if needed.
5754 */
5755 public Uid.Pkg getPackageStatsLocked(int uid, String pkg) {
5756 Uid u = getUidStatsLocked(uid);
5757 return u.getPackageStatsLocked(pkg);
5758 }
5759
5760 /**
5761 * Retrieve the statistics object for a particular service, creating
5762 * if needed.
5763 */
5764 public Uid.Pkg.Serv getServiceStatsLocked(int uid, String pkg, String name) {
5765 Uid u = getUidStatsLocked(uid);
5766 return u.getServiceStatsLocked(pkg, name);
5767 }
5768
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07005769 /**
5770 * Massage data to distribute any reasonable work down to more specific
5771 * owners. Must only be called on a dead BatteryStats object!
5772 */
5773 public void distributeWorkLocked(int which) {
5774 // Aggregate all CPU time associated with WIFI.
5775 Uid wifiUid = mUidStats.get(Process.WIFI_UID);
5776 if (wifiUid != null) {
5777 long uSecTime = computeBatteryRealtime(SystemClock.elapsedRealtime() * 1000, which);
5778 for (Uid.Proc proc : wifiUid.mProcessStats.values()) {
5779 long totalRunningTime = getGlobalWifiRunningTime(uSecTime, which);
5780 for (int i=0; i<mUidStats.size(); i++) {
5781 Uid uid = mUidStats.valueAt(i);
5782 if (uid.mUid != Process.WIFI_UID) {
5783 long uidRunningTime = uid.getWifiRunningTime(uSecTime, which);
5784 if (uidRunningTime > 0) {
5785 Uid.Proc uidProc = uid.getProcessStatsLocked("*wifi*");
5786 long time = proc.getUserTime(which);
5787 time = (time*uidRunningTime)/totalRunningTime;
5788 uidProc.mUserTime += time;
5789 proc.mUserTime -= time;
5790 time = proc.getSystemTime(which);
5791 time = (time*uidRunningTime)/totalRunningTime;
5792 uidProc.mSystemTime += time;
5793 proc.mSystemTime -= time;
5794 time = proc.getForegroundTime(which);
5795 time = (time*uidRunningTime)/totalRunningTime;
5796 uidProc.mForegroundTime += time;
5797 proc.mForegroundTime -= time;
5798 for (int sb=0; sb<proc.mSpeedBins.length; sb++) {
5799 SamplingCounter sc = proc.mSpeedBins[sb];
5800 if (sc != null) {
5801 time = sc.getCountLocked(which);
5802 time = (time*uidRunningTime)/totalRunningTime;
5803 SamplingCounter uidSc = uidProc.mSpeedBins[sb];
5804 if (uidSc == null) {
5805 uidSc = new SamplingCounter(mUnpluggables);
5806 uidProc.mSpeedBins[sb] = uidSc;
5807 }
5808 uidSc.mCount.addAndGet((int)time);
5809 sc.mCount.addAndGet((int)-time);
5810 }
5811 }
5812 totalRunningTime -= uidRunningTime;
5813 }
5814 }
5815 }
5816 }
5817 }
5818 }
5819
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005820 public void shutdownLocked() {
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005821 writeSyncLocked();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005822 mShuttingDown = true;
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005823 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005824
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005825 Parcel mPendingWrite = null;
5826 final ReentrantLock mWriteLock = new ReentrantLock();
5827
5828 public void writeAsyncLocked() {
5829 writeLocked(false);
5830 }
5831
5832 public void writeSyncLocked() {
5833 writeLocked(true);
5834 }
5835
5836 void writeLocked(boolean sync) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005837 if (mFile == null) {
5838 Slog.w("BatteryStats", "writeLocked: no file associated with this instance");
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005839 return;
5840 }
5841
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07005842 if (mShuttingDown) {
5843 return;
5844 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005845
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005846 Parcel out = Parcel.obtain();
5847 writeSummaryToParcel(out);
5848 mLastWriteTime = SystemClock.elapsedRealtime();
5849
5850 if (mPendingWrite != null) {
5851 mPendingWrite.recycle();
5852 }
5853 mPendingWrite = out;
5854
5855 if (sync) {
5856 commitPendingDataToDisk();
5857 } else {
5858 Thread thr = new Thread("BatteryStats-Write") {
5859 @Override
5860 public void run() {
5861 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
5862 commitPendingDataToDisk();
5863 }
5864 };
5865 thr.start();
5866 }
5867 }
5868
5869 public void commitPendingDataToDisk() {
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07005870 final Parcel next;
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005871 synchronized (this) {
5872 next = mPendingWrite;
5873 mPendingWrite = null;
Dianne Hackbornf47d8f22010-10-08 10:46:55 -07005874 if (next == null) {
5875 return;
5876 }
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005877
5878 mWriteLock.lock();
5879 }
5880
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005881 try {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005882 FileOutputStream stream = new FileOutputStream(mFile.chooseForWrite());
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005883 stream.write(next.marshall());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005884 stream.flush();
Dianne Hackborn8bdf5932010-10-15 12:54:40 -07005885 FileUtils.sync(stream);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005886 stream.close();
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005887 mFile.commit();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005888 } catch (IOException e) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005889 Slog.w("BatteryStats", "Error writing battery statistics", e);
Dianne Hackbornce2ef762010-09-20 11:39:14 -07005890 mFile.rollback();
5891 } finally {
5892 next.recycle();
5893 mWriteLock.unlock();
Suchi Amalapurapu8550f252009-09-29 15:20:32 -07005894 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005895 }
5896
5897 static byte[] readFully(FileInputStream stream) throws java.io.IOException {
5898 int pos = 0;
5899 int avail = stream.available();
5900 byte[] data = new byte[avail];
5901 while (true) {
5902 int amt = stream.read(data, pos, data.length-pos);
5903 //Log.i("foo", "Read " + amt + " bytes at " + pos
5904 // + " of avail " + data.length);
5905 if (amt <= 0) {
5906 //Log.i("foo", "**** FINISHED READING: pos=" + pos
5907 // + " len=" + data.length);
5908 return data;
5909 }
5910 pos += amt;
5911 avail = stream.available();
5912 if (avail > data.length-pos) {
5913 byte[] newData = new byte[pos+avail];
5914 System.arraycopy(data, 0, newData, 0, pos);
5915 data = newData;
5916 }
5917 }
5918 }
5919
5920 public void readLocked() {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005921 if (mFile == null) {
5922 Slog.w("BatteryStats", "readLocked: no file associated with this instance");
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005923 return;
5924 }
5925
5926 mUidStats.clear();
5927
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005928 try {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005929 File file = mFile.chooseForRead();
5930 if (!file.exists()) {
5931 return;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005932 }
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005933 FileInputStream stream = new FileInputStream(file);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005934
5935 byte[] raw = readFully(stream);
5936 Parcel in = Parcel.obtain();
5937 in.unmarshall(raw, 0, raw.length);
5938 in.setDataPosition(0);
5939 stream.close();
5940
5941 readSummaryFromParcel(in);
5942 } catch(java.io.IOException e) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07005943 Slog.e("BatteryStats", "Error reading battery statistics", e);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005944 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005945
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005946 long now = SystemClock.elapsedRealtime();
Dianne Hackborne8c88e62011-08-17 19:09:09 -07005947 if (USE_OLD_HISTORY) {
5948 addHistoryRecordLocked(now, HistoryItem.CMD_START);
5949 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005950 addHistoryBufferLocked(now, HistoryItem.CMD_START);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08005951 }
5952
5953 public int describeContents() {
5954 return 0;
5955 }
5956
Dianne Hackbornae384452011-06-28 12:33:48 -07005957 void readHistory(Parcel in, boolean andOldHistory) {
5958 final long historyBaseTime = in.readLong();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005959
5960 mHistoryBuffer.setDataSize(0);
5961 mHistoryBuffer.setDataPosition(0);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005962 mHistoryTagPool.clear();
5963 mNextHistoryTagIdx = 0;
5964 mNumHistoryTagChars = 0;
Dianne Hackborn099bc622014-01-22 13:39:16 -08005965
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005966 int numTags = in.readInt();
5967 for (int i=0; i<numTags; i++) {
Dianne Hackborn099bc622014-01-22 13:39:16 -08005968 int idx = in.readInt();
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005969 String str = in.readString();
5970 int uid = in.readInt();
5971 HistoryTag tag = new HistoryTag();
5972 tag.string = str;
5973 tag.uid = uid;
5974 tag.poolIdx = idx;
5975 mHistoryTagPool.put(tag, idx);
5976 if (idx >= mNextHistoryTagIdx) {
5977 mNextHistoryTagIdx = idx+1;
Dianne Hackborn099bc622014-01-22 13:39:16 -08005978 }
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08005979 mNumHistoryTagChars += tag.string.length() + 1;
Dianne Hackborn099bc622014-01-22 13:39:16 -08005980 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07005981
5982 int bufSize = in.readInt();
5983 int curPos = in.dataPosition();
5984 if (bufSize >= (MAX_MAX_HISTORY_BUFFER*3)) {
5985 Slog.w(TAG, "File corrupt: history data buffer too large " + bufSize);
5986 } else if ((bufSize&~3) != bufSize) {
5987 Slog.w(TAG, "File corrupt: history data buffer not aligned " + bufSize);
5988 } else {
5989 if (DEBUG_HISTORY) Slog.i(TAG, "***************** READING NEW HISTORY: " + bufSize
5990 + " bytes at " + curPos);
5991 mHistoryBuffer.appendFrom(in, curPos, bufSize);
5992 in.setDataPosition(curPos + bufSize);
Dianne Hackborn32907cf2010-06-10 17:50:20 -07005993 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07005994
Dianne Hackbornae384452011-06-28 12:33:48 -07005995 if (andOldHistory) {
5996 readOldHistory(in);
5997 }
5998
5999 if (DEBUG_HISTORY) {
6000 StringBuilder sb = new StringBuilder(128);
6001 sb.append("****************** OLD mHistoryBaseTime: ");
6002 TimeUtils.formatDuration(mHistoryBaseTime, sb);
6003 Slog.i(TAG, sb.toString());
6004 }
6005 mHistoryBaseTime = historyBaseTime;
6006 if (DEBUG_HISTORY) {
6007 StringBuilder sb = new StringBuilder(128);
6008 sb.append("****************** NEW mHistoryBaseTime: ");
6009 TimeUtils.formatDuration(mHistoryBaseTime, sb);
6010 Slog.i(TAG, sb.toString());
6011 }
6012
6013 // We are just arbitrarily going to insert 1 minute from the sample of
6014 // the last run until samples in this run.
6015 if (mHistoryBaseTime > 0) {
6016 long oldnow = SystemClock.elapsedRealtime();
6017 mHistoryBaseTime = (mHistoryBaseTime - oldnow) + 60*1000;
6018 if (DEBUG_HISTORY) {
6019 StringBuilder sb = new StringBuilder(128);
6020 sb.append("****************** ADJUSTED mHistoryBaseTime: ");
6021 TimeUtils.formatDuration(mHistoryBaseTime, sb);
6022 Slog.i(TAG, sb.toString());
6023 }
Dianne Hackborn1e4b9f32010-06-23 14:10:57 -07006024 }
Dianne Hackborn32907cf2010-06-10 17:50:20 -07006025 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006026
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006027 void readOldHistory(Parcel in) {
Dianne Hackborne8c88e62011-08-17 19:09:09 -07006028 if (!USE_OLD_HISTORY) {
6029 return;
6030 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006031 mHistory = mHistoryEnd = mHistoryCache = null;
6032 long time;
Conley Owens5e3357f2011-05-02 09:59:30 -07006033 while (in.dataAvail() > 0 && (time=in.readLong()) >= 0) {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006034 HistoryItem rec = new HistoryItem(time, in);
6035 addHistoryRecordLocked(rec);
6036 }
6037 }
6038
Dianne Hackbornae384452011-06-28 12:33:48 -07006039 void writeHistory(Parcel out, boolean andOldHistory) {
6040 if (DEBUG_HISTORY) {
6041 StringBuilder sb = new StringBuilder(128);
6042 sb.append("****************** WRITING mHistoryBaseTime: ");
6043 TimeUtils.formatDuration(mHistoryBaseTime, sb);
6044 sb.append(" mLastHistoryTime: ");
6045 TimeUtils.formatDuration(mLastHistoryTime, sb);
6046 Slog.i(TAG, sb.toString());
6047 }
6048 out.writeLong(mHistoryBaseTime + mLastHistoryTime);
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08006049 out.writeInt(mHistoryTagPool.size());
6050 for (HashMap.Entry<HistoryTag, Integer> ent : mHistoryTagPool.entrySet()) {
6051 HistoryTag tag = ent.getKey();
Dianne Hackborn099bc622014-01-22 13:39:16 -08006052 out.writeInt(ent.getValue());
Dianne Hackborn71fc13e2014-02-03 10:50:53 -08006053 out.writeString(tag.string);
6054 out.writeInt(tag.uid);
Dianne Hackborn099bc622014-01-22 13:39:16 -08006055 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006056 out.writeInt(mHistoryBuffer.dataSize());
6057 if (DEBUG_HISTORY) Slog.i(TAG, "***************** WRITING HISTORY: "
6058 + mHistoryBuffer.dataSize() + " bytes at " + out.dataPosition());
6059 out.appendFrom(mHistoryBuffer, 0, mHistoryBuffer.dataSize());
Dianne Hackbornae384452011-06-28 12:33:48 -07006060
6061 if (andOldHistory) {
6062 writeOldHistory(out);
6063 }
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006064 }
6065
6066 void writeOldHistory(Parcel out) {
Dianne Hackborne8c88e62011-08-17 19:09:09 -07006067 if (!USE_OLD_HISTORY) {
6068 return;
6069 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006070 HistoryItem rec = mHistory;
Dianne Hackborn32907cf2010-06-10 17:50:20 -07006071 while (rec != null) {
6072 if (rec.time >= 0) rec.writeToParcel(out, 0);
6073 rec = rec.next;
6074 }
6075 out.writeLong(-1);
6076 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006077
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006078 private void readSummaryFromParcel(Parcel in) {
6079 final int version = in.readInt();
6080 if (version != VERSION) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006081 Slog.w("BatteryStats", "readFromParcel: version got " + version
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006082 + ", expected " + VERSION + "; erasing old stats");
6083 return;
6084 }
6085
Dianne Hackbornae384452011-06-28 12:33:48 -07006086 readHistory(in, true);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006087
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006088 mStartCount = in.readInt();
6089 mBatteryUptime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006090 mBatteryRealtime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006091 mUptime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006092 mRealtime = in.readLong();
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08006093 mStartClockTime = in.readLong();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006094 mDischargeUnplugLevel = in.readInt();
Evan Millar633a1742009-04-02 16:36:33 -07006095 mDischargeCurrentLevel = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006096 mLowDischargeAmountSinceCharge = in.readInt();
6097 mHighDischargeAmountSinceCharge = in.readInt();
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08006098 mDischargeAmountScreenOnSinceCharge = in.readInt();
6099 mDischargeAmountScreenOffSinceCharge = in.readInt();
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006100
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006101 mStartCount++;
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006102
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006103 mScreenOn = false;
6104 mScreenOnTimer.readSummaryFromParcelLocked(in);
Dianne Hackborn617f8772009-03-31 15:04:46 -07006105 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
6106 mScreenBrightnessTimer[i].readSummaryFromParcelLocked(in);
6107 }
6108 mInputEventCounter.readSummaryFromParcelLocked(in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006109 mPhoneOn = false;
6110 mPhoneOnTimer.readSummaryFromParcelLocked(in);
Wink Saville52840902011-02-18 12:40:47 -08006111 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn627bba72009-03-24 22:32:56 -07006112 mPhoneSignalStrengthsTimer[i].readSummaryFromParcelLocked(in);
6113 }
Amith Yamasanif37447b2009-10-08 18:28:01 -07006114 mPhoneSignalScanningTimer.readSummaryFromParcelLocked(in);
Dianne Hackborn627bba72009-03-24 22:32:56 -07006115 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
6116 mPhoneDataConnectionsTimer[i].readSummaryFromParcelLocked(in);
6117 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006118 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006119 mNetworkByteActivityCounters[i].readSummaryFromParcelLocked(in);
6120 mNetworkPacketActivityCounters[i].readSummaryFromParcelLocked(in);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006121 }
The Android Open Source Project10592532009-03-18 17:39:46 -07006122 mWifiOn = false;
6123 mWifiOnTimer.readSummaryFromParcelLocked(in);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006124 mGlobalWifiRunning = false;
6125 mGlobalWifiRunningTimer.readSummaryFromParcelLocked(in);
The Android Open Source Project10592532009-03-18 17:39:46 -07006126 mBluetoothOn = false;
6127 mBluetoothOnTimer.readSummaryFromParcelLocked(in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006128
Evan Millarc64edde2009-04-18 12:26:32 -07006129 int NKW = in.readInt();
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006130 if (NKW > 10000) {
6131 Slog.w(TAG, "File corrupt: too many kernel wake locks " + NKW);
6132 return;
6133 }
Evan Millarc64edde2009-04-18 12:26:32 -07006134 for (int ikw = 0; ikw < NKW; ikw++) {
6135 if (in.readInt() != 0) {
6136 String kwltName = in.readString();
6137 getKernelWakelockTimerLocked(kwltName).readSummaryFromParcelLocked(in);
6138 }
6139 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07006140
6141 sNumSpeedSteps = in.readInt();
6142
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006143 final int NU = in.readInt();
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006144 if (NU > 10000) {
6145 Slog.w(TAG, "File corrupt: too many uids " + NU);
6146 return;
6147 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006148 for (int iu = 0; iu < NU; iu++) {
6149 int uid = in.readInt();
6150 Uid u = new Uid(uid);
6151 mUidStats.put(uid, u);
6152
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006153 u.mWifiRunning = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006154 if (in.readInt() != 0) {
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006155 u.mWifiRunningTimer.readSummaryFromParcelLocked(in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006156 }
The Android Open Source Project10592532009-03-18 17:39:46 -07006157 u.mFullWifiLockOut = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006158 if (in.readInt() != 0) {
6159 u.mFullWifiLockTimer.readSummaryFromParcelLocked(in);
6160 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07006161 u.mWifiScanStarted = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006162 if (in.readInt() != 0) {
Nick Pelly6ccaa542012-06-15 15:22:47 -07006163 u.mWifiScanTimer.readSummaryFromParcelLocked(in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006164 }
Robert Greenwalta029ea12013-09-25 16:38:12 -07006165 u.mWifiBatchedScanBinStarted = Uid.NO_BATCHED_SCAN_STARTED;
6166 for (int i = 0; i < Uid.NUM_WIFI_BATCHED_SCAN_BINS; i++) {
6167 if (in.readInt() != 0) {
6168 u.makeWifiBatchedScanBin(i, null);
6169 u.mWifiBatchedScanTimer[i].readSummaryFromParcelLocked(in);
6170 }
6171 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07006172 u.mWifiMulticastEnabled = false;
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006173 if (in.readInt() != 0) {
6174 u.mWifiMulticastTimer.readSummaryFromParcelLocked(in);
6175 }
6176 u.mAudioTurnedOn = false;
6177 if (in.readInt() != 0) {
Dianne Hackborna06de0f2012-12-11 16:34:47 -08006178 u.createAudioTurnedOnTimerLocked().readSummaryFromParcelLocked(in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006179 }
6180 u.mVideoTurnedOn = false;
6181 if (in.readInt() != 0) {
Dianne Hackborna06de0f2012-12-11 16:34:47 -08006182 u.createVideoTurnedOnTimerLocked().readSummaryFromParcelLocked(in);
6183 }
6184 if (in.readInt() != 0) {
Jeff Sharkey3e013e82013-04-25 14:48:19 -07006185 u.createForegroundActivityTimerLocked().readSummaryFromParcelLocked(in);
6186 }
6187 if (in.readInt() != 0) {
Dianne Hackborna06de0f2012-12-11 16:34:47 -08006188 u.createVibratorOnTimerLocked().readSummaryFromParcelLocked(in);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006189 }
Robert Greenwalt5347bd42009-05-13 15:10:16 -07006190
Dianne Hackborn617f8772009-03-31 15:04:46 -07006191 if (in.readInt() != 0) {
6192 if (u.mUserActivityCounters == null) {
6193 u.initUserActivityLocked();
6194 }
6195 for (int i=0; i<Uid.NUM_USER_ACTIVITY_TYPES; i++) {
6196 u.mUserActivityCounters[i].readSummaryFromParcelLocked(in);
6197 }
6198 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006199
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006200 if (in.readInt() != 0) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006201 if (u.mNetworkByteActivityCounters == null) {
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006202 u.initNetworkActivityLocked();
6203 }
6204 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006205 u.mNetworkByteActivityCounters[i].readSummaryFromParcelLocked(in);
6206 u.mNetworkPacketActivityCounters[i].readSummaryFromParcelLocked(in);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006207 }
6208 }
6209
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006210 int NW = in.readInt();
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08006211 if (NW > 100) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006212 Slog.w(TAG, "File corrupt: too many wake locks " + NW);
6213 return;
6214 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006215 for (int iw = 0; iw < NW; iw++) {
6216 String wlName = in.readString();
6217 if (in.readInt() != 0) {
6218 u.getWakeTimerLocked(wlName, WAKE_TYPE_FULL).readSummaryFromParcelLocked(in);
6219 }
6220 if (in.readInt() != 0) {
6221 u.getWakeTimerLocked(wlName, WAKE_TYPE_PARTIAL).readSummaryFromParcelLocked(in);
6222 }
6223 if (in.readInt() != 0) {
6224 u.getWakeTimerLocked(wlName, WAKE_TYPE_WINDOW).readSummaryFromParcelLocked(in);
6225 }
6226 }
6227
6228 int NP = in.readInt();
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08006229 if (NP > 1000) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006230 Slog.w(TAG, "File corrupt: too many sensors " + NP);
6231 return;
6232 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006233 for (int is = 0; is < NP; is++) {
6234 int seNumber = in.readInt();
6235 if (in.readInt() != 0) {
6236 u.getSensorTimerLocked(seNumber, true)
6237 .readSummaryFromParcelLocked(in);
6238 }
6239 }
6240
6241 NP = in.readInt();
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08006242 if (NP > 1000) {
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006243 Slog.w(TAG, "File corrupt: too many processes " + NP);
6244 return;
6245 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006246 for (int ip = 0; ip < NP; ip++) {
6247 String procName = in.readString();
6248 Uid.Proc p = u.getProcessStatsLocked(procName);
6249 p.mUserTime = p.mLoadedUserTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006250 p.mSystemTime = p.mLoadedSystemTime = in.readLong();
Jeff Sharkey3e013e82013-04-25 14:48:19 -07006251 p.mForegroundTime = p.mLoadedForegroundTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006252 p.mStarts = p.mLoadedStarts = in.readInt();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006253 int NSB = in.readInt();
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08006254 if (NSB > 100) {
6255 Slog.w(TAG, "File corrupt: too many speed bins " + NSB);
6256 return;
6257 }
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006258 p.mSpeedBins = new SamplingCounter[NSB];
6259 for (int i=0; i<NSB; i++) {
6260 if (in.readInt() != 0) {
6261 p.mSpeedBins[i] = new SamplingCounter(mUnpluggables);
6262 p.mSpeedBins[i].readSummaryFromParcelLocked(in);
6263 }
6264 }
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08006265 if (!p.readExcessivePowerFromParcelLocked(in)) {
6266 return;
6267 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006268 }
6269
6270 NP = in.readInt();
Dianne Hackborn1afd1c92010-03-18 22:47:17 -07006271 if (NP > 10000) {
6272 Slog.w(TAG, "File corrupt: too many packages " + NP);
6273 return;
6274 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006275 for (int ip = 0; ip < NP; ip++) {
6276 String pkgName = in.readString();
6277 Uid.Pkg p = u.getPackageStatsLocked(pkgName);
6278 p.mWakeups = p.mLoadedWakeups = in.readInt();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006279 final int NS = in.readInt();
Dianne Hackborn7b9c56f2010-12-07 11:14:53 -08006280 if (NS > 1000) {
6281 Slog.w(TAG, "File corrupt: too many services " + NS);
6282 return;
6283 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006284 for (int is = 0; is < NS; is++) {
6285 String servName = in.readString();
6286 Uid.Pkg.Serv s = u.getServiceStatsLocked(pkgName, servName);
6287 s.mStartTime = s.mLoadedStartTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006288 s.mStarts = s.mLoadedStarts = in.readInt();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006289 s.mLaunches = s.mLoadedLaunches = in.readInt();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006290 }
6291 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006292 }
6293 }
6294
6295 /**
6296 * Writes a summary of the statistics to a Parcel, in a format suitable to be written to
6297 * disk. This format does not allow a lossless round-trip.
6298 *
6299 * @param out the Parcel to be written to.
6300 */
6301 public void writeSummaryToParcel(Parcel out) {
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08006302 pullPendingStateUpdatesLocked();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006303
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006304 final long NOW_SYS = SystemClock.uptimeMillis() * 1000;
6305 final long NOWREAL_SYS = SystemClock.elapsedRealtime() * 1000;
6306 final long NOW = getBatteryUptimeLocked(NOW_SYS);
6307 final long NOWREAL = getBatteryRealtimeLocked(NOWREAL_SYS);
6308
6309 out.writeInt(VERSION);
6310
Dianne Hackbornae384452011-06-28 12:33:48 -07006311 writeHistory(out, true);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006312
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006313 out.writeInt(mStartCount);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006314 out.writeLong(computeBatteryUptime(NOW_SYS, STATS_SINCE_CHARGED));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006315 out.writeLong(computeBatteryRealtime(NOWREAL_SYS, STATS_SINCE_CHARGED));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006316 out.writeLong(computeUptime(NOW_SYS, STATS_SINCE_CHARGED));
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006317 out.writeLong(computeRealtime(NOWREAL_SYS, STATS_SINCE_CHARGED));
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08006318 out.writeLong(mStartClockTime);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006319 out.writeInt(mDischargeUnplugLevel);
Evan Millar633a1742009-04-02 16:36:33 -07006320 out.writeInt(mDischargeCurrentLevel);
Dianne Hackborne4a59512010-12-07 11:08:07 -08006321 out.writeInt(getLowDischargeAmountSinceCharge());
6322 out.writeInt(getHighDischargeAmountSinceCharge());
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08006323 out.writeInt(getDischargeAmountScreenOnSinceCharge());
6324 out.writeInt(getDischargeAmountScreenOffSinceCharge());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006325
6326 mScreenOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
Dianne Hackborn617f8772009-03-31 15:04:46 -07006327 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
6328 mScreenBrightnessTimer[i].writeSummaryFromParcelLocked(out, NOWREAL);
6329 }
6330 mInputEventCounter.writeSummaryFromParcelLocked(out);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006331 mPhoneOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
Wink Saville52840902011-02-18 12:40:47 -08006332 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn627bba72009-03-24 22:32:56 -07006333 mPhoneSignalStrengthsTimer[i].writeSummaryFromParcelLocked(out, NOWREAL);
6334 }
Amith Yamasanif37447b2009-10-08 18:28:01 -07006335 mPhoneSignalScanningTimer.writeSummaryFromParcelLocked(out, NOWREAL);
Dianne Hackborn627bba72009-03-24 22:32:56 -07006336 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
6337 mPhoneDataConnectionsTimer[i].writeSummaryFromParcelLocked(out, NOWREAL);
6338 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006339 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006340 mNetworkByteActivityCounters[i].writeSummaryFromParcelLocked(out);
6341 mNetworkPacketActivityCounters[i].writeSummaryFromParcelLocked(out);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006342 }
The Android Open Source Project10592532009-03-18 17:39:46 -07006343 mWifiOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006344 mGlobalWifiRunningTimer.writeSummaryFromParcelLocked(out, NOWREAL);
The Android Open Source Project10592532009-03-18 17:39:46 -07006345 mBluetoothOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006346
Evan Millarc64edde2009-04-18 12:26:32 -07006347 out.writeInt(mKernelWakelockStats.size());
6348 for (Map.Entry<String, SamplingTimer> ent : mKernelWakelockStats.entrySet()) {
6349 Timer kwlt = ent.getValue();
6350 if (kwlt != null) {
6351 out.writeInt(1);
6352 out.writeString(ent.getKey());
6353 ent.getValue().writeSummaryFromParcelLocked(out, NOWREAL);
6354 } else {
6355 out.writeInt(0);
6356 }
6357 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006358
Amith Yamasanie43530a2009-08-21 13:11:37 -07006359 out.writeInt(sNumSpeedSteps);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006360 final int NU = mUidStats.size();
6361 out.writeInt(NU);
6362 for (int iu = 0; iu < NU; iu++) {
6363 out.writeInt(mUidStats.keyAt(iu));
6364 Uid u = mUidStats.valueAt(iu);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006365
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006366 if (u.mWifiRunningTimer != null) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006367 out.writeInt(1);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006368 u.mWifiRunningTimer.writeSummaryFromParcelLocked(out, NOWREAL);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006369 } else {
6370 out.writeInt(0);
6371 }
6372 if (u.mFullWifiLockTimer != null) {
6373 out.writeInt(1);
6374 u.mFullWifiLockTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6375 } else {
6376 out.writeInt(0);
6377 }
Nick Pelly6ccaa542012-06-15 15:22:47 -07006378 if (u.mWifiScanTimer != null) {
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006379 out.writeInt(1);
Nick Pelly6ccaa542012-06-15 15:22:47 -07006380 u.mWifiScanTimer.writeSummaryFromParcelLocked(out, NOWREAL);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006381 } else {
6382 out.writeInt(0);
6383 }
Robert Greenwalta029ea12013-09-25 16:38:12 -07006384 for (int i = 0; i < Uid.NUM_WIFI_BATCHED_SCAN_BINS; i++) {
6385 if (u.mWifiBatchedScanTimer[i] != null) {
6386 out.writeInt(1);
6387 u.mWifiBatchedScanTimer[i].writeSummaryFromParcelLocked(out, NOWREAL);
6388 } else {
6389 out.writeInt(0);
6390 }
6391 }
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006392 if (u.mWifiMulticastTimer != null) {
6393 out.writeInt(1);
6394 u.mWifiMulticastTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6395 } else {
6396 out.writeInt(0);
6397 }
6398 if (u.mAudioTurnedOnTimer != null) {
6399 out.writeInt(1);
6400 u.mAudioTurnedOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6401 } else {
6402 out.writeInt(0);
6403 }
6404 if (u.mVideoTurnedOnTimer != null) {
6405 out.writeInt(1);
6406 u.mVideoTurnedOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6407 } else {
6408 out.writeInt(0);
6409 }
Jeff Sharkey3e013e82013-04-25 14:48:19 -07006410 if (u.mForegroundActivityTimer != null) {
6411 out.writeInt(1);
6412 u.mForegroundActivityTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6413 } else {
6414 out.writeInt(0);
6415 }
Dianne Hackborna06de0f2012-12-11 16:34:47 -08006416 if (u.mVibratorOnTimer != null) {
6417 out.writeInt(1);
6418 u.mVibratorOnTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6419 } else {
6420 out.writeInt(0);
6421 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006422
Dianne Hackborn617f8772009-03-31 15:04:46 -07006423 if (u.mUserActivityCounters == null) {
6424 out.writeInt(0);
6425 } else {
6426 out.writeInt(1);
6427 for (int i=0; i<Uid.NUM_USER_ACTIVITY_TYPES; i++) {
6428 u.mUserActivityCounters[i].writeSummaryFromParcelLocked(out);
6429 }
6430 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006431
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006432 if (u.mNetworkByteActivityCounters == null) {
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006433 out.writeInt(0);
6434 } else {
6435 out.writeInt(1);
6436 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006437 u.mNetworkByteActivityCounters[i].writeSummaryFromParcelLocked(out);
6438 u.mNetworkPacketActivityCounters[i].writeSummaryFromParcelLocked(out);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006439 }
6440 }
6441
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006442 int NW = u.mWakelockStats.size();
6443 out.writeInt(NW);
6444 if (NW > 0) {
6445 for (Map.Entry<String, BatteryStatsImpl.Uid.Wakelock> ent
6446 : u.mWakelockStats.entrySet()) {
6447 out.writeString(ent.getKey());
6448 Uid.Wakelock wl = ent.getValue();
6449 if (wl.mTimerFull != null) {
6450 out.writeInt(1);
6451 wl.mTimerFull.writeSummaryFromParcelLocked(out, NOWREAL);
6452 } else {
6453 out.writeInt(0);
6454 }
6455 if (wl.mTimerPartial != null) {
6456 out.writeInt(1);
6457 wl.mTimerPartial.writeSummaryFromParcelLocked(out, NOWREAL);
6458 } else {
6459 out.writeInt(0);
6460 }
6461 if (wl.mTimerWindow != null) {
6462 out.writeInt(1);
6463 wl.mTimerWindow.writeSummaryFromParcelLocked(out, NOWREAL);
6464 } else {
6465 out.writeInt(0);
6466 }
6467 }
6468 }
6469
6470 int NSE = u.mSensorStats.size();
6471 out.writeInt(NSE);
6472 if (NSE > 0) {
6473 for (Map.Entry<Integer, BatteryStatsImpl.Uid.Sensor> ent
6474 : u.mSensorStats.entrySet()) {
6475 out.writeInt(ent.getKey());
6476 Uid.Sensor se = ent.getValue();
6477 if (se.mTimer != null) {
6478 out.writeInt(1);
6479 se.mTimer.writeSummaryFromParcelLocked(out, NOWREAL);
6480 } else {
6481 out.writeInt(0);
6482 }
6483 }
6484 }
6485
6486 int NP = u.mProcessStats.size();
6487 out.writeInt(NP);
6488 if (NP > 0) {
6489 for (Map.Entry<String, BatteryStatsImpl.Uid.Proc> ent
6490 : u.mProcessStats.entrySet()) {
6491 out.writeString(ent.getKey());
6492 Uid.Proc ps = ent.getValue();
6493 out.writeLong(ps.mUserTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006494 out.writeLong(ps.mSystemTime);
Jeff Sharkey3e013e82013-04-25 14:48:19 -07006495 out.writeLong(ps.mForegroundTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006496 out.writeInt(ps.mStarts);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006497 final int N = ps.mSpeedBins.length;
6498 out.writeInt(N);
6499 for (int i=0; i<N; i++) {
6500 if (ps.mSpeedBins[i] != null) {
6501 out.writeInt(1);
6502 ps.mSpeedBins[i].writeSummaryFromParcelLocked(out);
6503 } else {
6504 out.writeInt(0);
6505 }
6506 }
Dianne Hackborn287952c2010-09-22 22:34:31 -07006507 ps.writeExcessivePowerToParcelLocked(out);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006508 }
6509 }
6510
6511 NP = u.mPackageStats.size();
6512 out.writeInt(NP);
6513 if (NP > 0) {
6514 for (Map.Entry<String, BatteryStatsImpl.Uid.Pkg> ent
6515 : u.mPackageStats.entrySet()) {
6516 out.writeString(ent.getKey());
6517 Uid.Pkg ps = ent.getValue();
6518 out.writeInt(ps.mWakeups);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006519 final int NS = ps.mServiceStats.size();
6520 out.writeInt(NS);
6521 if (NS > 0) {
6522 for (Map.Entry<String, BatteryStatsImpl.Uid.Pkg.Serv> sent
6523 : ps.mServiceStats.entrySet()) {
6524 out.writeString(sent.getKey());
6525 BatteryStatsImpl.Uid.Pkg.Serv ss = sent.getValue();
6526 long time = ss.getStartTimeToNowLocked(NOW);
6527 out.writeLong(time);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006528 out.writeInt(ss.mStarts);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006529 out.writeInt(ss.mLaunches);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006530 }
6531 }
6532 }
6533 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006534 }
6535 }
6536
6537 public void readFromParcel(Parcel in) {
6538 readFromParcelLocked(in);
6539 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006540
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006541 void readFromParcelLocked(Parcel in) {
6542 int magic = in.readInt();
6543 if (magic != MAGIC) {
6544 throw new ParcelFormatException("Bad magic number");
6545 }
6546
Dianne Hackbornae384452011-06-28 12:33:48 -07006547 readHistory(in, false);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006548
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006549 mStartCount = in.readInt();
6550 mBatteryUptime = in.readLong();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006551 mBatteryLastUptime = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006552 mBatteryRealtime = in.readLong();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006553 mBatteryLastRealtime = 0;
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08006554 mStartClockTime = in.readLong();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006555 mScreenOn = false;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006556 mScreenOnTimer = new StopwatchTimer(null, -1, null, mUnpluggables, in);
Dianne Hackborn617f8772009-03-31 15:04:46 -07006557 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006558 mScreenBrightnessTimer[i] = new StopwatchTimer(null, -100-i,
6559 null, mUnpluggables, in);
Dianne Hackborn617f8772009-03-31 15:04:46 -07006560 }
6561 mInputEventCounter = new Counter(mUnpluggables, in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006562 mPhoneOn = false;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006563 mPhoneOnTimer = new StopwatchTimer(null, -2, null, mUnpluggables, in);
Wink Saville52840902011-02-18 12:40:47 -08006564 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006565 mPhoneSignalStrengthsTimer[i] = new StopwatchTimer(null, -200-i,
6566 null, mUnpluggables, in);
Dianne Hackborn627bba72009-03-24 22:32:56 -07006567 }
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006568 mPhoneSignalScanningTimer = new StopwatchTimer(null, -200+1, null, mUnpluggables, in);
Dianne Hackborn627bba72009-03-24 22:32:56 -07006569 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006570 mPhoneDataConnectionsTimer[i] = new StopwatchTimer(null, -300-i,
6571 null, mUnpluggables, in);
Dianne Hackborn627bba72009-03-24 22:32:56 -07006572 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006573 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006574 mNetworkByteActivityCounters[i] = new LongSamplingCounter(mUnpluggables, in);
6575 mNetworkPacketActivityCounters[i] = new LongSamplingCounter(mUnpluggables, in);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006576 }
The Android Open Source Project10592532009-03-18 17:39:46 -07006577 mWifiOn = false;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006578 mWifiOnTimer = new StopwatchTimer(null, -2, null, mUnpluggables, in);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006579 mGlobalWifiRunning = false;
6580 mGlobalWifiRunningTimer = new StopwatchTimer(null, -2, null, mUnpluggables, in);
The Android Open Source Project10592532009-03-18 17:39:46 -07006581 mBluetoothOn = false;
Dianne Hackborn0d903a82010-09-07 23:51:03 -07006582 mBluetoothOnTimer = new StopwatchTimer(null, -2, null, mUnpluggables, in);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006583 mUptime = in.readLong();
6584 mUptimeStart = in.readLong();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006585 mLastUptime = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006586 mRealtime = in.readLong();
6587 mRealtimeStart = in.readLong();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006588 mLastRealtime = 0;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006589 mOnBattery = in.readInt() != 0;
6590 mOnBatteryInternal = false; // we are no longer really running.
6591 mTrackBatteryPastUptime = in.readLong();
6592 mTrackBatteryUptimeStart = in.readLong();
6593 mTrackBatteryPastRealtime = in.readLong();
6594 mTrackBatteryRealtimeStart = in.readLong();
6595 mUnpluggedBatteryUptime = in.readLong();
6596 mUnpluggedBatteryRealtime = in.readLong();
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006597 mDischargeUnplugLevel = in.readInt();
Evan Millar633a1742009-04-02 16:36:33 -07006598 mDischargeCurrentLevel = in.readInt();
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006599 mLowDischargeAmountSinceCharge = in.readInt();
6600 mHighDischargeAmountSinceCharge = in.readInt();
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08006601 mDischargeAmountScreenOn = in.readInt();
6602 mDischargeAmountScreenOnSinceCharge = in.readInt();
6603 mDischargeAmountScreenOff = in.readInt();
6604 mDischargeAmountScreenOffSinceCharge = in.readInt();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006605 mLastWriteTime = in.readLong();
6606
Amith Yamasani3718aaa2009-06-09 06:32:35 -07006607 mRadioDataUptime = in.readLong();
6608 mRadioDataStart = -1;
6609
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07006610 mBluetoothPingCount = in.readInt();
6611 mBluetoothPingStart = -1;
6612
Evan Millarc64edde2009-04-18 12:26:32 -07006613 mKernelWakelockStats.clear();
6614 int NKW = in.readInt();
6615 for (int ikw = 0; ikw < NKW; ikw++) {
6616 if (in.readInt() != 0) {
6617 String wakelockName = in.readString();
Amith Yamasani244fa5c2009-05-22 14:36:07 -07006618 in.readInt(); // Extra 0/1 written by Timer.writeTimerToParcel
Evan Millarc64edde2009-04-18 12:26:32 -07006619 SamplingTimer kwlt = new SamplingTimer(mUnpluggables, mOnBattery, in);
6620 mKernelWakelockStats.put(wakelockName, kwlt);
6621 }
6622 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006623
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006624 mPartialTimers.clear();
6625 mFullTimers.clear();
6626 mWindowTimers.clear();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006627 mWifiRunningTimers.clear();
6628 mFullWifiLockTimers.clear();
Nick Pelly6ccaa542012-06-15 15:22:47 -07006629 mWifiScanTimers.clear();
Robert Greenwalta029ea12013-09-25 16:38:12 -07006630 mWifiBatchedScanTimers.clear();
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006631 mWifiMulticastTimers.clear();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006632
Amith Yamasanie43530a2009-08-21 13:11:37 -07006633 sNumSpeedSteps = in.readInt();
6634
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006635 int numUids = in.readInt();
6636 mUidStats.clear();
6637 for (int i = 0; i < numUids; i++) {
6638 int uid = in.readInt();
6639 Uid u = new Uid(uid);
6640 u.readFromParcelLocked(mUnpluggables, in);
6641 mUidStats.append(uid, u);
6642 }
6643 }
6644
6645 public void writeToParcel(Parcel out, int flags) {
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006646 writeToParcelLocked(out, true, flags);
6647 }
6648
6649 public void writeToParcelWithoutUids(Parcel out, int flags) {
6650 writeToParcelLocked(out, false, flags);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006651 }
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006652
6653 @SuppressWarnings("unused")
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006654 void writeToParcelLocked(Parcel out, boolean inclUids, int flags) {
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006655 // Need to update with current kernel wake lock counts.
Dianne Hackborna7c837f2014-01-15 16:20:44 -08006656 pullPendingStateUpdatesLocked();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006657
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006658 final long uSecUptime = SystemClock.uptimeMillis() * 1000;
6659 final long uSecRealtime = SystemClock.elapsedRealtime() * 1000;
6660 final long batteryUptime = getBatteryUptimeLocked(uSecUptime);
6661 final long batteryRealtime = getBatteryRealtimeLocked(uSecRealtime);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006662
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006663 out.writeInt(MAGIC);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006664
Dianne Hackbornae384452011-06-28 12:33:48 -07006665 writeHistory(out, false);
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006666
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006667 out.writeInt(mStartCount);
6668 out.writeLong(mBatteryUptime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006669 out.writeLong(mBatteryRealtime);
Dianne Hackborn5f4a5f92014-01-24 16:59:34 -08006670 out.writeLong(mStartClockTime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006671 mScreenOnTimer.writeToParcel(out, batteryRealtime);
Dianne Hackborn617f8772009-03-31 15:04:46 -07006672 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
6673 mScreenBrightnessTimer[i].writeToParcel(out, batteryRealtime);
6674 }
6675 mInputEventCounter.writeToParcel(out);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006676 mPhoneOnTimer.writeToParcel(out, batteryRealtime);
Wink Saville52840902011-02-18 12:40:47 -08006677 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn627bba72009-03-24 22:32:56 -07006678 mPhoneSignalStrengthsTimer[i].writeToParcel(out, batteryRealtime);
6679 }
Amith Yamasanif37447b2009-10-08 18:28:01 -07006680 mPhoneSignalScanningTimer.writeToParcel(out, batteryRealtime);
Dianne Hackborn627bba72009-03-24 22:32:56 -07006681 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
6682 mPhoneDataConnectionsTimer[i].writeToParcel(out, batteryRealtime);
6683 }
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006684 for (int i = 0; i < NUM_NETWORK_ACTIVITY_TYPES; i++) {
Dianne Hackborn57ed6a62013-12-09 18:15:56 -08006685 mNetworkByteActivityCounters[i].writeToParcel(out);
6686 mNetworkPacketActivityCounters[i].writeToParcel(out);
Jeff Sharkey7a1c3fc2013-06-04 12:29:00 -07006687 }
The Android Open Source Project10592532009-03-18 17:39:46 -07006688 mWifiOnTimer.writeToParcel(out, batteryRealtime);
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006689 mGlobalWifiRunningTimer.writeToParcel(out, batteryRealtime);
The Android Open Source Project10592532009-03-18 17:39:46 -07006690 mBluetoothOnTimer.writeToParcel(out, batteryRealtime);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006691 out.writeLong(mUptime);
6692 out.writeLong(mUptimeStart);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006693 out.writeLong(mRealtime);
6694 out.writeLong(mRealtimeStart);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006695 out.writeInt(mOnBattery ? 1 : 0);
6696 out.writeLong(batteryUptime);
6697 out.writeLong(mTrackBatteryUptimeStart);
6698 out.writeLong(batteryRealtime);
6699 out.writeLong(mTrackBatteryRealtimeStart);
6700 out.writeLong(mUnpluggedBatteryUptime);
6701 out.writeLong(mUnpluggedBatteryRealtime);
Dianne Hackborn6b7b4842010-06-14 17:17:44 -07006702 out.writeInt(mDischargeUnplugLevel);
Evan Millar633a1742009-04-02 16:36:33 -07006703 out.writeInt(mDischargeCurrentLevel);
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006704 out.writeInt(mLowDischargeAmountSinceCharge);
6705 out.writeInt(mHighDischargeAmountSinceCharge);
Dianne Hackbornc1b40e32011-01-05 18:27:40 -08006706 out.writeInt(mDischargeAmountScreenOn);
6707 out.writeInt(mDischargeAmountScreenOnSinceCharge);
6708 out.writeInt(mDischargeAmountScreenOff);
6709 out.writeInt(mDischargeAmountScreenOffSinceCharge);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006710 out.writeLong(mLastWriteTime);
6711
Amith Yamasani3718aaa2009-06-09 06:32:35 -07006712 // Write radio uptime for data
Amith Yamasani3f7e35c2009-07-13 16:02:45 -07006713 out.writeLong(getRadioDataUptime());
6714
6715 out.writeInt(getBluetoothPingCount());
Amith Yamasani3718aaa2009-06-09 06:32:35 -07006716
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006717 if (inclUids) {
6718 out.writeInt(mKernelWakelockStats.size());
6719 for (Map.Entry<String, SamplingTimer> ent : mKernelWakelockStats.entrySet()) {
6720 SamplingTimer kwlt = ent.getValue();
6721 if (kwlt != null) {
6722 out.writeInt(1);
6723 out.writeString(ent.getKey());
6724 Timer.writeTimerToParcel(out, kwlt, batteryRealtime);
6725 } else {
6726 out.writeInt(0);
6727 }
Evan Millarc64edde2009-04-18 12:26:32 -07006728 }
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006729 } else {
6730 out.writeInt(0);
Evan Millarc64edde2009-04-18 12:26:32 -07006731 }
Amith Yamasanie43530a2009-08-21 13:11:37 -07006732
6733 out.writeInt(sNumSpeedSteps);
6734
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006735 if (inclUids) {
6736 int size = mUidStats.size();
6737 out.writeInt(size);
6738 for (int i = 0; i < size; i++) {
6739 out.writeInt(mUidStats.keyAt(i));
6740 Uid uid = mUidStats.valueAt(i);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006741
Dianne Hackborn3bee5af82010-07-23 00:22:04 -07006742 uid.writeToParcelLocked(out, batteryRealtime);
6743 }
6744 } else {
6745 out.writeInt(0);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006746 }
6747 }
6748
6749 public static final Parcelable.Creator<BatteryStatsImpl> CREATOR =
6750 new Parcelable.Creator<BatteryStatsImpl>() {
6751 public BatteryStatsImpl createFromParcel(Parcel in) {
6752 return new BatteryStatsImpl(in);
6753 }
6754
6755 public BatteryStatsImpl[] newArray(int size) {
6756 return new BatteryStatsImpl[size];
6757 }
6758 };
Jaikumar Ganesh5a1e4cf2010-10-18 17:05:09 -07006759
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006760 public void prepareForDumpLocked() {
6761 // Need to retrieve current kernel wake lock stats before printing.
Dianne Hackborna7c837f2014-01-15 16:20:44 -08006762 pullPendingStateUpdatesLocked();
Dianne Hackborn0ffc9882011-04-13 18:15:56 -07006763 }
6764
Dianne Hackborn099bc622014-01-22 13:39:16 -08006765 public void dumpLocked(Context context, PrintWriter pw, boolean isUnpluggedOnly, int reqUid,
6766 boolean historyOnly) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006767 if (DEBUG) {
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006768 Printer pr = new PrintWriterPrinter(pw);
6769 pr.println("*** Screen timer:");
6770 mScreenOnTimer.logState(pr, " ");
Dianne Hackborn617f8772009-03-31 15:04:46 -07006771 for (int i=0; i<NUM_SCREEN_BRIGHTNESS_BINS; i++) {
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006772 pr.println("*** Screen brightness #" + i + ":");
6773 mScreenBrightnessTimer[i].logState(pr, " ");
Dianne Hackborn617f8772009-03-31 15:04:46 -07006774 }
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006775 pr.println("*** Input event counter:");
6776 mInputEventCounter.logState(pr, " ");
6777 pr.println("*** Phone timer:");
6778 mPhoneOnTimer.logState(pr, " ");
Wink Saville52840902011-02-18 12:40:47 -08006779 for (int i=0; i<SignalStrength.NUM_SIGNAL_STRENGTH_BINS; i++) {
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006780 pr.println("*** Signal strength #" + i + ":");
6781 mPhoneSignalStrengthsTimer[i].logState(pr, " ");
Dianne Hackborn627bba72009-03-24 22:32:56 -07006782 }
Amith Yamasanif37447b2009-10-08 18:28:01 -07006783 pr.println("*** Signal scanning :");
6784 mPhoneSignalScanningTimer.logState(pr, " ");
Dianne Hackborn627bba72009-03-24 22:32:56 -07006785 for (int i=0; i<NUM_DATA_CONNECTION_TYPES; i++) {
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006786 pr.println("*** Data connection type #" + i + ":");
6787 mPhoneDataConnectionsTimer[i].logState(pr, " ");
Dianne Hackborn627bba72009-03-24 22:32:56 -07006788 }
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006789 pr.println("*** Wifi timer:");
6790 mWifiOnTimer.logState(pr, " ");
6791 pr.println("*** WifiRunning timer:");
Dianne Hackborn58e0eef2010-09-16 01:22:10 -07006792 mGlobalWifiRunningTimer.logState(pr, " ");
Dianne Hackborn1d442e02009-04-20 18:14:05 -07006793 pr.println("*** Bluetooth timer:");
6794 mBluetoothOnTimer.logState(pr, " ");
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006795 }
Dianne Hackborn099bc622014-01-22 13:39:16 -08006796 super.dumpLocked(context, pw, isUnpluggedOnly, reqUid, historyOnly);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006797 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08006798}