blob: 199cb4981fe67d51e799c4a6eb27658e1c500838 [file] [log] [blame]
Jeff Brown96307042012-07-27 15:51:34 -07001/*
2 * Copyright (C) 2012 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.server.power;
18
Andrew Zeng6d07baf2018-04-20 14:13:16 -070019import android.annotation.Nullable;
Pavel Grafov28939982017-10-03 15:11:52 +010020import android.annotation.UserIdInt;
Jeff Brown13014b52014-04-07 19:45:27 -070021import android.app.ActivityManagerInternal;
Dianne Hackborn713df152013-05-17 11:27:57 -070022import android.app.AppOpsManager;
Pavel Grafov28939982017-10-03 15:11:52 +010023import android.app.trust.TrustManager;
Jeff Brown96307042012-07-27 15:51:34 -070024import android.content.BroadcastReceiver;
25import android.content.Context;
26import android.content.Intent;
Jeff Brown037c33e2014-04-09 00:31:55 -070027import android.hardware.input.InputManagerInternal;
Beverly69721d62018-05-09 17:41:44 -040028import android.media.AudioAttributes;
Jeff Brown84e27562012-12-07 13:56:34 -080029import android.media.AudioManager;
30import android.media.Ringtone;
31import android.media.RingtoneManager;
Alison Cichowlas5c38fc22017-01-25 17:11:06 -050032import android.metrics.LogMaker;
Jeff Brown84e27562012-12-07 13:56:34 -080033import android.net.Uri;
Jeff Brown96307042012-07-27 15:51:34 -070034import android.os.BatteryStats;
35import android.os.Handler;
36import android.os.Looper;
37import android.os.Message;
38import android.os.PowerManager;
Michael Wrighte3001042019-02-05 00:13:14 +000039import android.os.PowerManager.WakeReason;
Jeff Brownfbe96702014-11-19 18:30:58 -080040import android.os.PowerManagerInternal;
Dianne Hackborn3d658bf2014-02-05 13:38:56 -080041import android.os.Process;
Jeff Brown96307042012-07-27 15:51:34 -070042import android.os.RemoteException;
43import android.os.SystemClock;
Dianne Hackborn5ac72a22012-08-29 18:32:08 -070044import android.os.UserHandle;
Beverly69721d62018-05-09 17:41:44 -040045import android.os.VibrationEffect;
46import android.os.Vibrator;
Jeff Brown96307042012-07-27 15:51:34 -070047import android.os.WorkSource;
Jeff Brown84e27562012-12-07 13:56:34 -080048import android.provider.Settings;
Peter Wang6a92dd42020-01-15 14:11:25 -080049import android.telephony.TelephonyManager;
Jeff Brown96307042012-07-27 15:51:34 -070050import android.util.EventLog;
51import android.util.Slog;
Michael Wrighte3001042019-02-05 00:13:14 +000052import android.view.WindowManagerPolicyConstants.OnReason;
Jeff Brown96307042012-07-27 15:51:34 -070053
Santos Cordon64a6e612018-08-22 19:27:04 +010054import com.android.internal.annotations.VisibleForTesting;
Beverlyae79ab92017-12-11 09:20:02 -050055import com.android.internal.app.IBatteryStats;
56import com.android.internal.logging.MetricsLogger;
57import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
Muhammad Qureshi41166302020-01-28 10:23:36 -080058import com.android.internal.util.FrameworkStatsLog;
Beverlyae79ab92017-12-11 09:20:02 -050059import com.android.server.EventLogTags;
60import com.android.server.LocalServices;
Yohei Yukawac3de83e2018-08-28 16:09:34 -070061import com.android.server.inputmethod.InputMethodManagerInternal;
Beverlyae79ab92017-12-11 09:20:02 -050062import com.android.server.policy.WindowManagerPolicy;
Beverly69721d62018-05-09 17:41:44 -040063import com.android.server.statusbar.StatusBarManagerInternal;
Beverlyae79ab92017-12-11 09:20:02 -050064
Santos Cordon9204cc82019-11-21 11:45:28 +000065import java.io.PrintWriter;
66
Jeff Brown96307042012-07-27 15:51:34 -070067/**
68 * Sends broadcasts about important power state changes.
Jeff Brown54308352012-10-04 17:59:58 -070069 * <p>
Jeff Brown96307042012-07-27 15:51:34 -070070 * This methods of this class may be called by the power manager service while
71 * its lock is being held. Internally it takes care of sending broadcasts to
72 * notify other components of the system or applications asynchronously.
Jeff Brown54308352012-10-04 17:59:58 -070073 * </p><p>
Jeff Brown96307042012-07-27 15:51:34 -070074 * The notifier is designed to collapse unnecessary broadcasts when it is not
75 * possible for the system to have observed an intermediate state.
Jeff Brown54308352012-10-04 17:59:58 -070076 * </p><p>
77 * For example, if the device wakes up, goes to sleep, wakes up again and goes to
78 * sleep again before the wake up notification is sent, then the system will
79 * be told about only one wake up and sleep. However, we always notify the
80 * fact that at least one transition occurred. It is especially important to
81 * tell the system when we go to sleep so that it can lock the keyguard if needed.
82 * </p>
Jeff Brown96307042012-07-27 15:51:34 -070083 */
Santos Cordon64a6e612018-08-22 19:27:04 +010084@VisibleForTesting
85public class Notifier {
Jeff Brown96307042012-07-27 15:51:34 -070086 private static final String TAG = "PowerManagerNotifier";
87
88 private static final boolean DEBUG = false;
89
Jeff Brownfbe96702014-11-19 18:30:58 -080090 private static final int INTERACTIVE_STATE_UNKNOWN = 0;
91 private static final int INTERACTIVE_STATE_AWAKE = 1;
92 private static final int INTERACTIVE_STATE_ASLEEP = 2;
Jeff Brown96307042012-07-27 15:51:34 -070093
94 private static final int MSG_USER_ACTIVITY = 1;
95 private static final int MSG_BROADCAST = 2;
Jeff Brown84e27562012-12-07 13:56:34 -080096 private static final int MSG_WIRELESS_CHARGING_STARTED = 3;
Pavel Grafov28939982017-10-03 15:11:52 +010097 private static final int MSG_PROFILE_TIMED_OUT = 5;
Beverlyc1313eb2018-01-31 18:07:21 -050098 private static final int MSG_WIRED_CHARGING_STARTED = 6;
Jeff Brown96307042012-07-27 15:51:34 -070099
Beverlyf364d7c2019-10-10 16:44:43 -0400100 private static final long[] CHARGING_VIBRATION_TIME = {
Beverly69721d62018-05-09 17:41:44 -0400101 40, 40, 40, 40, 40, 40, 40, 40, 40, // ramp-up sampling rate = 40ms
102 40, 40, 40, 40, 40, 40, 40 // ramp-down sampling rate = 40ms
103 };
Beverlyf364d7c2019-10-10 16:44:43 -0400104 private static final int[] CHARGING_VIBRATION_AMPLITUDE = {
Beverly69721d62018-05-09 17:41:44 -0400105 1, 4, 11, 25, 44, 67, 91, 114, 123, // ramp-up amplitude (from 0 to 50%)
106 103, 79, 55, 34, 17, 7, 2 // ramp-up amplitude
107 };
Beverlyf364d7c2019-10-10 16:44:43 -0400108 private static final VibrationEffect CHARGING_VIBRATION_EFFECT =
109 VibrationEffect.createWaveform(CHARGING_VIBRATION_TIME, CHARGING_VIBRATION_AMPLITUDE,
Beverly69721d62018-05-09 17:41:44 -0400110 -1);
111 private static final AudioAttributes VIBRATION_ATTRIBUTES = new AudioAttributes.Builder()
112 .setContentType(AudioAttributes.CONTENT_TYPE_SONIFICATION)
113 .build();
114
Jeff Brown96307042012-07-27 15:51:34 -0700115 private final Object mLock = new Object();
116
117 private final Context mContext;
118 private final IBatteryStats mBatteryStats;
Svet Ganovf7b47252018-02-26 11:11:27 -0800119 private final AppOpsManager mAppOps;
Jeff Brown96307042012-07-27 15:51:34 -0700120 private final SuspendBlocker mSuspendBlocker;
121 private final WindowManagerPolicy mPolicy;
Jeff Brown13014b52014-04-07 19:45:27 -0700122 private final ActivityManagerInternal mActivityManagerInternal;
Jeff Brown037c33e2014-04-09 00:31:55 -0700123 private final InputManagerInternal mInputManagerInternal;
Yohei Yukawafa6e0a82015-07-23 15:08:59 -0700124 private final InputMethodManagerInternal mInputMethodManagerInternal;
Andrew Zeng6d07baf2018-04-20 14:13:16 -0700125 @Nullable private final StatusBarManagerInternal mStatusBarManagerInternal;
Pavel Grafov28939982017-10-03 15:11:52 +0100126 private final TrustManager mTrustManager;
Beverly69721d62018-05-09 17:41:44 -0400127 private final Vibrator mVibrator;
Santos Cordon9204cc82019-11-21 11:45:28 +0000128 private final WakeLockLog mWakeLockLog;
Jeff Brown96307042012-07-27 15:51:34 -0700129
130 private final NotifierHandler mHandler;
131 private final Intent mScreenOnIntent;
132 private final Intent mScreenOffIntent;
133
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700134 // True if the device should suspend when the screen is off due to proximity.
135 private final boolean mSuspendWhenScreenOffDueToProximityConfig;
136
Beverlyf364d7c2019-10-10 16:44:43 -0400137 // True if the device should show the wireless charging animation when the device
138 // begins charging wirelessly
139 private final boolean mShowWirelessChargingAnimationConfig;
140
Jeff Brown416c49c2015-05-26 19:50:18 -0700141 // The current interactive state. This is set as soon as an interactive state
142 // transition begins so as to capture the reason that it happened. At some point
143 // this state will propagate to the pending state then eventually to the
144 // broadcasted state over the course of reporting the transition asynchronously.
145 private boolean mInteractive = true;
146 private int mInteractiveChangeReason;
Michael Wrighte3001042019-02-05 00:13:14 +0000147 private long mInteractiveChangeStartTime; // In SystemClock.uptimeMillis()
Jeff Brown416c49c2015-05-26 19:50:18 -0700148 private boolean mInteractiveChanging;
Jeff Brown96307042012-07-27 15:51:34 -0700149
Jeff Brown416c49c2015-05-26 19:50:18 -0700150 // The pending interactive state that we will eventually want to broadcast.
151 // This is designed so that we can collapse redundant sequences of awake/sleep
152 // transition pairs while still guaranteeing that at least one transition is observed
153 // whenever this happens.
154 private int mPendingInteractiveState;
Jeff Brown54308352012-10-04 17:59:58 -0700155 private boolean mPendingWakeUpBroadcast;
156 private boolean mPendingGoToSleepBroadcast;
157
Jeff Brownfbe96702014-11-19 18:30:58 -0800158 // The currently broadcasted interactive state. This reflects what other parts of the
Jeff Brown96307042012-07-27 15:51:34 -0700159 // system have observed.
Jeff Brownfbe96702014-11-19 18:30:58 -0800160 private int mBroadcastedInteractiveState;
Jeff Brown96307042012-07-27 15:51:34 -0700161 private boolean mBroadcastInProgress;
162 private long mBroadcastStartTime;
163
164 // True if a user activity message should be sent.
165 private boolean mUserActivityPending;
166
167 public Notifier(Looper looper, Context context, IBatteryStats batteryStats,
Svet Ganovf7b47252018-02-26 11:11:27 -0800168 SuspendBlocker suspendBlocker, WindowManagerPolicy policy) {
Jeff Brown96307042012-07-27 15:51:34 -0700169 mContext = context;
170 mBatteryStats = batteryStats;
Svet Ganovf7b47252018-02-26 11:11:27 -0800171 mAppOps = mContext.getSystemService(AppOpsManager.class);
Jeff Brown96307042012-07-27 15:51:34 -0700172 mSuspendBlocker = suspendBlocker;
173 mPolicy = policy;
Jeff Brown13014b52014-04-07 19:45:27 -0700174 mActivityManagerInternal = LocalServices.getService(ActivityManagerInternal.class);
Jeff Brown037c33e2014-04-09 00:31:55 -0700175 mInputManagerInternal = LocalServices.getService(InputManagerInternal.class);
Yohei Yukawafa6e0a82015-07-23 15:08:59 -0700176 mInputMethodManagerInternal = LocalServices.getService(InputMethodManagerInternal.class);
Beverlyae79ab92017-12-11 09:20:02 -0500177 mStatusBarManagerInternal = LocalServices.getService(StatusBarManagerInternal.class);
Pavel Grafov28939982017-10-03 15:11:52 +0100178 mTrustManager = mContext.getSystemService(TrustManager.class);
Beverly69721d62018-05-09 17:41:44 -0400179 mVibrator = mContext.getSystemService(Vibrator.class);
Jeff Brown96307042012-07-27 15:51:34 -0700180
181 mHandler = new NotifierHandler(looper);
182 mScreenOnIntent = new Intent(Intent.ACTION_SCREEN_ON);
183 mScreenOnIntent.addFlags(
Chad Brubaker291df4f2017-03-14 10:23:02 -0700184 Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_FOREGROUND
185 | Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS);
Jeff Brown96307042012-07-27 15:51:34 -0700186 mScreenOffIntent = new Intent(Intent.ACTION_SCREEN_OFF);
187 mScreenOffIntent.addFlags(
Chad Brubaker291df4f2017-03-14 10:23:02 -0700188 Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_FOREGROUND
189 | Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS);
Jeff Browne95c3cd2014-05-02 16:59:26 -0700190
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700191 mSuspendWhenScreenOffDueToProximityConfig = context.getResources().getBoolean(
192 com.android.internal.R.bool.config_suspendWhenScreenOffDueToProximity);
Beverlyf364d7c2019-10-10 16:44:43 -0400193 mShowWirelessChargingAnimationConfig = context.getResources().getBoolean(
194 com.android.internal.R.bool.config_showBuiltinWirelessChargingAnim);
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700195
Santos Cordon9204cc82019-11-21 11:45:28 +0000196 mWakeLockLog = new WakeLockLog();
197
Jeff Browne95c3cd2014-05-02 16:59:26 -0700198 // Initialize interactive state for battery stats.
199 try {
200 mBatteryStats.noteInteractive(true);
201 } catch (RemoteException ex) { }
Muhammad Qureshi41166302020-01-28 10:23:36 -0800202 FrameworkStatsLog.write(FrameworkStatsLog.INTERACTIVE_STATE_CHANGED,
203 FrameworkStatsLog.INTERACTIVE_STATE_CHANGED__STATE__ON);
Jeff Brown96307042012-07-27 15:51:34 -0700204 }
205
206 /**
207 * Called when a wake lock is acquired.
208 */
Dianne Hackborn713df152013-05-17 11:27:57 -0700209 public void onWakeLockAcquired(int flags, String tag, String packageName,
Dianne Hackborna1f1a3c2014-02-24 18:12:28 -0800210 int ownerUid, int ownerPid, WorkSource workSource, String historyTag) {
Jeff Brown96307042012-07-27 15:51:34 -0700211 if (DEBUG) {
212 Slog.d(TAG, "onWakeLockAcquired: flags=" + flags + ", tag=\"" + tag
Dianne Hackborn713df152013-05-17 11:27:57 -0700213 + "\", packageName=" + packageName
214 + ", ownerUid=" + ownerUid + ", ownerPid=" + ownerPid
Jeff Brown96307042012-07-27 15:51:34 -0700215 + ", workSource=" + workSource);
216 }
217
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700218 final int monitorType = getBatteryStatsWakeLockMonitorType(flags);
219 if (monitorType >= 0) {
220 try {
221 final boolean unimportantForLogging = ownerUid == Process.SYSTEM_UID
222 && (flags & PowerManager.UNIMPORTANT_FOR_LOGGING) != 0;
223 if (workSource != null) {
224 mBatteryStats.noteStartWakelockFromSource(workSource, ownerPid, tag,
225 historyTag, monitorType, unimportantForLogging);
226 } else {
227 mBatteryStats.noteStartWakelock(ownerUid, ownerPid, tag, historyTag,
228 monitorType, unimportantForLogging);
229 // XXX need to deal with disabled operations.
Svet Ganovf7b47252018-02-26 11:11:27 -0800230 mAppOps.startOpNoThrow(AppOpsManager.OP_WAKE_LOCK, ownerUid, packageName);
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700231 }
232 } catch (RemoteException ex) {
233 // Ignore
Jeff Brown96307042012-07-27 15:51:34 -0700234 }
235 }
Santos Cordon9204cc82019-11-21 11:45:28 +0000236
237 mWakeLockLog.onWakeLockAcquired(tag, ownerUid, flags);
Jeff Brown96307042012-07-27 15:51:34 -0700238 }
239
Dianne Hackbornd0db6f02016-07-18 14:14:20 -0700240 public void onLongPartialWakeLockStart(String tag, int ownerUid, WorkSource workSource,
241 String historyTag) {
242 if (DEBUG) {
243 Slog.d(TAG, "onLongPartialWakeLockStart: ownerUid=" + ownerUid
244 + ", workSource=" + workSource);
245 }
246
247 try {
248 if (workSource != null) {
Narayan Kamath96a92562018-01-02 18:57:17 +0000249 mBatteryStats.noteLongPartialWakelockStartFromSource(tag, historyTag, workSource);
Muhammad Qureshi41166302020-01-28 10:23:36 -0800250 FrameworkStatsLog.write(FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED,
251 workSource, tag, historyTag,
252 FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED__STATE__ON);
Dianne Hackbornd0db6f02016-07-18 14:14:20 -0700253 } else {
254 mBatteryStats.noteLongPartialWakelockStart(tag, historyTag, ownerUid);
Muhammad Qureshi41166302020-01-28 10:23:36 -0800255 FrameworkStatsLog.write_non_chained(
256 FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED, ownerUid, null, tag,
257 historyTag,
258 FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED__STATE__ON);
Dianne Hackbornd0db6f02016-07-18 14:14:20 -0700259 }
260 } catch (RemoteException ex) {
261 // Ignore
262 }
263 }
264
265 public void onLongPartialWakeLockFinish(String tag, int ownerUid, WorkSource workSource,
266 String historyTag) {
267 if (DEBUG) {
268 Slog.d(TAG, "onLongPartialWakeLockFinish: ownerUid=" + ownerUid
269 + ", workSource=" + workSource);
270 }
271
272 try {
273 if (workSource != null) {
Narayan Kamath96a92562018-01-02 18:57:17 +0000274 mBatteryStats.noteLongPartialWakelockFinishFromSource(tag, historyTag, workSource);
Muhammad Qureshi41166302020-01-28 10:23:36 -0800275 FrameworkStatsLog.write(FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED,
276 workSource, tag, historyTag,
277 FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED__STATE__OFF);
Dianne Hackbornd0db6f02016-07-18 14:14:20 -0700278 } else {
279 mBatteryStats.noteLongPartialWakelockFinish(tag, historyTag, ownerUid);
Muhammad Qureshi41166302020-01-28 10:23:36 -0800280 FrameworkStatsLog.write_non_chained(
281 FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED, ownerUid, null, tag,
282 historyTag,
283 FrameworkStatsLog.LONG_PARTIAL_WAKELOCK_STATE_CHANGED__STATE__OFF);
Dianne Hackbornd0db6f02016-07-18 14:14:20 -0700284 }
285 } catch (RemoteException ex) {
286 // Ignore
287 }
288 }
289
Jeff Brown96307042012-07-27 15:51:34 -0700290 /**
Dianne Hackborne5167ca2014-03-08 14:39:10 -0800291 * Called when a wake lock is changing.
292 */
293 public void onWakeLockChanging(int flags, String tag, String packageName,
294 int ownerUid, int ownerPid, WorkSource workSource, String historyTag,
295 int newFlags, String newTag, String newPackageName, int newOwnerUid,
296 int newOwnerPid, WorkSource newWorkSource, String newHistoryTag) {
297
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700298 final int monitorType = getBatteryStatsWakeLockMonitorType(flags);
299 final int newMonitorType = getBatteryStatsWakeLockMonitorType(newFlags);
300 if (workSource != null && newWorkSource != null
301 && monitorType >= 0 && newMonitorType >= 0) {
Dianne Hackborne5167ca2014-03-08 14:39:10 -0800302 if (DEBUG) {
303 Slog.d(TAG, "onWakeLockChanging: flags=" + newFlags + ", tag=\"" + newTag
304 + "\", packageName=" + newPackageName
305 + ", ownerUid=" + newOwnerUid + ", ownerPid=" + newOwnerPid
306 + ", workSource=" + newWorkSource);
307 }
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700308
309 final boolean unimportantForLogging = newOwnerUid == Process.SYSTEM_UID
310 && (newFlags & PowerManager.UNIMPORTANT_FOR_LOGGING) != 0;
Dianne Hackborne5167ca2014-03-08 14:39:10 -0800311 try {
Dianne Hackborncbefd8d2014-05-14 11:42:00 -0700312 mBatteryStats.noteChangeWakelockFromSource(workSource, ownerPid, tag, historyTag,
313 monitorType, newWorkSource, newOwnerPid, newTag, newHistoryTag,
Dianne Hackborne5167ca2014-03-08 14:39:10 -0800314 newMonitorType, unimportantForLogging);
315 } catch (RemoteException ex) {
316 // Ignore
317 }
318 } else {
Dianne Hackborncbefd8d2014-05-14 11:42:00 -0700319 onWakeLockReleased(flags, tag, packageName, ownerUid, ownerPid, workSource, historyTag);
Dianne Hackborne5167ca2014-03-08 14:39:10 -0800320 onWakeLockAcquired(newFlags, newTag, newPackageName, newOwnerUid, newOwnerPid,
321 newWorkSource, newHistoryTag);
322 }
323 }
324
325 /**
Jeff Brown96307042012-07-27 15:51:34 -0700326 * Called when a wake lock is released.
327 */
Dianne Hackborn713df152013-05-17 11:27:57 -0700328 public void onWakeLockReleased(int flags, String tag, String packageName,
Dianne Hackborncbefd8d2014-05-14 11:42:00 -0700329 int ownerUid, int ownerPid, WorkSource workSource, String historyTag) {
Jeff Brown96307042012-07-27 15:51:34 -0700330 if (DEBUG) {
331 Slog.d(TAG, "onWakeLockReleased: flags=" + flags + ", tag=\"" + tag
Dianne Hackborn713df152013-05-17 11:27:57 -0700332 + "\", packageName=" + packageName
333 + ", ownerUid=" + ownerUid + ", ownerPid=" + ownerPid
Jeff Brown96307042012-07-27 15:51:34 -0700334 + ", workSource=" + workSource);
335 }
336
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700337 final int monitorType = getBatteryStatsWakeLockMonitorType(flags);
338 if (monitorType >= 0) {
339 try {
340 if (workSource != null) {
341 mBatteryStats.noteStopWakelockFromSource(workSource, ownerPid, tag,
342 historyTag, monitorType);
343 } else {
344 mBatteryStats.noteStopWakelock(ownerUid, ownerPid, tag,
345 historyTag, monitorType);
Svet Ganovf7b47252018-02-26 11:11:27 -0800346 mAppOps.finishOp(AppOpsManager.OP_WAKE_LOCK, ownerUid, packageName);
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700347 }
348 } catch (RemoteException ex) {
349 // Ignore
Jeff Brown96307042012-07-27 15:51:34 -0700350 }
351 }
Santos Cordon9204cc82019-11-21 11:45:28 +0000352 mWakeLockLog.onWakeLockReleased(tag, ownerUid);
Jeff Brown96307042012-07-27 15:51:34 -0700353 }
354
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700355 private int getBatteryStatsWakeLockMonitorType(int flags) {
Jeff Brown96307042012-07-27 15:51:34 -0700356 switch (flags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
357 case PowerManager.PARTIAL_WAKE_LOCK:
Jeff Brown96307042012-07-27 15:51:34 -0700358 return BatteryStats.WAKE_TYPE_PARTIAL;
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700359
360 case PowerManager.SCREEN_DIM_WAKE_LOCK:
361 case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
Jeff Brown96307042012-07-27 15:51:34 -0700362 return BatteryStats.WAKE_TYPE_FULL;
Jeff Brownc4bd42c2015-06-12 18:00:11 -0700363
364 case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
365 if (mSuspendWhenScreenOffDueToProximityConfig) {
366 return -1;
367 }
368 return BatteryStats.WAKE_TYPE_PARTIAL;
369
370 case PowerManager.DRAW_WAKE_LOCK:
371 return BatteryStats.WAKE_TYPE_DRAW;
372
373 case PowerManager.DOZE_WAKE_LOCK:
374 // Doze wake locks are an internal implementation detail of the
375 // communication between dream manager service and power manager
376 // service. They have no additive battery impact.
377 return -1;
378
379 default:
380 return -1;
Jeff Brown96307042012-07-27 15:51:34 -0700381 }
382 }
383
384 /**
Jeff Brownfbe96702014-11-19 18:30:58 -0800385 * Notifies that the device is changing wakefulness.
Jeff Brown416c49c2015-05-26 19:50:18 -0700386 * This function may be called even if the previous change hasn't finished in
387 * which case it will assume that the state did not fully converge before the
388 * next transition began and will recover accordingly.
Jeff Brown96307042012-07-27 15:51:34 -0700389 */
Michael Wrighte3001042019-02-05 00:13:14 +0000390 public void onWakefulnessChangeStarted(final int wakefulness, int reason, long eventTime) {
Jeff Brown416c49c2015-05-26 19:50:18 -0700391 final boolean interactive = PowerManagerInternal.isInteractive(wakefulness);
Jeff Brown96307042012-07-27 15:51:34 -0700392 if (DEBUG) {
Jeff Brownfbe96702014-11-19 18:30:58 -0800393 Slog.d(TAG, "onWakefulnessChangeStarted: wakefulness=" + wakefulness
Jeff Brown416c49c2015-05-26 19:50:18 -0700394 + ", reason=" + reason + ", interactive=" + interactive);
Jeff Brown96307042012-07-27 15:51:34 -0700395 }
396
Jeff Brownfbe96702014-11-19 18:30:58 -0800397 // Tell the activity manager about changes in wakefulness, not just interactivity.
398 // It needs more granularity than other components.
399 mHandler.post(new Runnable() {
400 @Override
401 public void run() {
402 mActivityManagerInternal.onWakefulnessChanged(wakefulness);
403 }
404 });
405
Jeff Brown416c49c2015-05-26 19:50:18 -0700406 // Handle any early interactive state changes.
407 // Finish pending incomplete ones from a previous cycle.
408 if (mInteractive != interactive) {
409 // Finish up late behaviors if needed.
410 if (mInteractiveChanging) {
411 handleLateInteractiveChange();
Jeff Brown96307042012-07-27 15:51:34 -0700412 }
Jeff Browne95c3cd2014-05-02 16:59:26 -0700413
Jeff Brown416c49c2015-05-26 19:50:18 -0700414 // Start input as soon as we start waking up or going to sleep.
415 mInputManagerInternal.setInteractive(interactive);
416
417 // Notify battery stats.
Jeff Browne95c3cd2014-05-02 16:59:26 -0700418 try {
Jeff Brownfbe96702014-11-19 18:30:58 -0800419 mBatteryStats.noteInteractive(interactive);
Jeff Browne95c3cd2014-05-02 16:59:26 -0700420 } catch (RemoteException ex) { }
Muhammad Qureshi41166302020-01-28 10:23:36 -0800421 FrameworkStatsLog.write(FrameworkStatsLog.INTERACTIVE_STATE_CHANGED,
422 interactive ? FrameworkStatsLog.INTERACTIVE_STATE_CHANGED__STATE__ON :
423 FrameworkStatsLog.INTERACTIVE_STATE_CHANGED__STATE__OFF);
Jeff Brown416c49c2015-05-26 19:50:18 -0700424
425 // Handle early behaviors.
426 mInteractive = interactive;
427 mInteractiveChangeReason = reason;
Michael Wrighte3001042019-02-05 00:13:14 +0000428 mInteractiveChangeStartTime = eventTime;
Jeff Brown416c49c2015-05-26 19:50:18 -0700429 mInteractiveChanging = true;
430 handleEarlyInteractiveChange();
431 }
432 }
433
434 /**
435 * Notifies that the device has finished changing wakefulness.
436 */
437 public void onWakefulnessChangeFinished() {
438 if (DEBUG) {
439 Slog.d(TAG, "onWakefulnessChangeFinished");
440 }
441
442 if (mInteractiveChanging) {
443 mInteractiveChanging = false;
444 handleLateInteractiveChange();
445 }
446 }
447
448 /**
449 * Handle early interactive state changes such as getting applications or the lock
450 * screen running and ready for the user to see (such as when turning on the screen).
451 */
452 private void handleEarlyInteractiveChange() {
453 synchronized (mLock) {
454 if (mInteractive) {
455 // Waking up...
456 mHandler.post(new Runnable() {
457 @Override
458 public void run() {
Michael Wrighte3001042019-02-05 00:13:14 +0000459 final int why = translateOnReason(mInteractiveChangeReason);
460 mPolicy.startedWakingUp(why);
Jeff Brown416c49c2015-05-26 19:50:18 -0700461 }
462 });
463
464 // Send interactive broadcast.
465 mPendingInteractiveState = INTERACTIVE_STATE_AWAKE;
466 mPendingWakeUpBroadcast = true;
467 updatePendingBroadcastLocked();
468 } else {
469 // Going to sleep...
470 // Tell the policy that we started going to sleep.
471 final int why = translateOffReason(mInteractiveChangeReason);
472 mHandler.post(new Runnable() {
473 @Override
474 public void run() {
475 mPolicy.startedGoingToSleep(why);
476 }
477 });
478 }
479 }
480 }
481
482 /**
483 * Handle late interactive state changes once they are finished so that the system can
484 * finish pending transitions (such as turning the screen off) before causing
485 * applications to change state visibly.
486 */
487 private void handleLateInteractiveChange() {
488 synchronized (mLock) {
Michael Wrighte3001042019-02-05 00:13:14 +0000489 final int interactiveChangeLatency =
490 (int) (SystemClock.uptimeMillis() - mInteractiveChangeStartTime);
Jeff Brown416c49c2015-05-26 19:50:18 -0700491 if (mInteractive) {
492 // Finished waking up...
Michael Wrighte3001042019-02-05 00:13:14 +0000493 final int why = translateOnReason(mInteractiveChangeReason);
Jeff Brown416c49c2015-05-26 19:50:18 -0700494 mHandler.post(new Runnable() {
495 @Override
496 public void run() {
Michael Wrighte3001042019-02-05 00:13:14 +0000497 LogMaker log = new LogMaker(MetricsEvent.SCREEN);
498 log.setType(MetricsEvent.TYPE_OPEN);
499 log.setSubtype(why);
500 log.setLatency(interactiveChangeLatency);
Steven Wu0e6e5de2019-03-12 17:13:14 -0400501 log.addTaggedData(
502 MetricsEvent.FIELD_SCREEN_WAKE_REASON, mInteractiveChangeReason);
Michael Wrighte3001042019-02-05 00:13:14 +0000503 MetricsLogger.action(log);
504 EventLogTags.writePowerScreenState(1, 0, 0, 0, interactiveChangeLatency);
505 mPolicy.finishedWakingUp(why);
Jeff Brown416c49c2015-05-26 19:50:18 -0700506 }
507 });
508 } else {
509 // Finished going to sleep...
510 // This is a good time to make transitions that we don't want the user to see,
511 // such as bringing the key guard to focus. There's no guarantee for this
512 // however because the user could turn the device on again at any time.
513 // Some things may need to be protected by other mechanisms that defer screen on.
514
515 // Cancel pending user activity.
516 if (mUserActivityPending) {
517 mUserActivityPending = false;
518 mHandler.removeMessages(MSG_USER_ACTIVITY);
519 }
520
521 // Tell the policy we finished going to sleep.
522 final int why = translateOffReason(mInteractiveChangeReason);
523 mHandler.post(new Runnable() {
524 @Override
525 public void run() {
Alison Cichowlas5c38fc22017-01-25 17:11:06 -0500526 LogMaker log = new LogMaker(MetricsEvent.SCREEN);
527 log.setType(MetricsEvent.TYPE_CLOSE);
528 log.setSubtype(why);
Michael Wrighte3001042019-02-05 00:13:14 +0000529 log.setLatency(interactiveChangeLatency);
Steven Wu0e6e5de2019-03-12 17:13:14 -0400530 log.addTaggedData(
531 MetricsEvent.FIELD_SCREEN_SLEEP_REASON, mInteractiveChangeReason);
Alison Cichowlas5c38fc22017-01-25 17:11:06 -0500532 MetricsLogger.action(log);
Michael Wrighte3001042019-02-05 00:13:14 +0000533 EventLogTags.writePowerScreenState(0, why, 0, 0, interactiveChangeLatency);
Jeff Brown416c49c2015-05-26 19:50:18 -0700534 mPolicy.finishedGoingToSleep(why);
535 }
536 });
537
538 // Send non-interactive broadcast.
539 mPendingInteractiveState = INTERACTIVE_STATE_ASLEEP;
540 mPendingGoToSleepBroadcast = true;
541 updatePendingBroadcastLocked();
542 }
543 }
544 }
545
546 private static int translateOffReason(int reason) {
547 switch (reason) {
548 case PowerManager.GO_TO_SLEEP_REASON_DEVICE_ADMIN:
549 return WindowManagerPolicy.OFF_BECAUSE_OF_ADMIN;
550 case PowerManager.GO_TO_SLEEP_REASON_TIMEOUT:
Robert Horvath5560f382019-07-10 10:46:38 +0200551 case PowerManager.GO_TO_SLEEP_REASON_INATTENTIVE:
Jeff Brown416c49c2015-05-26 19:50:18 -0700552 return WindowManagerPolicy.OFF_BECAUSE_OF_TIMEOUT;
553 default:
554 return WindowManagerPolicy.OFF_BECAUSE_OF_USER;
Jeff Browne95c3cd2014-05-02 16:59:26 -0700555 }
Jeff Brown96307042012-07-27 15:51:34 -0700556 }
557
Michael Wrighte3001042019-02-05 00:13:14 +0000558 private static @OnReason int translateOnReason(@WakeReason int reason) {
559 switch (reason) {
560 case PowerManager.WAKE_REASON_POWER_BUTTON:
561 case PowerManager.WAKE_REASON_PLUGGED_IN:
562 case PowerManager.WAKE_REASON_GESTURE:
563 case PowerManager.WAKE_REASON_CAMERA_LAUNCH:
564 case PowerManager.WAKE_REASON_WAKE_KEY:
565 case PowerManager.WAKE_REASON_WAKE_MOTION:
566 case PowerManager.WAKE_REASON_LID:
567 return WindowManagerPolicy.ON_BECAUSE_OF_USER;
568 case PowerManager.WAKE_REASON_APPLICATION:
569 return WindowManagerPolicy.ON_BECAUSE_OF_APPLICATION;
570 default:
571 return WindowManagerPolicy.ON_BECAUSE_OF_UNKNOWN;
572 }
573 }
574
Jeff Brown96307042012-07-27 15:51:34 -0700575 /**
576 * Called when there has been user activity.
577 */
578 public void onUserActivity(int event, int uid) {
579 if (DEBUG) {
580 Slog.d(TAG, "onUserActivity: event=" + event + ", uid=" + uid);
581 }
582
583 try {
584 mBatteryStats.noteUserActivity(uid, event);
585 } catch (RemoteException ex) {
586 // Ignore
587 }
588
589 synchronized (mLock) {
590 if (!mUserActivityPending) {
591 mUserActivityPending = true;
592 Message msg = mHandler.obtainMessage(MSG_USER_ACTIVITY);
593 msg.setAsynchronous(true);
594 mHandler.sendMessage(msg);
595 }
596 }
597 }
598
Jeff Brown84e27562012-12-07 13:56:34 -0800599 /**
Dianne Hackborn280a64e2015-07-13 14:48:08 -0700600 * Called when the screen has turned on.
601 */
Michael Wrighte3001042019-02-05 00:13:14 +0000602 public void onWakeUp(int reason, String details, int reasonUid, String opPackageName,
603 int opUid) {
Dianne Hackborn280a64e2015-07-13 14:48:08 -0700604 if (DEBUG) {
Michael Wrighte3001042019-02-05 00:13:14 +0000605 Slog.d(TAG, "onWakeUp: reason=" + PowerManager.wakeReasonToString(reason)
606 + ", details=" + details + ", reasonUid=" + reasonUid
Dianne Hackborn280a64e2015-07-13 14:48:08 -0700607 + " opPackageName=" + opPackageName + " opUid=" + opUid);
608 }
609
610 try {
Michael Wrighte3001042019-02-05 00:13:14 +0000611 mBatteryStats.noteWakeUp(details, reasonUid);
Dianne Hackborn280a64e2015-07-13 14:48:08 -0700612 if (opPackageName != null) {
Svet Ganovf7b47252018-02-26 11:11:27 -0800613 mAppOps.noteOpNoThrow(AppOpsManager.OP_TURN_SCREEN_ON, opUid, opPackageName);
Dianne Hackborn280a64e2015-07-13 14:48:08 -0700614 }
615 } catch (RemoteException ex) {
616 // Ignore
617 }
Dianne Hackborn280a64e2015-07-13 14:48:08 -0700618 }
619
620 /**
Beverlyae79ab92017-12-11 09:20:02 -0500621 * Called when profile screen lock timeout has expired.
Jeff Brown84e27562012-12-07 13:56:34 -0800622 */
Beverlyae79ab92017-12-11 09:20:02 -0500623 public void onProfileTimeout(@UserIdInt int userId) {
624 final Message msg = mHandler.obtainMessage(MSG_PROFILE_TIMED_OUT);
625 msg.setAsynchronous(true);
626 msg.arg1 = userId;
627 mHandler.sendMessage(msg);
628 }
629
630 /**
Beverly91d0a632018-07-02 16:45:00 -0400631 * Called when wireless charging has started - to provide user feedback (sound and visual).
Beverlyae79ab92017-12-11 09:20:02 -0500632 */
Beverly91d0a632018-07-02 16:45:00 -0400633 public void onWirelessChargingStarted(int batteryLevel, @UserIdInt int userId) {
Jeff Brown84e27562012-12-07 13:56:34 -0800634 if (DEBUG) {
635 Slog.d(TAG, "onWirelessChargingStarted");
636 }
637
638 mSuspendBlocker.acquire();
639 Message msg = mHandler.obtainMessage(MSG_WIRELESS_CHARGING_STARTED);
640 msg.setAsynchronous(true);
Beverlyae79ab92017-12-11 09:20:02 -0500641 msg.arg1 = batteryLevel;
Beverly91d0a632018-07-02 16:45:00 -0400642 msg.arg2 = userId;
Pavel Grafov28939982017-10-03 15:11:52 +0100643 mHandler.sendMessage(msg);
644 }
645
Beverlyc1313eb2018-01-31 18:07:21 -0500646 /**
Beverly91d0a632018-07-02 16:45:00 -0400647 * Called when wired charging has started - to provide user feedback
Beverlyc1313eb2018-01-31 18:07:21 -0500648 */
Beverly91d0a632018-07-02 16:45:00 -0400649 public void onWiredChargingStarted(@UserIdInt int userId) {
Beverlyc1313eb2018-01-31 18:07:21 -0500650 if (DEBUG) {
651 Slog.d(TAG, "onWiredChargingStarted");
652 }
653
654 mSuspendBlocker.acquire();
655 Message msg = mHandler.obtainMessage(MSG_WIRED_CHARGING_STARTED);
656 msg.setAsynchronous(true);
Beverly91d0a632018-07-02 16:45:00 -0400657 msg.arg1 = userId;
Beverlyc1313eb2018-01-31 18:07:21 -0500658 mHandler.sendMessage(msg);
659 }
660
Santos Cordon9204cc82019-11-21 11:45:28 +0000661 /**
662 * Dumps data for bugreports.
663 *
664 * @param pw The stream to print to.
665 */
666 public void dump(PrintWriter pw) {
667 if (mWakeLockLog != null) {
668 mWakeLockLog.dump(pw);
669 }
670 }
671
Jeff Brown96307042012-07-27 15:51:34 -0700672 private void updatePendingBroadcastLocked() {
673 if (!mBroadcastInProgress
Jeff Brown416c49c2015-05-26 19:50:18 -0700674 && mPendingInteractiveState != INTERACTIVE_STATE_UNKNOWN
Jeff Brown54308352012-10-04 17:59:58 -0700675 && (mPendingWakeUpBroadcast || mPendingGoToSleepBroadcast
Jeff Brown416c49c2015-05-26 19:50:18 -0700676 || mPendingInteractiveState != mBroadcastedInteractiveState)) {
Jeff Brown96307042012-07-27 15:51:34 -0700677 mBroadcastInProgress = true;
678 mSuspendBlocker.acquire();
679 Message msg = mHandler.obtainMessage(MSG_BROADCAST);
680 msg.setAsynchronous(true);
681 mHandler.sendMessage(msg);
682 }
683 }
684
Jeff Brown54308352012-10-04 17:59:58 -0700685 private void finishPendingBroadcastLocked() {
686 mBroadcastInProgress = false;
687 mSuspendBlocker.release();
688 }
689
Jeff Brown96307042012-07-27 15:51:34 -0700690 private void sendUserActivity() {
691 synchronized (mLock) {
692 if (!mUserActivityPending) {
693 return;
694 }
695 mUserActivityPending = false;
696 }
Peter Wang6a92dd42020-01-15 14:11:25 -0800697 TelephonyManager tm = mContext.getSystemService(TelephonyManager.class);
698 tm.notifyUserActivity();
Jeff Brown96307042012-07-27 15:51:34 -0700699 mPolicy.userActivity();
700 }
701
702 private void sendNextBroadcast() {
703 final int powerState;
Jeff Brown96307042012-07-27 15:51:34 -0700704 synchronized (mLock) {
Jeff Brownfbe96702014-11-19 18:30:58 -0800705 if (mBroadcastedInteractiveState == INTERACTIVE_STATE_UNKNOWN) {
Robert Horvath4fbab202019-11-29 15:36:39 +0100706 // Broadcasted power state is unknown.
707 // Send wake up or go to sleep.
708 switch (mPendingInteractiveState) {
709 case INTERACTIVE_STATE_ASLEEP:
710 mPendingGoToSleepBroadcast = false;
711 mBroadcastedInteractiveState = INTERACTIVE_STATE_ASLEEP;
712 break;
713
714 case INTERACTIVE_STATE_AWAKE:
715 default:
716 mPendingWakeUpBroadcast = false;
717 mBroadcastedInteractiveState = INTERACTIVE_STATE_AWAKE;
718 break;
719 }
Jeff Brownfbe96702014-11-19 18:30:58 -0800720 } else if (mBroadcastedInteractiveState == INTERACTIVE_STATE_AWAKE) {
Jeff Brown54308352012-10-04 17:59:58 -0700721 // Broadcasted power state is awake. Send asleep if needed.
722 if (mPendingWakeUpBroadcast || mPendingGoToSleepBroadcast
Jeff Brown416c49c2015-05-26 19:50:18 -0700723 || mPendingInteractiveState == INTERACTIVE_STATE_ASLEEP) {
Jeff Brown54308352012-10-04 17:59:58 -0700724 mPendingGoToSleepBroadcast = false;
Jeff Brownfbe96702014-11-19 18:30:58 -0800725 mBroadcastedInteractiveState = INTERACTIVE_STATE_ASLEEP;
Jeff Brown54308352012-10-04 17:59:58 -0700726 } else {
727 finishPendingBroadcastLocked();
728 return;
729 }
730 } else {
731 // Broadcasted power state is asleep. Send awake if needed.
732 if (mPendingWakeUpBroadcast || mPendingGoToSleepBroadcast
Jeff Brown416c49c2015-05-26 19:50:18 -0700733 || mPendingInteractiveState == INTERACTIVE_STATE_AWAKE) {
Jeff Brown54308352012-10-04 17:59:58 -0700734 mPendingWakeUpBroadcast = false;
Jeff Brownfbe96702014-11-19 18:30:58 -0800735 mBroadcastedInteractiveState = INTERACTIVE_STATE_AWAKE;
Jeff Brown54308352012-10-04 17:59:58 -0700736 } else {
737 finishPendingBroadcastLocked();
738 return;
739 }
Jeff Brown96307042012-07-27 15:51:34 -0700740 }
741
Jeff Brown96307042012-07-27 15:51:34 -0700742 mBroadcastStartTime = SystemClock.uptimeMillis();
Jeff Brownfbe96702014-11-19 18:30:58 -0800743 powerState = mBroadcastedInteractiveState;
Jeff Brown96307042012-07-27 15:51:34 -0700744 }
745
746 EventLog.writeEvent(EventLogTags.POWER_SCREEN_BROADCAST_SEND, 1);
747
Jeff Brownfbe96702014-11-19 18:30:58 -0800748 if (powerState == INTERACTIVE_STATE_AWAKE) {
Jeff Brown96307042012-07-27 15:51:34 -0700749 sendWakeUpBroadcast();
750 } else {
Jim Millerc522d162014-07-01 17:10:21 -0700751 sendGoToSleepBroadcast();
Jeff Brown96307042012-07-27 15:51:34 -0700752 }
753 }
754
755 private void sendWakeUpBroadcast() {
756 if (DEBUG) {
757 Slog.d(TAG, "Sending wake up broadcast.");
758 }
759
Sudheer Shankafc46e9b2016-10-21 17:55:27 -0700760 if (mActivityManagerInternal.isSystemReady()) {
Dianne Hackborn5ac72a22012-08-29 18:32:08 -0700761 mContext.sendOrderedBroadcastAsUser(mScreenOnIntent, UserHandle.ALL, null,
Jeff Brown96307042012-07-27 15:51:34 -0700762 mWakeUpBroadcastDone, mHandler, 0, null, null);
763 } else {
764 EventLog.writeEvent(EventLogTags.POWER_SCREEN_BROADCAST_STOP, 2, 1);
765 sendNextBroadcast();
766 }
767 }
768
769 private final BroadcastReceiver mWakeUpBroadcastDone = new BroadcastReceiver() {
770 @Override
771 public void onReceive(Context context, Intent intent) {
772 EventLog.writeEvent(EventLogTags.POWER_SCREEN_BROADCAST_DONE, 1,
773 SystemClock.uptimeMillis() - mBroadcastStartTime, 1);
774 sendNextBroadcast();
775 }
776 };
777
Jim Millerc522d162014-07-01 17:10:21 -0700778 private void sendGoToSleepBroadcast() {
Jeff Brown96307042012-07-27 15:51:34 -0700779 if (DEBUG) {
780 Slog.d(TAG, "Sending go to sleep broadcast.");
781 }
782
Sudheer Shankafc46e9b2016-10-21 17:55:27 -0700783 if (mActivityManagerInternal.isSystemReady()) {
Dianne Hackborn5ac72a22012-08-29 18:32:08 -0700784 mContext.sendOrderedBroadcastAsUser(mScreenOffIntent, UserHandle.ALL, null,
Jeff Brown96307042012-07-27 15:51:34 -0700785 mGoToSleepBroadcastDone, mHandler, 0, null, null);
786 } else {
787 EventLog.writeEvent(EventLogTags.POWER_SCREEN_BROADCAST_STOP, 3, 1);
788 sendNextBroadcast();
789 }
790 }
791
792 private final BroadcastReceiver mGoToSleepBroadcastDone = new BroadcastReceiver() {
793 @Override
794 public void onReceive(Context context, Intent intent) {
795 EventLog.writeEvent(EventLogTags.POWER_SCREEN_BROADCAST_DONE, 0,
796 SystemClock.uptimeMillis() - mBroadcastStartTime, 1);
797 sendNextBroadcast();
798 }
799 };
800
Beverlyf364d7c2019-10-10 16:44:43 -0400801 private void playChargingStartedFeedback(@UserIdInt int userId, boolean wireless) {
802 if (!isChargingFeedbackEnabled(userId)) {
803 return;
804 }
805
806 // vibrate
807 final boolean vibrate = Settings.Secure.getIntForUser(mContext.getContentResolver(),
808 Settings.Secure.CHARGING_VIBRATION_ENABLED, 1, userId) != 0;
809 if (vibrate) {
810 mVibrator.vibrate(CHARGING_VIBRATION_EFFECT, VIBRATION_ATTRIBUTES);
811 }
812
813 // play sound
Jeff Brown84e27562012-12-07 13:56:34 -0800814 final String soundPath = Settings.Global.getString(mContext.getContentResolver(),
Beverlyf364d7c2019-10-10 16:44:43 -0400815 wireless ? Settings.Global.WIRELESS_CHARGING_STARTED_SOUND
816 : Settings.Global.CHARGING_STARTED_SOUND);
817 final Uri soundUri = Uri.parse("file://" + soundPath);
818 if (soundUri != null) {
819 final Ringtone sfx = RingtoneManager.getRingtone(mContext, soundUri);
820 if (sfx != null) {
821 sfx.setStreamType(AudioManager.STREAM_SYSTEM);
822 sfx.play();
Jeff Brown84e27562012-12-07 13:56:34 -0800823 }
824 }
Beverlyae79ab92017-12-11 09:20:02 -0500825 }
Jeff Brown84e27562012-12-07 13:56:34 -0800826
Beverly91d0a632018-07-02 16:45:00 -0400827 private void showWirelessChargingStarted(int batteryLevel, @UserIdInt int userId) {
Beverlyf364d7c2019-10-10 16:44:43 -0400828 // play sounds + haptics
829 playChargingStartedFeedback(userId, true /* wireless */);
830
831 // show animation
832 if (mShowWirelessChargingAnimationConfig && mStatusBarManagerInternal != null) {
Andrew Zeng6d07baf2018-04-20 14:13:16 -0700833 mStatusBarManagerInternal.showChargingAnimation(batteryLevel);
834 }
Jeff Brown84e27562012-12-07 13:56:34 -0800835 mSuspendBlocker.release();
836 }
837
Beverly91d0a632018-07-02 16:45:00 -0400838 private void showWiredChargingStarted(@UserIdInt int userId) {
Beverlyf364d7c2019-10-10 16:44:43 -0400839 playChargingStartedFeedback(userId, false /* wireless */);
Beverlyc1313eb2018-01-31 18:07:21 -0500840 mSuspendBlocker.release();
841 }
842
Pavel Grafov28939982017-10-03 15:11:52 +0100843 private void lockProfile(@UserIdInt int userId) {
844 mTrustManager.setDeviceLockedForUser(userId, true /*locked*/);
845 }
846
Beverly91d0a632018-07-02 16:45:00 -0400847 private boolean isChargingFeedbackEnabled(@UserIdInt int userId) {
848 final boolean enabled = Settings.Secure.getIntForUser(mContext.getContentResolver(),
849 Settings.Secure.CHARGING_SOUNDS_ENABLED, 1, userId) != 0;
Beverly69721d62018-05-09 17:41:44 -0400850 final boolean dndOff = Settings.Global.getInt(mContext.getContentResolver(),
851 Settings.Global.ZEN_MODE, Settings.Global.ZEN_MODE_IMPORTANT_INTERRUPTIONS)
852 == Settings.Global.ZEN_MODE_OFF;
853 return enabled && dndOff;
854 }
855
Jeff Brown96307042012-07-27 15:51:34 -0700856 private final class NotifierHandler extends Handler {
Pavel Grafov28939982017-10-03 15:11:52 +0100857
Jeff Brown96307042012-07-27 15:51:34 -0700858 public NotifierHandler(Looper looper) {
Jeff Browna2910d02012-08-25 12:29:46 -0700859 super(looper, null, true /*async*/);
Jeff Brown96307042012-07-27 15:51:34 -0700860 }
Jeff Brown96307042012-07-27 15:51:34 -0700861 @Override
862 public void handleMessage(Message msg) {
863 switch (msg.what) {
864 case MSG_USER_ACTIVITY:
865 sendUserActivity();
866 break;
Jeff Brown96307042012-07-27 15:51:34 -0700867 case MSG_BROADCAST:
868 sendNextBroadcast();
869 break;
Jeff Brown84e27562012-12-07 13:56:34 -0800870 case MSG_WIRELESS_CHARGING_STARTED:
Beverly91d0a632018-07-02 16:45:00 -0400871 showWirelessChargingStarted(msg.arg1, msg.arg2);
Jeff Brown84e27562012-12-07 13:56:34 -0800872 break;
Pavel Grafov28939982017-10-03 15:11:52 +0100873 case MSG_PROFILE_TIMED_OUT:
874 lockProfile(msg.arg1);
875 break;
Beverlyc1313eb2018-01-31 18:07:21 -0500876 case MSG_WIRED_CHARGING_STARTED:
Beverly91d0a632018-07-02 16:45:00 -0400877 showWiredChargingStarted(msg.arg1);
Beverly69721d62018-05-09 17:41:44 -0400878 break;
Jeff Brown96307042012-07-27 15:51:34 -0700879 }
880 }
881 }
882}