1 /* 2 * Copyright (C) 2024 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 17 #ifndef _DISPLAY_TE2_MANAGER_H_ 18 #define _DISPLAY_TE2_MANAGER_H_ 19 20 #include "ExynosDisplay.h" 21 #include "ExynosHWCHelper.h" 22 23 enum class ProximitySensorState : uint32_t { 24 NONE = 0, 25 ACTIVE, 26 INACTIVE, 27 }; 28 29 // TODO: Rename this and integrate with refresh rate throttler related features into this class. 30 class DisplayTe2Manager : public RefreshRateChangeListener { 31 public: 32 DisplayTe2Manager(ExynosDisplay* display, int32_t panelIndex, int fixedTe2DefaultRateHz); 33 ~DisplayTe2Manager() = default; 34 35 // Set the rate while option is fixed TE2. This should be set by the sensor. 36 int32_t setFixedTe2Rate(int targetTe2RateHz); 37 // Set the rate while option is changeable TE2. This should be set by the composer 38 // while the display state is idle or active. 39 int32_t setChangeableTe2Rate(int targetTe2RateHz); 40 // Update TE2 option to either fixed or changeable according to the proximity sensor state. 41 // Ideally we should use changeable TE2 if the proximity sensor is active. Also set the min 42 // refresh rate of fixed TE2. It equals to the refresh rate while display is idle after 43 // switching to changeable TE2, and we can use it for the notification of refresh rate 44 // change. 45 void updateTe2OptionForProximity(bool proximityActive, int minRefreshRate, bool dozeMode); isOptionFixedTe2()46 bool isOptionFixedTe2() { return mIsOptionFixedTe2; } 47 48 // By default we will continue the TE2 setting after entering doze mode. The ALSP may not 49 // work properly if it's changeable TE2 with lower refresh rates, e.g. 1Hz. To avoid this 50 // problem, we should update the setting to fixed TE2 no matter the proximity sensor is 51 // active or not. 52 void updateTe2ForDozeMode(); 53 // The TE2 might be enforced to different settings after entering doze mode. We should 54 // restore the previous settings to keep the request from ALSP. 55 void restoreTe2FromDozeMode(); 56 57 // Handle the notifications while the proximity sensor state is changed. 58 void handleProximitySensorStateChange(bool active); 59 60 void dump(String8& result) const; 61 62 private: 63 static constexpr const char* kTe2RateFileNode = 64 "/sys/devices/platform/exynos-drm/%s-panel/te2_rate_hz"; 65 static constexpr const char* kTe2OptionFileNode = 66 "/sys/devices/platform/exynos-drm/%s-panel/te2_option"; 67 getPanelString()68 const char* getPanelString() { 69 return (mPanelIndex == 0 ? "primary" : mPanelIndex == 1 ? "secondary" : "unknown"); 70 } 71 getPanelTe2RatePath()72 const String8 getPanelTe2RatePath() { 73 return String8::format(kTe2RateFileNode, getPanelString()); 74 } 75 getPanelTe2OptionPath()76 const String8 getPanelTe2OptionPath() { 77 return String8::format(kTe2OptionFileNode, getPanelString()); 78 } 79 80 void setTe2Option(bool fixedTe2); 81 int32_t setTe2Rate(int targetTe2RateHz); 82 int32_t setFixedTe2RateInternal(int targetTe2RateHz, bool enforce); 83 84 virtual void onRefreshRateChange(int refreshRate) override; 85 86 ExynosDisplay* mDisplay; 87 int32_t mPanelIndex; 88 // The min refresh rate of fixed TE2. For the refresh rates lower than this, the changeable 89 // TE2 should be used. 90 int mMinRefreshRateForFixedTe2; 91 int mFixedTe2RateHz; 92 // True when the current option is fixed TE2, otherwise it's changeable TE2. 93 bool mIsOptionFixedTe2; 94 // True when the refresh rate change listener of VariableRefreshRateController is 95 // registered successfully. Thus we can receive the notification of refresh rate change 96 // for changeable TE2 usage. 97 bool mRefreshRateChangeListenerRegistered; 98 99 // Indicates that TE2 was changed from changeable to fixed after entering doze mode. We 100 // should restore the setting after exiting doze mode. 101 bool mPendingOptionChangeableTe2; 102 // After entering doze mode, the TE2 rate will be enforced to mFixedTe2RateForDozeMode. 103 // We should save the previous rate as a pending value and restore it after exiting doze 104 // mode. 105 int mPendingFixedTe2Rate; 106 // After entering doze mode, the TE2 will be enforced to fixed 30Hz. 107 const int kFixedTe2RateForDozeMode = 30; 108 109 Mutex mTe2Mutex; 110 111 class ProximitySensorStateNotifierWorker : public Worker { 112 public: 113 explicit ProximitySensorStateNotifierWorker(DisplayTe2Manager* te2Manager); 114 ~ProximitySensorStateNotifierWorker(); 115 116 void onStateChanged(bool active); 117 118 protected: 119 void Routine() override; 120 121 private: 122 static constexpr uint32_t kDebounceTimeMs = 500U; 123 124 DisplayTe2Manager* mTe2Manager; 125 bool mIsStateActive; 126 bool mReceivedFirstStateAfterTimeout; 127 enum ProximitySensorState mPendingState; 128 }; 129 130 std::unique_ptr<ProximitySensorStateNotifierWorker> mProximitySensorStateNotifierWorker; 131 }; 132 133 #endif // _DISPLAY_TE2_MANAGER_H_ 134