PowerManagerService.java revision d862ebb6036a769cb3be371b396e9e33f89ee365
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.IAppOpsService;
20import com.android.internal.app.IBatteryStats;
21import com.android.internal.os.BackgroundThread;
22import com.android.server.BatteryService;
23import com.android.server.EventLogTags;
24import com.android.server.LocalServices;
25import com.android.server.ServiceThread;
26import com.android.server.lights.Light;
27import com.android.server.lights.LightsManager;
28import com.android.server.Watchdog;
29
30import android.Manifest;
31import android.content.BroadcastReceiver;
32import android.content.ContentResolver;
33import android.content.Context;
34import android.content.Intent;
35import android.content.IntentFilter;
36import android.content.pm.PackageManager;
37import android.content.res.Resources;
38import android.database.ContentObserver;
39import android.hardware.SensorManager;
40import android.hardware.SystemSensorManager;
41import android.hardware.display.DisplayManagerInternal;
42import android.hardware.display.DisplayManagerInternal.DisplayPowerRequest;
43import android.net.Uri;
44import android.os.BatteryManager;
45import android.os.Binder;
46import android.os.Handler;
47import android.os.IBinder;
48import android.os.IPowerManager;
49import android.os.Looper;
50import android.os.Message;
51import android.os.PowerManager;
52import android.os.PowerManagerInternal;
53import android.os.Process;
54import android.os.RemoteException;
55import android.os.SystemClock;
56import android.os.SystemProperties;
57import android.os.SystemService;
58import android.os.UserHandle;
59import android.os.WorkSource;
60import android.provider.Settings;
61import android.service.dreams.DreamManagerInternal;
62import android.util.EventLog;
63import android.util.Log;
64import android.util.Slog;
65import android.util.TimeUtils;
66import android.view.Display;
67import android.view.WindowManagerPolicy;
68
69import java.io.FileDescriptor;
70import java.io.PrintWriter;
71import java.util.ArrayList;
72
73import libcore.util.Objects;
74
75/**
76 * The power manager service is responsible for coordinating power management
77 * functions on the device.
78 */
79public final class PowerManagerService extends com.android.server.SystemService
80        implements Watchdog.Monitor {
81    private static final String TAG = "PowerManagerService";
82
83    private static final boolean DEBUG = false;
84    private static final boolean DEBUG_SPEW = DEBUG && true;
85
86    // Message: Sent when a user activity timeout occurs to update the power state.
87    private static final int MSG_USER_ACTIVITY_TIMEOUT = 1;
88    // Message: Sent when the device enters or exits a dreaming or dozing state.
89    private static final int MSG_SANDMAN = 2;
90    // Message: Sent when the screen on blocker is released.
91    private static final int MSG_SCREEN_ON_BLOCKER_RELEASED = 3;
92    // Message: Sent to poll whether the boot animation has terminated.
93    private static final int MSG_CHECK_IF_BOOT_ANIMATION_FINISHED = 4;
94
95    // Dirty bit: mWakeLocks changed
96    private static final int DIRTY_WAKE_LOCKS = 1 << 0;
97    // Dirty bit: mWakefulness changed
98    private static final int DIRTY_WAKEFULNESS = 1 << 1;
99    // Dirty bit: user activity was poked or may have timed out
100    private static final int DIRTY_USER_ACTIVITY = 1 << 2;
101    // Dirty bit: actual display power state was updated asynchronously
102    private static final int DIRTY_ACTUAL_DISPLAY_POWER_STATE_UPDATED = 1 << 3;
103    // Dirty bit: mBootCompleted changed
104    private static final int DIRTY_BOOT_COMPLETED = 1 << 4;
105    // Dirty bit: settings changed
106    private static final int DIRTY_SETTINGS = 1 << 5;
107    // Dirty bit: mIsPowered changed
108    private static final int DIRTY_IS_POWERED = 1 << 6;
109    // Dirty bit: mStayOn changed
110    private static final int DIRTY_STAY_ON = 1 << 7;
111    // Dirty bit: battery state changed
112    private static final int DIRTY_BATTERY_STATE = 1 << 8;
113    // Dirty bit: proximity state changed
114    private static final int DIRTY_PROXIMITY_POSITIVE = 1 << 9;
115    // Dirty bit: screen on blocker state became held or unheld
116    private static final int DIRTY_SCREEN_ON_BLOCKER_RELEASED = 1 << 10;
117    // Dirty bit: dock state changed
118    private static final int DIRTY_DOCK_STATE = 1 << 11;
119
120    // Wakefulness: The device is asleep and can only be awoken by a call to wakeUp().
121    // The screen should be off or in the process of being turned off by the display controller.
122    // The device typically passes through the dozing state first.
123    private static final int WAKEFULNESS_ASLEEP = 0;
124    // Wakefulness: The device is fully awake.  It can be put to sleep by a call to goToSleep().
125    // When the user activity timeout expires, the device may start dreaming or go to sleep.
126    private static final int WAKEFULNESS_AWAKE = 1;
127    // Wakefulness: The device is dreaming.  It can be awoken by a call to wakeUp(),
128    // which ends the dream.  The device goes to sleep when goToSleep() is called, when
129    // the dream ends or when unplugged.
130    // User activity may brighten the screen but does not end the dream.
131    private static final int WAKEFULNESS_DREAMING = 2;
132    // Wakefulness: The device is dozing.  It is almost asleep but is allowing a special
133    // low-power "doze" dream to run which keeps the display on but lets the application
134    // processor be suspended.  It can be awoken by a call to wakeUp() which ends the dream.
135    // The device fully goes to sleep if the dream cannot be started or ends on its own.
136    private static final int WAKEFULNESS_DOZING = 3;
137
138    // Summarizes the state of all active wakelocks.
139    private static final int WAKE_LOCK_CPU = 1 << 0;
140    private static final int WAKE_LOCK_SCREEN_BRIGHT = 1 << 1;
141    private static final int WAKE_LOCK_SCREEN_DIM = 1 << 2;
142    private static final int WAKE_LOCK_BUTTON_BRIGHT = 1 << 3;
143    private static final int WAKE_LOCK_PROXIMITY_SCREEN_OFF = 1 << 4;
144    private static final int WAKE_LOCK_STAY_AWAKE = 1 << 5; // only set if already awake
145    private static final int WAKE_LOCK_DOZE = 1 << 6;
146
147    // Summarizes the user activity state.
148    private static final int USER_ACTIVITY_SCREEN_BRIGHT = 1 << 0;
149    private static final int USER_ACTIVITY_SCREEN_DIM = 1 << 1;
150
151    // Default timeout in milliseconds.  This is only used until the settings
152    // provider populates the actual default value (R.integer.def_screen_off_timeout).
153    private static final int DEFAULT_SCREEN_OFF_TIMEOUT = 15 * 1000;
154
155    // The name of the boot animation service in init.rc.
156    private static final String BOOT_ANIMATION_SERVICE = "bootanim";
157
158    // Poll interval in milliseconds for watching boot animation finished.
159    private static final int BOOT_ANIMATION_POLL_INTERVAL = 200;
160
161    // Used to send the hint to the PowerHAL indicating transitions
162    // from and to the low power mode.
163    private static final int POWER_HINT_LOW_POWER_MODE = 5;
164
165    private final Context mContext;
166    private LightsManager mLightsManager;
167    private BatteryService mBatteryService;
168    private DisplayManagerInternal mDisplayManagerInternal;
169    private IBatteryStats mBatteryStats;
170    private IAppOpsService mAppOps;
171    private ServiceThread mHandlerThread;
172    private PowerManagerHandler mHandler;
173    private WindowManagerPolicy mPolicy;
174    private Notifier mNotifier;
175    private WirelessChargerDetector mWirelessChargerDetector;
176    private SettingsObserver mSettingsObserver;
177    private DreamManagerInternal mDreamManager;
178    private Light mAttentionLight;
179
180    private final Object mLock = new Object();
181
182    // A bitfield that indicates what parts of the power state have
183    // changed and need to be recalculated.
184    private int mDirty;
185
186    // Indicates whether the device is awake or asleep or somewhere in between.
187    // This is distinct from the screen power state, which is managed separately.
188    private int mWakefulness;
189
190    // True if the sandman has just been summoned for the first time since entering the
191    // dreaming or dozing state.  Indicates whether a new dream should begin.
192    private boolean mSandmanSummoned;
193
194    // True if MSG_SANDMAN has been scheduled.
195    private boolean mSandmanScheduled;
196
197    // Table of all suspend blockers.
198    // There should only be a few of these.
199    private final ArrayList<SuspendBlocker> mSuspendBlockers = new ArrayList<SuspendBlocker>();
200
201    // Table of all wake locks acquired by applications.
202    private final ArrayList<WakeLock> mWakeLocks = new ArrayList<WakeLock>();
203
204    // A bitfield that summarizes the state of all active wakelocks.
205    private int mWakeLockSummary;
206
207    // True if the device is in an interactive state.
208    private boolean mInteractive;
209    private boolean mInteractiveChanging;
210
211    // If true, instructs the display controller to wait for the proximity sensor to
212    // go negative before turning the screen on.
213    private boolean mRequestWaitForNegativeProximity;
214
215    // Timestamp of the last time the device was awoken or put to sleep.
216    private long mLastWakeTime;
217    private long mLastSleepTime;
218
219    // Timestamp of the last call to user activity.
220    private long mLastUserActivityTime;
221    private long mLastUserActivityTimeNoChangeLights;
222
223    // A bitfield that summarizes the effect of the user activity timer.
224    // A zero value indicates that the user activity timer has expired.
225    private int mUserActivitySummary;
226
227    // The desired display power state.  The actual state may lag behind the
228    // requested because it is updated asynchronously by the display power controller.
229    private final DisplayPowerRequest mDisplayPowerRequest = new DisplayPowerRequest();
230
231    // True if the display power state has been fully applied, which means the display
232    // is actually on or actually off or whatever was requested.
233    private boolean mDisplayReady;
234
235    // The suspend blocker used to keep the CPU alive when an application has acquired
236    // a wake lock.
237    private final SuspendBlocker mWakeLockSuspendBlocker;
238
239    // True if the wake lock suspend blocker has been acquired.
240    private boolean mHoldingWakeLockSuspendBlocker;
241
242    // The suspend blocker used to keep the CPU alive when the display is on, the
243    // display is getting ready or there is user activity (in which case the display
244    // must be on).
245    private final SuspendBlocker mDisplaySuspendBlocker;
246
247    // True if the display suspend blocker has been acquired.
248    private boolean mHoldingDisplaySuspendBlocker;
249
250    // The screen on blocker used to keep the screen from turning on while the lock
251    // screen is coming up.
252    private final ScreenOnBlockerImpl mScreenOnBlocker;
253
254    // True if systemReady() has been called.
255    private boolean mSystemReady;
256
257    // True if boot completed occurred.  We keep the screen on until this happens.
258    private boolean mBootCompleted;
259
260    // True if auto-suspend mode is enabled.
261    // Refer to autosuspend.h.
262    private boolean mHalAutoSuspendModeEnabled;
263
264    // True if interactive mode is enabled.
265    // Refer to power.h.
266    private boolean mHalInteractiveModeEnabled;
267
268    // True if the device is plugged into a power source.
269    private boolean mIsPowered;
270
271    // The current plug type, such as BatteryManager.BATTERY_PLUGGED_WIRELESS.
272    private int mPlugType;
273
274    // The current battery level percentage.
275    private int mBatteryLevel;
276
277    // The battery level percentage at the time the dream started.
278    // This is used to terminate a dream and go to sleep if the battery is
279    // draining faster than it is charging and the user activity timeout has expired.
280    private int mBatteryLevelWhenDreamStarted;
281
282    // The current dock state.
283    private int mDockState = Intent.EXTRA_DOCK_STATE_UNDOCKED;
284
285    // True to decouple auto-suspend mode from the display state.
286    private boolean mDecoupleHalAutoSuspendModeFromDisplayConfig;
287
288    // True to decouple interactive mode from the display state.
289    private boolean mDecoupleHalInteractiveModeFromDisplayConfig;
290
291    // True if the device should wake up when plugged or unplugged.
292    private boolean mWakeUpWhenPluggedOrUnpluggedConfig;
293
294    // True if the device should suspend when the screen is off due to proximity.
295    private boolean mSuspendWhenScreenOffDueToProximityConfig;
296
297    // True if dreams are supported on this device.
298    private boolean mDreamsSupportedConfig;
299
300    // Default value for dreams enabled
301    private boolean mDreamsEnabledByDefaultConfig;
302
303    // Default value for dreams activate-on-sleep
304    private boolean mDreamsActivatedOnSleepByDefaultConfig;
305
306    // Default value for dreams activate-on-dock
307    private boolean mDreamsActivatedOnDockByDefaultConfig;
308
309    // True if dreams can run while not plugged in.
310    private boolean mDreamsEnabledOnBatteryConfig;
311
312    // Minimum battery level to allow dreaming when powered.
313    // Use -1 to disable this safety feature.
314    private int mDreamsBatteryLevelMinimumWhenPoweredConfig;
315
316    // Minimum battery level to allow dreaming when not powered.
317    // Use -1 to disable this safety feature.
318    private int mDreamsBatteryLevelMinimumWhenNotPoweredConfig;
319
320    // If the battery level drops by this percentage and the user activity timeout
321    // has expired, then assume the device is receiving insufficient current to charge
322    // effectively and terminate the dream.  Use -1 to disable this safety feature.
323    private int mDreamsBatteryLevelDrainCutoffConfig;
324
325    // True if dreams are enabled by the user.
326    private boolean mDreamsEnabledSetting;
327
328    // True if dreams should be activated on sleep.
329    private boolean mDreamsActivateOnSleepSetting;
330
331    // True if dreams should be activated on dock.
332    private boolean mDreamsActivateOnDockSetting;
333
334    // The minimum screen off timeout, in milliseconds.
335    private int mMinimumScreenOffTimeoutConfig;
336
337    // The screen dim duration, in milliseconds.
338    // This is subtracted from the end of the screen off timeout so the
339    // minimum screen off timeout should be longer than this.
340    private int mMaximumScreenDimDurationConfig;
341
342    // The maximum screen dim time expressed as a ratio relative to the screen
343    // off timeout.  If the screen off timeout is very short then we want the
344    // dim timeout to also be quite short so that most of the time is spent on.
345    // Otherwise the user won't get much screen on time before dimming occurs.
346    private float mMaximumScreenDimRatioConfig;
347
348    // The screen off timeout setting value in milliseconds.
349    private int mScreenOffTimeoutSetting;
350
351    // The maximum allowable screen off timeout according to the device
352    // administration policy.  Overrides other settings.
353    private int mMaximumScreenOffTimeoutFromDeviceAdmin = Integer.MAX_VALUE;
354
355    // The stay on while plugged in setting.
356    // A bitfield of battery conditions under which to make the screen stay on.
357    private int mStayOnWhilePluggedInSetting;
358
359    // True if the device should stay on.
360    private boolean mStayOn;
361
362    // True if the proximity sensor reads a positive result.
363    private boolean mProximityPositive;
364
365    // Screen brightness setting limits.
366    private int mScreenBrightnessSettingMinimum;
367    private int mScreenBrightnessSettingMaximum;
368    private int mScreenBrightnessSettingDefault;
369
370    // The screen brightness setting, from 0 to 255.
371    // Use -1 if no value has been set.
372    private int mScreenBrightnessSetting;
373
374    // The screen auto-brightness adjustment setting, from -1 to 1.
375    // Use 0 if there is no adjustment.
376    private float mScreenAutoBrightnessAdjustmentSetting;
377
378    // The screen brightness mode.
379    // One of the Settings.System.SCREEN_BRIGHTNESS_MODE_* constants.
380    private int mScreenBrightnessModeSetting;
381
382    // The screen brightness setting override from the window manager
383    // to allow the current foreground activity to override the brightness.
384    // Use -1 to disable.
385    private int mScreenBrightnessOverrideFromWindowManager = -1;
386
387    // The user activity timeout override from the window manager
388    // to allow the current foreground activity to override the user activity timeout.
389    // Use -1 to disable.
390    private long mUserActivityTimeoutOverrideFromWindowManager = -1;
391
392    // The screen brightness setting override from the settings application
393    // to temporarily adjust the brightness until next updated,
394    // Use -1 to disable.
395    private int mTemporaryScreenBrightnessSettingOverride = -1;
396
397    // The screen brightness adjustment setting override from the settings
398    // application to temporarily adjust the auto-brightness adjustment factor
399    // until next updated, in the range -1..1.
400    // Use NaN to disable.
401    private float mTemporaryScreenAutoBrightnessAdjustmentSettingOverride = Float.NaN;
402
403    // Time when we last logged a warning about calling userActivity() without permission.
404    private long mLastWarningAboutUserActivityPermission = Long.MIN_VALUE;
405
406    // If true, the device is in low power mode.
407    private boolean mLowPowerModeEnabled;
408
409    private final ArrayList<PowerManagerInternal.LowPowerModeListener> mLowPowerModeListeners
410            = new ArrayList<PowerManagerInternal.LowPowerModeListener>();
411
412    private native void nativeInit();
413
414    private static native void nativeAcquireSuspendBlocker(String name);
415    private static native void nativeReleaseSuspendBlocker(String name);
416    private static native void nativeSetInteractive(boolean enable);
417    private static native void nativeSetAutoSuspend(boolean enable);
418    private static native void nativeSendPowerHint(int hintId, int data);
419
420    public PowerManagerService(Context context) {
421        super(context);
422        mContext = context;
423        synchronized (mLock) {
424            mWakeLockSuspendBlocker = createSuspendBlockerLocked("PowerManagerService.WakeLocks");
425            mDisplaySuspendBlocker = createSuspendBlockerLocked("PowerManagerService.Display");
426            mDisplaySuspendBlocker.acquire();
427            mHoldingDisplaySuspendBlocker = true;
428            mHalAutoSuspendModeEnabled = false;
429            mHalInteractiveModeEnabled = true;
430
431            mScreenOnBlocker = new ScreenOnBlockerImpl();
432            mWakefulness = WAKEFULNESS_AWAKE;
433            mInteractive = true;
434
435            nativeInit();
436            nativeSetAutoSuspend(false);
437            nativeSetInteractive(true);
438        }
439    }
440
441    @Override
442    public void onStart() {
443        publishBinderService(Context.POWER_SERVICE, new BinderService());
444        publishLocalService(PowerManagerInternal.class, new LocalService());
445    }
446
447    /**
448     * Initialize the power manager.
449     * Must be called before any other functions within the power manager are called.
450     */
451    public void init(LightsManager ls,
452            BatteryService bs, IBatteryStats bss,
453            IAppOpsService appOps) {
454        mLightsManager = ls;
455        mBatteryService = bs;
456        mBatteryStats = bss;
457        mAppOps = appOps;
458        mDisplayManagerInternal = getLocalService(DisplayManagerInternal.class);
459        mHandlerThread = new ServiceThread(TAG,
460                Process.THREAD_PRIORITY_DISPLAY, false /*allowIo*/);
461        mHandlerThread.start();
462        mHandler = new PowerManagerHandler(mHandlerThread.getLooper());
463
464        Watchdog.getInstance().addMonitor(this);
465        Watchdog.getInstance().addThread(mHandler);
466    }
467
468    void setPolicy(WindowManagerPolicy policy) {
469        synchronized (mLock) {
470            mPolicy = policy;
471        }
472    }
473
474    public void systemReady() {
475        synchronized (mLock) {
476            mSystemReady = true;
477            mDreamManager = LocalServices.getService(DreamManagerInternal.class);
478
479            PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
480            mScreenBrightnessSettingMinimum = pm.getMinimumScreenBrightnessSetting();
481            mScreenBrightnessSettingMaximum = pm.getMaximumScreenBrightnessSetting();
482            mScreenBrightnessSettingDefault = pm.getDefaultScreenBrightnessSetting();
483
484            SensorManager sensorManager = new SystemSensorManager(mContext, mHandler.getLooper());
485
486            // The notifier runs on the system server's main looper so as not to interfere
487            // with the animations and other critical functions of the power manager.
488            mNotifier = new Notifier(Looper.getMainLooper(), mContext, mBatteryStats,
489                    mAppOps, createSuspendBlockerLocked("PowerManagerService.Broadcasts"),
490                    mScreenOnBlocker, mPolicy);
491
492            mWirelessChargerDetector = new WirelessChargerDetector(sensorManager,
493                    createSuspendBlockerLocked("PowerManagerService.WirelessChargerDetector"),
494                    mHandler);
495            mSettingsObserver = new SettingsObserver(mHandler);
496            mAttentionLight = mLightsManager.getLight(LightsManager.LIGHT_ID_ATTENTION);
497
498            // Initialize display power management.
499            mDisplayManagerInternal.initPowerManagement(
500                    mDisplayPowerCallbacks, mHandler, sensorManager);
501
502            // Register for broadcasts from other components of the system.
503            IntentFilter filter = new IntentFilter();
504            filter.addAction(Intent.ACTION_BATTERY_CHANGED);
505            mContext.registerReceiver(new BatteryReceiver(), filter, null, mHandler);
506
507            filter = new IntentFilter();
508            filter.addAction(Intent.ACTION_BOOT_COMPLETED);
509            filter.setPriority(IntentFilter.SYSTEM_HIGH_PRIORITY);
510            mContext.registerReceiver(new BootCompletedReceiver(), filter, null, mHandler);
511
512            filter = new IntentFilter();
513            filter.addAction(Intent.ACTION_DREAMING_STARTED);
514            filter.addAction(Intent.ACTION_DREAMING_STOPPED);
515            mContext.registerReceiver(new DreamReceiver(), filter, null, mHandler);
516
517            filter = new IntentFilter();
518            filter.addAction(Intent.ACTION_USER_SWITCHED);
519            mContext.registerReceiver(new UserSwitchedReceiver(), filter, null, mHandler);
520
521            filter = new IntentFilter();
522            filter.addAction(Intent.ACTION_DOCK_EVENT);
523            mContext.registerReceiver(new DockReceiver(), filter, null, mHandler);
524
525            // Register for settings changes.
526            final ContentResolver resolver = mContext.getContentResolver();
527            resolver.registerContentObserver(Settings.Secure.getUriFor(
528                    Settings.Secure.SCREENSAVER_ENABLED),
529                    false, mSettingsObserver, UserHandle.USER_ALL);
530            resolver.registerContentObserver(Settings.Secure.getUriFor(
531                    Settings.Secure.SCREENSAVER_ACTIVATE_ON_SLEEP),
532                    false, mSettingsObserver, UserHandle.USER_ALL);
533            resolver.registerContentObserver(Settings.Secure.getUriFor(
534                    Settings.Secure.SCREENSAVER_ACTIVATE_ON_DOCK),
535                    false, mSettingsObserver, UserHandle.USER_ALL);
536            resolver.registerContentObserver(Settings.System.getUriFor(
537                    Settings.System.SCREEN_OFF_TIMEOUT),
538                    false, mSettingsObserver, UserHandle.USER_ALL);
539            resolver.registerContentObserver(Settings.Global.getUriFor(
540                    Settings.Global.STAY_ON_WHILE_PLUGGED_IN),
541                    false, mSettingsObserver, UserHandle.USER_ALL);
542            resolver.registerContentObserver(Settings.System.getUriFor(
543                    Settings.System.SCREEN_BRIGHTNESS),
544                    false, mSettingsObserver, UserHandle.USER_ALL);
545            resolver.registerContentObserver(Settings.System.getUriFor(
546                    Settings.System.SCREEN_BRIGHTNESS_MODE),
547                    false, mSettingsObserver, UserHandle.USER_ALL);
548            resolver.registerContentObserver(Settings.System.getUriFor(
549                    Settings.System.SCREEN_AUTO_BRIGHTNESS_ADJ),
550                    false, mSettingsObserver, UserHandle.USER_ALL);
551            resolver.registerContentObserver(Settings.Global.getUriFor(
552                    Settings.Global.LOW_POWER_MODE),
553                    false, mSettingsObserver, UserHandle.USER_ALL);
554            // Go.
555            readConfigurationLocked();
556            updateSettingsLocked();
557            mDirty |= DIRTY_BATTERY_STATE;
558            updatePowerStateLocked();
559        }
560    }
561
562    private void readConfigurationLocked() {
563        final Resources resources = mContext.getResources();
564
565        mDecoupleHalAutoSuspendModeFromDisplayConfig = resources.getBoolean(
566                com.android.internal.R.bool.config_powerDecoupleAutoSuspendModeFromDisplay);
567        mDecoupleHalInteractiveModeFromDisplayConfig = resources.getBoolean(
568                com.android.internal.R.bool.config_powerDecoupleInteractiveModeFromDisplay);
569        mWakeUpWhenPluggedOrUnpluggedConfig = resources.getBoolean(
570                com.android.internal.R.bool.config_unplugTurnsOnScreen);
571        mSuspendWhenScreenOffDueToProximityConfig = resources.getBoolean(
572                com.android.internal.R.bool.config_suspendWhenScreenOffDueToProximity);
573        mDreamsSupportedConfig = resources.getBoolean(
574                com.android.internal.R.bool.config_dreamsSupported);
575        mDreamsEnabledByDefaultConfig = resources.getBoolean(
576                com.android.internal.R.bool.config_dreamsEnabledByDefault);
577        mDreamsActivatedOnSleepByDefaultConfig = resources.getBoolean(
578                com.android.internal.R.bool.config_dreamsActivatedOnSleepByDefault);
579        mDreamsActivatedOnDockByDefaultConfig = resources.getBoolean(
580                com.android.internal.R.bool.config_dreamsActivatedOnDockByDefault);
581        mDreamsEnabledOnBatteryConfig = resources.getBoolean(
582                com.android.internal.R.bool.config_dreamsEnabledOnBattery);
583        mDreamsBatteryLevelMinimumWhenPoweredConfig = resources.getInteger(
584                com.android.internal.R.integer.config_dreamsBatteryLevelMinimumWhenPowered);
585        mDreamsBatteryLevelMinimumWhenNotPoweredConfig = resources.getInteger(
586                com.android.internal.R.integer.config_dreamsBatteryLevelMinimumWhenNotPowered);
587        mDreamsBatteryLevelDrainCutoffConfig = resources.getInteger(
588                com.android.internal.R.integer.config_dreamsBatteryLevelDrainCutoff);
589        mMinimumScreenOffTimeoutConfig = resources.getInteger(
590                com.android.internal.R.integer.config_minimumScreenOffTimeout);
591        mMaximumScreenDimDurationConfig = resources.getInteger(
592                com.android.internal.R.integer.config_maximumScreenDimDuration);
593        mMaximumScreenDimRatioConfig = resources.getFraction(
594                com.android.internal.R.fraction.config_maximumScreenDimRatio, 1, 1);
595    }
596
597    private void updateSettingsLocked() {
598        final ContentResolver resolver = mContext.getContentResolver();
599
600        mDreamsEnabledSetting = (Settings.Secure.getIntForUser(resolver,
601                Settings.Secure.SCREENSAVER_ENABLED,
602                mDreamsEnabledByDefaultConfig ? 1 : 0,
603                UserHandle.USER_CURRENT) != 0);
604        mDreamsActivateOnSleepSetting = (Settings.Secure.getIntForUser(resolver,
605                Settings.Secure.SCREENSAVER_ACTIVATE_ON_SLEEP,
606                mDreamsActivatedOnSleepByDefaultConfig ? 1 : 0,
607                UserHandle.USER_CURRENT) != 0);
608        mDreamsActivateOnDockSetting = (Settings.Secure.getIntForUser(resolver,
609                Settings.Secure.SCREENSAVER_ACTIVATE_ON_DOCK,
610                mDreamsActivatedOnDockByDefaultConfig ? 1 : 0,
611                UserHandle.USER_CURRENT) != 0);
612        mScreenOffTimeoutSetting = Settings.System.getIntForUser(resolver,
613                Settings.System.SCREEN_OFF_TIMEOUT, DEFAULT_SCREEN_OFF_TIMEOUT,
614                UserHandle.USER_CURRENT);
615        mStayOnWhilePluggedInSetting = Settings.Global.getInt(resolver,
616                Settings.Global.STAY_ON_WHILE_PLUGGED_IN, BatteryManager.BATTERY_PLUGGED_AC);
617
618        final int oldScreenBrightnessSetting = mScreenBrightnessSetting;
619        mScreenBrightnessSetting = Settings.System.getIntForUser(resolver,
620                Settings.System.SCREEN_BRIGHTNESS, mScreenBrightnessSettingDefault,
621                UserHandle.USER_CURRENT);
622        if (oldScreenBrightnessSetting != mScreenBrightnessSetting) {
623            mTemporaryScreenBrightnessSettingOverride = -1;
624        }
625
626        final float oldScreenAutoBrightnessAdjustmentSetting =
627                mScreenAutoBrightnessAdjustmentSetting;
628        mScreenAutoBrightnessAdjustmentSetting = Settings.System.getFloatForUser(resolver,
629                Settings.System.SCREEN_AUTO_BRIGHTNESS_ADJ, 0.0f,
630                UserHandle.USER_CURRENT);
631        if (oldScreenAutoBrightnessAdjustmentSetting != mScreenAutoBrightnessAdjustmentSetting) {
632            mTemporaryScreenAutoBrightnessAdjustmentSettingOverride = Float.NaN;
633        }
634
635        mScreenBrightnessModeSetting = Settings.System.getIntForUser(resolver,
636                Settings.System.SCREEN_BRIGHTNESS_MODE,
637                Settings.System.SCREEN_BRIGHTNESS_MODE_MANUAL, UserHandle.USER_CURRENT);
638
639        final boolean lowPowerModeEnabled = Settings.Global.getInt(resolver,
640                Settings.Global.LOW_POWER_MODE, 0) != 0;
641        if (lowPowerModeEnabled != mLowPowerModeEnabled) {
642            powerHintInternal(POWER_HINT_LOW_POWER_MODE, lowPowerModeEnabled ? 1 : 0);
643            mLowPowerModeEnabled = lowPowerModeEnabled;
644            BackgroundThread.getHandler().post(new Runnable() {
645                @Override
646                public void run() {
647                    ArrayList<PowerManagerInternal.LowPowerModeListener> listeners;
648                    synchronized (mLock) {
649                        listeners = new ArrayList<PowerManagerInternal.LowPowerModeListener>(
650                                mLowPowerModeListeners);
651                    }
652                    for (int i=0; i<listeners.size(); i++) {
653                        listeners.get(i).onLowPowerModeChanged(lowPowerModeEnabled);
654                    }
655                }
656            });
657        }
658
659        mDirty |= DIRTY_SETTINGS;
660    }
661
662    private void handleSettingsChangedLocked() {
663        updateSettingsLocked();
664        updatePowerStateLocked();
665    }
666
667    private void acquireWakeLockInternal(IBinder lock, int flags, String tag, String packageName,
668            WorkSource ws, String historyTag, int uid, int pid) {
669        synchronized (mLock) {
670            if (DEBUG_SPEW) {
671                Slog.d(TAG, "acquireWakeLockInternal: lock=" + Objects.hashCode(lock)
672                        + ", flags=0x" + Integer.toHexString(flags)
673                        + ", tag=\"" + tag + "\", ws=" + ws + ", uid=" + uid + ", pid=" + pid);
674            }
675
676            WakeLock wakeLock;
677            int index = findWakeLockIndexLocked(lock);
678            if (index >= 0) {
679                wakeLock = mWakeLocks.get(index);
680                if (!wakeLock.hasSameProperties(flags, tag, ws, uid, pid)) {
681                    // Update existing wake lock.  This shouldn't happen but is harmless.
682                    notifyWakeLockChangingLocked(wakeLock, flags, tag, packageName,
683                            uid, pid, ws, historyTag);
684                    wakeLock.updateProperties(flags, tag, packageName, ws, historyTag, uid, pid);
685                }
686            } else {
687                wakeLock = new WakeLock(lock, flags, tag, packageName, ws, historyTag, uid, pid);
688                try {
689                    lock.linkToDeath(wakeLock, 0);
690                } catch (RemoteException ex) {
691                    throw new IllegalArgumentException("Wake lock is already dead.");
692                }
693                notifyWakeLockAcquiredLocked(wakeLock);
694                mWakeLocks.add(wakeLock);
695            }
696
697            applyWakeLockFlagsOnAcquireLocked(wakeLock);
698            mDirty |= DIRTY_WAKE_LOCKS;
699            updatePowerStateLocked();
700        }
701    }
702
703    @SuppressWarnings("deprecation")
704    private static boolean isScreenLock(final WakeLock wakeLock) {
705        switch (wakeLock.mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
706            case PowerManager.FULL_WAKE_LOCK:
707            case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
708            case PowerManager.SCREEN_DIM_WAKE_LOCK:
709                return true;
710        }
711        return false;
712    }
713
714    private void applyWakeLockFlagsOnAcquireLocked(WakeLock wakeLock) {
715        if ((wakeLock.mFlags & PowerManager.ACQUIRE_CAUSES_WAKEUP) != 0
716                && isScreenLock(wakeLock)) {
717            wakeUpNoUpdateLocked(SystemClock.uptimeMillis());
718        }
719    }
720
721    private void releaseWakeLockInternal(IBinder lock, int flags) {
722        synchronized (mLock) {
723            int index = findWakeLockIndexLocked(lock);
724            if (index < 0) {
725                if (DEBUG_SPEW) {
726                    Slog.d(TAG, "releaseWakeLockInternal: lock=" + Objects.hashCode(lock)
727                            + " [not found], flags=0x" + Integer.toHexString(flags));
728                }
729                return;
730            }
731
732            WakeLock wakeLock = mWakeLocks.get(index);
733            if (DEBUG_SPEW) {
734                Slog.d(TAG, "releaseWakeLockInternal: lock=" + Objects.hashCode(lock)
735                        + " [" + wakeLock.mTag + "], flags=0x" + Integer.toHexString(flags));
736            }
737
738            mWakeLocks.remove(index);
739            notifyWakeLockReleasedLocked(wakeLock);
740            wakeLock.mLock.unlinkToDeath(wakeLock, 0);
741
742            if ((flags & PowerManager.WAIT_FOR_PROXIMITY_NEGATIVE) != 0) {
743                mRequestWaitForNegativeProximity = true;
744            }
745
746            applyWakeLockFlagsOnReleaseLocked(wakeLock);
747            mDirty |= DIRTY_WAKE_LOCKS;
748            updatePowerStateLocked();
749        }
750    }
751
752    private void handleWakeLockDeath(WakeLock wakeLock) {
753        synchronized (mLock) {
754            if (DEBUG_SPEW) {
755                Slog.d(TAG, "handleWakeLockDeath: lock=" + Objects.hashCode(wakeLock.mLock)
756                        + " [" + wakeLock.mTag + "]");
757            }
758
759            int index = mWakeLocks.indexOf(wakeLock);
760            if (index < 0) {
761                return;
762            }
763
764            mWakeLocks.remove(index);
765            notifyWakeLockReleasedLocked(wakeLock);
766
767            applyWakeLockFlagsOnReleaseLocked(wakeLock);
768            mDirty |= DIRTY_WAKE_LOCKS;
769            updatePowerStateLocked();
770        }
771    }
772
773    private void applyWakeLockFlagsOnReleaseLocked(WakeLock wakeLock) {
774        if ((wakeLock.mFlags & PowerManager.ON_AFTER_RELEASE) != 0
775                && isScreenLock(wakeLock)) {
776            userActivityNoUpdateLocked(SystemClock.uptimeMillis(),
777                    PowerManager.USER_ACTIVITY_EVENT_OTHER,
778                    PowerManager.USER_ACTIVITY_FLAG_NO_CHANGE_LIGHTS,
779                    wakeLock.mOwnerUid);
780        }
781    }
782
783    private void updateWakeLockWorkSourceInternal(IBinder lock, WorkSource ws, String historyTag) {
784        synchronized (mLock) {
785            int index = findWakeLockIndexLocked(lock);
786            if (index < 0) {
787                if (DEBUG_SPEW) {
788                    Slog.d(TAG, "updateWakeLockWorkSourceInternal: lock=" + Objects.hashCode(lock)
789                            + " [not found], ws=" + ws);
790                }
791                throw new IllegalArgumentException("Wake lock not active");
792            }
793
794            WakeLock wakeLock = mWakeLocks.get(index);
795            if (DEBUG_SPEW) {
796                Slog.d(TAG, "updateWakeLockWorkSourceInternal: lock=" + Objects.hashCode(lock)
797                        + " [" + wakeLock.mTag + "], ws=" + ws);
798            }
799
800            if (!wakeLock.hasSameWorkSource(ws)) {
801                notifyWakeLockChangingLocked(wakeLock, wakeLock.mFlags, wakeLock.mTag,
802                        wakeLock.mPackageName, wakeLock.mOwnerUid, wakeLock.mOwnerPid,
803                        ws, historyTag);
804                wakeLock.mHistoryTag = historyTag;
805                wakeLock.updateWorkSource(ws);
806            }
807        }
808    }
809
810    private int findWakeLockIndexLocked(IBinder lock) {
811        final int count = mWakeLocks.size();
812        for (int i = 0; i < count; i++) {
813            if (mWakeLocks.get(i).mLock == lock) {
814                return i;
815            }
816        }
817        return -1;
818    }
819
820    private void notifyWakeLockAcquiredLocked(WakeLock wakeLock) {
821        if (mSystemReady) {
822            wakeLock.mNotifiedAcquired = true;
823            mNotifier.onWakeLockAcquired(wakeLock.mFlags, wakeLock.mTag, wakeLock.mPackageName,
824                    wakeLock.mOwnerUid, wakeLock.mOwnerPid, wakeLock.mWorkSource,
825                    wakeLock.mHistoryTag);
826        }
827    }
828
829    private void notifyWakeLockChangingLocked(WakeLock wakeLock, int flags, String tag,
830            String packageName, int uid, int pid, WorkSource ws, String historyTag) {
831        if (mSystemReady && wakeLock.mNotifiedAcquired) {
832            mNotifier.onWakeLockChanging(wakeLock.mFlags, wakeLock.mTag, wakeLock.mPackageName,
833                    wakeLock.mOwnerUid, wakeLock.mOwnerPid, wakeLock.mWorkSource,
834                    wakeLock.mHistoryTag, flags, tag, packageName, uid, pid, ws, historyTag);
835        }
836    }
837
838    private void notifyWakeLockReleasedLocked(WakeLock wakeLock) {
839        if (mSystemReady && wakeLock.mNotifiedAcquired) {
840            wakeLock.mNotifiedAcquired = false;
841            mNotifier.onWakeLockReleased(wakeLock.mFlags, wakeLock.mTag,
842                    wakeLock.mPackageName, wakeLock.mOwnerUid, wakeLock.mOwnerPid,
843                    wakeLock.mWorkSource, wakeLock.mHistoryTag);
844        }
845    }
846
847    @SuppressWarnings("deprecation")
848    private boolean isWakeLockLevelSupportedInternal(int level) {
849        synchronized (mLock) {
850            switch (level) {
851                case PowerManager.PARTIAL_WAKE_LOCK:
852                case PowerManager.SCREEN_DIM_WAKE_LOCK:
853                case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
854                case PowerManager.FULL_WAKE_LOCK:
855                case PowerManager.DOZE_WAKE_LOCK:
856                    return true;
857
858                case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
859                    return mSystemReady && mDisplayManagerInternal.isProximitySensorAvailable();
860
861                default:
862                    return false;
863            }
864        }
865    }
866
867    // Called from native code.
868    private void userActivityFromNative(long eventTime, int event, int flags) {
869        userActivityInternal(eventTime, event, flags, Process.SYSTEM_UID);
870    }
871
872    private void userActivityInternal(long eventTime, int event, int flags, int uid) {
873        synchronized (mLock) {
874            if (userActivityNoUpdateLocked(eventTime, event, flags, uid)) {
875                updatePowerStateLocked();
876            }
877        }
878    }
879
880    private boolean userActivityNoUpdateLocked(long eventTime, int event, int flags, int uid) {
881        if (DEBUG_SPEW) {
882            Slog.d(TAG, "userActivityNoUpdateLocked: eventTime=" + eventTime
883                    + ", event=" + event + ", flags=0x" + Integer.toHexString(flags)
884                    + ", uid=" + uid);
885        }
886
887        if (eventTime < mLastSleepTime || eventTime < mLastWakeTime
888                || mWakefulness == WAKEFULNESS_ASLEEP || mWakefulness == WAKEFULNESS_DOZING
889                || !mBootCompleted || !mSystemReady) {
890            return false;
891        }
892
893        mNotifier.onUserActivity(event, uid);
894
895        if ((flags & PowerManager.USER_ACTIVITY_FLAG_NO_CHANGE_LIGHTS) != 0) {
896            if (eventTime > mLastUserActivityTimeNoChangeLights
897                    && eventTime > mLastUserActivityTime) {
898                mLastUserActivityTimeNoChangeLights = eventTime;
899                mDirty |= DIRTY_USER_ACTIVITY;
900                return true;
901            }
902        } else {
903            if (eventTime > mLastUserActivityTime) {
904                mLastUserActivityTime = eventTime;
905                mDirty |= DIRTY_USER_ACTIVITY;
906                return true;
907            }
908        }
909        return false;
910    }
911
912    private void wakeUpInternal(long eventTime) {
913        synchronized (mLock) {
914            if (wakeUpNoUpdateLocked(eventTime)) {
915                updatePowerStateLocked();
916            }
917        }
918    }
919
920    private boolean wakeUpNoUpdateLocked(long eventTime) {
921        if (DEBUG_SPEW) {
922            Slog.d(TAG, "wakeUpNoUpdateLocked: eventTime=" + eventTime);
923        }
924
925        if (eventTime < mLastSleepTime || mWakefulness == WAKEFULNESS_AWAKE
926                || !mBootCompleted || !mSystemReady) {
927            return false;
928        }
929
930        switch (mWakefulness) {
931            case WAKEFULNESS_ASLEEP:
932                Slog.i(TAG, "Waking up from sleep...");
933                break;
934            case WAKEFULNESS_DREAMING:
935                Slog.i(TAG, "Waking up from dream...");
936                break;
937            case WAKEFULNESS_DOZING:
938                Slog.i(TAG, "Waking up from dozing...");
939                break;
940        }
941
942        mLastWakeTime = eventTime;
943        mDirty |= DIRTY_WAKEFULNESS;
944        mWakefulness = WAKEFULNESS_AWAKE;
945        setInteractiveStateLocked(true, 0);
946
947        userActivityNoUpdateLocked(
948                eventTime, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
949        return true;
950    }
951
952    private void goToSleepInternal(long eventTime, int reason, int flags) {
953        synchronized (mLock) {
954            if (goToSleepNoUpdateLocked(eventTime, reason, flags)) {
955                updatePowerStateLocked();
956            }
957        }
958    }
959
960    // This method is called goToSleep for historical reasons but we actually start
961    // dozing before really going to sleep.
962    @SuppressWarnings("deprecation")
963    private boolean goToSleepNoUpdateLocked(long eventTime, int reason, int flags) {
964        if (DEBUG_SPEW) {
965            Slog.d(TAG, "goToSleepNoUpdateLocked: eventTime=" + eventTime
966                    + ", reason=" + reason + ", flags=" + flags);
967        }
968
969        if (eventTime < mLastWakeTime
970                || mWakefulness == WAKEFULNESS_ASLEEP
971                || mWakefulness == WAKEFULNESS_DOZING
972                || !mBootCompleted || !mSystemReady) {
973            return false;
974        }
975
976        switch (reason) {
977            case PowerManager.GO_TO_SLEEP_REASON_DEVICE_ADMIN:
978                Slog.i(TAG, "Going to sleep due to device administration policy...");
979                break;
980            case PowerManager.GO_TO_SLEEP_REASON_TIMEOUT:
981                Slog.i(TAG, "Going to sleep due to screen timeout...");
982                break;
983            default:
984                Slog.i(TAG, "Going to sleep by user request...");
985                reason = PowerManager.GO_TO_SLEEP_REASON_USER;
986                break;
987        }
988
989        mLastSleepTime = eventTime;
990        mDirty |= DIRTY_WAKEFULNESS;
991        mWakefulness = WAKEFULNESS_DOZING;
992        mSandmanSummoned = true;
993        setInteractiveStateLocked(false, reason);
994
995        // Report the number of wake locks that will be cleared by going to sleep.
996        int numWakeLocksCleared = 0;
997        final int numWakeLocks = mWakeLocks.size();
998        for (int i = 0; i < numWakeLocks; i++) {
999            final WakeLock wakeLock = mWakeLocks.get(i);
1000            switch (wakeLock.mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
1001                case PowerManager.FULL_WAKE_LOCK:
1002                case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
1003                case PowerManager.SCREEN_DIM_WAKE_LOCK:
1004                    numWakeLocksCleared += 1;
1005                    break;
1006            }
1007        }
1008        EventLog.writeEvent(EventLogTags.POWER_SLEEP_REQUESTED, numWakeLocksCleared);
1009
1010        // Skip dozing if requested.
1011        if ((flags & PowerManager.GO_TO_SLEEP_FLAG_NO_DOZE) != 0) {
1012            reallyGoToSleepNoUpdateLocked(eventTime);
1013        }
1014        return true;
1015    }
1016
1017    private void napInternal(long eventTime) {
1018        synchronized (mLock) {
1019            if (napNoUpdateLocked(eventTime)) {
1020                updatePowerStateLocked();
1021            }
1022        }
1023    }
1024
1025    private boolean napNoUpdateLocked(long eventTime) {
1026        if (DEBUG_SPEW) {
1027            Slog.d(TAG, "napNoUpdateLocked: eventTime=" + eventTime);
1028        }
1029
1030        if (eventTime < mLastWakeTime || mWakefulness != WAKEFULNESS_AWAKE
1031                || !mBootCompleted || !mSystemReady) {
1032            return false;
1033        }
1034
1035        Slog.i(TAG, "Nap time...");
1036
1037        mDirty |= DIRTY_WAKEFULNESS;
1038        mWakefulness = WAKEFULNESS_DREAMING;
1039        mSandmanSummoned = true;
1040        setInteractiveStateLocked(true, 0);
1041        return true;
1042    }
1043
1044    // Done dozing, drop everything and go to sleep.
1045    private boolean reallyGoToSleepNoUpdateLocked(long eventTime) {
1046        if (DEBUG_SPEW) {
1047            Slog.d(TAG, "reallyGoToSleepNoUpdateLocked: eventTime=" + eventTime);
1048        }
1049
1050        if (eventTime < mLastWakeTime || mWakefulness == WAKEFULNESS_ASLEEP
1051                || !mBootCompleted || !mSystemReady) {
1052            return false;
1053        }
1054
1055        Slog.i(TAG, "Sleeping...");
1056
1057        mDirty |= DIRTY_WAKEFULNESS;
1058        mWakefulness = WAKEFULNESS_ASLEEP;
1059        setInteractiveStateLocked(false, PowerManager.GO_TO_SLEEP_REASON_TIMEOUT);
1060        return true;
1061    }
1062
1063    private void setInteractiveStateLocked(boolean interactive, int reason) {
1064        if (mInteractive != interactive) {
1065            finishInteractiveStateChangeLocked();
1066
1067            mInteractive = interactive;
1068            mInteractiveChanging = true;
1069            mNotifier.onInteractiveStateChangeStarted(interactive, reason);
1070        }
1071    }
1072
1073    private void finishInteractiveStateChangeLocked() {
1074        if (mInteractiveChanging) {
1075            mNotifier.onInteractiveStateChangeFinished(mInteractive);
1076            mInteractiveChanging = false;
1077        }
1078    }
1079
1080    /**
1081     * Updates the global power state based on dirty bits recorded in mDirty.
1082     *
1083     * This is the main function that performs power state transitions.
1084     * We centralize them here so that we can recompute the power state completely
1085     * each time something important changes, and ensure that we do it the same
1086     * way each time.  The point is to gather all of the transition logic here.
1087     */
1088    private void updatePowerStateLocked() {
1089        if (!mSystemReady || mDirty == 0) {
1090            return;
1091        }
1092        if (!Thread.holdsLock(mLock)) {
1093            Slog.wtf(TAG, "Power manager lock was not held when calling updatePowerStateLocked");
1094        }
1095
1096        // Phase 0: Basic state updates.
1097        updateIsPoweredLocked(mDirty);
1098        updateStayOnLocked(mDirty);
1099
1100        // Phase 1: Update wakefulness.
1101        // Loop because the wake lock and user activity computations are influenced
1102        // by changes in wakefulness.
1103        final long now = SystemClock.uptimeMillis();
1104        int dirtyPhase2 = 0;
1105        for (;;) {
1106            int dirtyPhase1 = mDirty;
1107            dirtyPhase2 |= dirtyPhase1;
1108            mDirty = 0;
1109
1110            updateWakeLockSummaryLocked(dirtyPhase1);
1111            updateUserActivitySummaryLocked(now, dirtyPhase1);
1112            if (!updateWakefulnessLocked(dirtyPhase1)) {
1113                break;
1114            }
1115        }
1116
1117        // Phase 2: Update dreams and display power state.
1118        updateDreamLocked(dirtyPhase2);
1119        updateDisplayPowerStateLocked(dirtyPhase2);
1120
1121        // Phase 3: Send notifications, if needed.
1122        if (mDisplayReady) {
1123            finishInteractiveStateChangeLocked();
1124        }
1125
1126        // Phase 4: Update suspend blocker.
1127        // Because we might release the last suspend blocker here, we need to make sure
1128        // we finished everything else first!
1129        updateSuspendBlockerLocked();
1130    }
1131
1132    /**
1133     * Updates the value of mIsPowered.
1134     * Sets DIRTY_IS_POWERED if a change occurred.
1135     */
1136    private void updateIsPoweredLocked(int dirty) {
1137        if ((dirty & DIRTY_BATTERY_STATE) != 0) {
1138            final boolean wasPowered = mIsPowered;
1139            final int oldPlugType = mPlugType;
1140            mIsPowered = mBatteryService.isPowered(BatteryManager.BATTERY_PLUGGED_ANY);
1141            mPlugType = mBatteryService.getPlugType();
1142            mBatteryLevel = mBatteryService.getBatteryLevel();
1143
1144            if (DEBUG_SPEW) {
1145                Slog.d(TAG, "updateIsPoweredLocked: wasPowered=" + wasPowered
1146                        + ", mIsPowered=" + mIsPowered
1147                        + ", oldPlugType=" + oldPlugType
1148                        + ", mPlugType=" + mPlugType
1149                        + ", mBatteryLevel=" + mBatteryLevel);
1150            }
1151
1152            if (wasPowered != mIsPowered || oldPlugType != mPlugType) {
1153                mDirty |= DIRTY_IS_POWERED;
1154
1155                // Update wireless dock detection state.
1156                final boolean dockedOnWirelessCharger = mWirelessChargerDetector.update(
1157                        mIsPowered, mPlugType, mBatteryLevel);
1158
1159                // Treat plugging and unplugging the devices as a user activity.
1160                // Users find it disconcerting when they plug or unplug the device
1161                // and it shuts off right away.
1162                // Some devices also wake the device when plugged or unplugged because
1163                // they don't have a charging LED.
1164                final long now = SystemClock.uptimeMillis();
1165                if (shouldWakeUpWhenPluggedOrUnpluggedLocked(wasPowered, oldPlugType,
1166                        dockedOnWirelessCharger)) {
1167                    wakeUpNoUpdateLocked(now);
1168                }
1169                userActivityNoUpdateLocked(
1170                        now, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
1171
1172                // Tell the notifier whether wireless charging has started so that
1173                // it can provide feedback to the user.
1174                if (dockedOnWirelessCharger) {
1175                    mNotifier.onWirelessChargingStarted();
1176                }
1177            }
1178        }
1179    }
1180
1181    private boolean shouldWakeUpWhenPluggedOrUnpluggedLocked(
1182            boolean wasPowered, int oldPlugType, boolean dockedOnWirelessCharger) {
1183        // Don't wake when powered unless configured to do so.
1184        if (!mWakeUpWhenPluggedOrUnpluggedConfig) {
1185            return false;
1186        }
1187
1188        // Don't wake when undocked from wireless charger.
1189        // See WirelessChargerDetector for justification.
1190        if (wasPowered && !mIsPowered
1191                && oldPlugType == BatteryManager.BATTERY_PLUGGED_WIRELESS) {
1192            return false;
1193        }
1194
1195        // Don't wake when docked on wireless charger unless we are certain of it.
1196        // See WirelessChargerDetector for justification.
1197        if (!wasPowered && mIsPowered
1198                && mPlugType == BatteryManager.BATTERY_PLUGGED_WIRELESS
1199                && !dockedOnWirelessCharger) {
1200            return false;
1201        }
1202
1203        // If already dreaming and becoming powered, then don't wake.
1204        if (mIsPowered && mWakefulness == WAKEFULNESS_DREAMING) {
1205            return false;
1206        }
1207
1208        // Otherwise wake up!
1209        return true;
1210    }
1211
1212    /**
1213     * Updates the value of mStayOn.
1214     * Sets DIRTY_STAY_ON if a change occurred.
1215     */
1216    private void updateStayOnLocked(int dirty) {
1217        if ((dirty & (DIRTY_BATTERY_STATE | DIRTY_SETTINGS)) != 0) {
1218            final boolean wasStayOn = mStayOn;
1219            if (mStayOnWhilePluggedInSetting != 0
1220                    && !isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked()) {
1221                mStayOn = mBatteryService.isPowered(mStayOnWhilePluggedInSetting);
1222            } else {
1223                mStayOn = false;
1224            }
1225
1226            if (mStayOn != wasStayOn) {
1227                mDirty |= DIRTY_STAY_ON;
1228            }
1229        }
1230    }
1231
1232    /**
1233     * Updates the value of mWakeLockSummary to summarize the state of all active wake locks.
1234     * Note that most wake-locks are ignored when the system is asleep.
1235     *
1236     * This function must have no other side-effects.
1237     */
1238    @SuppressWarnings("deprecation")
1239    private void updateWakeLockSummaryLocked(int dirty) {
1240        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_WAKEFULNESS)) != 0) {
1241            mWakeLockSummary = 0;
1242
1243            final int numWakeLocks = mWakeLocks.size();
1244            for (int i = 0; i < numWakeLocks; i++) {
1245                final WakeLock wakeLock = mWakeLocks.get(i);
1246                switch (wakeLock.mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
1247                    case PowerManager.PARTIAL_WAKE_LOCK:
1248                        mWakeLockSummary |= WAKE_LOCK_CPU;
1249                        break;
1250                    case PowerManager.FULL_WAKE_LOCK:
1251                        mWakeLockSummary |= WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_BUTTON_BRIGHT;
1252                        break;
1253                    case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
1254                        mWakeLockSummary |= WAKE_LOCK_SCREEN_BRIGHT;
1255                        break;
1256                    case PowerManager.SCREEN_DIM_WAKE_LOCK:
1257                        mWakeLockSummary |= WAKE_LOCK_SCREEN_DIM;
1258                        break;
1259                    case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
1260                        mWakeLockSummary |= WAKE_LOCK_PROXIMITY_SCREEN_OFF;
1261                        break;
1262                    case PowerManager.DOZE_WAKE_LOCK:
1263                        mWakeLockSummary |= WAKE_LOCK_DOZE;
1264                        break;
1265                }
1266            }
1267
1268            // Cancel wake locks that make no sense based on the current state.
1269            if (mWakefulness != WAKEFULNESS_DOZING) {
1270                mWakeLockSummary &= ~WAKE_LOCK_DOZE;
1271            }
1272            if (mWakefulness == WAKEFULNESS_ASLEEP
1273                    || (mWakeLockSummary & WAKE_LOCK_DOZE) != 0) {
1274                mWakeLockSummary &= ~(WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_SCREEN_DIM
1275                        | WAKE_LOCK_BUTTON_BRIGHT);
1276                if (mWakefulness == WAKEFULNESS_ASLEEP) {
1277                    mWakeLockSummary &= ~WAKE_LOCK_PROXIMITY_SCREEN_OFF;
1278                }
1279            }
1280
1281            // Infer implied wake locks where necessary based on the current state.
1282            if ((mWakeLockSummary & (WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_SCREEN_DIM)) != 0) {
1283                if (mWakefulness == WAKEFULNESS_AWAKE) {
1284                    mWakeLockSummary |= WAKE_LOCK_CPU | WAKE_LOCK_STAY_AWAKE;
1285                } else if (mWakefulness == WAKEFULNESS_DREAMING) {
1286                    mWakeLockSummary |= WAKE_LOCK_CPU;
1287                }
1288            }
1289
1290            if (DEBUG_SPEW) {
1291                Slog.d(TAG, "updateWakeLockSummaryLocked: mWakefulness="
1292                        + wakefulnessToString(mWakefulness)
1293                        + ", mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary));
1294            }
1295        }
1296    }
1297
1298    /**
1299     * Updates the value of mUserActivitySummary to summarize the user requested
1300     * state of the system such as whether the screen should be bright or dim.
1301     * Note that user activity is ignored when the system is asleep.
1302     *
1303     * This function must have no other side-effects.
1304     */
1305    private void updateUserActivitySummaryLocked(long now, int dirty) {
1306        // Update the status of the user activity timeout timer.
1307        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_USER_ACTIVITY
1308                | DIRTY_WAKEFULNESS | DIRTY_SETTINGS)) != 0) {
1309            mHandler.removeMessages(MSG_USER_ACTIVITY_TIMEOUT);
1310
1311            long nextTimeout = 0;
1312            if (mWakefulness == WAKEFULNESS_AWAKE
1313                    || mWakefulness == WAKEFULNESS_DREAMING
1314                    || mWakefulness == WAKEFULNESS_DOZING) {
1315                final int screenOffTimeout = getScreenOffTimeoutLocked();
1316                final int screenDimDuration = getScreenDimDurationLocked(screenOffTimeout);
1317
1318                mUserActivitySummary = 0;
1319                if (mLastUserActivityTime >= mLastWakeTime) {
1320                    nextTimeout = mLastUserActivityTime
1321                            + screenOffTimeout - screenDimDuration;
1322                    if (now < nextTimeout) {
1323                        mUserActivitySummary |= USER_ACTIVITY_SCREEN_BRIGHT;
1324                    } else {
1325                        nextTimeout = mLastUserActivityTime + screenOffTimeout;
1326                        if (now < nextTimeout) {
1327                            mUserActivitySummary |= USER_ACTIVITY_SCREEN_DIM;
1328                        }
1329                    }
1330                }
1331                if (mUserActivitySummary == 0
1332                        && mLastUserActivityTimeNoChangeLights >= mLastWakeTime) {
1333                    nextTimeout = mLastUserActivityTimeNoChangeLights + screenOffTimeout;
1334                    if (now < nextTimeout
1335                            && mDisplayPowerRequest.wantScreenOnNormal()) {
1336                        mUserActivitySummary = mDisplayPowerRequest.screenState
1337                                == DisplayPowerRequest.SCREEN_STATE_BRIGHT ?
1338                                USER_ACTIVITY_SCREEN_BRIGHT : USER_ACTIVITY_SCREEN_DIM;
1339                    }
1340                }
1341                if (mUserActivitySummary != 0) {
1342                    Message msg = mHandler.obtainMessage(MSG_USER_ACTIVITY_TIMEOUT);
1343                    msg.setAsynchronous(true);
1344                    mHandler.sendMessageAtTime(msg, nextTimeout);
1345                }
1346            } else {
1347                mUserActivitySummary = 0;
1348            }
1349
1350            if (DEBUG_SPEW) {
1351                Slog.d(TAG, "updateUserActivitySummaryLocked: mWakefulness="
1352                        + wakefulnessToString(mWakefulness)
1353                        + ", mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary)
1354                        + ", nextTimeout=" + TimeUtils.formatUptime(nextTimeout));
1355            }
1356        }
1357    }
1358
1359    /**
1360     * Called when a user activity timeout has occurred.
1361     * Simply indicates that something about user activity has changed so that the new
1362     * state can be recomputed when the power state is updated.
1363     *
1364     * This function must have no other side-effects besides setting the dirty
1365     * bit and calling update power state.  Wakefulness transitions are handled elsewhere.
1366     */
1367    private void handleUserActivityTimeout() { // runs on handler thread
1368        synchronized (mLock) {
1369            if (DEBUG_SPEW) {
1370                Slog.d(TAG, "handleUserActivityTimeout");
1371            }
1372
1373            mDirty |= DIRTY_USER_ACTIVITY;
1374            updatePowerStateLocked();
1375        }
1376    }
1377
1378    private int getScreenOffTimeoutLocked() {
1379        int timeout = mScreenOffTimeoutSetting;
1380        if (isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked()) {
1381            timeout = Math.min(timeout, mMaximumScreenOffTimeoutFromDeviceAdmin);
1382        }
1383        if (mUserActivityTimeoutOverrideFromWindowManager >= 0) {
1384            timeout = (int)Math.min(timeout, mUserActivityTimeoutOverrideFromWindowManager);
1385        }
1386        return Math.max(timeout, mMinimumScreenOffTimeoutConfig);
1387    }
1388
1389    private int getScreenDimDurationLocked(int screenOffTimeout) {
1390        return Math.min(mMaximumScreenDimDurationConfig,
1391                (int)(screenOffTimeout * mMaximumScreenDimRatioConfig));
1392    }
1393
1394    /**
1395     * Updates the wakefulness of the device.
1396     *
1397     * This is the function that decides whether the device should start dreaming
1398     * based on the current wake locks and user activity state.  It may modify mDirty
1399     * if the wakefulness changes.
1400     *
1401     * Returns true if the wakefulness changed and we need to restart power state calculation.
1402     */
1403    private boolean updateWakefulnessLocked(int dirty) {
1404        boolean changed = false;
1405        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_USER_ACTIVITY | DIRTY_BOOT_COMPLETED
1406                | DIRTY_WAKEFULNESS | DIRTY_STAY_ON | DIRTY_PROXIMITY_POSITIVE
1407                | DIRTY_DOCK_STATE)) != 0) {
1408            if (mWakefulness == WAKEFULNESS_AWAKE && isItBedTimeYetLocked()) {
1409                if (DEBUG_SPEW) {
1410                    Slog.d(TAG, "updateWakefulnessLocked: Bed time...");
1411                }
1412                final long time = SystemClock.uptimeMillis();
1413                if (shouldNapAtBedTimeLocked()) {
1414                    changed = napNoUpdateLocked(time);
1415                } else {
1416                    changed = goToSleepNoUpdateLocked(time,
1417                            PowerManager.GO_TO_SLEEP_REASON_TIMEOUT, 0);
1418                }
1419            }
1420        }
1421        return changed;
1422    }
1423
1424    /**
1425     * Returns true if the device should automatically nap and start dreaming when the user
1426     * activity timeout has expired and it's bedtime.
1427     */
1428    private boolean shouldNapAtBedTimeLocked() {
1429        return mDreamsActivateOnSleepSetting
1430                || (mDreamsActivateOnDockSetting
1431                        && mDockState != Intent.EXTRA_DOCK_STATE_UNDOCKED);
1432    }
1433
1434    /**
1435     * Returns true if the device should go to sleep now.
1436     * Also used when exiting a dream to determine whether we should go back
1437     * to being fully awake or else go to sleep for good.
1438     */
1439    private boolean isItBedTimeYetLocked() {
1440        return mBootCompleted && !isBeingKeptAwakeLocked();
1441    }
1442
1443    /**
1444     * Returns true if the device is being kept awake by a wake lock, user activity
1445     * or the stay on while powered setting.  We also keep the phone awake when
1446     * the proximity sensor returns a positive result so that the device does not
1447     * lock while in a phone call.  This function only controls whether the device
1448     * will go to sleep or dream which is independent of whether it will be allowed
1449     * to suspend.
1450     */
1451    private boolean isBeingKeptAwakeLocked() {
1452        return mStayOn
1453                || mProximityPositive
1454                || (mWakeLockSummary & WAKE_LOCK_STAY_AWAKE) != 0
1455                || (mUserActivitySummary & (USER_ACTIVITY_SCREEN_BRIGHT
1456                        | USER_ACTIVITY_SCREEN_DIM)) != 0;
1457    }
1458
1459    /**
1460     * Determines whether to post a message to the sandman to update the dream state.
1461     */
1462    private void updateDreamLocked(int dirty) {
1463        if ((dirty & (DIRTY_WAKEFULNESS
1464                | DIRTY_USER_ACTIVITY
1465                | DIRTY_WAKE_LOCKS
1466                | DIRTY_BOOT_COMPLETED
1467                | DIRTY_SETTINGS
1468                | DIRTY_IS_POWERED
1469                | DIRTY_STAY_ON
1470                | DIRTY_PROXIMITY_POSITIVE
1471                | DIRTY_BATTERY_STATE)) != 0) {
1472            scheduleSandmanLocked();
1473        }
1474    }
1475
1476    private void scheduleSandmanLocked() {
1477        if (!mSandmanScheduled) {
1478            mSandmanScheduled = true;
1479            Message msg = mHandler.obtainMessage(MSG_SANDMAN);
1480            msg.setAsynchronous(true);
1481            mHandler.sendMessage(msg);
1482        }
1483    }
1484
1485    /**
1486     * Called when the device enters or exits a dreaming or dozing state.
1487     *
1488     * We do this asynchronously because we must call out of the power manager to start
1489     * the dream and we don't want to hold our lock while doing so.  There is a risk that
1490     * the device will wake or go to sleep in the meantime so we have to handle that case.
1491     */
1492    private void handleSandman() { // runs on handler thread
1493        // Handle preconditions.
1494        final boolean startDreaming;
1495        final int wakefulness;
1496        synchronized (mLock) {
1497            mSandmanScheduled = false;
1498            wakefulness = mWakefulness;
1499            if (mSandmanSummoned) {
1500                startDreaming = ((wakefulness == WAKEFULNESS_DREAMING && canDreamLocked())
1501                        || wakefulness == WAKEFULNESS_DOZING);
1502                mSandmanSummoned = false;
1503            } else {
1504                startDreaming = false;
1505            }
1506        }
1507
1508        // Start dreaming if needed.
1509        // We only control the dream on the handler thread, so we don't need to worry about
1510        // concurrent attempts to start or stop the dream.
1511        final boolean isDreaming;
1512        if (mDreamManager != null) {
1513            // Restart the dream whenever the sandman is summoned.
1514            if (startDreaming) {
1515                mDreamManager.stopDream();
1516                mDreamManager.startDream(wakefulness == WAKEFULNESS_DOZING);
1517            }
1518            isDreaming = mDreamManager.isDreaming();
1519        } else {
1520            isDreaming = false;
1521        }
1522
1523        // Update dream state.
1524        synchronized (mLock) {
1525            // Remember the initial battery level when the dream started.
1526            if (startDreaming && isDreaming) {
1527                mBatteryLevelWhenDreamStarted = mBatteryLevel;
1528                if (wakefulness == WAKEFULNESS_DOZING) {
1529                    Slog.i(TAG, "Dozing...");
1530                } else {
1531                    Slog.i(TAG, "Dreaming...");
1532                }
1533            }
1534
1535            // If preconditions changed, wait for the next iteration to determine
1536            // whether the dream should continue (or be restarted).
1537            if (mSandmanSummoned || mWakefulness != wakefulness) {
1538                return; // wait for next cycle
1539            }
1540
1541            // Determine whether the dream should continue.
1542            if (wakefulness == WAKEFULNESS_DREAMING) {
1543                if (isDreaming && canDreamLocked()) {
1544                    if (mDreamsBatteryLevelDrainCutoffConfig >= 0
1545                            && mBatteryLevel < mBatteryLevelWhenDreamStarted
1546                                    - mDreamsBatteryLevelDrainCutoffConfig
1547                            && !isBeingKeptAwakeLocked()) {
1548                        // If the user activity timeout expired and the battery appears
1549                        // to be draining faster than it is charging then stop dreaming
1550                        // and go to sleep.
1551                        Slog.i(TAG, "Stopping dream because the battery appears to "
1552                                + "be draining faster than it is charging.  "
1553                                + "Battery level when dream started: "
1554                                + mBatteryLevelWhenDreamStarted + "%.  "
1555                                + "Battery level now: " + mBatteryLevel + "%.");
1556                    } else {
1557                        return; // continue dreaming
1558                    }
1559                }
1560
1561                // Dream has ended or will be stopped.  Update the power state.
1562                if (isItBedTimeYetLocked()) {
1563                    goToSleepNoUpdateLocked(SystemClock.uptimeMillis(),
1564                            PowerManager.GO_TO_SLEEP_REASON_TIMEOUT, 0);
1565                    updatePowerStateLocked();
1566                } else {
1567                    wakeUpNoUpdateLocked(SystemClock.uptimeMillis());
1568                    updatePowerStateLocked();
1569                }
1570            } else if (wakefulness == WAKEFULNESS_DOZING) {
1571                if (isDreaming) {
1572                    return; // continue dozing
1573                }
1574
1575                // Doze has ended or will be stopped.  Update the power state.
1576                reallyGoToSleepNoUpdateLocked(SystemClock.uptimeMillis());
1577                updatePowerStateLocked();
1578            }
1579        }
1580
1581        // Stop dream.
1582        if (isDreaming) {
1583            mDreamManager.stopDream();
1584        }
1585    }
1586
1587    /**
1588     * Returns true if the device is allowed to dream in its current state.
1589     * This function is not called when dozing.
1590     */
1591    private boolean canDreamLocked() {
1592        if (mWakefulness != WAKEFULNESS_DREAMING
1593                || !mDreamsSupportedConfig
1594                || !mDreamsEnabledSetting
1595                || !mDisplayPowerRequest.wantScreenOnNormal()
1596                || !mBootCompleted) {
1597            return false;
1598        }
1599        if (!isBeingKeptAwakeLocked()) {
1600            if (!mIsPowered && !mDreamsEnabledOnBatteryConfig) {
1601                return false;
1602            }
1603            if (!mIsPowered
1604                    && mDreamsBatteryLevelMinimumWhenNotPoweredConfig >= 0
1605                    && mBatteryLevel < mDreamsBatteryLevelMinimumWhenNotPoweredConfig) {
1606                return false;
1607            }
1608            if (mIsPowered
1609                    && mDreamsBatteryLevelMinimumWhenPoweredConfig >= 0
1610                    && mBatteryLevel < mDreamsBatteryLevelMinimumWhenPoweredConfig) {
1611                return false;
1612            }
1613        }
1614        return true;
1615    }
1616
1617    private void handleScreenOnBlockerReleased() {
1618        synchronized (mLock) {
1619            mDirty |= DIRTY_SCREEN_ON_BLOCKER_RELEASED;
1620            updatePowerStateLocked();
1621        }
1622    }
1623
1624    /**
1625     * Updates the display power state asynchronously.
1626     * When the update is finished, mDisplayReady will be set to true.  The display
1627     * controller posts a message to tell us when the actual display power state
1628     * has been updated so we come back here to double-check and finish up.
1629     *
1630     * This function recalculates the display power state each time.
1631     */
1632    private void updateDisplayPowerStateLocked(int dirty) {
1633        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_USER_ACTIVITY | DIRTY_WAKEFULNESS
1634                | DIRTY_ACTUAL_DISPLAY_POWER_STATE_UPDATED | DIRTY_BOOT_COMPLETED
1635                | DIRTY_SETTINGS | DIRTY_SCREEN_ON_BLOCKER_RELEASED)) != 0) {
1636            final int newScreenState = getDesiredScreenPowerStateLocked();
1637            mDisplayPowerRequest.screenState = newScreenState;
1638
1639            int screenBrightness = mScreenBrightnessSettingDefault;
1640            float screenAutoBrightnessAdjustment = 0.0f;
1641            boolean autoBrightness = (mScreenBrightnessModeSetting ==
1642                    Settings.System.SCREEN_BRIGHTNESS_MODE_AUTOMATIC);
1643            if (isValidBrightness(mScreenBrightnessOverrideFromWindowManager)) {
1644                screenBrightness = mScreenBrightnessOverrideFromWindowManager;
1645                autoBrightness = false;
1646            } else if (isValidBrightness(mTemporaryScreenBrightnessSettingOverride)) {
1647                screenBrightness = mTemporaryScreenBrightnessSettingOverride;
1648            } else if (isValidBrightness(mScreenBrightnessSetting)) {
1649                screenBrightness = mScreenBrightnessSetting;
1650            }
1651            if (autoBrightness) {
1652                screenBrightness = mScreenBrightnessSettingDefault;
1653                if (isValidAutoBrightnessAdjustment(
1654                        mTemporaryScreenAutoBrightnessAdjustmentSettingOverride)) {
1655                    screenAutoBrightnessAdjustment =
1656                            mTemporaryScreenAutoBrightnessAdjustmentSettingOverride;
1657                } else if (isValidAutoBrightnessAdjustment(
1658                        mScreenAutoBrightnessAdjustmentSetting)) {
1659                    screenAutoBrightnessAdjustment = mScreenAutoBrightnessAdjustmentSetting;
1660                }
1661            }
1662            screenBrightness = Math.max(Math.min(screenBrightness,
1663                    mScreenBrightnessSettingMaximum), mScreenBrightnessSettingMinimum);
1664            screenAutoBrightnessAdjustment = Math.max(Math.min(
1665                    screenAutoBrightnessAdjustment, 1.0f), -1.0f);
1666            mDisplayPowerRequest.screenBrightness = screenBrightness;
1667            mDisplayPowerRequest.screenAutoBrightnessAdjustment =
1668                    screenAutoBrightnessAdjustment;
1669            mDisplayPowerRequest.useAutoBrightness = autoBrightness;
1670
1671            mDisplayPowerRequest.useProximitySensor = shouldUseProximitySensorLocked();
1672
1673            mDisplayPowerRequest.blockScreenOn = mScreenOnBlocker.isHeld();
1674
1675            mDisplayPowerRequest.lowPowerMode = mLowPowerModeEnabled;
1676
1677            mDisplayReady = mDisplayManagerInternal.requestPowerState(mDisplayPowerRequest,
1678                    mRequestWaitForNegativeProximity);
1679            mRequestWaitForNegativeProximity = false;
1680
1681            if (DEBUG_SPEW) {
1682                Slog.d(TAG, "updateScreenStateLocked: mDisplayReady=" + mDisplayReady
1683                        + ", newScreenState=" + newScreenState
1684                        + ", mWakefulness=" + mWakefulness
1685                        + ", mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary)
1686                        + ", mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary)
1687                        + ", mBootCompleted=" + mBootCompleted);
1688            }
1689        }
1690    }
1691
1692    private static boolean isValidBrightness(int value) {
1693        return value >= 0 && value <= 255;
1694    }
1695
1696    private static boolean isValidAutoBrightnessAdjustment(float value) {
1697        // Handles NaN by always returning false.
1698        return value >= -1.0f && value <= 1.0f;
1699    }
1700
1701    private int getDesiredScreenPowerStateLocked() {
1702        if (mWakefulness == WAKEFULNESS_ASLEEP) {
1703            return DisplayPowerRequest.SCREEN_STATE_OFF;
1704        }
1705
1706        if ((mWakeLockSummary & WAKE_LOCK_DOZE) != 0) {
1707            return DisplayPowerRequest.SCREEN_STATE_DOZE;
1708        }
1709
1710        if ((mWakeLockSummary & WAKE_LOCK_SCREEN_BRIGHT) != 0
1711                || (mUserActivitySummary & USER_ACTIVITY_SCREEN_BRIGHT) != 0
1712                || !mBootCompleted) {
1713            return DisplayPowerRequest.SCREEN_STATE_BRIGHT;
1714        }
1715
1716        return DisplayPowerRequest.SCREEN_STATE_DIM;
1717    }
1718
1719    private final DisplayManagerInternal.DisplayPowerCallbacks mDisplayPowerCallbacks =
1720            new DisplayManagerInternal.DisplayPowerCallbacks() {
1721        private int mDisplayState = Display.STATE_UNKNOWN;
1722
1723        @Override
1724        public void onStateChanged() {
1725            synchronized (mLock) {
1726                mDirty |= DIRTY_ACTUAL_DISPLAY_POWER_STATE_UPDATED;
1727                updatePowerStateLocked();
1728            }
1729        }
1730
1731        @Override
1732        public void onProximityPositive() {
1733            synchronized (mLock) {
1734                mProximityPositive = true;
1735                mDirty |= DIRTY_PROXIMITY_POSITIVE;
1736                updatePowerStateLocked();
1737            }
1738        }
1739
1740        @Override
1741        public void onProximityNegative() {
1742            synchronized (mLock) {
1743                mProximityPositive = false;
1744                mDirty |= DIRTY_PROXIMITY_POSITIVE;
1745                userActivityNoUpdateLocked(SystemClock.uptimeMillis(),
1746                        PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
1747                updatePowerStateLocked();
1748            }
1749        }
1750
1751        @Override
1752        public void onDisplayStateChange(int state) {
1753            // This method is only needed to support legacy display blanking behavior
1754            // where the display's power state is coupled to suspend or to the power HAL.
1755            // The order of operations matters here.
1756            synchronized (mLock) {
1757                if (mDisplayState != state) {
1758                    mDisplayState = state;
1759                    if (state == Display.STATE_OFF) {
1760                        if (!mDecoupleHalInteractiveModeFromDisplayConfig) {
1761                            setHalInteractiveModeLocked(false);
1762                        }
1763                        if (!mDecoupleHalAutoSuspendModeFromDisplayConfig) {
1764                            setHalAutoSuspendModeLocked(true);
1765                        }
1766                    } else {
1767                        if (!mDecoupleHalAutoSuspendModeFromDisplayConfig) {
1768                            setHalAutoSuspendModeLocked(false);
1769                        }
1770                        if (!mDecoupleHalInteractiveModeFromDisplayConfig) {
1771                            setHalInteractiveModeLocked(true);
1772                        }
1773                    }
1774                }
1775            }
1776        }
1777
1778        @Override
1779        public void acquireSuspendBlocker() {
1780            mDisplaySuspendBlocker.acquire();
1781        }
1782
1783        @Override
1784        public void releaseSuspendBlocker() {
1785            mDisplaySuspendBlocker.release();
1786        }
1787
1788        @Override
1789        public String toString() {
1790            synchronized (this) {
1791                return "state=" + Display.stateToString(mDisplayState);
1792            }
1793        }
1794    };
1795
1796    private boolean shouldUseProximitySensorLocked() {
1797        return (mWakeLockSummary & WAKE_LOCK_PROXIMITY_SCREEN_OFF) != 0;
1798    }
1799
1800    /**
1801     * Updates the suspend blocker that keeps the CPU alive.
1802     *
1803     * This function must have no other side-effects.
1804     */
1805    private void updateSuspendBlockerLocked() {
1806        final boolean needWakeLockSuspendBlocker = ((mWakeLockSummary & WAKE_LOCK_CPU) != 0);
1807        final boolean needDisplaySuspendBlocker = needDisplaySuspendBlockerLocked();
1808        final boolean autoSuspend = !needDisplaySuspendBlocker;
1809
1810        // Disable auto-suspend if needed.
1811        if (!autoSuspend) {
1812            if (mDecoupleHalAutoSuspendModeFromDisplayConfig) {
1813                setHalAutoSuspendModeLocked(false);
1814            }
1815            if (mDecoupleHalInteractiveModeFromDisplayConfig) {
1816                setHalInteractiveModeLocked(true);
1817            }
1818        }
1819
1820        // First acquire suspend blockers if needed.
1821        if (needWakeLockSuspendBlocker && !mHoldingWakeLockSuspendBlocker) {
1822            mWakeLockSuspendBlocker.acquire();
1823            mHoldingWakeLockSuspendBlocker = true;
1824        }
1825        if (needDisplaySuspendBlocker && !mHoldingDisplaySuspendBlocker) {
1826            mDisplaySuspendBlocker.acquire();
1827            mHoldingDisplaySuspendBlocker = true;
1828        }
1829
1830        // Then release suspend blockers if needed.
1831        if (!needWakeLockSuspendBlocker && mHoldingWakeLockSuspendBlocker) {
1832            mWakeLockSuspendBlocker.release();
1833            mHoldingWakeLockSuspendBlocker = false;
1834        }
1835        if (!needDisplaySuspendBlocker && mHoldingDisplaySuspendBlocker) {
1836            mDisplaySuspendBlocker.release();
1837            mHoldingDisplaySuspendBlocker = false;
1838        }
1839
1840        // Enable auto-suspend if needed.
1841        if (autoSuspend) {
1842            if (mDecoupleHalInteractiveModeFromDisplayConfig) {
1843                setHalInteractiveModeLocked(false);
1844            }
1845            if (mDecoupleHalAutoSuspendModeFromDisplayConfig) {
1846                setHalAutoSuspendModeLocked(true);
1847            }
1848        }
1849    }
1850
1851    /**
1852     * Return true if we must keep a suspend blocker active on behalf of the display.
1853     * We do so if the screen is on or is in transition between states.
1854     */
1855    private boolean needDisplaySuspendBlockerLocked() {
1856        if (!mDisplayReady) {
1857            return true;
1858        }
1859        if (mDisplayPowerRequest.wantScreenOnNormal()) {
1860            // If we asked for the screen to be on but it is off due to the proximity
1861            // sensor then we may suspend but only if the configuration allows it.
1862            // On some hardware it may not be safe to suspend because the proximity
1863            // sensor may not be correctly configured as a wake-up source.
1864            if (!mDisplayPowerRequest.useProximitySensor || !mProximityPositive
1865                    || !mSuspendWhenScreenOffDueToProximityConfig) {
1866                return true;
1867            }
1868        }
1869        // Let the system suspend if the screen is off or dozing.
1870        return false;
1871    }
1872
1873    private void setHalAutoSuspendModeLocked(boolean enable) {
1874        if (enable != mHalAutoSuspendModeEnabled) {
1875            if (DEBUG) {
1876                Slog.d(TAG, "Setting HAL auto-suspend mode to " + enable);
1877            }
1878            mHalAutoSuspendModeEnabled = enable;
1879            nativeSetAutoSuspend(enable);
1880        }
1881    }
1882
1883    private void setHalInteractiveModeLocked(boolean enable) {
1884        if (enable != mHalInteractiveModeEnabled) {
1885            if (DEBUG) {
1886                Slog.d(TAG, "Setting HAL interactive mode to " + enable);
1887            }
1888            mHalInteractiveModeEnabled = enable;
1889            nativeSetInteractive(enable);
1890        }
1891    }
1892
1893    private boolean isInteractiveInternal() {
1894        synchronized (mLock) {
1895            return mInteractive;
1896        }
1897    }
1898
1899    private void handleBatteryStateChangedLocked() {
1900        mDirty |= DIRTY_BATTERY_STATE;
1901        updatePowerStateLocked();
1902    }
1903
1904    private void startWatchingForBootAnimationFinished() {
1905        mHandler.sendEmptyMessage(MSG_CHECK_IF_BOOT_ANIMATION_FINISHED);
1906    }
1907
1908    private void checkIfBootAnimationFinished() {
1909        if (DEBUG) {
1910            Slog.d(TAG, "Check if boot animation finished...");
1911        }
1912
1913        if (SystemService.isRunning(BOOT_ANIMATION_SERVICE)) {
1914            mHandler.sendEmptyMessageDelayed(MSG_CHECK_IF_BOOT_ANIMATION_FINISHED,
1915                    BOOT_ANIMATION_POLL_INTERVAL);
1916            return;
1917        }
1918
1919        synchronized (mLock) {
1920            if (!mBootCompleted) {
1921                Slog.i(TAG, "Boot animation finished.");
1922                handleBootCompletedLocked();
1923            }
1924        }
1925    }
1926
1927    private void handleBootCompletedLocked() {
1928        final long now = SystemClock.uptimeMillis();
1929        mBootCompleted = true;
1930        mDirty |= DIRTY_BOOT_COMPLETED;
1931        userActivityNoUpdateLocked(
1932                now, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
1933        updatePowerStateLocked();
1934    }
1935
1936    private void shutdownOrRebootInternal(final boolean shutdown, final boolean confirm,
1937            final String reason, boolean wait) {
1938        if (mHandler == null || !mSystemReady) {
1939            throw new IllegalStateException("Too early to call shutdown() or reboot()");
1940        }
1941
1942        Runnable runnable = new Runnable() {
1943            @Override
1944            public void run() {
1945                synchronized (this) {
1946                    if (shutdown) {
1947                        ShutdownThread.shutdown(mContext, confirm);
1948                    } else {
1949                        ShutdownThread.reboot(mContext, reason, confirm);
1950                    }
1951                }
1952            }
1953        };
1954
1955        // ShutdownThread must run on a looper capable of displaying the UI.
1956        Message msg = Message.obtain(mHandler, runnable);
1957        msg.setAsynchronous(true);
1958        mHandler.sendMessage(msg);
1959
1960        // PowerManager.reboot() is documented not to return so just wait for the inevitable.
1961        if (wait) {
1962            synchronized (runnable) {
1963                while (true) {
1964                    try {
1965                        runnable.wait();
1966                    } catch (InterruptedException e) {
1967                    }
1968                }
1969            }
1970        }
1971    }
1972
1973    private void crashInternal(final String message) {
1974        Thread t = new Thread("PowerManagerService.crash()") {
1975            @Override
1976            public void run() {
1977                throw new RuntimeException(message);
1978            }
1979        };
1980        try {
1981            t.start();
1982            t.join();
1983        } catch (InterruptedException e) {
1984            Log.wtf(TAG, e);
1985        }
1986    }
1987
1988    private void setStayOnSettingInternal(int val) {
1989        Settings.Global.putInt(mContext.getContentResolver(),
1990                Settings.Global.STAY_ON_WHILE_PLUGGED_IN, val);
1991    }
1992
1993    private void setMaximumScreenOffTimeoutFromDeviceAdminInternal(int timeMs) {
1994        synchronized (mLock) {
1995            mMaximumScreenOffTimeoutFromDeviceAdmin = timeMs;
1996            mDirty |= DIRTY_SETTINGS;
1997            updatePowerStateLocked();
1998        }
1999    }
2000
2001    private boolean isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked() {
2002        return mMaximumScreenOffTimeoutFromDeviceAdmin >= 0
2003                && mMaximumScreenOffTimeoutFromDeviceAdmin < Integer.MAX_VALUE;
2004    }
2005
2006    private void setAttentionLightInternal(boolean on, int color) {
2007        Light light;
2008        synchronized (mLock) {
2009            if (!mSystemReady) {
2010                return;
2011            }
2012            light = mAttentionLight;
2013        }
2014
2015        // Control light outside of lock.
2016        light.setFlashing(color, Light.LIGHT_FLASH_HARDWARE, (on ? 3 : 0), 0);
2017    }
2018
2019    private void setScreenBrightnessOverrideFromWindowManagerInternal(int brightness) {
2020        synchronized (mLock) {
2021            if (mScreenBrightnessOverrideFromWindowManager != brightness) {
2022                mScreenBrightnessOverrideFromWindowManager = brightness;
2023                mDirty |= DIRTY_SETTINGS;
2024                updatePowerStateLocked();
2025            }
2026        }
2027    }
2028
2029    private void setUserActivityTimeoutOverrideFromWindowManagerInternal(long timeoutMillis) {
2030        synchronized (mLock) {
2031            if (mUserActivityTimeoutOverrideFromWindowManager != timeoutMillis) {
2032                mUserActivityTimeoutOverrideFromWindowManager = timeoutMillis;
2033                mDirty |= DIRTY_SETTINGS;
2034                updatePowerStateLocked();
2035            }
2036        }
2037    }
2038
2039    private void setTemporaryScreenBrightnessSettingOverrideInternal(int brightness) {
2040        synchronized (mLock) {
2041            if (mTemporaryScreenBrightnessSettingOverride != brightness) {
2042                mTemporaryScreenBrightnessSettingOverride = brightness;
2043                mDirty |= DIRTY_SETTINGS;
2044                updatePowerStateLocked();
2045            }
2046        }
2047    }
2048
2049    private void setTemporaryScreenAutoBrightnessAdjustmentSettingOverrideInternal(float adj) {
2050        synchronized (mLock) {
2051            // Note: This condition handles NaN because NaN is not equal to any other
2052            // value, including itself.
2053            if (mTemporaryScreenAutoBrightnessAdjustmentSettingOverride != adj) {
2054                mTemporaryScreenAutoBrightnessAdjustmentSettingOverride = adj;
2055                mDirty |= DIRTY_SETTINGS;
2056                updatePowerStateLocked();
2057            }
2058        }
2059    }
2060
2061    private void powerHintInternal(int hintId, int data) {
2062        nativeSendPowerHint(hintId, data);
2063    }
2064
2065    /**
2066     * Low-level function turn the device off immediately, without trying
2067     * to be clean.  Most people should use {@link ShutdownThread} for a clean shutdown.
2068     */
2069    public static void lowLevelShutdown() {
2070        SystemProperties.set("sys.powerctl", "shutdown");
2071    }
2072
2073    /**
2074     * Low-level function to reboot the device. On success, this
2075     * function doesn't return. If more than 20 seconds passes from
2076     * the time a reboot is requested (120 seconds for reboot to
2077     * recovery), this method returns.
2078     *
2079     * @param reason code to pass to the kernel (e.g. "recovery"), or null.
2080     */
2081    public static void lowLevelReboot(String reason) {
2082        if (reason == null) {
2083            reason = "";
2084        }
2085        long duration;
2086        if (reason.equals(PowerManager.REBOOT_RECOVERY)) {
2087            // If we are rebooting to go into recovery, instead of
2088            // setting sys.powerctl directly we'll start the
2089            // pre-recovery service which will do some preparation for
2090            // recovery and then reboot for us.
2091            //
2092            // This preparation can take more than 20 seconds if
2093            // there's a very large update package, so lengthen the
2094            // timeout.
2095            SystemProperties.set("ctl.start", "pre-recovery");
2096            duration = 120 * 1000L;
2097        } else {
2098            SystemProperties.set("sys.powerctl", "reboot," + reason);
2099            duration = 20 * 1000L;
2100        }
2101        try {
2102            Thread.sleep(duration);
2103        } catch (InterruptedException e) {
2104            Thread.currentThread().interrupt();
2105        }
2106    }
2107
2108    @Override // Watchdog.Monitor implementation
2109    public void monitor() {
2110        // Grab and release lock for watchdog monitor to detect deadlocks.
2111        synchronized (mLock) {
2112        }
2113    }
2114
2115    private void dumpInternal(PrintWriter pw) {
2116        pw.println("POWER MANAGER (dumpsys power)\n");
2117
2118        final WirelessChargerDetector wcd;
2119        synchronized (mLock) {
2120            pw.println("Power Manager State:");
2121            pw.println("  mDirty=0x" + Integer.toHexString(mDirty));
2122            pw.println("  mWakefulness=" + wakefulnessToString(mWakefulness));
2123            pw.println("  mInteractive=" + mInteractive);
2124            pw.println("  mIsPowered=" + mIsPowered);
2125            pw.println("  mPlugType=" + mPlugType);
2126            pw.println("  mBatteryLevel=" + mBatteryLevel);
2127            pw.println("  mBatteryLevelWhenDreamStarted=" + mBatteryLevelWhenDreamStarted);
2128            pw.println("  mDockState=" + mDockState);
2129            pw.println("  mStayOn=" + mStayOn);
2130            pw.println("  mProximityPositive=" + mProximityPositive);
2131            pw.println("  mBootCompleted=" + mBootCompleted);
2132            pw.println("  mSystemReady=" + mSystemReady);
2133            pw.println("  mHalAutoSuspendModeEnabled=" + mHalAutoSuspendModeEnabled);
2134            pw.println("  mHalInteractiveModeEnabled=" + mHalInteractiveModeEnabled);
2135            pw.println("  mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary));
2136            pw.println("  mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary));
2137            pw.println("  mRequestWaitForNegativeProximity=" + mRequestWaitForNegativeProximity);
2138            pw.println("  mSandmanScheduled=" + mSandmanScheduled);
2139            pw.println("  mSandmanSummoned=" + mSandmanSummoned);
2140            pw.println("  mLastWakeTime=" + TimeUtils.formatUptime(mLastWakeTime));
2141            pw.println("  mLastSleepTime=" + TimeUtils.formatUptime(mLastSleepTime));
2142            pw.println("  mLastUserActivityTime=" + TimeUtils.formatUptime(mLastUserActivityTime));
2143            pw.println("  mLastUserActivityTimeNoChangeLights="
2144                    + TimeUtils.formatUptime(mLastUserActivityTimeNoChangeLights));
2145            pw.println("  mDisplayReady=" + mDisplayReady);
2146            pw.println("  mHoldingWakeLockSuspendBlocker=" + mHoldingWakeLockSuspendBlocker);
2147            pw.println("  mHoldingDisplaySuspendBlocker=" + mHoldingDisplaySuspendBlocker);
2148
2149            pw.println();
2150            pw.println("Settings and Configuration:");
2151            pw.println("  mDecoupleHalAutoSuspendModeFromDisplayConfig="
2152                    + mDecoupleHalAutoSuspendModeFromDisplayConfig);
2153            pw.println("  mDecoupleHalInteractiveModeFromDisplayConfig="
2154                    + mDecoupleHalInteractiveModeFromDisplayConfig);
2155            pw.println("  mWakeUpWhenPluggedOrUnpluggedConfig="
2156                    + mWakeUpWhenPluggedOrUnpluggedConfig);
2157            pw.println("  mSuspendWhenScreenOffDueToProximityConfig="
2158                    + mSuspendWhenScreenOffDueToProximityConfig);
2159            pw.println("  mDreamsSupportedConfig=" + mDreamsSupportedConfig);
2160            pw.println("  mDreamsEnabledByDefaultConfig=" + mDreamsEnabledByDefaultConfig);
2161            pw.println("  mDreamsActivatedOnSleepByDefaultConfig="
2162                    + mDreamsActivatedOnSleepByDefaultConfig);
2163            pw.println("  mDreamsActivatedOnDockByDefaultConfig="
2164                    + mDreamsActivatedOnDockByDefaultConfig);
2165            pw.println("  mDreamsEnabledOnBatteryConfig="
2166                    + mDreamsEnabledOnBatteryConfig);
2167            pw.println("  mDreamsBatteryLevelMinimumWhenPoweredConfig="
2168                    + mDreamsBatteryLevelMinimumWhenPoweredConfig);
2169            pw.println("  mDreamsBatteryLevelMinimumWhenNotPoweredConfig="
2170                    + mDreamsBatteryLevelMinimumWhenNotPoweredConfig);
2171            pw.println("  mDreamsBatteryLevelDrainCutoffConfig="
2172                    + mDreamsBatteryLevelDrainCutoffConfig);
2173            pw.println("  mDreamsEnabledSetting=" + mDreamsEnabledSetting);
2174            pw.println("  mDreamsActivateOnSleepSetting=" + mDreamsActivateOnSleepSetting);
2175            pw.println("  mDreamsActivateOnDockSetting=" + mDreamsActivateOnDockSetting);
2176            pw.println("  mMinimumScreenOffTimeoutConfig=" + mMinimumScreenOffTimeoutConfig);
2177            pw.println("  mMaximumScreenDimDurationConfig=" + mMaximumScreenDimDurationConfig);
2178            pw.println("  mMaximumScreenDimRatioConfig=" + mMaximumScreenDimRatioConfig);
2179            pw.println("  mScreenOffTimeoutSetting=" + mScreenOffTimeoutSetting);
2180            pw.println("  mMaximumScreenOffTimeoutFromDeviceAdmin="
2181                    + mMaximumScreenOffTimeoutFromDeviceAdmin + " (enforced="
2182                    + isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked() + ")");
2183            pw.println("  mStayOnWhilePluggedInSetting=" + mStayOnWhilePluggedInSetting);
2184            pw.println("  mScreenBrightnessSetting=" + mScreenBrightnessSetting);
2185            pw.println("  mScreenAutoBrightnessAdjustmentSetting="
2186                    + mScreenAutoBrightnessAdjustmentSetting);
2187            pw.println("  mScreenBrightnessModeSetting=" + mScreenBrightnessModeSetting);
2188            pw.println("  mScreenBrightnessOverrideFromWindowManager="
2189                    + mScreenBrightnessOverrideFromWindowManager);
2190            pw.println("  mUserActivityTimeoutOverrideFromWindowManager="
2191                    + mUserActivityTimeoutOverrideFromWindowManager);
2192            pw.println("  mTemporaryScreenBrightnessSettingOverride="
2193                    + mTemporaryScreenBrightnessSettingOverride);
2194            pw.println("  mTemporaryScreenAutoBrightnessAdjustmentSettingOverride="
2195                    + mTemporaryScreenAutoBrightnessAdjustmentSettingOverride);
2196            pw.println("  mScreenBrightnessSettingMinimum=" + mScreenBrightnessSettingMinimum);
2197            pw.println("  mScreenBrightnessSettingMaximum=" + mScreenBrightnessSettingMaximum);
2198            pw.println("  mScreenBrightnessSettingDefault=" + mScreenBrightnessSettingDefault);
2199
2200            final int screenOffTimeout = getScreenOffTimeoutLocked();
2201            final int screenDimDuration = getScreenDimDurationLocked(screenOffTimeout);
2202            pw.println();
2203            pw.println("Screen off timeout: " + screenOffTimeout + " ms");
2204            pw.println("Screen dim duration: " + screenDimDuration + " ms");
2205
2206            pw.println();
2207            pw.println("Wake Locks: size=" + mWakeLocks.size());
2208            for (WakeLock wl : mWakeLocks) {
2209                pw.println("  " + wl);
2210            }
2211
2212            pw.println();
2213            pw.println("Suspend Blockers: size=" + mSuspendBlockers.size());
2214            for (SuspendBlocker sb : mSuspendBlockers) {
2215                pw.println("  " + sb);
2216            }
2217
2218            pw.println();
2219            pw.println("Screen On Blocker: " + mScreenOnBlocker);
2220
2221            pw.println();
2222            pw.println("Display Power: " + mDisplayPowerCallbacks);
2223
2224            wcd = mWirelessChargerDetector;
2225        }
2226
2227        if (wcd != null) {
2228            wcd.dump(pw);
2229        }
2230    }
2231
2232    private SuspendBlocker createSuspendBlockerLocked(String name) {
2233        SuspendBlocker suspendBlocker = new SuspendBlockerImpl(name);
2234        mSuspendBlockers.add(suspendBlocker);
2235        return suspendBlocker;
2236    }
2237
2238    private static String wakefulnessToString(int wakefulness) {
2239        switch (wakefulness) {
2240            case WAKEFULNESS_ASLEEP:
2241                return "Asleep";
2242            case WAKEFULNESS_AWAKE:
2243                return "Awake";
2244            case WAKEFULNESS_DREAMING:
2245                return "Dreaming";
2246            case WAKEFULNESS_DOZING:
2247                return "Dozing";
2248            default:
2249                return Integer.toString(wakefulness);
2250        }
2251    }
2252
2253    private static WorkSource copyWorkSource(WorkSource workSource) {
2254        return workSource != null ? new WorkSource(workSource) : null;
2255    }
2256
2257    private final class BatteryReceiver extends BroadcastReceiver {
2258        @Override
2259        public void onReceive(Context context, Intent intent) {
2260            synchronized (mLock) {
2261                handleBatteryStateChangedLocked();
2262            }
2263        }
2264    }
2265
2266    private final class BootCompletedReceiver extends BroadcastReceiver {
2267        @Override
2268        public void onReceive(Context context, Intent intent) {
2269            // This is our early signal that the system thinks it has finished booting.
2270            // However, the boot animation may still be running for a few more seconds
2271            // since it is ultimately in charge of when it terminates.
2272            // Defer transitioning into the boot completed state until the animation exits.
2273            // We do this so that the screen does not start to dim prematurely before
2274            // the user has actually had a chance to interact with the device.
2275            startWatchingForBootAnimationFinished();
2276        }
2277    }
2278
2279    private final class DreamReceiver extends BroadcastReceiver {
2280        @Override
2281        public void onReceive(Context context, Intent intent) {
2282            synchronized (mLock) {
2283                scheduleSandmanLocked();
2284            }
2285        }
2286    }
2287
2288    private final class UserSwitchedReceiver extends BroadcastReceiver {
2289        @Override
2290        public void onReceive(Context context, Intent intent) {
2291            synchronized (mLock) {
2292                handleSettingsChangedLocked();
2293            }
2294        }
2295    }
2296
2297    private final class DockReceiver extends BroadcastReceiver {
2298        @Override
2299        public void onReceive(Context context, Intent intent) {
2300            synchronized (mLock) {
2301                int dockState = intent.getIntExtra(Intent.EXTRA_DOCK_STATE,
2302                        Intent.EXTRA_DOCK_STATE_UNDOCKED);
2303                if (mDockState != dockState) {
2304                    mDockState = dockState;
2305                    mDirty |= DIRTY_DOCK_STATE;
2306                    updatePowerStateLocked();
2307                }
2308            }
2309        }
2310    }
2311
2312    private final class SettingsObserver extends ContentObserver {
2313        public SettingsObserver(Handler handler) {
2314            super(handler);
2315        }
2316
2317        @Override
2318        public void onChange(boolean selfChange, Uri uri) {
2319            synchronized (mLock) {
2320                handleSettingsChangedLocked();
2321            }
2322        }
2323    }
2324
2325    /**
2326     * Handler for asynchronous operations performed by the power manager.
2327     */
2328    private final class PowerManagerHandler extends Handler {
2329        public PowerManagerHandler(Looper looper) {
2330            super(looper, null, true /*async*/);
2331        }
2332
2333        @Override
2334        public void handleMessage(Message msg) {
2335            switch (msg.what) {
2336                case MSG_USER_ACTIVITY_TIMEOUT:
2337                    handleUserActivityTimeout();
2338                    break;
2339                case MSG_SANDMAN:
2340                    handleSandman();
2341                    break;
2342                case MSG_SCREEN_ON_BLOCKER_RELEASED:
2343                    handleScreenOnBlockerReleased();
2344                    break;
2345                case MSG_CHECK_IF_BOOT_ANIMATION_FINISHED:
2346                    checkIfBootAnimationFinished();
2347                    break;
2348            }
2349        }
2350    }
2351
2352    /**
2353     * Represents a wake lock that has been acquired by an application.
2354     */
2355    private final class WakeLock implements IBinder.DeathRecipient {
2356        public final IBinder mLock;
2357        public int mFlags;
2358        public String mTag;
2359        public final String mPackageName;
2360        public WorkSource mWorkSource;
2361        public String mHistoryTag;
2362        public final int mOwnerUid;
2363        public final int mOwnerPid;
2364        public boolean mNotifiedAcquired;
2365
2366        public WakeLock(IBinder lock, int flags, String tag, String packageName,
2367                WorkSource workSource, String historyTag, int ownerUid, int ownerPid) {
2368            mLock = lock;
2369            mFlags = flags;
2370            mTag = tag;
2371            mPackageName = packageName;
2372            mWorkSource = copyWorkSource(workSource);
2373            mHistoryTag = historyTag;
2374            mOwnerUid = ownerUid;
2375            mOwnerPid = ownerPid;
2376        }
2377
2378        @Override
2379        public void binderDied() {
2380            PowerManagerService.this.handleWakeLockDeath(this);
2381        }
2382
2383        public boolean hasSameProperties(int flags, String tag, WorkSource workSource,
2384                int ownerUid, int ownerPid) {
2385            return mFlags == flags
2386                    && mTag.equals(tag)
2387                    && hasSameWorkSource(workSource)
2388                    && mOwnerUid == ownerUid
2389                    && mOwnerPid == ownerPid;
2390        }
2391
2392        public void updateProperties(int flags, String tag, String packageName,
2393                WorkSource workSource, String historyTag, int ownerUid, int ownerPid) {
2394            if (!mPackageName.equals(packageName)) {
2395                throw new IllegalStateException("Existing wake lock package name changed: "
2396                        + mPackageName + " to " + packageName);
2397            }
2398            if (mOwnerUid != ownerUid) {
2399                throw new IllegalStateException("Existing wake lock uid changed: "
2400                        + mOwnerUid + " to " + ownerUid);
2401            }
2402            if (mOwnerPid != ownerPid) {
2403                throw new IllegalStateException("Existing wake lock pid changed: "
2404                        + mOwnerPid + " to " + ownerPid);
2405            }
2406            mFlags = flags;
2407            mTag = tag;
2408            updateWorkSource(workSource);
2409            mHistoryTag = historyTag;
2410        }
2411
2412        public boolean hasSameWorkSource(WorkSource workSource) {
2413            return Objects.equal(mWorkSource, workSource);
2414        }
2415
2416        public void updateWorkSource(WorkSource workSource) {
2417            mWorkSource = copyWorkSource(workSource);
2418        }
2419
2420        @Override
2421        public String toString() {
2422            return getLockLevelString()
2423                    + " '" + mTag + "'" + getLockFlagsString()
2424                    + " (uid=" + mOwnerUid + ", pid=" + mOwnerPid + ", ws=" + mWorkSource + ")";
2425        }
2426
2427        @SuppressWarnings("deprecation")
2428        private String getLockLevelString() {
2429            switch (mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {
2430                case PowerManager.FULL_WAKE_LOCK:
2431                    return "FULL_WAKE_LOCK                ";
2432                case PowerManager.SCREEN_BRIGHT_WAKE_LOCK:
2433                    return "SCREEN_BRIGHT_WAKE_LOCK       ";
2434                case PowerManager.SCREEN_DIM_WAKE_LOCK:
2435                    return "SCREEN_DIM_WAKE_LOCK          ";
2436                case PowerManager.PARTIAL_WAKE_LOCK:
2437                    return "PARTIAL_WAKE_LOCK             ";
2438                case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK:
2439                    return "PROXIMITY_SCREEN_OFF_WAKE_LOCK";
2440                case PowerManager.DOZE_WAKE_LOCK:
2441                    return "DOZE_WAKE_LOCK                ";
2442                default:
2443                    return "???                           ";
2444            }
2445        }
2446
2447        private String getLockFlagsString() {
2448            String result = "";
2449            if ((mFlags & PowerManager.ACQUIRE_CAUSES_WAKEUP) != 0) {
2450                result += " ACQUIRE_CAUSES_WAKEUP";
2451            }
2452            if ((mFlags & PowerManager.ON_AFTER_RELEASE) != 0) {
2453                result += " ON_AFTER_RELEASE";
2454            }
2455            return result;
2456        }
2457    }
2458
2459    private final class SuspendBlockerImpl implements SuspendBlocker {
2460        private final String mName;
2461        private int mReferenceCount;
2462
2463        public SuspendBlockerImpl(String name) {
2464            mName = name;
2465        }
2466
2467        @Override
2468        protected void finalize() throws Throwable {
2469            try {
2470                if (mReferenceCount != 0) {
2471                    Log.wtf(TAG, "Suspend blocker \"" + mName
2472                            + "\" was finalized without being released!");
2473                    mReferenceCount = 0;
2474                    nativeReleaseSuspendBlocker(mName);
2475                }
2476            } finally {
2477                super.finalize();
2478            }
2479        }
2480
2481        @Override
2482        public void acquire() {
2483            synchronized (this) {
2484                mReferenceCount += 1;
2485                if (mReferenceCount == 1) {
2486                    if (DEBUG_SPEW) {
2487                        Slog.d(TAG, "Acquiring suspend blocker \"" + mName + "\".");
2488                    }
2489                    nativeAcquireSuspendBlocker(mName);
2490                }
2491            }
2492        }
2493
2494        @Override
2495        public void release() {
2496            synchronized (this) {
2497                mReferenceCount -= 1;
2498                if (mReferenceCount == 0) {
2499                    if (DEBUG_SPEW) {
2500                        Slog.d(TAG, "Releasing suspend blocker \"" + mName + "\".");
2501                    }
2502                    nativeReleaseSuspendBlocker(mName);
2503                } else if (mReferenceCount < 0) {
2504                    Log.wtf(TAG, "Suspend blocker \"" + mName
2505                            + "\" was released without being acquired!", new Throwable());
2506                    mReferenceCount = 0;
2507                }
2508            }
2509        }
2510
2511        @Override
2512        public String toString() {
2513            synchronized (this) {
2514                return mName + ": ref count=" + mReferenceCount;
2515            }
2516        }
2517    }
2518
2519    private final class ScreenOnBlockerImpl implements ScreenOnBlocker {
2520        private int mNestCount;
2521
2522        public boolean isHeld() {
2523            synchronized (this) {
2524                return mNestCount != 0;
2525            }
2526        }
2527
2528        @Override
2529        public void acquire() {
2530            synchronized (this) {
2531                mNestCount += 1;
2532                if (DEBUG) {
2533                    Slog.d(TAG, "Screen on blocked: mNestCount=" + mNestCount);
2534                }
2535            }
2536        }
2537
2538        @Override
2539        public void release() {
2540            synchronized (this) {
2541                mNestCount -= 1;
2542                if (mNestCount < 0) {
2543                    Log.wtf(TAG, "Screen on blocker was released without being acquired!",
2544                            new Throwable());
2545                    mNestCount = 0;
2546                }
2547                if (mNestCount == 0) {
2548                    mHandler.sendEmptyMessage(MSG_SCREEN_ON_BLOCKER_RELEASED);
2549                }
2550                if (DEBUG) {
2551                    Slog.d(TAG, "Screen on unblocked: mNestCount=" + mNestCount);
2552                }
2553            }
2554        }
2555
2556        @Override
2557        public String toString() {
2558            synchronized (this) {
2559                return "held=" + (mNestCount != 0) + ", mNestCount=" + mNestCount;
2560            }
2561        }
2562    }
2563
2564    private final class BinderService extends IPowerManager.Stub {
2565        @Override // Binder call
2566        public void acquireWakeLockWithUid(IBinder lock, int flags, String tag,
2567                String packageName, int uid) {
2568            if (uid < 0) {
2569                uid = Binder.getCallingUid();
2570            }
2571            acquireWakeLock(lock, flags, tag, packageName, new WorkSource(uid), null);
2572        }
2573
2574        @Override // Binder call
2575        public void powerHint(int hintId, int data) {
2576            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER, null);
2577            powerHintInternal(hintId, data);
2578        }
2579
2580        @Override // Binder call
2581        public void acquireWakeLock(IBinder lock, int flags, String tag, String packageName,
2582                WorkSource ws, String historyTag) {
2583            if (lock == null) {
2584                throw new IllegalArgumentException("lock must not be null");
2585            }
2586            if (packageName == null) {
2587                throw new IllegalArgumentException("packageName must not be null");
2588            }
2589            PowerManager.validateWakeLockParameters(flags, tag);
2590
2591            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WAKE_LOCK, null);
2592            if (ws != null && ws.size() != 0) {
2593                mContext.enforceCallingOrSelfPermission(
2594                        android.Manifest.permission.UPDATE_DEVICE_STATS, null);
2595            } else {
2596                ws = null;
2597            }
2598
2599            final int uid = Binder.getCallingUid();
2600            final int pid = Binder.getCallingPid();
2601            final long ident = Binder.clearCallingIdentity();
2602            try {
2603                acquireWakeLockInternal(lock, flags, tag, packageName, ws, historyTag, uid, pid);
2604            } finally {
2605                Binder.restoreCallingIdentity(ident);
2606            }
2607        }
2608
2609        @Override // Binder call
2610        public void releaseWakeLock(IBinder lock, int flags) {
2611            if (lock == null) {
2612                throw new IllegalArgumentException("lock must not be null");
2613            }
2614
2615            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WAKE_LOCK, null);
2616
2617            final long ident = Binder.clearCallingIdentity();
2618            try {
2619                releaseWakeLockInternal(lock, flags);
2620            } finally {
2621                Binder.restoreCallingIdentity(ident);
2622            }
2623        }
2624
2625        @Override // Binder call
2626        public void updateWakeLockUids(IBinder lock, int[] uids) {
2627            WorkSource ws = null;
2628
2629            if (uids != null) {
2630                ws = new WorkSource();
2631                // XXX should WorkSource have a way to set uids as an int[] instead of adding them
2632                // one at a time?
2633                for (int i = 0; i < uids.length; i++) {
2634                    ws.add(uids[i]);
2635                }
2636            }
2637            updateWakeLockWorkSource(lock, ws, null);
2638        }
2639
2640        @Override // Binder call
2641        public void updateWakeLockWorkSource(IBinder lock, WorkSource ws, String historyTag) {
2642            if (lock == null) {
2643                throw new IllegalArgumentException("lock must not be null");
2644            }
2645
2646            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.WAKE_LOCK, null);
2647            if (ws != null && ws.size() != 0) {
2648                mContext.enforceCallingOrSelfPermission(
2649                        android.Manifest.permission.UPDATE_DEVICE_STATS, null);
2650            } else {
2651                ws = null;
2652            }
2653
2654            final long ident = Binder.clearCallingIdentity();
2655            try {
2656                updateWakeLockWorkSourceInternal(lock, ws, historyTag);
2657            } finally {
2658                Binder.restoreCallingIdentity(ident);
2659            }
2660        }
2661
2662        @Override // Binder call
2663        public boolean isWakeLockLevelSupported(int level) {
2664            final long ident = Binder.clearCallingIdentity();
2665            try {
2666                return isWakeLockLevelSupportedInternal(level);
2667            } finally {
2668                Binder.restoreCallingIdentity(ident);
2669            }
2670        }
2671
2672        @Override // Binder call
2673        public void userActivity(long eventTime, int event, int flags) {
2674            final long now = SystemClock.uptimeMillis();
2675            if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DEVICE_POWER)
2676                    != PackageManager.PERMISSION_GRANTED) {
2677                // Once upon a time applications could call userActivity().
2678                // Now we require the DEVICE_POWER permission.  Log a warning and ignore the
2679                // request instead of throwing a SecurityException so we don't break old apps.
2680                synchronized (mLock) {
2681                    if (now >= mLastWarningAboutUserActivityPermission + (5 * 60 * 1000)) {
2682                        mLastWarningAboutUserActivityPermission = now;
2683                        Slog.w(TAG, "Ignoring call to PowerManager.userActivity() because the "
2684                                + "caller does not have DEVICE_POWER permission.  "
2685                                + "Please fix your app!  "
2686                                + " pid=" + Binder.getCallingPid()
2687                                + " uid=" + Binder.getCallingUid());
2688                    }
2689                }
2690                return;
2691            }
2692
2693            if (eventTime > SystemClock.uptimeMillis()) {
2694                throw new IllegalArgumentException("event time must not be in the future");
2695            }
2696
2697            final int uid = Binder.getCallingUid();
2698            final long ident = Binder.clearCallingIdentity();
2699            try {
2700                userActivityInternal(eventTime, event, flags, uid);
2701            } finally {
2702                Binder.restoreCallingIdentity(ident);
2703            }
2704        }
2705
2706        @Override // Binder call
2707        public void wakeUp(long eventTime) {
2708            if (eventTime > SystemClock.uptimeMillis()) {
2709                throw new IllegalArgumentException("event time must not be in the future");
2710            }
2711
2712            mContext.enforceCallingOrSelfPermission(
2713                    android.Manifest.permission.DEVICE_POWER, null);
2714
2715            final long ident = Binder.clearCallingIdentity();
2716            try {
2717                wakeUpInternal(eventTime);
2718            } finally {
2719                Binder.restoreCallingIdentity(ident);
2720            }
2721        }
2722
2723        @Override // Binder call
2724        public void goToSleep(long eventTime, int reason, int flags) {
2725            if (eventTime > SystemClock.uptimeMillis()) {
2726                throw new IllegalArgumentException("event time must not be in the future");
2727            }
2728
2729            mContext.enforceCallingOrSelfPermission(
2730                    android.Manifest.permission.DEVICE_POWER, null);
2731
2732            final long ident = Binder.clearCallingIdentity();
2733            try {
2734                goToSleepInternal(eventTime, reason, flags);
2735            } finally {
2736                Binder.restoreCallingIdentity(ident);
2737            }
2738        }
2739
2740        @Override // Binder call
2741        public void nap(long eventTime) {
2742            if (eventTime > SystemClock.uptimeMillis()) {
2743                throw new IllegalArgumentException("event time must not be in the future");
2744            }
2745
2746            mContext.enforceCallingOrSelfPermission(
2747                    android.Manifest.permission.DEVICE_POWER, null);
2748
2749            final long ident = Binder.clearCallingIdentity();
2750            try {
2751                napInternal(eventTime);
2752            } finally {
2753                Binder.restoreCallingIdentity(ident);
2754            }
2755        }
2756
2757        @Override // Binder call
2758        public boolean isInteractive() {
2759            final long ident = Binder.clearCallingIdentity();
2760            try {
2761                return isInteractiveInternal();
2762            } finally {
2763                Binder.restoreCallingIdentity(ident);
2764            }
2765        }
2766
2767        /**
2768         * Reboots the device.
2769         *
2770         * @param confirm If true, shows a reboot confirmation dialog.
2771         * @param reason The reason for the reboot, or null if none.
2772         * @param wait If true, this call waits for the reboot to complete and does not return.
2773         */
2774        @Override // Binder call
2775        public void reboot(boolean confirm, String reason, boolean wait) {
2776            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);
2777            if (PowerManager.REBOOT_RECOVERY.equals(reason)) {
2778                mContext.enforceCallingOrSelfPermission(android.Manifest.permission.RECOVERY, null);
2779            }
2780
2781            final long ident = Binder.clearCallingIdentity();
2782            try {
2783                shutdownOrRebootInternal(false, confirm, reason, wait);
2784            } finally {
2785                Binder.restoreCallingIdentity(ident);
2786            }
2787        }
2788
2789        /**
2790         * Shuts down the device.
2791         *
2792         * @param confirm If true, shows a shutdown confirmation dialog.
2793         * @param wait If true, this call waits for the shutdown to complete and does not return.
2794         */
2795        @Override // Binder call
2796        public void shutdown(boolean confirm, boolean wait) {
2797            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);
2798
2799            final long ident = Binder.clearCallingIdentity();
2800            try {
2801                shutdownOrRebootInternal(true, confirm, null, wait);
2802            } finally {
2803                Binder.restoreCallingIdentity(ident);
2804            }
2805        }
2806
2807        /**
2808         * Crash the runtime (causing a complete restart of the Android framework).
2809         * Requires REBOOT permission.  Mostly for testing.  Should not return.
2810         */
2811        @Override // Binder call
2812        public void crash(String message) {
2813            mContext.enforceCallingOrSelfPermission(android.Manifest.permission.REBOOT, null);
2814
2815            final long ident = Binder.clearCallingIdentity();
2816            try {
2817                crashInternal(message);
2818            } finally {
2819                Binder.restoreCallingIdentity(ident);
2820            }
2821        }
2822
2823        /**
2824         * Set the setting that determines whether the device stays on when plugged in.
2825         * The argument is a bit string, with each bit specifying a power source that,
2826         * when the device is connected to that source, causes the device to stay on.
2827         * See {@link android.os.BatteryManager} for the list of power sources that
2828         * can be specified. Current values include
2829         * {@link android.os.BatteryManager#BATTERY_PLUGGED_AC}
2830         * and {@link android.os.BatteryManager#BATTERY_PLUGGED_USB}
2831         *
2832         * Used by "adb shell svc power stayon ..."
2833         *
2834         * @param val an {@code int} containing the bits that specify which power sources
2835         * should cause the device to stay on.
2836         */
2837        @Override // Binder call
2838        public void setStayOnSetting(int val) {
2839            mContext.enforceCallingOrSelfPermission(
2840                    android.Manifest.permission.WRITE_SETTINGS, null);
2841
2842            final long ident = Binder.clearCallingIdentity();
2843            try {
2844                setStayOnSettingInternal(val);
2845            } finally {
2846                Binder.restoreCallingIdentity(ident);
2847            }
2848        }
2849
2850        /**
2851         * Used by device administration to set the maximum screen off timeout.
2852         *
2853         * This method must only be called by the device administration policy manager.
2854         */
2855        @Override // Binder call
2856        public void setMaximumScreenOffTimeoutFromDeviceAdmin(int timeMs) {
2857            final long ident = Binder.clearCallingIdentity();
2858            try {
2859                setMaximumScreenOffTimeoutFromDeviceAdminInternal(timeMs);
2860            } finally {
2861                Binder.restoreCallingIdentity(ident);
2862            }
2863        }
2864
2865        /**
2866         * Used by the settings application and brightness control widgets to
2867         * temporarily override the current screen brightness setting so that the
2868         * user can observe the effect of an intended settings change without applying
2869         * it immediately.
2870         *
2871         * The override will be canceled when the setting value is next updated.
2872         *
2873         * @param brightness The overridden brightness.
2874         *
2875         * @see android.provider.Settings.System#SCREEN_BRIGHTNESS
2876         */
2877        @Override // Binder call
2878        public void setTemporaryScreenBrightnessSettingOverride(int brightness) {
2879            mContext.enforceCallingOrSelfPermission(
2880                    android.Manifest.permission.DEVICE_POWER, null);
2881
2882            final long ident = Binder.clearCallingIdentity();
2883            try {
2884                setTemporaryScreenBrightnessSettingOverrideInternal(brightness);
2885            } finally {
2886                Binder.restoreCallingIdentity(ident);
2887            }
2888        }
2889
2890        /**
2891         * Used by the settings application and brightness control widgets to
2892         * temporarily override the current screen auto-brightness adjustment setting so that the
2893         * user can observe the effect of an intended settings change without applying
2894         * it immediately.
2895         *
2896         * The override will be canceled when the setting value is next updated.
2897         *
2898         * @param adj The overridden brightness, or Float.NaN to disable the override.
2899         *
2900         * @see android.provider.Settings.System#SCREEN_AUTO_BRIGHTNESS_ADJ
2901         */
2902        @Override // Binder call
2903        public void setTemporaryScreenAutoBrightnessAdjustmentSettingOverride(float adj) {
2904            mContext.enforceCallingOrSelfPermission(
2905                    android.Manifest.permission.DEVICE_POWER, null);
2906
2907            final long ident = Binder.clearCallingIdentity();
2908            try {
2909                setTemporaryScreenAutoBrightnessAdjustmentSettingOverrideInternal(adj);
2910            } finally {
2911                Binder.restoreCallingIdentity(ident);
2912            }
2913        }
2914
2915        /**
2916         * Used by the phone application to make the attention LED flash when ringing.
2917         */
2918        @Override // Binder call
2919        public void setAttentionLight(boolean on, int color) {
2920            mContext.enforceCallingOrSelfPermission(
2921                    android.Manifest.permission.DEVICE_POWER, null);
2922
2923            final long ident = Binder.clearCallingIdentity();
2924            try {
2925                setAttentionLightInternal(on, color);
2926            } finally {
2927                Binder.restoreCallingIdentity(ident);
2928            }
2929        }
2930
2931        @Override // Binder call
2932        protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
2933            if (mContext.checkCallingOrSelfPermission(Manifest.permission.DUMP)
2934                    != PackageManager.PERMISSION_GRANTED) {
2935                pw.println("Permission Denial: can't dump PowerManager from from pid="
2936                        + Binder.getCallingPid()
2937                        + ", uid=" + Binder.getCallingUid());
2938                return;
2939            }
2940
2941            final long ident = Binder.clearCallingIdentity();
2942            try {
2943                dumpInternal(pw);
2944            } finally {
2945                Binder.restoreCallingIdentity(ident);
2946            }
2947        }
2948    }
2949
2950    private final class LocalService extends PowerManagerInternal {
2951        /**
2952         * Used by the window manager to override the screen brightness based on the
2953         * current foreground activity.
2954         *
2955         * This method must only be called by the window manager.
2956         *
2957         * @param brightness The overridden brightness, or -1 to disable the override.
2958         */
2959        @Override
2960        public void setScreenBrightnessOverrideFromWindowManager(int brightness) {
2961            mContext.enforceCallingOrSelfPermission(
2962                    android.Manifest.permission.DEVICE_POWER, null);
2963
2964            final long ident = Binder.clearCallingIdentity();
2965            try {
2966                setScreenBrightnessOverrideFromWindowManagerInternal(brightness);
2967            } finally {
2968                Binder.restoreCallingIdentity(ident);
2969            }
2970        }
2971
2972        /**
2973         * Used by the window manager to override the button brightness based on the
2974         * current foreground activity.
2975         *
2976         * This method must only be called by the window manager.
2977         *
2978         * @param brightness The overridden brightness, or -1 to disable the override.
2979         */
2980        @Override
2981        public void setButtonBrightnessOverrideFromWindowManager(int brightness) {
2982            // Do nothing.
2983            // Button lights are not currently supported in the new implementation.
2984            mContext.enforceCallingOrSelfPermission(
2985                    android.Manifest.permission.DEVICE_POWER, null);
2986        }
2987
2988        /**
2989         * Used by the window manager to override the user activity timeout based on the
2990         * current foreground activity.  It can only be used to make the timeout shorter
2991         * than usual, not longer.
2992         *
2993         * This method must only be called by the window manager.
2994         *
2995         * @param timeoutMillis The overridden timeout, or -1 to disable the override.
2996         */
2997        @Override
2998        public void setUserActivityTimeoutOverrideFromWindowManager(long timeoutMillis) {
2999            mContext.enforceCallingOrSelfPermission(
3000                    android.Manifest.permission.DEVICE_POWER, null);
3001
3002            final long ident = Binder.clearCallingIdentity();
3003            try {
3004                setUserActivityTimeoutOverrideFromWindowManagerInternal(timeoutMillis);
3005            } finally {
3006                Binder.restoreCallingIdentity(ident);
3007            }
3008        }
3009
3010        @Override
3011        public boolean getLowPowerModeEnabled() {
3012            synchronized (mLock) {
3013                return mLowPowerModeEnabled;
3014            }
3015        }
3016
3017        @Override
3018        public void registerLowPowerModeObserver(LowPowerModeListener listener) {
3019            synchronized (mLock) {
3020                mLowPowerModeListeners.add(listener);
3021            }
3022        }
3023
3024        @Override
3025        public void setPolicy(WindowManagerPolicy policy) {
3026            PowerManagerService.this.setPolicy(policy);
3027        }
3028    }
3029}
3030