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