PowerManagerService.java revision 9e316a1a2a8d734315bbd56a85308f9657a92913
1/*
2 * Copyright (C) 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.server.power;
18
19import com.android.internal.app.IBatteryStats;
20import com.android.server.BatteryService;
21import com.android.server.EventLogTags;
22import com.android.server.LightsService;
23import com.android.server.TwilightService;
24import com.android.server.Watchdog;
25import com.android.server.am.ActivityManagerService;
26import com.android.server.display.DisplayManagerService;
27import com.android.server.dreams.DreamManagerService;
28
29import android.Manifest;
30import android.content.BroadcastReceiver;
31import android.content.ContentResolver;
32import android.content.Context;
33import android.content.Intent;
34import android.content.IntentFilter;
35import android.content.pm.PackageManager;
36import android.content.res.Resources;
37import android.database.ContentObserver;
38import android.net.Uri;
39import android.os.BatteryManager;
40import android.os.Binder;
41import android.os.Handler;
42import android.os.HandlerThread;
43import android.os.IBinder;
44import android.os.IPowerManager;
45import android.os.Looper;
46import android.os.Message;
47import android.os.PowerManager;
48import android.os.Process;
49import android.os.RemoteException;
50import android.os.SystemClock;
51import android.os.UserHandle;
52import android.os.WorkSource;
53import android.provider.Settings;
54import android.util.EventLog;
55import android.util.Log;
56import android.util.Slog;
57import android.util.TimeUtils;
58import android.view.WindowManagerPolicy;
59
60import java.io.FileDescriptor;
61import java.io.IOException;
62import java.io.PrintWriter;
63import java.util.ArrayList;
64
65import libcore.util.Objects;
66
67/**
68 * The power manager service is responsible for coordinating power management
69 * functions on the device.
70 */
71public final class PowerManagerService extends IPowerManager.Stub
72        implements Watchdog.Monitor {
73    private static final String TAG = "PowerManagerService";
74
75    private static final boolean DEBUG = false;
76    private static final boolean DEBUG_SPEW = DEBUG && true;
77
78    // Message: Sent when a user activity timeout occurs to update the power state.
79    private static final int MSG_USER_ACTIVITY_TIMEOUT = 1;
80    // Message: Sent when the device enters or exits a napping or dreaming state.
81    private static final int MSG_SANDMAN = 2;
82    // Message: Sent when the screen on blocker is released.
83    private static final int MSG_SCREEN_ON_BLOCKER_RELEASED = 3;
84
85    // Dirty bit: mWakeLocks changed
86    private static final int DIRTY_WAKE_LOCKS = 1 << 0;
87    // Dirty bit: mWakefulness changed
88    private static final int DIRTY_WAKEFULNESS = 1 << 1;
89    // Dirty bit: user activity was poked or may have timed out
90    private static final int DIRTY_USER_ACTIVITY = 1 << 2;
91    // Dirty bit: actual display power state was updated asynchronously
92    private static final int DIRTY_ACTUAL_DISPLAY_POWER_STATE_UPDATED = 1 << 3;
93    // Dirty bit: mBootCompleted changed
94    private static final int DIRTY_BOOT_COMPLETED = 1 << 4;
95    // Dirty bit: settings changed
96    private static final int DIRTY_SETTINGS = 1 << 5;
97    // Dirty bit: mIsPowered changed
98    private static final int DIRTY_IS_POWERED = 1 << 6;
99    // Dirty bit: mStayOn changed
100    private static final int DIRTY_STAY_ON = 1 << 7;
101    // Dirty bit: battery state changed
102    private static final int DIRTY_BATTERY_STATE = 1 << 8;
103    // Dirty bit: proximity state changed
104    private static final int DIRTY_PROXIMITY_POSITIVE = 1 << 9;
105    // Dirty bit: screen on blocker state became held or unheld
106    private static final int DIRTY_SCREEN_ON_BLOCKER_RELEASED = 1 << 10;
107
108    // Wakefulness: The device is asleep and can only be awoken by a call to wakeUp().
109    // The screen should be off or in the process of being turned off by the display controller.
110    private static final int WAKEFULNESS_ASLEEP = 0;
111    // Wakefulness: The device is fully awake.  It can be put to sleep by a call to goToSleep().
112    // When the user activity timeout expires, the device may start napping or go to sleep.
113    private static final int WAKEFULNESS_AWAKE = 1;
114    // Wakefulness: The device is napping.  It is deciding whether to dream or go to sleep
115    // but hasn't gotten around to it yet.  It can be awoken by a call to wakeUp(), which
116    // ends the nap. User activity may brighten the screen but does not end the nap.
117    private static final int WAKEFULNESS_NAPPING = 2;
118    // Wakefulness: The device is dreaming.  It can be awoken by a call to wakeUp(),
119    // which ends the dream.  The device goes to sleep when goToSleep() is called, when
120    // the dream ends or when unplugged.
121    // User activity may brighten the screen but does not end the dream.
122    private static final int WAKEFULNESS_DREAMING = 3;
123
124    // Summarizes the state of all active wakelocks.
125    private static final int WAKE_LOCK_CPU = 1 << 0;
126    private static final int WAKE_LOCK_SCREEN_BRIGHT = 1 << 1;
127    private static final int WAKE_LOCK_SCREEN_DIM = 1 << 2;
128    private static final int WAKE_LOCK_BUTTON_BRIGHT = 1 << 3;
129    private static final int WAKE_LOCK_PROXIMITY_SCREEN_OFF = 1 << 4;
130
131    // Summarizes the user activity state.
132    private static final int USER_ACTIVITY_SCREEN_BRIGHT = 1 << 0;
133    private static final int USER_ACTIVITY_SCREEN_DIM = 1 << 1;
134
135    // Default and minimum screen off timeout in milliseconds.
136    private static final int DEFAULT_SCREEN_OFF_TIMEOUT = 15 * 1000;
137    private static final int MINIMUM_SCREEN_OFF_TIMEOUT = 10 * 1000;
138
139    // The screen dim duration, in milliseconds.
140    // This is subtracted from the end of the screen off timeout so the
141    // minimum screen off timeout should be longer than this.
142    private static final int SCREEN_DIM_DURATION = 7 * 1000;
143
144    // The maximum screen dim time expressed as a ratio relative to the screen
145    // off timeout.  If the screen off timeout is very short then we want the
146    // dim timeout to also be quite short so that most of the time is spent on.
147    // Otherwise the user won't get much screen on time before dimming occurs.
148    private static final float MAXIMUM_SCREEN_DIM_RATIO = 0.2f;
149
150    // Upper bound on the battery charge percentage in order to consider turning
151    // the screen on when the device starts charging wirelessly.
152    // See point of use for more details.
153    private static final int WIRELESS_CHARGER_TURN_ON_BATTERY_LEVEL_LIMIT = 95;
154
155    private Context mContext;
156    private LightsService mLightsService;
157    private BatteryService mBatteryService;
158    private DisplayManagerService mDisplayManagerService;
159    private IBatteryStats mBatteryStats;
160    private HandlerThread mHandlerThread;
161    private PowerManagerHandler mHandler;
162    private WindowManagerPolicy mPolicy;
163    private Notifier mNotifier;
164    private DisplayPowerController mDisplayPowerController;
165    private SettingsObserver mSettingsObserver;
166    private DreamManagerService mDreamManager;
167    private LightsService.Light mAttentionLight;
168
169    private final Object mLock = new Object();
170
171    // A bitfield that indicates what parts of the power state have
172    // changed and need to be recalculated.
173    private int mDirty;
174
175    // Indicates whether the device is awake or asleep or somewhere in between.
176    // This is distinct from the screen power state, which is managed separately.
177    private int mWakefulness;
178
179    // True if MSG_SANDMAN has been scheduled.
180    private boolean mSandmanScheduled;
181
182    // Table of all suspend blockers.
183    // There should only be a few of these.
184    private final ArrayList<SuspendBlocker> mSuspendBlockers = new ArrayList<SuspendBlocker>();
185
186    // Table of all wake locks acquired by applications.
187    private final ArrayList<WakeLock> mWakeLocks = new ArrayList<WakeLock>();
188
189    // A bitfield that summarizes the state of all active wakelocks.
190    private int mWakeLockSummary;
191
192    // If true, instructs the display controller to wait for the proximity sensor to
193    // go negative before turning the screen on.
194    private boolean mRequestWaitForNegativeProximity;
195
196    // Timestamp of the last time the device was awoken or put to sleep.
197    private long mLastWakeTime;
198    private long mLastSleepTime;
199
200    // True if we need to send a wake up or go to sleep finished notification
201    // when the display is ready.
202    private boolean mSendWakeUpFinishedNotificationWhenReady;
203    private boolean mSendGoToSleepFinishedNotificationWhenReady;
204
205    // Timestamp of the last call to user activity.
206    private long mLastUserActivityTime;
207    private long mLastUserActivityTimeNoChangeLights;
208
209    // A bitfield that summarizes the effect of the user activity timer.
210    // A zero value indicates that the user activity timer has expired.
211    private int mUserActivitySummary;
212
213    // The desired display power state.  The actual state may lag behind the
214    // requested because it is updated asynchronously by the display power controller.
215    private final DisplayPowerRequest mDisplayPowerRequest = new DisplayPowerRequest();
216
217    // The time the screen was last turned off, in elapsedRealtime() timebase.
218    private long mLastScreenOffEventElapsedRealTime;
219
220    // True if the display power state has been fully applied, which means the display
221    // is actually on or actually off or whatever was requested.
222    private boolean mDisplayReady;
223
224    // True if holding a wake-lock to block suspend of the CPU.
225    private boolean mHoldingWakeLockSuspendBlocker;
226
227    // The suspend blocker used to keep the CPU alive when wake locks have been acquired.
228    private final SuspendBlocker mWakeLockSuspendBlocker;
229
230    // The screen on blocker used to keep the screen from turning on while the lock
231    // screen is coming up.
232    private final ScreenOnBlockerImpl mScreenOnBlocker;
233
234    // The display blanker used to turn the screen on or off.
235    private final DisplayBlankerImpl mDisplayBlanker;
236
237    // True if systemReady() has been called.
238    private boolean mSystemReady;
239
240    // True if boot completed occurred.  We keep the screen on until this happens.
241    private boolean mBootCompleted;
242
243    // True if the device is plugged into a power source.
244    private boolean mIsPowered;
245
246    // The current plug type, such as BatteryManager.BATTERY_PLUGGED_WIRELESS.
247    private int mPlugType;
248
249    // True if the device should wake up when plugged or unplugged.
250    private boolean mWakeUpWhenPluggedOrUnpluggedConfig;
251
252    // True if dreams are supported on this device.
253    private boolean mDreamsSupportedConfig;
254
255    // True if dreams are enabled by the user.
256    private boolean mDreamsEnabledSetting;
257
258    // True if dreams should be activated on sleep.
259    private boolean mDreamsActivateOnSleepSetting;
260
261    // The screen off timeout setting value in milliseconds.
262    private int mScreenOffTimeoutSetting;
263
264    // The maximum allowable screen off timeout according to the device
265    // administration policy.  Overrides other settings.
266    private int mMaximumScreenOffTimeoutFromDeviceAdmin = Integer.MAX_VALUE;
267
268    // The stay on while plugged in setting.
269    // A bitfield of battery conditions under which to make the screen stay on.
270    private int mStayOnWhilePluggedInSetting;
271
272    // True if the device should stay on.
273    private boolean mStayOn;
274
275    // True if the proximity sensor reads a positive result.
276    private boolean mProximityPositive;
277
278    // Screen brightness setting limits.
279    private int mScreenBrightnessSettingMinimum;
280    private int mScreenBrightnessSettingMaximum;
281    private int mScreenBrightnessSettingDefault;
282
283    // The screen brightness setting, from 0 to 255.
284    // Use -1 if no value has been set.
285    private int mScreenBrightnessSetting;
286
287    // The screen auto-brightness adjustment setting, from -1 to 1.
288    // Use 0 if there is no adjustment.
289    private float mScreenAutoBrightnessAdjustmentSetting;
290
291    // The screen brightness mode.
292    // One of the Settings.System.SCREEN_BRIGHTNESS_MODE_* constants.
293    private int mScreenBrightnessModeSetting;
294
295    // The screen brightness setting override from the window manager
296    // to allow the current foreground activity to override the brightness.
297    // Use -1 to disable.
298    private int mScreenBrightnessOverrideFromWindowManager = -1;
299
300    // The user activity timeout override from the window manager
301    // to allow the current foreground activity to override the user activity timeout.
302    // Use -1 to disable.
303    private long mUserActivityTimeoutOverrideFromWindowManager = -1;
304
305    // The screen brightness setting override from the settings application
306    // to temporarily adjust the brightness until next updated,
307    // Use -1 to disable.
308    private int mTemporaryScreenBrightnessSettingOverride = -1;
309
310    // The screen brightness adjustment setting override from the settings
311    // application to temporarily adjust the auto-brightness adjustment factor
312    // until next updated, in the range -1..1.
313    // Use NaN to disable.
314    private float mTemporaryScreenAutoBrightnessAdjustmentSettingOverride = Float.NaN;
315
316    // Time when we last logged a warning about calling userActivity() without permission.
317    private long mLastWarningAboutUserActivityPermission = Long.MIN_VALUE;
318
319    private native void nativeInit();
320    private static native void nativeShutdown();
321    private static native void nativeReboot(String reason) throws IOException;
322
323    private static native void nativeSetPowerState(boolean screenOn, boolean screenBright);
324    private static native void nativeAcquireSuspendBlocker(String name);
325    private static native void nativeReleaseSuspendBlocker(String name);
326    private static native void nativeSetInteractive(boolean enable);
327    private static native void nativeSetAutoSuspend(boolean enable);
328
329    public PowerManagerService() {
330        synchronized (mLock) {
331            mWakeLockSuspendBlocker = createSuspendBlockerLocked("PowerManagerService");
332            mWakeLockSuspendBlocker.acquire();
333            mScreenOnBlocker = new ScreenOnBlockerImpl();
334            mDisplayBlanker = new DisplayBlankerImpl();
335            mHoldingWakeLockSuspendBlocker = true;
336            mWakefulness = WAKEFULNESS_AWAKE;
337        }
338
339        nativeInit();
340        nativeSetPowerState(true, true);
341    }
342
343    /**
344     * Initialize the power manager.
345     * Must be called before any other functions within the power manager are called.
346     */
347    public void init(Context context, LightsService ls,
348            ActivityManagerService am, BatteryService bs, IBatteryStats bss,
349            DisplayManagerService dm) {
350        mContext = context;
351        mLightsService = ls;
352        mBatteryService = bs;
353        mBatteryStats = bss;
354        mDisplayManagerService = dm;
355        mHandlerThread = new HandlerThread(TAG);
356        mHandlerThread.start();
357        mHandler = new PowerManagerHandler(mHandlerThread.getLooper());
358
359        Watchdog.getInstance().addMonitor(this);
360
361        // Forcibly turn the screen on at boot so that it is in a known power state.
362        // We do this in init() rather than in the constructor because setting the
363        // screen state requires a call into surface flinger which then needs to call back
364        // into the activity manager to check permissions.  Unfortunately the
365        // activity manager is not running when the constructor is called, so we
366        // have to defer setting the screen state until this point.
367        mDisplayBlanker.unblankAllDisplays();
368    }
369
370    public void setPolicy(WindowManagerPolicy policy) {
371        synchronized (mLock) {
372            mPolicy = policy;
373        }
374    }
375
376    public void systemReady(TwilightService twilight, DreamManagerService dreamManager) {
377        synchronized (mLock) {
378            mSystemReady = true;
379            mDreamManager = dreamManager;
380
381            PowerManager pm = (PowerManager)mContext.getSystemService(Context.POWER_SERVICE);
382            mScreenBrightnessSettingMinimum = pm.getMinimumScreenBrightnessSetting();
383            mScreenBrightnessSettingMaximum = pm.getMaximumScreenBrightnessSetting();
384            mScreenBrightnessSettingDefault = pm.getDefaultScreenBrightnessSetting();
385
386            // The notifier runs on the system server's main looper so as not to interfere
387            // with the animations and other critical functions of the power manager.
388            mNotifier = new Notifier(Looper.getMainLooper(), mContext, mBatteryStats,
389                    createSuspendBlockerLocked("PowerManagerService.Broadcasts"),
390                    mScreenOnBlocker, mPolicy);
391
392            // The display power controller runs on the power manager service's
393            // own handler thread.
394            mDisplayPowerController = new DisplayPowerController(mHandler.getLooper(),
395                    mContext, mNotifier, mLightsService, twilight,
396                    createSuspendBlockerLocked("PowerManagerService.Display"),
397                    mDisplayBlanker, mDisplayPowerControllerCallbacks, mHandler);
398
399            mSettingsObserver = new SettingsObserver(mHandler);
400            mAttentionLight = mLightsService.getLight(LightsService.LIGHT_ID_ATTENTION);
401
402            // Register for broadcasts from other components of the system.
403            IntentFilter filter = new IntentFilter();
404            filter.addAction(Intent.ACTION_BATTERY_CHANGED);
405            mContext.registerReceiver(new BatteryReceiver(), filter, null, mHandler);
406
407            filter = new IntentFilter();
408            filter.addAction(Intent.ACTION_BOOT_COMPLETED);
409            mContext.registerReceiver(new BootCompletedReceiver(), filter, null, mHandler);
410
411            filter = new IntentFilter();
412            filter.addAction(Intent.ACTION_DREAMING_STARTED);
413            filter.addAction(Intent.ACTION_DREAMING_STOPPED);
414            mContext.registerReceiver(new DreamReceiver(), filter, null, mHandler);
415
416            filter = new IntentFilter();
417            filter.addAction(Intent.ACTION_USER_SWITCHED);
418            mContext.registerReceiver(new UserSwitchedReceiver(), filter, null, mHandler);
419
420            // Register for settings changes.
421            final ContentResolver resolver = mContext.getContentResolver();
422            resolver.registerContentObserver(Settings.Secure.getUriFor(
423                    Settings.Secure.SCREENSAVER_ENABLED),
424                    false, mSettingsObserver, UserHandle.USER_ALL);
425            resolver.registerContentObserver(Settings.Secure.getUriFor(
426                    Settings.Secure.SCREENSAVER_ACTIVATE_ON_SLEEP),
427                    false, mSettingsObserver, UserHandle.USER_ALL);
428            resolver.registerContentObserver(Settings.System.getUriFor(
429                    Settings.System.SCREEN_OFF_TIMEOUT),
430                    false, mSettingsObserver, UserHandle.USER_ALL);
431            resolver.registerContentObserver(Settings.Global.getUriFor(
432                    Settings.Global.STAY_ON_WHILE_PLUGGED_IN),
433                    false, mSettingsObserver, UserHandle.USER_ALL);
434            resolver.registerContentObserver(Settings.System.getUriFor(
435                    Settings.System.SCREEN_BRIGHTNESS),
436                    false, mSettingsObserver, UserHandle.USER_ALL);
437            resolver.registerContentObserver(Settings.System.getUriFor(
438                    Settings.System.SCREEN_BRIGHTNESS_MODE),
439                    false, mSettingsObserver, UserHandle.USER_ALL);
440
441            // Go.
442            readConfigurationLocked();
443            updateSettingsLocked();
444            mDirty |= DIRTY_BATTERY_STATE;
445            updatePowerStateLocked();
446        }
447    }
448
449    private void readConfigurationLocked() {
450        final Resources resources = mContext.getResources();
451
452        mWakeUpWhenPluggedOrUnpluggedConfig = resources.getBoolean(
453                com.android.internal.R.bool.config_unplugTurnsOnScreen);
454        mDreamsSupportedConfig = resources.getBoolean(
455                com.android.internal.R.bool.config_enableDreams);
456    }
457
458    private void updateSettingsLocked() {
459        final ContentResolver resolver = mContext.getContentResolver();
460
461        mDreamsEnabledSetting = (Settings.Secure.getIntForUser(resolver,
462                Settings.Secure.SCREENSAVER_ENABLED, 0,
463                UserHandle.USER_CURRENT) != 0);
464        mDreamsActivateOnSleepSetting = (Settings.Secure.getIntForUser(resolver,
465                Settings.Secure.SCREENSAVER_ACTIVATE_ON_SLEEP, 0,
466                UserHandle.USER_CURRENT) != 0);
467        mScreenOffTimeoutSetting = Settings.System.getIntForUser(resolver,
468                Settings.System.SCREEN_OFF_TIMEOUT, DEFAULT_SCREEN_OFF_TIMEOUT,
469                UserHandle.USER_CURRENT);
470        mStayOnWhilePluggedInSetting = Settings.Global.getInt(resolver,
471                Settings.Global.STAY_ON_WHILE_PLUGGED_IN, BatteryManager.BATTERY_PLUGGED_AC);
472
473        final int oldScreenBrightnessSetting = mScreenBrightnessSetting;
474        mScreenBrightnessSetting = Settings.System.getIntForUser(resolver,
475                Settings.System.SCREEN_BRIGHTNESS, mScreenBrightnessSettingDefault,
476                UserHandle.USER_CURRENT);
477        if (oldScreenBrightnessSetting != mScreenBrightnessSetting) {
478            mTemporaryScreenBrightnessSettingOverride = -1;
479        }
480
481        final float oldScreenAutoBrightnessAdjustmentSetting =
482                mScreenAutoBrightnessAdjustmentSetting;
483        mScreenAutoBrightnessAdjustmentSetting = Settings.System.getFloatForUser(resolver,
484                Settings.System.SCREEN_AUTO_BRIGHTNESS_ADJ, 0.0f,
485                UserHandle.USER_CURRENT);
486        if (oldScreenAutoBrightnessAdjustmentSetting != mScreenAutoBrightnessAdjustmentSetting) {
487            mTemporaryScreenAutoBrightnessAdjustmentSettingOverride = Float.NaN;
488        }
489
490        mScreenBrightnessModeSetting = Settings.System.getIntForUser(resolver,
491                Settings.System.SCREEN_BRIGHTNESS_MODE,
492                Settings.System.SCREEN_BRIGHTNESS_MODE_MANUAL, UserHandle.USER_CURRENT);
493
494        mDirty |= DIRTY_SETTINGS;
495    }
496
497    private void handleSettingsChangedLocked() {
498        updateSettingsLocked();
499        updatePowerStateLocked();
500    }
501
502    @Override // Binder call
503    public void acquireWakeLock(IBinder lock, int flags, String tag, WorkSource ws) {
504        if (lock == null) {
505            throw new IllegalArgumentException("lock must not be null");
506        }
507        PowerManager.validateWakeLockParameters(flags, tag);
508
509        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WAKE_LOCK, null);
510        if (ws != null && ws.size() != 0) {
511            mContext.enforceCallingOrSelfPermission(
512                    android.Manifest.permission.UPDATE_DEVICE_STATS, null);
513        } else {
514            ws = null;
515        }
516
517        final int uid = Binder.getCallingUid();
518        final int pid = Binder.getCallingPid();
519        final long ident = Binder.clearCallingIdentity();
520        try {
521            acquireWakeLockInternal(lock, flags, tag, ws, uid, pid);
522        } finally {
523            Binder.restoreCallingIdentity(ident);
524        }
525    }
526
527    private void acquireWakeLockInternal(IBinder lock, int flags, String tag, WorkSource ws,
528            int uid, int pid) {
529        synchronized (mLock) {
530            if (DEBUG_SPEW) {
531                Slog.d(TAG, "acquireWakeLockInternal: lock=" + Objects.hashCode(lock)
532                        + ", flags=0x" + Integer.toHexString(flags)
533                        + ", tag=\"" + tag + "\", ws=" + ws + ", uid=" + uid + ", pid=" + pid);
534            }
535
536            WakeLock wakeLock;
537            int index = findWakeLockIndexLocked(lock);
538            if (index >= 0) {
539                wakeLock = mWakeLocks.get(index);
540                if (!wakeLock.hasSameProperties(flags, tag, ws, uid, pid)) {
541                    // Update existing wake lock.  This shouldn't happen but is harmless.
542                    notifyWakeLockReleasedLocked(wakeLock);
543                    wakeLock.updateProperties(flags, tag, ws, uid, pid);
544                    notifyWakeLockAcquiredLocked(wakeLock);
545                }
546            } else {
547                wakeLock = new WakeLock(lock, flags, tag, ws, uid, pid);
548                try {
549                    lock.linkToDeath(wakeLock, 0);
550                } catch (RemoteException ex) {
551                    throw new IllegalArgumentException("Wake lock is already dead.");
552                }
553                notifyWakeLockAcquiredLocked(wakeLock);
554                mWakeLocks.add(wakeLock);
555            }
556
557            applyWakeLockFlagsOnAcquireLocked(wakeLock);
558            mDirty |= DIRTY_WAKE_LOCKS;
559            updatePowerStateLocked();
560        }
561    }
562
563    private void applyWakeLockFlagsOnAcquireLocked(WakeLock wakeLock) {
564        if ((wakeLock.mFlags & PowerManager.ACQUIRE_CAUSES_WAKEUP) != 0) {
565            wakeUpNoUpdateLocked(SystemClock.uptimeMillis());
566        }
567    }
568
569    @Override // Binder call
570    public void releaseWakeLock(IBinder lock, int flags) {
571        if (lock == null) {
572            throw new IllegalArgumentException("lock must not be null");
573        }
574
575        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WAKE_LOCK, null);
576
577        final long ident = Binder.clearCallingIdentity();
578        try {
579            releaseWakeLockInternal(lock, flags);
580        } finally {
581            Binder.restoreCallingIdentity(ident);
582        }
583    }
584
585    private void releaseWakeLockInternal(IBinder lock, int flags) {
586        synchronized (mLock) {
587            if (DEBUG_SPEW) {
588                Slog.d(TAG, "releaseWakeLockInternal: lock=" + Objects.hashCode(lock)
589                        + ", flags=0x" + Integer.toHexString(flags));
590            }
591
592            int index = findWakeLockIndexLocked(lock);
593            if (index < 0) {
594                return;
595            }
596
597            WakeLock wakeLock = mWakeLocks.get(index);
598            mWakeLocks.remove(index);
599            notifyWakeLockReleasedLocked(wakeLock);
600            wakeLock.mLock.unlinkToDeath(wakeLock, 0);
601
602            if ((flags & PowerManager.WAIT_FOR_PROXIMITY_NEGATIVE) != 0) {
603                mRequestWaitForNegativeProximity = true;
604            }
605
606            applyWakeLockFlagsOnReleaseLocked(wakeLock);
607            mDirty |= DIRTY_WAKE_LOCKS;
608            updatePowerStateLocked();
609        }
610    }
611
612    private void handleWakeLockDeath(WakeLock wakeLock) {
613        synchronized (mLock) {
614            if (DEBUG_SPEW) {
615                Slog.d(TAG, "handleWakeLockDeath: lock=" + Objects.hashCode(wakeLock.mLock));
616            }
617
618            int index = mWakeLocks.indexOf(wakeLock);
619            if (index < 0) {
620                return;
621            }
622
623            mWakeLocks.remove(index);
624            notifyWakeLockReleasedLocked(wakeLock);
625
626            applyWakeLockFlagsOnReleaseLocked(wakeLock);
627            mDirty |= DIRTY_WAKE_LOCKS;
628            updatePowerStateLocked();
629        }
630    }
631
632    private void applyWakeLockFlagsOnReleaseLocked(WakeLock wakeLock) {
633        if ((wakeLock.mFlags & PowerManager.ON_AFTER_RELEASE) != 0) {
634            userActivityNoUpdateLocked(SystemClock.uptimeMillis(),
635                    PowerManager.USER_ACTIVITY_EVENT_OTHER,
636                    PowerManager.USER_ACTIVITY_FLAG_NO_CHANGE_LIGHTS,
637                    wakeLock.mOwnerUid);
638        }
639    }
640
641    @Override // Binder call
642    public void updateWakeLockWorkSource(IBinder lock, WorkSource ws) {
643        if (lock == null) {
644            throw new IllegalArgumentException("lock must not be null");
645        }
646
647        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WAKE_LOCK, null);
648        if (ws != null && ws.size() != 0) {
649            mContext.enforceCallingOrSelfPermission(
650                    android.Manifest.permission.UPDATE_DEVICE_STATS, null);
651        } else {
652            ws = null;
653        }
654
655        final long ident = Binder.clearCallingIdentity();
656        try {
657            updateWakeLockWorkSourceInternal(lock, ws);
658        } finally {
659            Binder.restoreCallingIdentity(ident);
660        }
661    }
662
663    private void updateWakeLockWorkSourceInternal(IBinder lock, WorkSource ws) {
664        synchronized (mLock) {
665            int index = findWakeLockIndexLocked(lock);
666            if (index < 0) {
667                throw new IllegalArgumentException("Wake lock not active");
668            }
669
670            WakeLock wakeLock = mWakeLocks.get(index);
671            if (!wakeLock.hasSameWorkSource(ws)) {
672                notifyWakeLockReleasedLocked(wakeLock);
673                wakeLock.updateWorkSource(ws);
674                notifyWakeLockAcquiredLocked(wakeLock);
675            }
676        }
677    }
678
679    private int findWakeLockIndexLocked(IBinder lock) {
680        final int count = mWakeLocks.size();
681        for (int i = 0; i < count; i++) {
682            if (mWakeLocks.get(i).mLock == lock) {
683                return i;
684            }
685        }
686        return -1;
687    }
688
689    private void notifyWakeLockAcquiredLocked(WakeLock wakeLock) {
690        if (mSystemReady) {
691            mNotifier.onWakeLockAcquired(wakeLock.mFlags, wakeLock.mTag,
692                    wakeLock.mOwnerUid, wakeLock.mOwnerPid, wakeLock.mWorkSource);
693        }
694    }
695
696    private void notifyWakeLockReleasedLocked(WakeLock wakeLock) {
697        if (mSystemReady) {
698            mNotifier.onWakeLockReleased(wakeLock.mFlags, wakeLock.mTag,
699                    wakeLock.mOwnerUid, wakeLock.mOwnerPid, wakeLock.mWorkSource);
700        }
701    }
702
703    @Override // Binder call
704    public boolean isWakeLockLevelSupported(int level) {
705        final long ident = Binder.clearCallingIdentity();
706        try {
707            return isWakeLockLevelSupportedInternal(level);
708        } finally {
709            Binder.restoreCallingIdentity(ident);
710        }
711    }
712
713    private boolean isWakeLockLevelSupportedInternal(int level) {
714        synchronized (mLock) {
715            switch (level) {
716                case PowerManager.PARTIAL_WAKE_LOCK:
717                case PowerManager.SCREEN_DIM_WAKE_LOCK:
718                case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
719                case PowerManager.FULL_WAKE_LOCK:
720                    return true;
721
722                case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
723                    return mSystemReady && mDisplayPowerController.isProximitySensorAvailable();
724
725                default:
726                    return false;
727            }
728        }
729    }
730
731    @Override // Binder call
732    public void userActivity(long eventTime, int event, int flags) {
733        final long now = SystemClock.uptimeMillis();
734        if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER)
735                != PackageManager.PERMISSION_GRANTED) {
736            // Once upon a time applications could call userActivity().
737            // Now we require the DEVICE_POWER permission.  Log a warning and ignore the
738            // request instead of throwing a SecurityException so we don't break old apps.
739            synchronized (mLock) {
740                if (now >= mLastWarningAboutUserActivityPermission + (5 * 60 * 1000)) {
741                    mLastWarningAboutUserActivityPermission = now;
742                    Slog.w(TAG, "Ignoring call to PowerManager.userActivity() because the "
743                            + "caller does not have DEVICE_POWER permission.  "
744                            + "Please fix your app!  "
745                            + " pid=" + Binder.getCallingPid()
746                            + " uid=" + Binder.getCallingUid());
747                }
748            }
749            return;
750        }
751
752        if (eventTime > SystemClock.uptimeMillis()) {
753            throw new IllegalArgumentException("event time must not be in the future");
754        }
755
756        final int uid = Binder.getCallingUid();
757        final long ident = Binder.clearCallingIdentity();
758        try {
759            userActivityInternal(eventTime, event, flags, uid);
760        } finally {
761            Binder.restoreCallingIdentity(ident);
762        }
763    }
764
765    // Called from native code.
766    private void userActivityFromNative(long eventTime, int event, int flags) {
767        userActivityInternal(eventTime, event, flags, Process.SYSTEM_UID);
768    }
769
770    private void userActivityInternal(long eventTime, int event, int flags, int uid) {
771        synchronized (mLock) {
772            if (userActivityNoUpdateLocked(eventTime, event, flags, uid)) {
773                updatePowerStateLocked();
774            }
775        }
776    }
777
778    private boolean userActivityNoUpdateLocked(long eventTime, int event, int flags, int uid) {
779        if (DEBUG_SPEW) {
780            Slog.d(TAG, "userActivityNoUpdateLocked: eventTime=" + eventTime
781                    + ", event=" + event + ", flags=0x" + Integer.toHexString(flags)
782                    + ", uid=" + uid);
783        }
784
785        if (eventTime < mLastSleepTime || eventTime < mLastWakeTime
786                || mWakefulness == WAKEFULNESS_ASLEEP || !mBootCompleted || !mSystemReady) {
787            return false;
788        }
789
790        mNotifier.onUserActivity(event, uid);
791
792        if ((flags & PowerManager.USER_ACTIVITY_FLAG_NO_CHANGE_LIGHTS) != 0) {
793            if (eventTime > mLastUserActivityTimeNoChangeLights
794                    && eventTime > mLastUserActivityTime) {
795                mLastUserActivityTimeNoChangeLights = eventTime;
796                mDirty |= DIRTY_USER_ACTIVITY;
797                return true;
798            }
799        } else {
800            if (eventTime > mLastUserActivityTime) {
801                mLastUserActivityTime = eventTime;
802                mDirty |= DIRTY_USER_ACTIVITY;
803                return true;
804            }
805        }
806        return false;
807    }
808
809    @Override // Binder call
810    public void wakeUp(long eventTime) {
811        if (eventTime > SystemClock.uptimeMillis()) {
812            throw new IllegalArgumentException("event time must not be in the future");
813        }
814
815        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
816
817        final long ident = Binder.clearCallingIdentity();
818        try {
819            wakeUpInternal(eventTime);
820        } finally {
821            Binder.restoreCallingIdentity(ident);
822        }
823    }
824
825    // Called from native code.
826    private void wakeUpFromNative(long eventTime) {
827        wakeUpInternal(eventTime);
828    }
829
830    private void wakeUpInternal(long eventTime) {
831        synchronized (mLock) {
832            if (wakeUpNoUpdateLocked(eventTime)) {
833                updatePowerStateLocked();
834            }
835        }
836    }
837
838    private boolean wakeUpNoUpdateLocked(long eventTime) {
839        if (DEBUG_SPEW) {
840            Slog.d(TAG, "wakeUpNoUpdateLocked: eventTime=" + eventTime);
841        }
842
843        if (eventTime < mLastSleepTime || mWakefulness == WAKEFULNESS_AWAKE
844                || !mBootCompleted || !mSystemReady) {
845            return false;
846        }
847
848        switch (mWakefulness) {
849            case WAKEFULNESS_ASLEEP:
850                Slog.i(TAG, "Waking up from sleep...");
851                sendPendingNotificationsLocked();
852                mNotifier.onWakeUpStarted();
853                mSendWakeUpFinishedNotificationWhenReady = true;
854                break;
855            case WAKEFULNESS_DREAMING:
856                Slog.i(TAG, "Waking up from dream...");
857                break;
858            case WAKEFULNESS_NAPPING:
859                Slog.i(TAG, "Waking up from nap...");
860                break;
861        }
862
863        mLastWakeTime = eventTime;
864        mWakefulness = WAKEFULNESS_AWAKE;
865        mDirty |= DIRTY_WAKEFULNESS;
866
867        userActivityNoUpdateLocked(
868                eventTime, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
869        return true;
870    }
871
872    @Override // Binder call
873    public void goToSleep(long eventTime, int reason) {
874        if (eventTime > SystemClock.uptimeMillis()) {
875            throw new IllegalArgumentException("event time must not be in the future");
876        }
877
878        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
879
880        final long ident = Binder.clearCallingIdentity();
881        try {
882            goToSleepInternal(eventTime, reason);
883        } finally {
884            Binder.restoreCallingIdentity(ident);
885        }
886    }
887
888    // Called from native code.
889    private void goToSleepFromNative(long eventTime, int reason) {
890        goToSleepInternal(eventTime, reason);
891    }
892
893    private void goToSleepInternal(long eventTime, int reason) {
894        synchronized (mLock) {
895            if (goToSleepNoUpdateLocked(eventTime, reason)) {
896                updatePowerStateLocked();
897            }
898        }
899    }
900
901    private boolean goToSleepNoUpdateLocked(long eventTime, int reason) {
902        if (DEBUG_SPEW) {
903            Slog.d(TAG, "goToSleepNoUpdateLocked: eventTime=" + eventTime + ", reason=" + reason);
904        }
905
906        if (eventTime < mLastWakeTime || mWakefulness == WAKEFULNESS_ASLEEP
907                || !mBootCompleted || !mSystemReady) {
908            return false;
909        }
910
911        switch (reason) {
912            case PowerManager.GO_TO_SLEEP_REASON_DEVICE_ADMIN:
913                Slog.i(TAG, "Going to sleep due to device administration policy...");
914                break;
915            case PowerManager.GO_TO_SLEEP_REASON_TIMEOUT:
916                Slog.i(TAG, "Going to sleep due to screen timeout...");
917                break;
918            default:
919                Slog.i(TAG, "Going to sleep by user request...");
920                reason = PowerManager.GO_TO_SLEEP_REASON_USER;
921                break;
922        }
923
924        sendPendingNotificationsLocked();
925        mNotifier.onGoToSleepStarted(reason);
926        mSendGoToSleepFinishedNotificationWhenReady = true;
927
928        mLastSleepTime = eventTime;
929        mDirty |= DIRTY_WAKEFULNESS;
930        mWakefulness = WAKEFULNESS_ASLEEP;
931
932        // Report the number of wake locks that will be cleared by going to sleep.
933        int numWakeLocksCleared = 0;
934        final int numWakeLocks = mWakeLocks.size();
935        for (int i = 0; i < numWakeLocks; i++) {
936            final WakeLock wakeLock = mWakeLocks.get(i);
937            switch (wakeLock.mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
938                case PowerManager.FULL_WAKE_LOCK:
939                case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
940                case PowerManager.SCREEN_DIM_WAKE_LOCK:
941                    numWakeLocksCleared += 1;
942                    break;
943            }
944        }
945        EventLog.writeEvent(EventLogTags.POWER_SLEEP_REQUESTED, numWakeLocksCleared);
946        return true;
947    }
948
949    @Override // Binder call
950    public void nap(long eventTime) {
951        if (eventTime > SystemClock.uptimeMillis()) {
952            throw new IllegalArgumentException("event time must not be in the future");
953        }
954
955        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
956
957        final long ident = Binder.clearCallingIdentity();
958        try {
959            napInternal(eventTime);
960        } finally {
961            Binder.restoreCallingIdentity(ident);
962        }
963    }
964
965    private void napInternal(long eventTime) {
966        synchronized (mLock) {
967            if (napNoUpdateLocked(eventTime)) {
968                updatePowerStateLocked();
969            }
970        }
971    }
972
973    private boolean napNoUpdateLocked(long eventTime) {
974        if (DEBUG_SPEW) {
975            Slog.d(TAG, "napNoUpdateLocked: eventTime=" + eventTime);
976        }
977
978        if (eventTime < mLastWakeTime || mWakefulness != WAKEFULNESS_AWAKE
979                || !mBootCompleted || !mSystemReady) {
980            return false;
981        }
982
983        Slog.i(TAG, "Nap time...");
984
985        mDirty |= DIRTY_WAKEFULNESS;
986        mWakefulness = WAKEFULNESS_NAPPING;
987        return true;
988    }
989
990    /**
991     * Updates the global power state based on dirty bits recorded in mDirty.
992     *
993     * This is the main function that performs power state transitions.
994     * We centralize them here so that we can recompute the power state completely
995     * each time something important changes, and ensure that we do it the same
996     * way each time.  The point is to gather all of the transition logic here.
997     */
998    private void updatePowerStateLocked() {
999        if (!mSystemReady || mDirty == 0) {
1000            return;
1001        }
1002
1003        // Phase 0: Basic state updates.
1004        updateIsPoweredLocked(mDirty);
1005        updateStayOnLocked(mDirty);
1006
1007        // Phase 1: Update wakefulness.
1008        // Loop because the wake lock and user activity computations are influenced
1009        // by changes in wakefulness.
1010        final long now = SystemClock.uptimeMillis();
1011        int dirtyPhase2 = 0;
1012        for (;;) {
1013            int dirtyPhase1 = mDirty;
1014            dirtyPhase2 |= dirtyPhase1;
1015            mDirty = 0;
1016
1017            updateWakeLockSummaryLocked(dirtyPhase1);
1018            updateUserActivitySummaryLocked(now, dirtyPhase1);
1019            if (!updateWakefulnessLocked(dirtyPhase1)) {
1020                break;
1021            }
1022        }
1023
1024        // Phase 2: Update dreams and display power state.
1025        updateDreamLocked(dirtyPhase2);
1026        updateDisplayPowerStateLocked(dirtyPhase2);
1027
1028        // Phase 3: Send notifications, if needed.
1029        if (mDisplayReady) {
1030            sendPendingNotificationsLocked();
1031        }
1032
1033        // Phase 4: Update suspend blocker.
1034        // Because we might release the last suspend blocker here, we need to make sure
1035        // we finished everything else first!
1036        updateSuspendBlockerLocked();
1037    }
1038
1039    private void sendPendingNotificationsLocked() {
1040        if (mSendWakeUpFinishedNotificationWhenReady) {
1041            mSendWakeUpFinishedNotificationWhenReady = false;
1042            mNotifier.onWakeUpFinished();
1043        }
1044        if (mSendGoToSleepFinishedNotificationWhenReady) {
1045            mSendGoToSleepFinishedNotificationWhenReady = false;
1046            mNotifier.onGoToSleepFinished();
1047        }
1048    }
1049
1050    /**
1051     * Updates the value of mIsPowered.
1052     * Sets DIRTY_IS_POWERED if a change occurred.
1053     */
1054    private void updateIsPoweredLocked(int dirty) {
1055        if ((dirty & DIRTY_BATTERY_STATE) != 0) {
1056            final boolean wasPowered = mIsPowered;
1057            final int oldPlugType = mPlugType;
1058            mIsPowered = mBatteryService.isPowered(BatteryManager.BATTERY_PLUGGED_ANY);
1059            mPlugType = mBatteryService.getPlugType();
1060
1061            if (DEBUG) {
1062                Slog.d(TAG, "updateIsPoweredLocked: wasPowered=" + wasPowered
1063                        + ", mIsPowered=" + mIsPowered
1064                        + ", oldPlugType=" + oldPlugType
1065                        + ", mPlugType=" + mPlugType);
1066            }
1067
1068            if (wasPowered != mIsPowered || oldPlugType != mPlugType) {
1069                mDirty |= DIRTY_IS_POWERED;
1070
1071                // Treat plugging and unplugging the devices as a user activity.
1072                // Users find it disconcerting when they plug or unplug the device
1073                // and it shuts off right away.
1074                // Some devices also wake the device when plugged or unplugged because
1075                // they don't have a charging LED.
1076                final long now = SystemClock.uptimeMillis();
1077                if (shouldWakeUpWhenPluggedOrUnpluggedLocked(wasPowered, oldPlugType)) {
1078                    wakeUpNoUpdateLocked(now);
1079                }
1080                userActivityNoUpdateLocked(
1081                        now, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
1082            }
1083        }
1084    }
1085
1086    private boolean shouldWakeUpWhenPluggedOrUnpluggedLocked(boolean wasPowered, int oldPlugType) {
1087        // Don't wake when powered unless configured to do so.
1088        if (!mWakeUpWhenPluggedOrUnpluggedConfig) {
1089            return false;
1090        }
1091
1092        // FIXME: Need more accurate detection of wireless chargers.
1093        //
1094        // We are unable to accurately detect whether the device is resting on the
1095        // charger unless it is actually receiving power.  This causes us some grief
1096        // because the device might not appear to be plugged into the wireless charger
1097        // unless it actually charging.
1098        //
1099        // To avoid spuriously waking the screen, we apply a special policy to
1100        // wireless chargers.
1101        //
1102        // 1. Don't wake the device when unplugged from wireless charger because
1103        //    it might be that the device is still resting on the wireless charger
1104        //    but is not receiving power anymore because the battery is full.
1105        //
1106        // 2. Don't wake the device when plugged into a wireless charger if the
1107        //    battery already appears to be mostly full.  This situation may indicate
1108        //    that the device was resting on the charger the whole time and simply
1109        //    wasn't receiving power because the battery was full.  We can't tell
1110        //    whether the device was just placed on the charger or whether it has
1111        //    been there for half of the night slowly discharging until it hit
1112        //    the point where it needed to start charging again.
1113        if (wasPowered && !mIsPowered
1114                && oldPlugType == BatteryManager.BATTERY_PLUGGED_WIRELESS) {
1115            return false;
1116        }
1117        if (!wasPowered && mIsPowered
1118                && mPlugType == BatteryManager.BATTERY_PLUGGED_WIRELESS
1119                && mBatteryService.getBatteryLevel() >=
1120                        WIRELESS_CHARGER_TURN_ON_BATTERY_LEVEL_LIMIT) {
1121            return false;
1122        }
1123
1124        // If already dreaming and becoming powered, then don't wake.
1125        if (mIsPowered && (mWakefulness == WAKEFULNESS_NAPPING
1126                || mWakefulness == WAKEFULNESS_DREAMING)) {
1127            return false;
1128        }
1129
1130        // Otherwise wake up!
1131        return true;
1132    }
1133
1134    /**
1135     * Updates the value of mStayOn.
1136     * Sets DIRTY_STAY_ON if a change occurred.
1137     */
1138    private void updateStayOnLocked(int dirty) {
1139        if ((dirty & (DIRTY_BATTERY_STATE | DIRTY_SETTINGS)) != 0) {
1140            final boolean wasStayOn = mStayOn;
1141            if (mStayOnWhilePluggedInSetting != 0
1142                    && !isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked()) {
1143                mStayOn = mBatteryService.isPowered(mStayOnWhilePluggedInSetting);
1144            } else {
1145                mStayOn = false;
1146            }
1147
1148            if (mStayOn != wasStayOn) {
1149                mDirty |= DIRTY_STAY_ON;
1150            }
1151        }
1152    }
1153
1154    /**
1155     * Updates the value of mWakeLockSummary to summarize the state of all active wake locks.
1156     * Note that most wake-locks are ignored when the system is asleep.
1157     *
1158     * This function must have no other side-effects.
1159     */
1160    private void updateWakeLockSummaryLocked(int dirty) {
1161        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_WAKEFULNESS)) != 0) {
1162            mWakeLockSummary = 0;
1163
1164            final int numWakeLocks = mWakeLocks.size();
1165            for (int i = 0; i < numWakeLocks; i++) {
1166                final WakeLock wakeLock = mWakeLocks.get(i);
1167                switch (wakeLock.mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
1168                    case PowerManager.PARTIAL_WAKE_LOCK:
1169                        mWakeLockSummary |= WAKE_LOCK_CPU;
1170                        break;
1171                    case PowerManager.FULL_WAKE_LOCK:
1172                        if (mWakefulness != WAKEFULNESS_ASLEEP) {
1173                            mWakeLockSummary |= WAKE_LOCK_CPU
1174                                    | WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_BUTTON_BRIGHT;
1175                        }
1176                        break;
1177                    case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
1178                        if (mWakefulness != WAKEFULNESS_ASLEEP) {
1179                            mWakeLockSummary |= WAKE_LOCK_CPU | WAKE_LOCK_SCREEN_BRIGHT;
1180                        }
1181                        break;
1182                    case PowerManager.SCREEN_DIM_WAKE_LOCK:
1183                        if (mWakefulness != WAKEFULNESS_ASLEEP) {
1184                            mWakeLockSummary |= WAKE_LOCK_CPU | WAKE_LOCK_SCREEN_DIM;
1185                        }
1186                        break;
1187                    case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
1188                        if (mWakefulness != WAKEFULNESS_ASLEEP) {
1189                            mWakeLockSummary |= WAKE_LOCK_CPU | WAKE_LOCK_PROXIMITY_SCREEN_OFF;
1190                        }
1191                        break;
1192                }
1193            }
1194
1195            if (DEBUG_SPEW) {
1196                Slog.d(TAG, "updateWakeLockSummaryLocked: mWakefulness="
1197                        + wakefulnessToString(mWakefulness)
1198                        + ", mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary));
1199            }
1200        }
1201    }
1202
1203    /**
1204     * Updates the value of mUserActivitySummary to summarize the user requested
1205     * state of the system such as whether the screen should be bright or dim.
1206     * Note that user activity is ignored when the system is asleep.
1207     *
1208     * This function must have no other side-effects.
1209     */
1210    private void updateUserActivitySummaryLocked(long now, int dirty) {
1211        // Update the status of the user activity timeout timer.
1212        if ((dirty & (DIRTY_USER_ACTIVITY | DIRTY_WAKEFULNESS | DIRTY_SETTINGS)) != 0) {
1213            mHandler.removeMessages(MSG_USER_ACTIVITY_TIMEOUT);
1214
1215            long nextTimeout = 0;
1216            if (mWakefulness != WAKEFULNESS_ASLEEP) {
1217                final int screenOffTimeout = getScreenOffTimeoutLocked();
1218                final int screenDimDuration = getScreenDimDurationLocked(screenOffTimeout);
1219
1220                mUserActivitySummary = 0;
1221                if (mLastUserActivityTime >= mLastWakeTime) {
1222                    nextTimeout = mLastUserActivityTime
1223                            + screenOffTimeout - screenDimDuration;
1224                    if (now < nextTimeout) {
1225                        mUserActivitySummary |= USER_ACTIVITY_SCREEN_BRIGHT;
1226                    } else {
1227                        nextTimeout = mLastUserActivityTime + screenOffTimeout;
1228                        if (now < nextTimeout) {
1229                            mUserActivitySummary |= USER_ACTIVITY_SCREEN_DIM;
1230                        }
1231                    }
1232                }
1233                if (mUserActivitySummary == 0
1234                        && mLastUserActivityTimeNoChangeLights >= mLastWakeTime) {
1235                    nextTimeout = mLastUserActivityTimeNoChangeLights + screenOffTimeout;
1236                    if (now < nextTimeout
1237                            && mDisplayPowerRequest.screenState
1238                                    != DisplayPowerRequest.SCREEN_STATE_OFF) {
1239                        mUserActivitySummary = mDisplayPowerRequest.screenState
1240                                == DisplayPowerRequest.SCREEN_STATE_BRIGHT ?
1241                                USER_ACTIVITY_SCREEN_BRIGHT : USER_ACTIVITY_SCREEN_DIM;
1242                    }
1243                }
1244                if (mUserActivitySummary != 0) {
1245                    Message msg = mHandler.obtainMessage(MSG_USER_ACTIVITY_TIMEOUT);
1246                    msg.setAsynchronous(true);
1247                    mHandler.sendMessageAtTime(msg, nextTimeout);
1248                }
1249            } else {
1250                mUserActivitySummary = 0;
1251            }
1252
1253            if (DEBUG_SPEW) {
1254                Slog.d(TAG, "updateUserActivitySummaryLocked: mWakefulness="
1255                        + wakefulnessToString(mWakefulness)
1256                        + ", mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary)
1257                        + ", nextTimeout=" + TimeUtils.formatUptime(nextTimeout));
1258            }
1259        }
1260    }
1261
1262    /**
1263     * Called when a user activity timeout has occurred.
1264     * Simply indicates that something about user activity has changed so that the new
1265     * state can be recomputed when the power state is updated.
1266     *
1267     * This function must have no other side-effects besides setting the dirty
1268     * bit and calling update power state.  Wakefulness transitions are handled elsewhere.
1269     */
1270    private void handleUserActivityTimeout() { // runs on handler thread
1271        synchronized (mLock) {
1272            if (DEBUG_SPEW) {
1273                Slog.d(TAG, "handleUserActivityTimeout");
1274            }
1275
1276            mDirty |= DIRTY_USER_ACTIVITY;
1277            updatePowerStateLocked();
1278        }
1279    }
1280
1281    private int getScreenOffTimeoutLocked() {
1282        int timeout = mScreenOffTimeoutSetting;
1283        if (isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked()) {
1284            timeout = Math.min(timeout, mMaximumScreenOffTimeoutFromDeviceAdmin);
1285        }
1286        if (mUserActivityTimeoutOverrideFromWindowManager >= 0) {
1287            timeout = (int)Math.min(timeout, mUserActivityTimeoutOverrideFromWindowManager);
1288        }
1289        return Math.max(timeout, MINIMUM_SCREEN_OFF_TIMEOUT);
1290    }
1291
1292    private int getScreenDimDurationLocked(int screenOffTimeout) {
1293        return Math.min(SCREEN_DIM_DURATION,
1294                (int)(screenOffTimeout * MAXIMUM_SCREEN_DIM_RATIO));
1295    }
1296
1297    /**
1298     * Updates the wakefulness of the device.
1299     *
1300     * This is the function that decides whether the device should start napping
1301     * based on the current wake locks and user activity state.  It may modify mDirty
1302     * if the wakefulness changes.
1303     *
1304     * Returns true if the wakefulness changed and we need to restart power state calculation.
1305     */
1306    private boolean updateWakefulnessLocked(int dirty) {
1307        boolean changed = false;
1308        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_USER_ACTIVITY | DIRTY_BOOT_COMPLETED
1309                | DIRTY_WAKEFULNESS | DIRTY_STAY_ON | DIRTY_PROXIMITY_POSITIVE)) != 0) {
1310            if (mWakefulness == WAKEFULNESS_AWAKE && isItBedTimeYetLocked()) {
1311                if (DEBUG_SPEW) {
1312                    Slog.d(TAG, "updateWakefulnessLocked: Bed time...");
1313                }
1314                final long time = SystemClock.uptimeMillis();
1315                if (mDreamsActivateOnSleepSetting) {
1316                    changed = napNoUpdateLocked(time);
1317                } else {
1318                    changed = goToSleepNoUpdateLocked(time,
1319                            PowerManager.GO_TO_SLEEP_REASON_TIMEOUT);
1320                }
1321            }
1322        }
1323        return changed;
1324    }
1325
1326    /**
1327     * Returns true if the device should go to sleep now.
1328     * Also used when exiting a dream to determine whether we should go back
1329     * to being fully awake or else go to sleep for good.
1330     */
1331    private boolean isItBedTimeYetLocked() {
1332        return mBootCompleted && !isBeingKeptAwakeLocked();
1333    }
1334
1335    /**
1336     * Returns true if the device is being kept awake by a wake lock, user activity
1337     * or the stay on while powered setting.
1338     */
1339    private boolean isBeingKeptAwakeLocked() {
1340        return mStayOn
1341                || mProximityPositive
1342                || (mWakeLockSummary & (WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_SCREEN_DIM)) != 0
1343                || (mUserActivitySummary & (USER_ACTIVITY_SCREEN_BRIGHT
1344                        | USER_ACTIVITY_SCREEN_DIM)) != 0;
1345    }
1346
1347    /**
1348     * Determines whether to post a message to the sandman to update the dream state.
1349     */
1350    private void updateDreamLocked(int dirty) {
1351        if ((dirty & (DIRTY_WAKEFULNESS
1352                | DIRTY_USER_ACTIVITY
1353                | DIRTY_WAKE_LOCKS
1354                | DIRTY_BOOT_COMPLETED
1355                | DIRTY_SETTINGS
1356                | DIRTY_IS_POWERED
1357                | DIRTY_STAY_ON
1358                | DIRTY_PROXIMITY_POSITIVE
1359                | DIRTY_BATTERY_STATE)) != 0) {
1360            scheduleSandmanLocked();
1361        }
1362    }
1363
1364    private void scheduleSandmanLocked() {
1365        if (!mSandmanScheduled) {
1366            mSandmanScheduled = true;
1367            Message msg = mHandler.obtainMessage(MSG_SANDMAN);
1368            msg.setAsynchronous(true);
1369            mHandler.sendMessage(msg);
1370        }
1371    }
1372
1373    /**
1374     * Called when the device enters or exits a napping or dreaming state.
1375     *
1376     * We do this asynchronously because we must call out of the power manager to start
1377     * the dream and we don't want to hold our lock while doing so.  There is a risk that
1378     * the device will wake or go to sleep in the meantime so we have to handle that case.
1379     */
1380    private void handleSandman() { // runs on handler thread
1381        // Handle preconditions.
1382        boolean startDreaming = false;
1383        synchronized (mLock) {
1384            mSandmanScheduled = false;
1385            boolean canDream = canDreamLocked();
1386            if (DEBUG_SPEW) {
1387                Log.d(TAG, "handleSandman: canDream=" + canDream
1388                        + ", mWakefulness=" + wakefulnessToString(mWakefulness));
1389            }
1390
1391            if (canDream && mWakefulness == WAKEFULNESS_NAPPING) {
1392                startDreaming = true;
1393            }
1394        }
1395
1396        // Start dreaming if needed.
1397        // We only control the dream on the handler thread, so we don't need to worry about
1398        // concurrent attempts to start or stop the dream.
1399        boolean isDreaming = false;
1400        if (mDreamManager != null) {
1401            if (startDreaming) {
1402                mDreamManager.startDream();
1403            }
1404            isDreaming = mDreamManager.isDreaming();
1405        }
1406
1407        // Update dream state.
1408        // We might need to stop the dream again if the preconditions changed.
1409        boolean continueDreaming = false;
1410        synchronized (mLock) {
1411            if (isDreaming && canDreamLocked()) {
1412                if (mWakefulness == WAKEFULNESS_NAPPING) {
1413                    mWakefulness = WAKEFULNESS_DREAMING;
1414                    mDirty |= DIRTY_WAKEFULNESS;
1415                    updatePowerStateLocked();
1416                    continueDreaming = true;
1417                } else if (mWakefulness == WAKEFULNESS_DREAMING) {
1418                    continueDreaming = true;
1419                }
1420            }
1421            if (!continueDreaming) {
1422                handleDreamFinishedLocked();
1423            }
1424        }
1425
1426        // Stop dreaming if needed.
1427        // It's possible that something else changed to make us need to start the dream again.
1428        // If so, then the power manager will have posted another message to the handler
1429        // to take care of it later.
1430        if (mDreamManager != null) {
1431            if (!continueDreaming) {
1432                mDreamManager.stopDream();
1433            }
1434        }
1435    }
1436
1437    /**
1438     * Returns true if the device is allowed to dream in its current state
1439     * assuming that it is currently napping or dreaming.
1440     */
1441    private boolean canDreamLocked() {
1442        return mDreamsSupportedConfig
1443                && mDreamsEnabledSetting
1444                && mDisplayPowerRequest.screenState != DisplayPowerRequest.SCREEN_STATE_OFF
1445                && mBootCompleted
1446                && (mIsPowered || isBeingKeptAwakeLocked());
1447    }
1448
1449    /**
1450     * Called when a dream is ending to figure out what to do next.
1451     */
1452    private void handleDreamFinishedLocked() {
1453        if (mWakefulness == WAKEFULNESS_NAPPING
1454                || mWakefulness == WAKEFULNESS_DREAMING) {
1455            if (isItBedTimeYetLocked()) {
1456                goToSleepNoUpdateLocked(SystemClock.uptimeMillis(),
1457                        PowerManager.GO_TO_SLEEP_REASON_TIMEOUT);
1458                updatePowerStateLocked();
1459            } else {
1460                wakeUpNoUpdateLocked(SystemClock.uptimeMillis());
1461                updatePowerStateLocked();
1462            }
1463        }
1464    }
1465
1466    private void handleScreenOnBlockerReleased() {
1467        synchronized (mLock) {
1468            mDirty |= DIRTY_SCREEN_ON_BLOCKER_RELEASED;
1469            updatePowerStateLocked();
1470        }
1471    }
1472
1473    /**
1474     * Updates the display power state asynchronously.
1475     * When the update is finished, mDisplayReady will be set to true.  The display
1476     * controller posts a message to tell us when the actual display power state
1477     * has been updated so we come back here to double-check and finish up.
1478     *
1479     * This function recalculates the display power state each time.
1480     */
1481    private void updateDisplayPowerStateLocked(int dirty) {
1482        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_USER_ACTIVITY | DIRTY_WAKEFULNESS
1483                | DIRTY_ACTUAL_DISPLAY_POWER_STATE_UPDATED | DIRTY_BOOT_COMPLETED
1484                | DIRTY_SETTINGS | DIRTY_SCREEN_ON_BLOCKER_RELEASED)) != 0) {
1485            int newScreenState = getDesiredScreenPowerStateLocked();
1486            if (newScreenState != mDisplayPowerRequest.screenState) {
1487                if (newScreenState == DisplayPowerRequest.SCREEN_STATE_OFF
1488                        && mDisplayPowerRequest.screenState
1489                                != DisplayPowerRequest.SCREEN_STATE_OFF) {
1490                    mLastScreenOffEventElapsedRealTime = SystemClock.elapsedRealtime();
1491                }
1492
1493                mDisplayPowerRequest.screenState = newScreenState;
1494                nativeSetPowerState(
1495                        newScreenState != DisplayPowerRequest.SCREEN_STATE_OFF,
1496                        newScreenState == DisplayPowerRequest.SCREEN_STATE_BRIGHT);
1497            }
1498
1499            int screenBrightness = mScreenBrightnessSettingDefault;
1500            float screenAutoBrightnessAdjustment = 0.0f;
1501            boolean autoBrightness = (mScreenBrightnessModeSetting ==
1502                    Settings.System.SCREEN_BRIGHTNESS_MODE_AUTOMATIC);
1503            if (isValidBrightness(mScreenBrightnessOverrideFromWindowManager)) {
1504                screenBrightness = mScreenBrightnessOverrideFromWindowManager;
1505                autoBrightness = false;
1506            } else if (isValidBrightness(mTemporaryScreenBrightnessSettingOverride)) {
1507                screenBrightness = mTemporaryScreenBrightnessSettingOverride;
1508            } else if (isValidBrightness(mScreenBrightnessSetting)) {
1509                screenBrightness = mScreenBrightnessSetting;
1510            }
1511            if (autoBrightness) {
1512                screenBrightness = mScreenBrightnessSettingDefault;
1513                if (isValidAutoBrightnessAdjustment(
1514                        mTemporaryScreenAutoBrightnessAdjustmentSettingOverride)) {
1515                    screenAutoBrightnessAdjustment =
1516                            mTemporaryScreenAutoBrightnessAdjustmentSettingOverride;
1517                } else if (isValidAutoBrightnessAdjustment(
1518                        mScreenAutoBrightnessAdjustmentSetting)) {
1519                    screenAutoBrightnessAdjustment = mScreenAutoBrightnessAdjustmentSetting;
1520                }
1521            }
1522            screenBrightness = Math.max(Math.min(screenBrightness,
1523                    mScreenBrightnessSettingMaximum), mScreenBrightnessSettingMinimum);
1524            screenAutoBrightnessAdjustment = Math.max(Math.min(
1525                    screenAutoBrightnessAdjustment, 1.0f), -1.0f);
1526            mDisplayPowerRequest.screenBrightness = screenBrightness;
1527            mDisplayPowerRequest.screenAutoBrightnessAdjustment =
1528                    screenAutoBrightnessAdjustment;
1529            mDisplayPowerRequest.useAutoBrightness = autoBrightness;
1530
1531            mDisplayPowerRequest.useProximitySensor = shouldUseProximitySensorLocked();
1532
1533            mDisplayPowerRequest.blockScreenOn = mScreenOnBlocker.isHeld();
1534
1535            mDisplayReady = mDisplayPowerController.requestPowerState(mDisplayPowerRequest,
1536                    mRequestWaitForNegativeProximity);
1537            mRequestWaitForNegativeProximity = false;
1538
1539            if (DEBUG_SPEW) {
1540                Slog.d(TAG, "updateScreenStateLocked: mDisplayReady=" + mDisplayReady
1541                        + ", newScreenState=" + newScreenState
1542                        + ", mWakefulness=" + mWakefulness
1543                        + ", mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary)
1544                        + ", mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary)
1545                        + ", mBootCompleted=" + mBootCompleted);
1546            }
1547        }
1548    }
1549
1550    private static boolean isValidBrightness(int value) {
1551        return value >= 0 && value <= 255;
1552    }
1553
1554    private static boolean isValidAutoBrightnessAdjustment(float value) {
1555        // Handles NaN by always returning false.
1556        return value >= -1.0f && value <= 1.0f;
1557    }
1558
1559    private int getDesiredScreenPowerStateLocked() {
1560        if (mWakefulness == WAKEFULNESS_ASLEEP) {
1561            return DisplayPowerRequest.SCREEN_STATE_OFF;
1562        }
1563
1564        if ((mWakeLockSummary & WAKE_LOCK_SCREEN_BRIGHT) != 0
1565                || (mUserActivitySummary & USER_ACTIVITY_SCREEN_BRIGHT) != 0
1566                || !mBootCompleted) {
1567            return DisplayPowerRequest.SCREEN_STATE_BRIGHT;
1568        }
1569
1570        return DisplayPowerRequest.SCREEN_STATE_DIM;
1571    }
1572
1573    private final DisplayPowerController.Callbacks mDisplayPowerControllerCallbacks =
1574            new DisplayPowerController.Callbacks() {
1575        @Override
1576        public void onStateChanged() {
1577            mDirty |= DIRTY_ACTUAL_DISPLAY_POWER_STATE_UPDATED;
1578            updatePowerStateLocked();
1579        }
1580
1581        @Override
1582        public void onProximityPositive() {
1583            mProximityPositive = true;
1584            mDirty |= DIRTY_PROXIMITY_POSITIVE;
1585            updatePowerStateLocked();
1586        }
1587
1588        @Override
1589        public void onProximityNegative() {
1590            mProximityPositive = false;
1591            mDirty |= DIRTY_PROXIMITY_POSITIVE;
1592            userActivityNoUpdateLocked(SystemClock.uptimeMillis(),
1593                    PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
1594            updatePowerStateLocked();
1595        }
1596    };
1597
1598    private boolean shouldUseProximitySensorLocked() {
1599        return (mWakeLockSummary & WAKE_LOCK_PROXIMITY_SCREEN_OFF) != 0;
1600    }
1601
1602    /**
1603     * Updates the suspend blocker that keeps the CPU alive.
1604     *
1605     * This function must have no other side-effects.
1606     */
1607    private void updateSuspendBlockerLocked() {
1608        boolean wantCpu = isCpuNeededLocked();
1609        if (wantCpu != mHoldingWakeLockSuspendBlocker) {
1610            mHoldingWakeLockSuspendBlocker = wantCpu;
1611            if (wantCpu) {
1612                if (DEBUG) {
1613                    Slog.d(TAG, "updateSuspendBlockerLocked: Acquiring suspend blocker.");
1614                }
1615                mWakeLockSuspendBlocker.acquire();
1616            } else {
1617                if (DEBUG) {
1618                    Slog.d(TAG, "updateSuspendBlockerLocked: Releasing suspend blocker.");
1619                }
1620                mWakeLockSuspendBlocker.release();
1621            }
1622        }
1623    }
1624
1625    private boolean isCpuNeededLocked() {
1626        return !mBootCompleted
1627                || mWakeLockSummary != 0
1628                || mUserActivitySummary != 0
1629                || mDisplayPowerRequest.screenState != DisplayPowerRequest.SCREEN_STATE_OFF
1630                || !mDisplayReady;
1631    }
1632
1633    @Override // Binder call
1634    public boolean isScreenOn() {
1635        final long ident = Binder.clearCallingIdentity();
1636        try {
1637            return isScreenOnInternal();
1638        } finally {
1639            Binder.restoreCallingIdentity(ident);
1640        }
1641    }
1642
1643    private boolean isScreenOnInternal() {
1644        synchronized (mLock) {
1645            return !mSystemReady
1646                    || mDisplayPowerRequest.screenState != DisplayPowerRequest.SCREEN_STATE_OFF;
1647        }
1648    }
1649
1650    private void handleBatteryStateChangedLocked() {
1651        mDirty |= DIRTY_BATTERY_STATE;
1652        updatePowerStateLocked();
1653    }
1654
1655    private void handleBootCompletedLocked() {
1656        final long now = SystemClock.uptimeMillis();
1657        mBootCompleted = true;
1658        mDirty |= DIRTY_BOOT_COMPLETED;
1659        userActivityNoUpdateLocked(
1660                now, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
1661        updatePowerStateLocked();
1662    }
1663
1664    /**
1665     * Reboot the device, passing 'reason' (may be null)
1666     * to the underlying __reboot system call.  Should not return.
1667     */
1668    @Override // Binder call
1669    public void reboot(boolean confirm, String reason, boolean wait) {
1670        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);
1671
1672        final long ident = Binder.clearCallingIdentity();
1673        try {
1674            rebootInternal(false, confirm, reason, wait);
1675        } finally {
1676            Binder.restoreCallingIdentity(ident);
1677        }
1678    }
1679
1680    /**
1681     * Shutdown the devic, passing 'reason' (may be null)
1682     * to the underlying __reboot system call.  Should not return.
1683     */
1684    @Override // Binder call
1685    public void shutdown(boolean confirm, boolean wait) {
1686        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);
1687
1688        final long ident = Binder.clearCallingIdentity();
1689        try {
1690            rebootInternal(true, confirm, null, wait);
1691        } finally {
1692            Binder.restoreCallingIdentity(ident);
1693        }
1694    }
1695
1696    private void rebootInternal(final boolean shutdown, final boolean confirm,
1697            final String reason, boolean wait) {
1698        if (mHandler == null || !mSystemReady) {
1699            throw new IllegalStateException("Too early to call reboot()");
1700        }
1701
1702        Runnable runnable = new Runnable() {
1703            public void run() {
1704                synchronized (this) {
1705                    if (shutdown) {
1706                        ShutdownThread.shutdown(mContext, confirm);
1707                    } else {
1708                        ShutdownThread.reboot(mContext, reason, confirm);
1709                    }
1710                }
1711            }
1712        };
1713
1714        // ShutdownThread must run on a looper capable of displaying the UI.
1715        Message msg = Message.obtain(mHandler, runnable);
1716        msg.setAsynchronous(true);
1717        mHandler.sendMessage(msg);
1718
1719        // PowerManager.reboot() is documented not to return so just wait for the inevitable.
1720        if (wait) {
1721            synchronized (runnable) {
1722                while (true) {
1723                    try {
1724                        runnable.wait();
1725                    } catch (InterruptedException e) {
1726                    }
1727                }
1728            }
1729        }
1730    }
1731
1732    /**
1733     * Crash the runtime (causing a complete restart of the Android framework).
1734     * Requires REBOOT permission.  Mostly for testing.  Should not return.
1735     */
1736    @Override // Binder call
1737    public void crash(String message) {
1738        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);
1739
1740        final long ident = Binder.clearCallingIdentity();
1741        try {
1742            crashInternal(message);
1743        } finally {
1744            Binder.restoreCallingIdentity(ident);
1745        }
1746    }
1747
1748    private void crashInternal(final String message) {
1749        Thread t = new Thread("PowerManagerService.crash()") {
1750            public void run() {
1751                throw new RuntimeException(message);
1752            }
1753        };
1754        try {
1755            t.start();
1756            t.join();
1757        } catch (InterruptedException e) {
1758            Log.wtf(TAG, e);
1759        }
1760    }
1761
1762    /**
1763     * Set the setting that determines whether the device stays on when plugged in.
1764     * The argument is a bit string, with each bit specifying a power source that,
1765     * when the device is connected to that source, causes the device to stay on.
1766     * See {@link android.os.BatteryManager} for the list of power sources that
1767     * can be specified. Current values include {@link android.os.BatteryManager#BATTERY_PLUGGED_AC}
1768     * and {@link android.os.BatteryManager#BATTERY_PLUGGED_USB}
1769     *
1770     * Used by "adb shell svc power stayon ..."
1771     *
1772     * @param val an {@code int} containing the bits that specify which power sources
1773     * should cause the device to stay on.
1774     */
1775    @Override // Binder call
1776    public void setStayOnSetting(int val) {
1777        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WRITE_SETTINGS, null);
1778
1779        final long ident = Binder.clearCallingIdentity();
1780        try {
1781            setStayOnSettingInternal(val);
1782        } finally {
1783            Binder.restoreCallingIdentity(ident);
1784        }
1785    }
1786
1787    private void setStayOnSettingInternal(int val) {
1788        Settings.Global.putInt(mContext.getContentResolver(),
1789                Settings.Global.STAY_ON_WHILE_PLUGGED_IN, val);
1790    }
1791
1792    /**
1793     * Used by device administration to set the maximum screen off timeout.
1794     *
1795     * This method must only be called by the device administration policy manager.
1796     */
1797    @Override // Binder call
1798    public void setMaximumScreenOffTimeoutFromDeviceAdmin(int timeMs) {
1799        final long ident = Binder.clearCallingIdentity();
1800        try {
1801            setMaximumScreenOffTimeoutFromDeviceAdminInternal(timeMs);
1802        } finally {
1803            Binder.restoreCallingIdentity(ident);
1804        }
1805    }
1806
1807    private void setMaximumScreenOffTimeoutFromDeviceAdminInternal(int timeMs) {
1808        synchronized (mLock) {
1809            mMaximumScreenOffTimeoutFromDeviceAdmin = timeMs;
1810            mDirty |= DIRTY_SETTINGS;
1811            updatePowerStateLocked();
1812        }
1813    }
1814
1815    private boolean isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked() {
1816        return mMaximumScreenOffTimeoutFromDeviceAdmin >= 0
1817                && mMaximumScreenOffTimeoutFromDeviceAdmin < Integer.MAX_VALUE;
1818    }
1819
1820    /**
1821     * Used by the phone application to make the attention LED flash when ringing.
1822     */
1823    @Override // Binder call
1824    public void setAttentionLight(boolean on, int color) {
1825        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
1826
1827        final long ident = Binder.clearCallingIdentity();
1828        try {
1829            setAttentionLightInternal(on, color);
1830        } finally {
1831            Binder.restoreCallingIdentity(ident);
1832        }
1833    }
1834
1835    private void setAttentionLightInternal(boolean on, int color) {
1836        LightsService.Light light;
1837        synchronized (mLock) {
1838            if (!mSystemReady) {
1839                return;
1840            }
1841            light = mAttentionLight;
1842        }
1843
1844        // Control light outside of lock.
1845        light.setFlashing(color, LightsService.LIGHT_FLASH_HARDWARE, (on ? 3 : 0), 0);
1846    }
1847
1848    /**
1849     * Used by the Watchdog.
1850     */
1851    public long timeSinceScreenWasLastOn() {
1852        synchronized (mLock) {
1853            if (mDisplayPowerRequest.screenState != DisplayPowerRequest.SCREEN_STATE_OFF) {
1854                return 0;
1855            }
1856            return SystemClock.elapsedRealtime() - mLastScreenOffEventElapsedRealTime;
1857        }
1858    }
1859
1860    /**
1861     * Used by the window manager to override the screen brightness based on the
1862     * current foreground activity.
1863     *
1864     * This method must only be called by the window manager.
1865     *
1866     * @param brightness The overridden brightness, or -1 to disable the override.
1867     */
1868    public void setScreenBrightnessOverrideFromWindowManager(int brightness) {
1869        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
1870
1871        final long ident = Binder.clearCallingIdentity();
1872        try {
1873            setScreenBrightnessOverrideFromWindowManagerInternal(brightness);
1874        } finally {
1875            Binder.restoreCallingIdentity(ident);
1876        }
1877    }
1878
1879    private void setScreenBrightnessOverrideFromWindowManagerInternal(int brightness) {
1880        synchronized (mLock) {
1881            if (mScreenBrightnessOverrideFromWindowManager != brightness) {
1882                mScreenBrightnessOverrideFromWindowManager = brightness;
1883                mDirty |= DIRTY_SETTINGS;
1884                updatePowerStateLocked();
1885            }
1886        }
1887    }
1888
1889    /**
1890     * Used by the window manager to override the button brightness based on the
1891     * current foreground activity.
1892     *
1893     * This method must only be called by the window manager.
1894     *
1895     * @param brightness The overridden brightness, or -1 to disable the override.
1896     */
1897    public void setButtonBrightnessOverrideFromWindowManager(int brightness) {
1898        // Do nothing.
1899        // Button lights are not currently supported in the new implementation.
1900        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
1901    }
1902
1903    /**
1904     * Used by the window manager to override the user activity timeout based on the
1905     * current foreground activity.  It can only be used to make the timeout shorter
1906     * than usual, not longer.
1907     *
1908     * This method must only be called by the window manager.
1909     *
1910     * @param timeoutMillis The overridden timeout, or -1 to disable the override.
1911     */
1912    public void setUserActivityTimeoutOverrideFromWindowManager(long timeoutMillis) {
1913        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
1914
1915        final long ident = Binder.clearCallingIdentity();
1916        try {
1917            setUserActivityTimeoutOverrideFromWindowManagerInternal(timeoutMillis);
1918        } finally {
1919            Binder.restoreCallingIdentity(ident);
1920        }
1921    }
1922
1923    private void setUserActivityTimeoutOverrideFromWindowManagerInternal(long timeoutMillis) {
1924        synchronized (mLock) {
1925            if (mUserActivityTimeoutOverrideFromWindowManager != timeoutMillis) {
1926                mUserActivityTimeoutOverrideFromWindowManager = timeoutMillis;
1927                mDirty |= DIRTY_SETTINGS;
1928                updatePowerStateLocked();
1929            }
1930        }
1931    }
1932
1933    /**
1934     * Used by the settings application and brightness control widgets to
1935     * temporarily override the current screen brightness setting so that the
1936     * user can observe the effect of an intended settings change without applying
1937     * it immediately.
1938     *
1939     * The override will be canceled when the setting value is next updated.
1940     *
1941     * @param brightness The overridden brightness.
1942     *
1943     * @see Settings.System#SCREEN_BRIGHTNESS
1944     */
1945    @Override // Binder call
1946    public void setTemporaryScreenBrightnessSettingOverride(int brightness) {
1947        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
1948
1949        final long ident = Binder.clearCallingIdentity();
1950        try {
1951            setTemporaryScreenBrightnessSettingOverrideInternal(brightness);
1952        } finally {
1953            Binder.restoreCallingIdentity(ident);
1954        }
1955    }
1956
1957    private void setTemporaryScreenBrightnessSettingOverrideInternal(int brightness) {
1958        synchronized (mLock) {
1959            if (mTemporaryScreenBrightnessSettingOverride != brightness) {
1960                mTemporaryScreenBrightnessSettingOverride = brightness;
1961                mDirty |= DIRTY_SETTINGS;
1962                updatePowerStateLocked();
1963            }
1964        }
1965    }
1966
1967    /**
1968     * Used by the settings application and brightness control widgets to
1969     * temporarily override the current screen auto-brightness adjustment setting so that the
1970     * user can observe the effect of an intended settings change without applying
1971     * it immediately.
1972     *
1973     * The override will be canceled when the setting value is next updated.
1974     *
1975     * @param adj The overridden brightness, or Float.NaN to disable the override.
1976     *
1977     * @see Settings.System#SCREEN_AUTO_BRIGHTNESS_ADJ
1978     */
1979    @Override // Binder call
1980    public void setTemporaryScreenAutoBrightnessAdjustmentSettingOverride(float adj) {
1981        mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
1982
1983        final long ident = Binder.clearCallingIdentity();
1984        try {
1985            setTemporaryScreenAutoBrightnessAdjustmentSettingOverrideInternal(adj);
1986        } finally {
1987            Binder.restoreCallingIdentity(ident);
1988        }
1989    }
1990
1991    private void setTemporaryScreenAutoBrightnessAdjustmentSettingOverrideInternal(float adj) {
1992        synchronized (mLock) {
1993            // Note: This condition handles NaN because NaN is not equal to any other
1994            // value, including itself.
1995            if (mTemporaryScreenAutoBrightnessAdjustmentSettingOverride != adj) {
1996                mTemporaryScreenAutoBrightnessAdjustmentSettingOverride = adj;
1997                mDirty |= DIRTY_SETTINGS;
1998                updatePowerStateLocked();
1999            }
2000        }
2001    }
2002
2003    /**
2004     * Low-level function turn the device off immediately, without trying
2005     * to be clean.  Most people should use {@link ShutdownThread} for a clean shutdown.
2006     */
2007    public static void lowLevelShutdown() {
2008        nativeShutdown();
2009    }
2010
2011    /**
2012     * Low-level function to reboot the device.
2013     *
2014     * @param reason code to pass to the kernel (e.g. "recovery"), or null.
2015     * @throws IOException if reboot fails for some reason (eg, lack of
2016     *         permission)
2017     */
2018    public static void lowLevelReboot(String reason) throws IOException {
2019        nativeReboot(reason);
2020    }
2021
2022    @Override // Watchdog.Monitor implementation
2023    public void monitor() {
2024        // Grab and release lock for watchdog monitor to detect deadlocks.
2025        synchronized (mLock) {
2026        }
2027    }
2028
2029    @Override // Binder call
2030    protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
2031        if (mContext.checkCallingOrSelfPermission(Manifest.permission.DUMP)
2032                != PackageManager.PERMISSION_GRANTED) {
2033            pw.println("Permission Denial: can't dump PowerManager from from pid="
2034                    + Binder.getCallingPid()
2035                    + ", uid=" + Binder.getCallingUid());
2036            return;
2037        }
2038
2039        pw.println("POWER MANAGER (dumpsys power)\n");
2040
2041        final DisplayPowerController dpc;
2042        synchronized (mLock) {
2043            pw.println("Power Manager State:");
2044            pw.println("  mDirty=0x" + Integer.toHexString(mDirty));
2045            pw.println("  mWakefulness=" + wakefulnessToString(mWakefulness));
2046            pw.println("  mIsPowered=" + mIsPowered);
2047            pw.println("  mPlugType=" + mPlugType);
2048            pw.println("  mStayOn=" + mStayOn);
2049            pw.println("  mProximityPositive=" + mProximityPositive);
2050            pw.println("  mBootCompleted=" + mBootCompleted);
2051            pw.println("  mSystemReady=" + mSystemReady);
2052            pw.println("  mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary));
2053            pw.println("  mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary));
2054            pw.println("  mRequestWaitForNegativeProximity=" + mRequestWaitForNegativeProximity);
2055            pw.println("  mSandmanScheduled=" + mSandmanScheduled);
2056            pw.println("  mLastWakeTime=" + TimeUtils.formatUptime(mLastWakeTime));
2057            pw.println("  mLastSleepTime=" + TimeUtils.formatUptime(mLastSleepTime));
2058            pw.println("  mSendWakeUpFinishedNotificationWhenReady="
2059                    + mSendWakeUpFinishedNotificationWhenReady);
2060            pw.println("  mSendGoToSleepFinishedNotificationWhenReady="
2061                    + mSendGoToSleepFinishedNotificationWhenReady);
2062            pw.println("  mLastUserActivityTime=" + TimeUtils.formatUptime(mLastUserActivityTime));
2063            pw.println("  mLastUserActivityTimeNoChangeLights="
2064                    + TimeUtils.formatUptime(mLastUserActivityTimeNoChangeLights));
2065            pw.println("  mDisplayReady=" + mDisplayReady);
2066            pw.println("  mHoldingWakeLockSuspendBlocker=" + mHoldingWakeLockSuspendBlocker);
2067
2068            pw.println();
2069            pw.println("Settings and Configuration:");
2070            pw.println("  mDreamsSupportedConfig=" + mDreamsSupportedConfig);
2071            pw.println("  mDreamsEnabledSetting=" + mDreamsEnabledSetting);
2072            pw.println("  mDreamsActivateOnSleepSetting=" + mDreamsActivateOnSleepSetting);
2073            pw.println("  mScreenOffTimeoutSetting=" + mScreenOffTimeoutSetting);
2074            pw.println("  mMaximumScreenOffTimeoutFromDeviceAdmin="
2075                    + mMaximumScreenOffTimeoutFromDeviceAdmin + " (enforced="
2076                    + isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked() + ")");
2077            pw.println("  mStayOnWhilePluggedInSetting=" + mStayOnWhilePluggedInSetting);
2078            pw.println("  mScreenBrightnessSetting=" + mScreenBrightnessSetting);
2079            pw.println("  mScreenAutoBrightnessAdjustmentSetting="
2080                    + mScreenAutoBrightnessAdjustmentSetting);
2081            pw.println("  mScreenBrightnessModeSetting=" + mScreenBrightnessModeSetting);
2082            pw.println("  mScreenBrightnessOverrideFromWindowManager="
2083                    + mScreenBrightnessOverrideFromWindowManager);
2084            pw.println("  mUserActivityTimeoutOverrideFromWindowManager="
2085                    + mUserActivityTimeoutOverrideFromWindowManager);
2086            pw.println("  mTemporaryScreenBrightnessSettingOverride="
2087                    + mTemporaryScreenBrightnessSettingOverride);
2088            pw.println("  mTemporaryScreenAutoBrightnessAdjustmentSettingOverride="
2089                    + mTemporaryScreenAutoBrightnessAdjustmentSettingOverride);
2090            pw.println("  mScreenBrightnessSettingMinimum=" + mScreenBrightnessSettingMinimum);
2091            pw.println("  mScreenBrightnessSettingMaximum=" + mScreenBrightnessSettingMaximum);
2092            pw.println("  mScreenBrightnessSettingDefault=" + mScreenBrightnessSettingDefault);
2093
2094            final int screenOffTimeout = getScreenOffTimeoutLocked();
2095            final int screenDimDuration = getScreenDimDurationLocked(screenOffTimeout);
2096            pw.println();
2097            pw.println("Screen off timeout: " + screenOffTimeout + " ms");
2098            pw.println("Screen dim duration: " + screenDimDuration + " ms");
2099
2100            pw.println();
2101            pw.println("Wake Locks: size=" + mWakeLocks.size());
2102            for (WakeLock wl : mWakeLocks) {
2103                pw.println("  " + wl);
2104            }
2105
2106            pw.println();
2107            pw.println("Suspend Blockers: size=" + mSuspendBlockers.size());
2108            for (SuspendBlocker sb : mSuspendBlockers) {
2109                pw.println("  " + sb);
2110            }
2111
2112            pw.println();
2113            pw.println("Screen On Blocker: " + mScreenOnBlocker);
2114
2115            pw.println();
2116            pw.println("Display Blanker: " + mDisplayBlanker);
2117
2118            dpc = mDisplayPowerController;
2119        }
2120
2121        if (dpc != null) {
2122            dpc.dump(pw);
2123        }
2124    }
2125
2126    private SuspendBlocker createSuspendBlockerLocked(String name) {
2127        SuspendBlocker suspendBlocker = new SuspendBlockerImpl(name);
2128        mSuspendBlockers.add(suspendBlocker);
2129        return suspendBlocker;
2130    }
2131
2132    private static String wakefulnessToString(int wakefulness) {
2133        switch (wakefulness) {
2134            case WAKEFULNESS_ASLEEP:
2135                return "Asleep";
2136            case WAKEFULNESS_AWAKE:
2137                return "Awake";
2138            case WAKEFULNESS_DREAMING:
2139                return "Dreaming";
2140            case WAKEFULNESS_NAPPING:
2141                return "Napping";
2142            default:
2143                return Integer.toString(wakefulness);
2144        }
2145    }
2146
2147    private static WorkSource copyWorkSource(WorkSource workSource) {
2148        return workSource != null ? new WorkSource(workSource) : null;
2149    }
2150
2151    private final class BatteryReceiver extends BroadcastReceiver {
2152        @Override
2153        public void onReceive(Context context, Intent intent) {
2154            synchronized (mLock) {
2155                handleBatteryStateChangedLocked();
2156            }
2157        }
2158    }
2159
2160    private final class BootCompletedReceiver extends BroadcastReceiver {
2161        @Override
2162        public void onReceive(Context context, Intent intent) {
2163            synchronized (mLock) {
2164                handleBootCompletedLocked();
2165            }
2166        }
2167    }
2168
2169    private final class DreamReceiver extends BroadcastReceiver {
2170        @Override
2171        public void onReceive(Context context, Intent intent) {
2172            synchronized (mLock) {
2173                scheduleSandmanLocked();
2174            }
2175        }
2176    }
2177
2178    private final class UserSwitchedReceiver extends BroadcastReceiver {
2179        @Override
2180        public void onReceive(Context context, Intent intent) {
2181            synchronized (mLock) {
2182                handleSettingsChangedLocked();
2183            }
2184        }
2185    }
2186
2187    private final class SettingsObserver extends ContentObserver {
2188        public SettingsObserver(Handler handler) {
2189            super(handler);
2190        }
2191
2192        @Override
2193        public void onChange(boolean selfChange, Uri uri) {
2194            synchronized (mLock) {
2195                handleSettingsChangedLocked();
2196            }
2197        }
2198    }
2199
2200    /**
2201     * Handler for asynchronous operations performed by the power manager.
2202     */
2203    private final class PowerManagerHandler extends Handler {
2204        public PowerManagerHandler(Looper looper) {
2205            super(looper, null, true /*async*/);
2206        }
2207
2208        @Override
2209        public void handleMessage(Message msg) {
2210            switch (msg.what) {
2211                case MSG_USER_ACTIVITY_TIMEOUT:
2212                    handleUserActivityTimeout();
2213                    break;
2214                case MSG_SANDMAN:
2215                    handleSandman();
2216                    break;
2217                case MSG_SCREEN_ON_BLOCKER_RELEASED:
2218                    handleScreenOnBlockerReleased();
2219                    break;
2220            }
2221        }
2222    }
2223
2224    /**
2225     * Represents a wake lock that has been acquired by an application.
2226     */
2227    private final class WakeLock implements IBinder.DeathRecipient {
2228        public final IBinder mLock;
2229        public int mFlags;
2230        public String mTag;
2231        public WorkSource mWorkSource;
2232        public int mOwnerUid;
2233        public int mOwnerPid;
2234
2235        public WakeLock(IBinder lock, int flags, String tag, WorkSource workSource,
2236                int ownerUid, int ownerPid) {
2237            mLock = lock;
2238            mFlags = flags;
2239            mTag = tag;
2240            mWorkSource = copyWorkSource(workSource);
2241            mOwnerUid = ownerUid;
2242            mOwnerPid = ownerPid;
2243        }
2244
2245        @Override
2246        public void binderDied() {
2247            PowerManagerService.this.handleWakeLockDeath(this);
2248        }
2249
2250        public boolean hasSameProperties(int flags, String tag, WorkSource workSource,
2251                int ownerUid, int ownerPid) {
2252            return mFlags == flags
2253                    && mTag.equals(tag)
2254                    && hasSameWorkSource(workSource)
2255                    && mOwnerUid == ownerUid
2256                    && mOwnerPid == ownerPid;
2257        }
2258
2259        public void updateProperties(int flags, String tag, WorkSource workSource,
2260                int ownerUid, int ownerPid) {
2261            mFlags = flags;
2262            mTag = tag;
2263            updateWorkSource(workSource);
2264            mOwnerUid = ownerUid;
2265            mOwnerPid = ownerPid;
2266        }
2267
2268        public boolean hasSameWorkSource(WorkSource workSource) {
2269            return Objects.equal(mWorkSource, workSource);
2270        }
2271
2272        public void updateWorkSource(WorkSource workSource) {
2273            mWorkSource = copyWorkSource(workSource);
2274        }
2275
2276        @Override
2277        public String toString() {
2278            return getLockLevelString()
2279                    + " '" + mTag + "'" + getLockFlagsString()
2280                    + " (uid=" + mOwnerUid + ", pid=" + mOwnerPid + ", ws=" + mWorkSource + ")";
2281        }
2282
2283        private String getLockLevelString() {
2284            switch (mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
2285                case PowerManager.FULL_WAKE_LOCK:
2286                    return "FULL_WAKE_LOCK                ";
2287                case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
2288                    return "SCREEN_BRIGHT_WAKE_LOCK       ";
2289                case PowerManager.SCREEN_DIM_WAKE_LOCK:
2290                    return "SCREEN_DIM_WAKE_LOCK          ";
2291                case PowerManager.PARTIAL_WAKE_LOCK:
2292                    return "PARTIAL_WAKE_LOCK             ";
2293                case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
2294                    return "PROXIMITY_SCREEN_OFF_WAKE_LOCK";
2295                default:
2296                    return "???                           ";
2297            }
2298        }
2299
2300        private String getLockFlagsString() {
2301            String result = "";
2302            if ((mFlags & PowerManager.ACQUIRE_CAUSES_WAKEUP) != 0) {
2303                result += " ACQUIRE_CAUSES_WAKEUP";
2304            }
2305            if ((mFlags & PowerManager.ON_AFTER_RELEASE) != 0) {
2306                result += " ON_AFTER_RELEASE";
2307            }
2308            return result;
2309        }
2310    }
2311
2312    private final class SuspendBlockerImpl implements SuspendBlocker {
2313        private final String mName;
2314        private int mReferenceCount;
2315
2316        public SuspendBlockerImpl(String name) {
2317            mName = name;
2318        }
2319
2320        @Override
2321        protected void finalize() throws Throwable {
2322            try {
2323                if (mReferenceCount != 0) {
2324                    Log.wtf(TAG, "Suspend blocker \"" + mName
2325                            + "\" was finalized without being released!");
2326                    mReferenceCount = 0;
2327                    nativeReleaseSuspendBlocker(mName);
2328                }
2329            } finally {
2330                super.finalize();
2331            }
2332        }
2333
2334        @Override
2335        public void acquire() {
2336            synchronized (this) {
2337                mReferenceCount += 1;
2338                if (mReferenceCount == 1) {
2339                    nativeAcquireSuspendBlocker(mName);
2340                }
2341            }
2342        }
2343
2344        @Override
2345        public void release() {
2346            synchronized (this) {
2347                mReferenceCount -= 1;
2348                if (mReferenceCount == 0) {
2349                    nativeReleaseSuspendBlocker(mName);
2350                } else if (mReferenceCount < 0) {
2351                    Log.wtf(TAG, "Suspend blocker \"" + mName
2352                            + "\" was released without being acquired!", new Throwable());
2353                    mReferenceCount = 0;
2354                }
2355            }
2356        }
2357
2358        @Override
2359        public String toString() {
2360            synchronized (this) {
2361                return mName + ": ref count=" + mReferenceCount;
2362            }
2363        }
2364    }
2365
2366    private final class ScreenOnBlockerImpl implements ScreenOnBlocker {
2367        private int mNestCount;
2368
2369        public boolean isHeld() {
2370            synchronized (this) {
2371                return mNestCount != 0;
2372            }
2373        }
2374
2375        @Override
2376        public void acquire() {
2377            synchronized (this) {
2378                mNestCount += 1;
2379                if (DEBUG) {
2380                    Slog.d(TAG, "Screen on blocked: mNestCount=" + mNestCount);
2381                }
2382            }
2383        }
2384
2385        @Override
2386        public void release() {
2387            synchronized (this) {
2388                mNestCount -= 1;
2389                if (mNestCount < 0) {
2390                    Log.wtf(TAG, "Screen on blocker was released without being acquired!",
2391                            new Throwable());
2392                    mNestCount = 0;
2393                }
2394                if (mNestCount == 0) {
2395                    mHandler.sendEmptyMessage(MSG_SCREEN_ON_BLOCKER_RELEASED);
2396                }
2397                if (DEBUG) {
2398                    Slog.d(TAG, "Screen on unblocked: mNestCount=" + mNestCount);
2399                }
2400            }
2401        }
2402
2403        @Override
2404        public String toString() {
2405            synchronized (this) {
2406                return "held=" + (mNestCount != 0) + ", mNestCount=" + mNestCount;
2407            }
2408        }
2409    }
2410
2411    private final class DisplayBlankerImpl implements DisplayBlanker {
2412        private boolean mBlanked;
2413
2414        @Override
2415        public void blankAllDisplays() {
2416            synchronized (this) {
2417                mBlanked = true;
2418                mDisplayManagerService.blankAllDisplaysFromPowerManager();
2419                nativeSetInteractive(false);
2420                nativeSetAutoSuspend(true);
2421            }
2422        }
2423
2424        @Override
2425        public void unblankAllDisplays() {
2426            synchronized (this) {
2427                nativeSetAutoSuspend(false);
2428                nativeSetInteractive(true);
2429                mDisplayManagerService.unblankAllDisplaysFromPowerManager();
2430                mBlanked = false;
2431            }
2432        }
2433
2434        @Override
2435        public String toString() {
2436            synchronized (this) {
2437                return "blanked=" + mBlanked;
2438            }
2439        }
2440    }
2441}
2442