PowerManagerServiceの起動WackLock処理に関するプロセス

37426 ワード

Step 1: frameworksbaseservicesjavacomandroidserverSystemServer.java PowerManagerServiceサービスを開始
private void startOtherServices() {
    ...
       try {
           // TODO: use boot phase
           mPowerManagerService.systemReady(mActivityManagerService.getAppOpsService());
       } catch (Throwable e) {
           reportWtf("making Power Manager Service ready", e);
        }
    ...
 }

Step 2:
frameworks\base\services\core\java\com\android\server\power\PowerManagerService.java
次に、PowerManagerServiceの起動時の準備手順を分析します.
主なワークフローは次のとおりです.
1.デフォルト、最大、最小の3種類の画面輝度を取得
2.SensorServiceと対話するためのSystemSensorManagerオブジェクトを作成します.SensorServiceはnativeのサービスであり、SystemServerプロセスにも存在し、様々なセンシングデバイスを管理しています.
3.Notiferオブジェクトを作成します.Notiferオブジェクトは、画面を閉じたり開いたりするなど、システム内のPower関連の変化をブロードキャストするために使用されます.
4.ワイヤレス充電検出用のWirelessChargerServiceオブジェクトを作成するセンサ
5.DisplayManagerServiceのinitPowerManagement()を呼び出す方法でPower管理モジュールを初期化する
6.登録Observerリスニングシステムの設定の変更.
7.他のモジュールをリスニングするIntentを登録します.
    public void systemReady(IAppOpsService appOps) {
        synchronized (mLock) {
            mSystemReady = true;
            mAppOps = appOps;
	         //  DreamManagerService
            mDreamManager = getLocalService(DreamManagerInternal.class);
	         //  DisplayManagerService
            mDisplayManagerInternal = getLocalService(DisplayManagerInternal.class);
            mPolicy = getLocalService(WindowManagerPolicy.class);
	         //  BatteryManagerService
            mBatteryManagerInternal = getLocalService(BatteryManagerInternal.class);
           //        ,         
            PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
            mScreenBrightnessSettingMinimum = pm.getMinimumScreenBrightnessSetting();
            mScreenBrightnessSettingMaximum = pm.getMaximumScreenBrightnessSetting();
            mScreenBrightnessSettingDefault = pm.getDefaultScreenBrightnessSetting();

            if (DEBUG_SPEW) {
                Slog.d(TAG, "mScreenBrightnessSettingMinimum = " + mScreenBrightnessSettingMinimum +
                    " mScreenBrightnessSettingMinimum = " + mScreenBrightnessSettingMaximum +
                    " mScreenBrightnessSettingDefault = " + mScreenBrightnessSettingDefault);
            }
            //    SensorManager  ,   SensorService  
            SensorManager sensorManager = new SystemSensorManager(mContext, mHandler.getLooper());

            // The notifier runs on the system server's main looper so as not to interfere
            // with the animations and other critical functions of the power manager.
            //  BatteryStatsService     
            mBatteryStats = BatteryStatsService.getService();
            //  Notifier  
            mNotifier = new Notifier(Looper.getMainLooper(), mContext, mBatteryStats,
                    mAppOps, createSuspendBlockerLocked("PowerManagerService.Broadcasts"),
                    mPolicy);
            //          WirelessChargerDetector
            mWirelessChargerDetector = new WirelessChargerDetector(sensorManager,
                    createSuspendBlockerLocked("PowerManagerService.WirelessChargerDetector"),
                    mHandler);
            //           
            mSettingsObserver = new SettingsObserver(mHandler);
            //   LightsService  
            mLightsManager = getLocalService(LightsManager.class);
            mAttentionLight = mLightsManager.getLight(LightsManager.LIGHT_ID_ATTENTION);
            mButtonLight = mLightsManager.getLight(LightsManager.LIGHT_ID_BUTTONS);
            mBacklight = mLightsManager.getLight(LightsManager.LIGHT_ID_BACKLIGHT);
            //   Power  
            // Initialize display power management.
            mDisplayManagerInternal.initPowerManagement(
                    mDisplayPowerCallbacks, mHandler, sensorManager);

            // Register for broadcasts from other components of the system.
            IntentFilter filter = new IntentFilter();
            filter.addAction(Intent.ACTION_BATTERY_CHANGED);
            filter.setPriority(IntentFilter.SYSTEM_HIGH_PRIORITY);
            mContext.registerReceiver(new BatteryReceiver(), filter, null, mHandler);

            filter = new IntentFilter();
            filter.addAction(Intent.ACTION_DREAMING_STARTED);//      
            filter.addAction(Intent.ACTION_DREAMING_STOPPED);//      
            mContext.registerReceiver(new DreamReceiver(), filter, null, mHandler);

            filter = new IntentFilter();
            filter.addAction(Intent.ACTION_USER_SWITCHED);//      
            mContext.registerReceiver(new UserSwitchedReceiver(), filter, null, mHandler);

            filter = new IntentFilter();
            filter.addAction(Intent.ACTION_DOCK_EVENT);//Dock       
            mContext.registerReceiver(new DockReceiver(), filter, null, mHandler);

            // Register for SD Hot Plug notification 
            filter = new IntentFilter();
            filter.addAction(Intent.ACTION_SD_INSERTED);//SD       
            filter.addDataScheme("file");
            mContext.registerReceiver(new SDHotPlugReceiver(), filter, null, mHandler);

          

            // Register for wfd notification
            mContext.registerReceiver(new WifiDisplayStatusChangedReceiver(),
                new IntentFilter(DisplayManager.ACTION_WIFI_DISPLAY_STATUS_CHANGED),
                null, mHandler);

            filter = new IntentFilter();
            filter.addAction("com.mediatek.SCREEN_TIMEOUT_MINIMUM");
            mContext.registerReceiver(new BroadcastReceiver() {
                @Override
                public void onReceive(Context context, Intent intent) {
                    if (DEBUG) {
                        Slog.d(TAG, "SCREEN_TIMEOUT_MINIMUM.");
                    }
                    mPreWakeUpWhenPluggedOrUnpluggedConfig = mWakeUpWhenPluggedOrUnpluggedConfig;
                    mWakeUpWhenPluggedOrUnpluggedConfig = false;
                    mUserActivityTimeoutMin = true;
                }
            }, filter, null, mHandler);

            filter = new IntentFilter();
            filter.addAction("com.mediatek.SCREEN_TIMEOUT_NORMAL");
            mContext.registerReceiver(new BroadcastReceiver() {
                @Override
                public void onReceive(Context context, Intent intent) {
                    if (DEBUG) {
                        Slog.d(TAG, "SCREEN_TIMEOUT_NORMAL.");
                    }
                    mWakeUpWhenPluggedOrUnpluggedConfig = mPreWakeUpWhenPluggedOrUnpluggedConfig;
                    mUserActivityTimeoutMin = false;
                }
            }, filter, null, mHandler);
            // Register for settings changes.
            final ContentResolver resolver = mContext.getContentResolver();
            resolver.registerContentObserver(Settings.Secure.getUriFor(
                    Settings.Secure.SCREENSAVER_ENABLED),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Secure.getUriFor(
                    Settings.Secure.SCREENSAVER_ACTIVATE_ON_SLEEP),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Secure.getUriFor(
                    Settings.Secure.SCREENSAVER_ACTIVATE_ON_DOCK),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.System.getUriFor(
                    Settings.System.SCREEN_OFF_TIMEOUT),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Secure.getUriFor(
                    Settings.Secure.SLEEP_TIMEOUT),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Global.getUriFor(
                    Settings.Global.STAY_ON_WHILE_PLUGGED_IN),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.System.getUriFor(
                    Settings.System.SCREEN_BRIGHTNESS),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.System.getUriFor(
                    Settings.System.SCREEN_BRIGHTNESS_MODE),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.System.getUriFor(
                    Settings.System.SCREEN_AUTO_BRIGHTNESS_ADJ),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Global.getUriFor(
                    Settings.Global.LOW_POWER_MODE),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Global.getUriFor(
                    Settings.Global.LOW_POWER_MODE_TRIGGER_LEVEL),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Global.getUriFor(
                    Settings.Global.THEATER_MODE_ON),
                    false, mSettingsObserver, UserHandle.USER_ALL);
            resolver.registerContentObserver(Settings.Secure.getUriFor(
                    Settings.Secure.DOUBLE_TAP_TO_WAKE),
                    false, mSettingsObserver, UserHandle.USER_ALL);

            // Go.
            if (DEBUG) {
                Slog.d(TAG, "system ready!");
            }
            readConfigurationLocked();
            updateSettingsLocked();
            mDirty |= DIRTY_BATTERY_STATE;
            updatePowerStateLocked();
        }
    }

Step 3:
   frameworks\base\services\core\java\com\android\server\power\PowerManagerService.java
updatePowerStatedLockedはPowerManagerService全体のコアメソッドであり、すべての以前のステータス変数の数値と関連サービスは現在のメソッドを搭載して操作する必要があります.
次に具体的な方法について具体的に紹介します.
private void updatePowerStateLocked() {
        if (!mSystemReady || mDirty == 0) {//mDirty=0      ,         ,    
            return;
        }
        if (!Thread.holdsLock(mLock)) {
            Slog.wtf(TAG, "Power manager lock was not held when calling updatePowerStateLocked");
        }

        Trace.traceBegin(Trace.TRACE_TAG_POWER, "updatePowerState");
        try {
            // Phase 0: Basic state updates.
            updateIsPoweredLocked(mDirty);//      
            updateStayOnLocked(mDirty);//  DIRTY_STAY_ON      
            updateScreenBrightnessBoostLocked(mDirty);//        

            // Phase 1: Update wakefulness.
            // Loop because the wake lock and user activity computations are influenced
            // by changes in wakefulness.
            final long now = SystemClock.uptimeMillis();
            int dirtyPhase2 = 0;
            for (;;) {
                int dirtyPhase1 = mDirty;
                dirtyPhase2 |= dirtyPhase1;
                mDirty = 0;

                updateWakeLockSummaryLocked(dirtyPhase1);//   PowerManagerService    WackLock     ,           
                updateUserActivitySummaryLocked(now, dirtyPhase1);//          userActivity   ,                  mUserActivitySummary     SCREEN_STATE_DIM(  )  SCREEN_STATE_OFF(  )
                if (!updateWakefulnessLocked(dirtyPhase1)) {
                    break;
                }
            }

            // Phase 2: Update display power state.
            boolean displayBecameReady = updateDisplayPowerStateLocked(dirtyPhase2);

            // Phase 3: Update dream state (depends on display ready signal).
            updateDreamLocked(dirtyPhase2, displayBecameReady);//        

            // Phase 4: Send notifications, if needed.
            finishWakefulnessChangeIfNeededLocked();

            // Phase 5: Update suspend blocker.
            // Because we might release the last suspend blocker here, we need to make sure
            // we finished everything else first!
            updateSuspendBlockerLocked();// sys/power     
        } finally {
            Trace.traceEnd(Trace.TRACE_TAG_POWER);
        }
    

updateIsPoweredLockedの主な役割は、現在の電源ステータスを更新することです.
    private void updateIsPoweredLocked(int dirty) {
        if ((dirty & DIRTY_BATTERY_STATE) != 0) {
            final boolean wasPowered = mIsPowered;
            final int oldPlugType = mPlugType;
            final boolean oldLevelLow = mBatteryLevelLow;
            mIsPowered = mBatteryManagerInternal.isPowered(BatteryManager.BATTERY_PLUGGED_ANY);//       
            mPlugType = mBatteryManagerInternal.getPlugType();//       
            mBatteryLevel = mBatteryManagerInternal.getBatteryLevel();//          
            mBatteryLevelLow = mBatteryManagerInternal.getBatteryLevelLow();


            if (DEBUG_SPEW) {
                Slog.d(TAG, "updateIsPoweredLocked: wasPowered=" + wasPowered
                        + ", mIsPowered=" + mIsPowered
                        + ", oldPlugType=" + oldPlugType
                        + ", mPlugType=" + mPlugType
                        + ", mBatteryLevel=" + mBatteryLevel);
            }


            if (wasPowered != mIsPowered || oldPlugType != mPlugType) {//             
                mDirty |= DIRTY_IS_POWERED;


                // Update wireless dock detection state.
                final boolean dockedOnWirelessCharger = mWirelessChargerDetector.update(//       
                        mIsPowered, mPlugType, mBatteryLevel);


                // Treat plugging and unplugging the devices as a user activity.
                // Users find it disconcerting when they plug or unplug the device
                // and it shuts off right away.
                // Some devices also wake the device when plugged or unplugged because
                // they don't have a charging LED.
                final long now = SystemClock.uptimeMillis();
                if (shouldWakeUpWhenPluggedOrUnpluggedLocked(wasPowered, oldPlugType,
                        dockedOnWirelessCharger)) {
                    wakeUpNoUpdateLocked(now, "android.server.power:POWER", Process.SYSTEM_UID,
                            mContext.getOpPackageName(), Process.SYSTEM_UID);
                }
                userActivityNoUpdateLocked(
                        now, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);


                // Tell the notifier whether wireless charging has started so that
                // it can provide feedback to the user.
                if (dockedOnWirelessCharger) {//        
                    mNotifier.onWirelessChargingStarted();
                }
            }


            if (wasPowered != mIsPowered || oldLevelLow != mBatteryLevelLow) {
                if (oldLevelLow != mBatteryLevelLow && !mBatteryLevelLow) {
                    if (DEBUG_SPEW) {
                        Slog.d(TAG, "updateIsPoweredLocked: resetting low power snooze");
                    }
                    mAutoLowPowerModeSnoozing = false;
                }
                updateLowPowerModeLocked();//        
            }
        }
    }

updateStayOnLocked 
充電しているかどうか、画面の明るさなど、携帯電話のある状態を表すと理解しています.
    private void updateStayOnLocked(int dirty) {
        if ((dirty & (DIRTY_BATTERY_STATE | DIRTY_SETTINGS)) != 0) {// dirty              
            final boolean wasStayOn = mStayOn;
            if (mStayOnWhilePluggedInSetting != 0//         ,                 
                    && !isMaximumScreenOffTimeoutFromDeviceAdminEnforcedLocked()) {
                //     mMaximumScreenOffTimeoutFromDeviceAdmin      .
                mStayOn = mBatteryManagerInternal.isPowered(mStayOnWhilePluggedInSetting);//         
            } else {
                mStayOn = false;
            }


            if (mStayOn != wasStayOn) {
                mDirty |= DIRTY_STAY_ON;
            }
        }
    }

 updateScreenBrightnessBoostLocked(mDirty);//画面の明るさの状態を更新
以下の論理は、現在の画面が最も明るい状態であるか否かを判断し、現在の携帯電話の状態が最も明るい状態であれば、遅延メッセージを送信し、後で再度判断すると理解できる.
そうでない場合は、次のmScreenBrightness BoostInProgressをfalseに設定し、mNotifer.onScreenBrightness BoostChanged()に移動します.画面の状態変化を設定する
    private void updateScreenBrightnessBoostLocked(int dirty) {
        if ((dirty & DIRTY_SCREEN_BRIGHTNESS_BOOST) != 0) {
            if (mScreenBrightnessBoostInProgress) {//             
                final long now = SystemClock.uptimeMillis();
                mHandler.removeMessages(MSG_SCREEN_BRIGHTNESS_BOOST_TIMEOUT);
                if (mLastScreenBrightnessBoostTime > mLastSleepTime) {//                  
                    final long boostTimeout = mLastScreenBrightnessBoostTime +
                            SCREEN_BRIGHTNESS_BOOST_TIMEOUT;
                    if (boostTimeout > now) {
                        Message msg = mHandler.obtainMessage(MSG_SCREEN_BRIGHTNESS_BOOST_TIMEOUT);//         ,               ,      DIRTY_SCREEN_BRIGHTNESS_BOOST ,           
                        msg.setAsynchronous(true);
                        mHandler.sendMessageAtTime(msg, boostTimeout);
                        return;
                    }
                }
                mScreenBrightnessBoostInProgress = false;//       ,                 false
                mNotifier.onScreenBrightnessBoostChanged();
                userActivityNoUpdateLocked(now,
                        PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, Process.SYSTEM_UID);
            }
        }
    }

updateWakeLockSummaryLocked  
//PowerManagerServiceのWackLockオブジェクトのタイプに基づいて、最終的なタイプのセットを計算します.
    private void updateWakeLockSummaryLocked(int dirty) {
        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_WAKEFULNESS)) != 0) {
            mWakeLockSummary = 0;

            final int numWakeLocks = mWakeLocks.size();
            for (int i = 0; i < numWakeLocks; i++) {
                final WakeLock wakeLock = mWakeLocks.get(i);
                switch (wakeLock.mFlags & PowerManager.WAKE_LOCK_LEVEL_MASK) {//   wakelock flag,mWakeLockSummary      
                    case PowerManager.PARTIAL_WAKE_LOCK://   CPU  ,           
                        if (!wakeLock.mDisabled) {
                            // We only respect this if the wake lock is not disabled.
                            mWakeLockSummary |= WAKE_LOCK_CPU;
                        }
                        break;
                    case PowerManager.FULL_WAKE_LOCK://CPU,             
                        mWakeLockSummary |= WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_BUTTON_BRIGHT;
                        break;
                    case PowerManager.SCREEN_BRIGHT_WAKE_LOCK://CPU        ,      
                        mWakeLockSummary |= WAKE_LOCK_SCREEN_BRIGHT;
                        break;
                    case PowerManager.SCREEN_DIM_WAKE_LOCK://CPU        ,      ,  CPU         
                        mWakeLockSummary |= WAKE_LOCK_SCREEN_DIM;
                        break;
                    case PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK://                
                        mWakeLockSummary |= WAKE_LOCK_PROXIMITY_SCREEN_OFF;
                        break;
                    case PowerManager.DOZE_WAKE_LOCK://        doze  
                        mWakeLockSummary |= WAKE_LOCK_DOZE;
                        break;
                    case PowerManager.DRAW_WAKE_LOCK://        DRAW  
                        mWakeLockSummary |= WAKE_LOCK_DRAW;
                        break;
                }
            }

            // Cancel wake locks that make no sense based on the current state.
            if (mWakefulness != WAKEFULNESS_DOZING) {
                mWakeLockSummary &= ~(WAKE_LOCK_DOZE | WAKE_LOCK_DRAW);//        ,      mWakeLockSummary,    
            }
            if (mWakefulness == WAKEFULNESS_ASLEEP
                    || (mWakeLockSummary & WAKE_LOCK_DOZE) != 0) {
                mWakeLockSummary &= ~(WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_SCREEN_DIM
                        | WAKE_LOCK_BUTTON_BRIGHT);
                if (mWakefulness == WAKEFULNESS_ASLEEP) {
                    /* Power Key Force Wakeup to Keep Proximity Wakelock */
                    // mWakeLockSummary &= ~WAKE_LOCK_PROXIMITY_SCREEN_OFF;
                }
            }

            // Infer implied wake locks where necessary based on the current state.
            if ((mWakeLockSummary & (WAKE_LOCK_SCREEN_BRIGHT | WAKE_LOCK_SCREEN_DIM)) != 0) {//      ,cpu     
                if (mWakefulness == WAKEFULNESS_AWAKE) {
                    mWakeLockSummary |= WAKE_LOCK_CPU | WAKE_LOCK_STAY_AWAKE;
                } else if (mWakefulness == WAKEFULNESS_DREAMING) {
                    mWakeLockSummary |= WAKE_LOCK_CPU;
                }
            }
            if ((mWakeLockSummary & WAKE_LOCK_DRAW) != 0) {
                mWakeLockSummary |= WAKE_LOCK_CPU;
            }

            if (DEBUG_SPEW) {
                Slog.d(TAG, "updateWakeLockSummaryLocked: mWakefulness="
                        + PowerManagerInternal.wakefulnessToString(mWakefulness)
                        + ", mWakeLockSummary=0x" + Integer.toHexString(mWakeLockSummary));
            }
        }
    }


updateUserActivitySummaryLocked();//最後にuserActivityが呼び出された時刻を判断し、画面の状態を表す変数mUserActivity Summaryの値をSCREEN_に設定できるかどうかを計算します.STATE_DIM(暗くなる)またはSCREEN_STATE_OFF(OFF)
メモuserActivityユーザープロセスがPowerManagerServiceに現在のユーザーがスリープに影響する時間を報告するために使用
    /**
     * Updates the value of mUserActivitySummary to summarize the user requested
     * state of the system such as whether the screen should be bright or dim.
     * Note that user activity is ignored when the system is asleep.
     *
     * This function must have no other side-effects.
     */
    private void updateUserActivitySummaryLocked(long now, int dirty) {
        // Update the status of the user activity timeout timer.
        if ((dirty & (DIRTY_WAKE_LOCKS | DIRTY_USER_ACTIVITY
                | DIRTY_WAKEFULNESS | DIRTY_SETTINGS)) != 0) {
            mHandler.removeMessages(MSG_USER_ACTIVITY_TIMEOUT);
            Slog.d(TAG+"zewei","updateUserActivitySummaryLocked" + "start");
            long nextTimeout = 0;
            /*   awake dreaming dozing,  mUserActivitySummary = 0*/
            if (mWakefulness == WAKEFULNESS_AWAKE
                    || mWakefulness == WAKEFULNESS_DREAMING
                    || mWakefulness == WAKEFULNESS_DOZING) {
                final int sleepTimeout = getSleepTimeoutLocked();/*    */
                final int screenOffTimeout = getScreenOffTimeoutLocked(sleepTimeout);//   timeout
                final int screenDimDuration = getScreenDimDurationLocked(screenOffTimeout);//       timeout
                final int screenButtonLightDuration = getButtonLightDurationLocked(screenOffTimeout);
                Slog.d(TAG+"zewei","updateUserActivitySummaryLocked" + "mWakefulness == WAKEFULNESS_AWAKE || mWakefulness == WAKEFULNESS_DREAMING || mWakefulness == WAKEFULNESS_DOZING  wwwww  "
+ "sleepTimeout == " + sleepTimeout +"   " + "screenOffTimeout == " + screenOffTimeout + "   " + "screenDimDuration ==" + screenDimDuration + "   " + "screenButtonLightDuration == " + screenButtonLightDuration);
                mUserActivitySummary = 0;
                if (mLastUserActivityTime >= mLastWakeTime) {//userActivity time         
                    if ( (mLastUserActivityButtonTime >= mLastWakeTime) && (now < mLastUserActivityButtonTime + screenButtonLightDuration) ) {
                        mUserActivitySummary |= USER_ACTIVITY_BUTTON_BRIGHT;
                        mUserActivitySummary |= USER_ACTIVITY_SCREEN_BRIGHT;
                        nextTimeout = mLastUserActivityButtonTime + screenButtonLightDuration;
                        Slog.d(TAG+"zewei","updateUserActivitySummaryLocked" +"(mLastUserActivityButtonTime >= mLastWakeTime) && (now < mLastUserActivityButtonTime + screenButtonLightDuration) wwwww  "
+ "nextTimeout == " + nextTimeout);
                    } else if (now < mLastUserActivityTime + screenOffTimeout - screenDimDuration) {
                        nextTimeout = mLastUserActivityTime + screenOffTimeout - screenDimDuration;//                                  
                        mUserActivitySummary |= USER_ACTIVITY_SCREEN_BRIGHT;
                        Slog.d(TAG+"zewei","updateUserActivitySummaryLocked" +"now < mLastUserActivityTime + screenOffTimeout - screenDimDuration  wwwww "
+ "nextTimeout == " + nextTimeout);
                    } else {
                        nextTimeout = mLastUserActivityTime + screenOffTimeout;//                    
                        Slog.d(TAG+"zewei","else wwwww  "
+ "nextTimeout == " + nextTimeout);
                        if (now < nextTimeout) {
                            mUserActivitySummary |= USER_ACTIVITY_SCREEN_DIM;
                            Slog.d(TAG+"zewei","mLastUserActivityTime >= mLastWakeTime wwwww");
                        }
                    }
                }
                if (mUserActivitySummary == 0
                        && mLastUserActivityTimeNoChangeLights >= mLastWakeTime) {
                    nextTimeout = mLastUserActivityTimeNoChangeLights + screenOffTimeout;
                    Slog.d(TAG+"zewei","mUserActivitySummary == 0&& mLastUserActivityTimeNoChangeLights >= mLastWakeTime wwwww " + "nextTimeout == " + nextTimeout);
                    if (now < nextTimeout) {
                    	  Slog.d(TAG+"zewei","mUserActivitySummary == 0&& mLastUserActivityTimeNoChangeLights >= mLastWakeTime" + "now < nextTimeout  wwwww ");
                        if (mDisplayPowerRequest.policy == DisplayPowerRequest.POLICY_BRIGHT) {
                            mUserActivitySummary = USER_ACTIVITY_SCREEN_BRIGHT;
                        } else if (mDisplayPowerRequest.policy == DisplayPowerRequest.POLICY_DIM) {
                            mUserActivitySummary = USER_ACTIVITY_SCREEN_DIM;
                        }
                    }
                }
                if (mUserActivitySummary == 0) {
                	  Slog.d(TAG+"zewei","mUserActivitySummary == 0  wwwww ");
                    if (sleepTimeout >= 0) {
                        final long anyUserActivity = Math.max(mLastUserActivityTime,
                                mLastUserActivityTimeNoChangeLights);
                        if (anyUserActivity >= mLastWakeTime) {
                            nextTimeout = anyUserActivity + sleepTimeout;
                            if (now < nextTimeout) {
                                mUserActivitySummary = USER_ACTIVITY_SCREEN_DREAM;
                            }
                        }
                    } else {
                        mUserActivitySummary = USER_ACTIVITY_SCREEN_DREAM;
                        nextTimeout = -1;//   -1,          
                        Slog.d(TAG+"zewei","mUserActivitySummary == 0  wwwww " + "nextTimeout == " + nextTimeout);
                    }
                }
                if (mUserActivitySummary != 0 && nextTimeout >= 0) {
                	Slog.d(TAG+"zewei","mUserActivitySummary != 0 && nextTimeout >= 0  wwwww ");
                    Message msg = mHandler.obtainMessage(MSG_USER_ACTIVITY_TIMEOUT);
                    msg.setAsynchronous(true);
                    mHandler.sendMessageAtTime(msg, nextTimeout);//     timeout         ,        
                }
            } else {
                mUserActivitySummary = 0;
            }

            if (DEBUG_SPEW) {
                Slog.d(TAG, "updateUserActivitySummaryLocked: mWakefulness="
                        + PowerManagerInternal.wakefulnessToString(mWakefulness)
                        + ", mUserActivitySummary=0x" + Integer.toHexString(mUserActivitySummary)
                        + ", nextTimeout=" + TimeUtils.formatUptime(nextTimeout));
            }
        }
    }

 updateDreamLocked(dirtyPhase2, displayBecameReady);//スクリーンセーバーを起動するかどうかを判断する
  private void updateDreamLocked(int dirty, boolean displayBecameReady) {
        if ((dirty & (DIRTY_WAKEFULNESS
                | DIRTY_USER_ACTIVITY
                | DIRTY_WAKE_LOCKS
                | DIRTY_BOOT_COMPLETED
                | DIRTY_BOOT_IPO
                | DIRTY_SETTINGS
                | DIRTY_IS_POWERED
                | DIRTY_STAY_ON
                | DIRTY_SD_STATE
                | DIRTY_PROXIMITY_POSITIVE
                | DIRTY_BATTERY_STATE)) != 0 || displayBecameReady) {
            if (mDisplayReady) {
                scheduleSandmanLocked();
            }
        }
    }

Step 4:
   frameworks\base\services\core\java\com\android\server\power\PowerManagerService.java
     updateSuspendBlockerLocked();//sys/powerにデータを格納する
    private void updateSuspendBlockerLocked() {
        final boolean needWakeLockSuspendBlocker = ((mWakeLockSummary & WAKE_LOCK_CPU) != 0);// cpu     
        final boolean needDisplaySuspendBlocker = needDisplaySuspendBlockerLocked();//  Display  ,   Display  
        final boolean autoSuspend = !needDisplaySuspendBlocker;
        final boolean interactive = mDisplayPowerRequest.isBrightOrDim();


        // Disable auto-suspend if needed.
        // FIXME We should consider just leaving auto-suspend enabled forever since
        // we already hold the necessary wakelocks.
        if (!autoSuspend && mDecoupleHalAutoSuspendModeFromDisplayConfig) {
            setHalAutoSuspendModeLocked(false);//  JNI
        }


        // First acquire suspend blockers if needed.、
        //      ,     wak_lock   
        if (needWakeLockSuspendBlocker && !mHoldingWakeLockSuspendBlocker) {
            mWakeLockSuspendBlocker.acquire();
            mHoldingWakeLockSuspendBlocker = true;
        }
        //          ,     wak_lock   
        if (needDisplaySuspendBlocker && !mHoldingDisplaySuspendBlocker) {
            mDisplaySuspendBlocker.acquire();
            mHoldingDisplaySuspendBlocker = true;
        }


        // Inform the power HAL about interactive mode.
        // Although we could set interactive strictly based on the wakefulness
        // as reported by isInteractive(), it is actually more desirable to track
        // the display policy state instead so that the interactive state observed
        // by the HAL more accurately tracks transitions between AWAKE and DOZING.
        // Refer to getDesiredScreenPolicyLocked() for details.
        if (mDecoupleHalInteractiveModeFromDisplayConfig) {
            // When becoming non-interactive, we want to defer sending this signal
            // until the display is actually ready so that all transitions have
            // completed.  This is probably a good sign that things have gotten
            // too tangled over here...
            if (interactive || mDisplayReady) {
                setHalInteractiveModeLocked(interactive);
            }
        }


        // Then release suspend blockers if needed.
        //      ,         
        if (!needWakeLockSuspendBlocker && mHoldingWakeLockSuspendBlocker) {
            mWakeLockSuspendBlocker.release();
            mHoldingWakeLockSuspendBlocker = false;
        }
        //           ,         
        if (!needDisplaySuspendBlocker && mHoldingDisplaySuspendBlocker) {
            mDisplaySuspendBlocker.release();
            mHoldingDisplaySuspendBlocker = false;
        }


        // Enable auto-suspend if needed.
        if (autoSuspend && mDecoupleHalAutoSuspendModeFromDisplayConfig) {
            setHalAutoSuspendModeLocked(true);
        }
    }

Step 4:
   frameworks\base\services\core\java\com\android\server\power\PowerManagerService.java     次にacquireとreleaseの方法の具体的な状況を見てみましょう
        @Override
        public void acquire() {
            synchronized (this) {
                mReferenceCount += 1;
                if (mReferenceCount == 1) {
                    if (DEBUG_SPEW) {
                        Slog.d(TAG, "Acquiring suspend blocker \"" + mName + "\".");
                    }
                    Trace.asyncTraceBegin(Trace.TRACE_TAG_POWER, mTraceName, 0);
                    nativeAcquireSuspendBlocker(mName);
                }
            }
        }


        @Override
        public void release() {
            synchronized (this) {
                mReferenceCount -= 1;
                if (mReferenceCount == 0) {
                    if (DEBUG_SPEW) {
                        Slog.d(TAG, "Releasing suspend blocker \"" + mName + "\".");
                    }
                    nativeReleaseSuspendBlocker(mName);
                    Trace.asyncTraceEnd(Trace.TRACE_TAG_POWER, mTraceName, 0);
                } else if (mReferenceCount < 0) {
                    Slog.wtf(TAG, "Suspend blocker \"" + mName
                            + "\" was released without being acquired!", new Throwable());
                    mReferenceCount = 0;
                }
            }
        }

Step 5:
   frameworks\base\services\core\jni\com_android_server_power_PowerManagerService.cpp
   次に見てみましょう
   nativeReleaseSuspendBlockerのJNI層での実装
   
static void nativeAcquireSuspendBlocker(JNIEnv *env, jclass /* clazz */, jstring nameStr) {
    ScopedUtfChars name(env, nameStr);
    acquire_wake_lock(PARTIAL_WAKE_LOCK, name.c_str());
}

static void nativeReleaseSuspendBlocker(JNIEnv *env, jclass /* clazz */, jstring nameStr) {
    ScopedUtfChars name(env, nameStr);
    release_wake_lock(name.c_str());
}

Step 6:    hardware\libhardware_legacy\power\power.c
   次に見てみましょう
   HAL層はどのように数値を書きます
const char * const OLD_PATHS[] = {
    "/sys/android_power/acquire_partial_wake_lock",
    "/sys/android_power/release_wake_lock",
};

const char * const NEW_PATHS[] = {
    "/sys/power/wake_lock",
    "/sys/power/wake_unlock",
};

...
initialize_fds(void)
{
    // XXX: should be this:
    //pthread_once(&g_initialized, open_file_descriptors);
    // XXX: not this:
    if (g_initialized == 0) {
        if(open_file_descriptors(NEW_PATHS) < 0)
            open_file_descriptors(OLD_PATHS);
        g_initialized = 1;
    }
}

int
acquire_wake_lock(int lock, const char* id)
{
    initialize_fds();

//    ALOGI("acquire_wake_lock lock=%d id='%s'
", lock, id); if (g_error) return -g_error; int fd; if (lock == PARTIAL_WAKE_LOCK) { fd = g_fds[ACQUIRE_PARTIAL_WAKE_LOCK]; } else { return -EINVAL; } return write(fd, id, strlen(id)); } int release_wake_lock(const char* id) { initialize_fds(); // ALOGI("release_wake_lock id='%s'
", id); if (g_error) return -g_error; ssize_t len = write(g_fds[RELEASE_WAKE_LOCK], id, strlen(id)); return len >= 0; }

Step 7:
kernel層とHAL層がどのように相互作用するかについては、こちらでは詳しく分析していませんが、コード情報を検索することで基本的にはここまでwacklockを処理していることがわかりました.
    kernel-3.18\kernel\power\wakelock.c
int pm_wake_lock(const char *buf)
{
	const char *str = buf;
	struct wakelock *wl;
	u64 timeout_ns = 0;
	size_t len;
	int ret = 0;

	if (!capable(CAP_BLOCK_SUSPEND))
		return -EPERM;

	while (*str && !isspace(*str))
		str++;

	len = str - buf;
	if (!len)
		return -EINVAL;

	if (*str && *str != '
') { /* Find out if there's a valid timeout string appended. */ ret = kstrtou64(skip_spaces(str), 10, &timeout_ns); if (ret) return -EINVAL; } mutex_lock(&wakelocks_lock); wl = wakelock_lookup_add(buf, len, true); if (IS_ERR(wl)) { ret = PTR_ERR(wl); goto out; } if (timeout_ns) { u64 timeout_ms = timeout_ns + NSEC_PER_MSEC - 1; do_div(timeout_ms, NSEC_PER_MSEC); __pm_wakeup_event(&wl->ws, timeout_ms); } else { __pm_stay_awake(&wl->ws); } wakelocks_lru_most_recent(wl); out: mutex_unlock(&wakelocks_lock); return ret; } int pm_wake_unlock(const char *buf) { struct wakelock *wl; size_t len; int ret = 0; if (!capable(CAP_BLOCK_SUSPEND)) return -EPERM; len = strlen(buf); if (!len) return -EINVAL; if (buf[len-1] == '
') len--; if (!len) return -EINVAL; mutex_lock(&wakelocks_lock); wl = wakelock_lookup_add(buf, len, false); if (IS_ERR(wl)) { ret = PTR_ERR(wl); goto out; } __pm_relax(&wl->ws); wakelocks_lru_most_recent(wl); wakelocks_gc(); out: mutex_unlock(&wakelocks_lock); return ret; }