• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2019 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 #define ATRACE_TAG (ATRACE_TAG_GRAPHICS | ATRACE_TAG_HAL)
18 
19 #include "ExynosPrimaryDisplayModule.h"
20 
21 #include <android-base/file.h>
22 #include <json/reader.h>
23 #include <json/value.h>
24 
25 #include <cmath>
26 
27 #include "BrightnessController.h"
28 #include "ExynosDisplayDrmInterfaceModule.h"
29 #include "ExynosHWCDebug.h"
30 
31 #ifdef FORCE_GPU_COMPOSITION
32 extern exynos_hwc_control exynosHWCControl;
33 #endif
34 
35 using namespace gs101;
36 
getMPPTypeFromDPPChannel(uint32_t channel)37 mpp_phycal_type_t getMPPTypeFromDPPChannel(uint32_t channel) {
38 
39     for (int i=0; i < MAX_DECON_DMA_TYPE; i++){
40         if(idma_channel_map[i].channel == channel)
41             return idma_channel_map[i].type;
42     }
43 
44     return MPP_P_TYPE_MAX;
45 }
46 
ExynosPrimaryDisplayModule(uint32_t index,ExynosDevice * device,const std::string & displayName)47 ExynosPrimaryDisplayModule::ExynosPrimaryDisplayModule(uint32_t index, ExynosDevice* device,
48                                                        const std::string& displayName)
49       : ExynosPrimaryDisplay(index, device, displayName), mAtcInit(false) {
50 #ifdef FORCE_GPU_COMPOSITION
51     exynosHWCControl.forceGpu = true;
52 #endif
53     mColorManager = std::make_unique<ColorManager>(this, static_cast<ExynosDeviceModule*>(device));
54 }
55 
~ExynosPrimaryDisplayModule()56 ExynosPrimaryDisplayModule::~ExynosPrimaryDisplayModule () {
57 }
58 
usePreDefinedWindow(bool use)59 void ExynosPrimaryDisplayModule::usePreDefinedWindow(bool use)
60 {
61 #ifdef FIX_BASE_WINDOW_INDEX
62     /* Use fixed base window index */
63     mBaseWindowIndex = FIX_BASE_WINDOW_INDEX;
64     return;
65 #endif
66 
67     if (use) {
68         mBaseWindowIndex = PRIMARY_DISP_BASE_WIN[mDevice->mDisplayMode];
69         mMaxWindowNum = mDisplayInterface->getMaxWindowNum() - PRIMARY_DISP_BASE_WIN[mDevice->mDisplayMode];
70     } else {
71         mBaseWindowIndex = 0;
72         mMaxWindowNum = mDisplayInterface->getMaxWindowNum();
73     }
74 }
75 
validateWinConfigData()76 int32_t ExynosPrimaryDisplayModule::validateWinConfigData()
77 {
78     bool flagValidConfig = true;
79 
80     if (ExynosDisplay::validateWinConfigData() != NO_ERROR)
81         flagValidConfig = false;
82 
83     for (size_t i = 0; i < mDpuData.configs.size(); i++) {
84         struct exynos_win_config_data &config = mDpuData.configs[i];
85         if (config.state == config.WIN_STATE_BUFFER) {
86             bool configInvalid = false;
87             uint32_t mppType = config.assignedMPP->mPhysicalType;
88             if ((config.src.w != config.dst.w) ||
89                 (config.src.h != config.dst.h)) {
90                 if ((mppType == MPP_DPP_GF) ||
91                     (mppType == MPP_DPP_VG) ||
92                     (mppType == MPP_DPP_VGF)) {
93                     DISPLAY_LOGE("WIN_CONFIG error: invalid assign id : "
94                             "%zu,  s_w : %d, d_w : %d, s_h : %d, d_h : %d, mppType : %d",
95                             i, config.src.w, config.dst.w, config.src.h, config.dst.h, mppType);
96                     configInvalid = true;
97                 }
98             }
99             if (configInvalid) {
100                 config.state = config.WIN_STATE_DISABLED;
101                 flagValidConfig = false;
102             }
103         }
104     }
105     if (flagValidConfig)
106         return NO_ERROR;
107     else
108         return -EINVAL;
109 }
110 
doPreProcessing()111 void ExynosPrimaryDisplayModule::doPreProcessing() {
112     ExynosDisplay::doPreProcessing();
113 
114     if (mDevice->checkNonInternalConnection()) {
115         mDisplayControl.adjustDisplayFrame = true;
116     } else {
117         mDisplayControl.adjustDisplayFrame = false;
118     }
119 }
120 
getColorModes(uint32_t * outNumModes,int32_t * outModes)121 int32_t ExynosPrimaryDisplayModule::getColorModes(
122         uint32_t* outNumModes, int32_t* outModes)
123 {
124     return mColorManager->getColorModes(outNumModes, outModes);
125 }
126 
setColorMode(int32_t mode)127 int32_t ExynosPrimaryDisplayModule::setColorMode(int32_t mode)
128 {
129     return mColorManager->setColorMode(mode);
130 }
131 
getRenderIntents(int32_t mode,uint32_t * outNumIntents,int32_t * outIntents)132 int32_t ExynosPrimaryDisplayModule::getRenderIntents(int32_t mode,
133         uint32_t* outNumIntents, int32_t* outIntents)
134 {
135     return mColorManager->getRenderIntents(mode, outNumIntents, outIntents);
136 }
137 
setColorModeWithRenderIntent(int32_t mode,int32_t intent)138 int32_t ExynosPrimaryDisplayModule::setColorModeWithRenderIntent(int32_t mode,
139         int32_t intent)
140 {
141     return mColorManager->setColorModeWithRenderIntent(mode, intent);
142 }
143 
setColorTransform(const float * matrix,int32_t hint)144 int32_t ExynosPrimaryDisplayModule::setColorTransform(
145         const float* matrix, int32_t hint)
146 {
147     return mColorManager->setColorTransform(matrix, hint);
148 }
149 
getClientTargetProperty(hwc_client_target_property_t * outClientTargetProperty,HwcDimmingStage * outDimmingStage)150 int32_t ExynosPrimaryDisplayModule::getClientTargetProperty(
151         hwc_client_target_property_t* outClientTargetProperty,
152         HwcDimmingStage *outDimmingStage) {
153     GsInterfaceType* displayColorInterface = getDisplayColorInterface();
154     if (displayColorInterface == nullptr) {
155         ALOGI("%s dc interface not created", __func__);
156         return ExynosDisplay::getClientTargetProperty(outClientTargetProperty);
157     }
158 
159     const DisplayType display = getDcDisplayType();
160     hwc::PixelFormat pixelFormat;
161     hwc::Dataspace dataspace;
162     bool dimming_linear;
163     if (!displayColorInterface->GetBlendingProperty(display, pixelFormat, dataspace,
164                                                     dimming_linear)) {
165         outClientTargetProperty->pixelFormat = toUnderlying(pixelFormat);
166         outClientTargetProperty->dataspace = toUnderlying(dataspace);
167         if (outDimmingStage != nullptr)
168             *outDimmingStage = dimming_linear
169                               ? HwcDimmingStage::DIMMING_LINEAR
170                               : HwcDimmingStage::DIMMING_OETF;
171 
172         return HWC2_ERROR_NONE;
173     }
174 
175     ALOGW("%s failed to get property of blending stage", __func__);
176     return ExynosDisplay::getClientTargetProperty(outClientTargetProperty);
177 }
178 
updateBrightnessTable()179 int32_t ExynosPrimaryDisplayModule::updateBrightnessTable() {
180     std::unique_ptr<const IBrightnessTable> table;
181     auto displayColorInterface = getDisplayColorInterface();
182     if (displayColorInterface == nullptr) {
183         ALOGE("%s displaycolor interface not available!", __func__);
184         return HWC2_ERROR_NO_RESOURCES;
185     }
186 
187     auto displayType = getDcDisplayType();
188     auto ret = displayColorInterface->GetBrightnessTable(displayType, table);
189     if (ret != android::OK) {
190         ALOGE("%s brightness table not available!", __func__);
191         return HWC2_ERROR_NO_RESOURCES;
192     }
193     // BrightnessController is not ready until this step
194     mBrightnessController->updateBrightnessTable(table);
195 
196     return HWC2_ERROR_NONE;
197 }
198 
deliverWinConfigData()199 int ExynosPrimaryDisplayModule::deliverWinConfigData()
200 {
201     int ret = 0;
202     ExynosDisplayDrmInterfaceModule *moduleDisplayInterface =
203         (ExynosDisplayDrmInterfaceModule*)(mDisplayInterface.get());
204     GsInterfaceType* displayColorInterface = getDisplayColorInterface();
205 
206     bool forceDisplayColorSetting = false;
207     if (!getDisplaySceneInfo().displaySettingDelivered || isForceColorUpdate())
208         forceDisplayColorSetting = true;
209 
210     setForceColorUpdate(false);
211 
212     if (displayColorInterface != nullptr) {
213         moduleDisplayInterface
214                 ->setColorSettingChanged(getDisplaySceneInfo().needDisplayColorSetting(),
215                                          forceDisplayColorSetting);
216     }
217 
218     checkAtcHdrMode();
219 
220     ret = ExynosDisplay::deliverWinConfigData();
221 
222     checkAtcAnimation();
223 
224     if (mDpuData.enable_readback &&
225        !mDpuData.readback_info.requested_from_service)
226         getDisplaySceneInfo().displaySettingDelivered = false;
227     else
228         getDisplaySceneInfo().displaySettingDelivered = true;
229 
230     return ret;
231 }
232 
updateColorConversionInfo()233 int32_t ExynosPrimaryDisplayModule::updateColorConversionInfo()
234 {
235     return mColorManager->updateColorConversionInfo();
236 }
237 
resetColorMappingInfo(ExynosMPPSource * mppSrc)238 int32_t ExynosPrimaryDisplayModule::resetColorMappingInfo(ExynosMPPSource* mppSrc) {
239     return mColorManager->resetColorMappingInfo(mppSrc);
240 }
241 
updatePresentColorConversionInfo()242 int32_t ExynosPrimaryDisplayModule::updatePresentColorConversionInfo()
243 {
244     int ret = NO_ERROR;
245     GsInterfaceType* displayColorInterface = getDisplayColorInterface();
246     if (displayColorInterface == nullptr) {
247         return ret;
248     }
249 
250     ExynosDisplayDrmInterfaceModule *moduleDisplayInterface =
251         (ExynosDisplayDrmInterfaceModule*)(mDisplayInterface.get());
252     auto refresh_rate = moduleDisplayInterface->getDesiredRefreshRate();
253     if (refresh_rate > 0) {
254         getDisplaySceneInfo().displayScene.refresh_rate = refresh_rate;
255     }
256     auto operation_rate = moduleDisplayInterface->getOperationRate();
257     if (operation_rate > 0) {
258         getDisplaySceneInfo().displayScene.operation_rate = static_cast<uint32_t>(operation_rate);
259     }
260 
261     getDisplaySceneInfo().displayScene.lhbm_on = mBrightnessController->isLhbmOn();
262     getDisplaySceneInfo().displayScene.dbv = mBrightnessController->getBrightnessLevel();
263     const DisplayType display = getDcDisplayType();
264     if ((ret = displayColorInterface->UpdatePresent(display, getDisplaySceneInfo().displayScene)) !=
265         0) {
266         DISPLAY_LOGE("Display Scene update error (%d)", ret);
267         return ret;
268     }
269 
270     return ret;
271 }
272 
getColorAdjustedDbv(uint32_t & dbv_adj)273 int32_t ExynosPrimaryDisplayModule::getColorAdjustedDbv(uint32_t &dbv_adj) {
274     GsInterfaceType* displayColorInterface = getDisplayColorInterface();
275     if (displayColorInterface == nullptr) {
276         return NO_ERROR;
277     }
278 
279     const DisplayType display = getDcDisplayType();
280     dbv_adj = displayColorInterface->GetPipelineData(display)->Panel().GetAdjustedBrightnessLevel();
281     return NO_ERROR;
282 }
283 
parseAtcProfile()284 bool ExynosPrimaryDisplayModule::parseAtcProfile() {
285     Json::Value root;
286     Json::CharReaderBuilder reader_builder;
287     std::unique_ptr<Json::CharReader> reader(reader_builder.newCharReader());
288     std::string atc_profile;
289 
290     if (!android::base::ReadFileToString(kAtcProfilePath, &atc_profile)) {
291         atc_profile = kAtcJsonRaw;
292         ALOGI("Use default atc profile file");
293     }
294 
295     if (!reader->parse(atc_profile.c_str(), atc_profile.c_str() + atc_profile.size(), &root,
296                        nullptr)) {
297         ALOGE("Failed to parse atc profile file");
298         return false;
299     }
300 
301     ALOGI("Atc Profile version = %s", root[kAtcProfileVersionStr].asString().c_str());
302     Json::Value nodes = root[kAtcProfileModesStr];
303     atc_mode mode;
304 
305     for (Json::Value::ArrayIndex i = 0; i < nodes.size(); ++i) {
306         std::string name = nodes[i][kAtcProfileModeNameStr].asString();
307 
308         if (nodes[i][kAtcProfileLuxMapStr].size() != nodes[i][kAtcProfileAlMapStr].size() &&
309             nodes[i][kAtcProfileAlMapStr].size() != nodes[i][kAtcProfileStMapStr].size()) {
310             ALOGE("Atc profile is unavailable !");
311             return false;
312         }
313 
314         uint32_t map_cnt = nodes[i][kAtcProfileLuxMapStr].size();
315 
316         mode.lux_map.clear();
317         for (uint32_t index = 0; index < map_cnt; ++index) {
318             mode.lux_map.emplace_back(atc_lux_map{nodes[i][kAtcProfileLuxMapStr][index].asUInt(),
319                                                   nodes[i][kAtcProfileAlMapStr][index].asUInt(),
320                                                   nodes[i][kAtcProfileStMapStr][index].asUInt()});
321         }
322 
323         if (!nodes[i][kAtcProfileStUpStepStr].empty())
324             mode.st_up_step = nodes[i][kAtcProfileStUpStepStr].asUInt();
325         else
326             mode.st_up_step = kAtcStStep;
327 
328         if (!nodes[i][kAtcProfileStDownStepStr].empty())
329             mode.st_down_step = nodes[i][kAtcProfileStDownStepStr].asUInt();
330         else
331             mode.st_down_step = kAtcStStep;
332 
333         if (nodes[i][kAtcProfileSubSettingStr].size() != kAtcSubSetting.size()) return false;
334 
335         for (auto it = kAtcSubSetting.begin(); it != kAtcSubSetting.end(); it++) {
336             mode.sub_setting[it->first.c_str()] =
337                     nodes[i][kAtcProfileSubSettingStr][it->first.c_str()].asUInt();
338         }
339         auto ret = mAtcModeSetting.insert(std::make_pair(name.c_str(), mode));
340         if (ret.second == false) {
341             ALOGE("Atc mode %s is already existed!", ret.first->first.c_str());
342             return false;
343         }
344     }
345 
346     if (mAtcModeSetting.find(kAtcModeNormalStr) == mAtcModeSetting.end()) {
347         ALOGW("Failed to find atc normal mode");
348         return false;
349     }
350     return true;
351 }
352 
isLbeSupported()353 bool ExynosPrimaryDisplayModule::isLbeSupported() {
354     return mLbeSupported;
355 }
356 
initLbe()357 void ExynosPrimaryDisplayModule::initLbe() {
358     if (!parseAtcProfile()) {
359         ALOGD("Failed to parseAtcMode");
360         mAtcInit = false;
361         return;
362     }
363 
364     mAtcInit = true;
365     mAtcAmbientLight.node = String8::format(ATC_AMBIENT_LIGHT_FILE_NAME, mIndex);
366     mAtcAmbientLight.value.set_dirty();
367     mAtcStrength.node = String8::format(ATC_ST_FILE_NAME, mIndex);
368     mAtcStrength.value.set_dirty();
369     mAtcEnable.node = String8::format(ATC_ENABLE_FILE_NAME, mIndex);
370     mAtcEnable.value.set_dirty();
371 
372     for (auto it = kAtcSubSetting.begin(); it != kAtcSubSetting.end(); it++) {
373         mAtcSubSetting[it->first.c_str()].node = String8::format(it->second.c_str(), mIndex);
374         mAtcSubSetting[it->first.c_str()].value.set_dirty();
375     }
376     mLbeSupported = true;
377 }
378 
getAtcLuxMapIndex(std::vector<atc_lux_map> map,uint32_t lux)379 uint32_t ExynosPrimaryDisplayModule::getAtcLuxMapIndex(std::vector<atc_lux_map> map, uint32_t lux) {
380     uint32_t index = 0;
381     for (uint32_t i = 0; i < map.size(); i++) {
382         if (lux < map[i].lux) {
383             break;
384         }
385         index = i;
386     }
387 
388     return index;
389 }
390 
setAtcStrength(uint32_t strength)391 int32_t ExynosPrimaryDisplayModule::setAtcStrength(uint32_t strength) {
392     mAtcStrength.value.store(strength);
393     if (mAtcStrength.value.is_dirty()) {
394         if (writeIntToFile(mAtcStrength.node.c_str(), mAtcStrength.value.get()) != NO_ERROR) {
395             return -EPERM;
396         }
397         mAtcStrength.value.clear_dirty();
398     }
399     return NO_ERROR;
400 }
401 
setAtcAmbientLight(uint32_t ambient_light)402 int32_t ExynosPrimaryDisplayModule::setAtcAmbientLight(uint32_t ambient_light) {
403     mAtcAmbientLight.value.store(ambient_light);
404     if (mAtcAmbientLight.value.is_dirty()) {
405         if (writeIntToFile(mAtcAmbientLight.node.c_str(), mAtcAmbientLight.value.get()) != NO_ERROR)
406             return -EPERM;
407         mAtcAmbientLight.value.clear_dirty();
408     }
409 
410     return NO_ERROR;
411 }
412 
setAtcMode(std::string mode_name)413 int32_t ExynosPrimaryDisplayModule::setAtcMode(std::string mode_name) {
414     ATRACE_CALL();
415     auto mode_data = mAtcModeSetting.find(mode_name);
416     uint32_t ambient_light = 0;
417     uint32_t strength = 0;
418     bool enable = (!mode_name.empty()) && (mode_data != mAtcModeSetting.end());
419 
420     if (enable) {
421         atc_mode mode = mode_data->second;
422         for (auto it = kAtcSubSetting.begin(); it != kAtcSubSetting.end(); it++) {
423             mAtcSubSetting[it->first.c_str()].value.store(mode.sub_setting[it->first.c_str()]);
424             if (mAtcSubSetting[it->first.c_str()].value.is_dirty()) {
425                 if (writeIntToFile(mAtcSubSetting[it->first.c_str()].node.c_str(),
426                                    mAtcSubSetting[it->first.c_str()].value.get()) != NO_ERROR)
427                     return -EPERM;
428                 mAtcSubSetting[it->first.c_str()].value.clear_dirty();
429             }
430         }
431         mAtcStUpStep = mode.st_up_step;
432         mAtcStDownStep = mode.st_down_step;
433 
434         uint32_t index = getAtcLuxMapIndex(mode.lux_map, mCurrentLux);
435         ambient_light = mode.lux_map[index].al;
436         strength = mode.lux_map[index].st;
437     }
438 
439     if (setAtcAmbientLight(ambient_light) != NO_ERROR) {
440         ALOGE("Fail to set atc ambient light for %s mode", mode_name.c_str());
441         return -EPERM;
442     }
443 
444     if (setAtcStDimming(strength) != NO_ERROR) {
445         ALOGE("Fail to set atc st dimming for %s mode", mode_name.c_str());
446         return -EPERM;
447     }
448 
449     if (!enable && isInAtcAnimation()) {
450         mPendingAtcOff = true;
451     } else {
452         if (setAtcEnable(enable) != NO_ERROR) {
453             ALOGE("Fail to set atc enable = %d", enable);
454             return -EPERM;
455         }
456         mPendingAtcOff = false;
457     }
458 
459     mCurrentAtcModeName = enable ? mode_name : "NULL";
460     ALOGI("atc enable=%d (mode=%s, pending off=%s)", enable, mCurrentAtcModeName.c_str(),
461           mPendingAtcOff ? "true" : "false");
462     return NO_ERROR;
463 }
setLbeState(LbeState state)464 void ExynosPrimaryDisplayModule::setLbeState(LbeState state) {
465     if (!mAtcInit) return;
466 
467     std::string modeStr;
468     bool enhanced_hbm = false;
469     bool fullHdrLayer = isFullScreenHdrLayer();
470 
471     switch (state) {
472         case LbeState::OFF:
473             mCurrentLux = 0;
474             break;
475         case LbeState::NORMAL:
476             modeStr = kAtcModeNormalStr;
477             break;
478         case LbeState::HIGH_BRIGHTNESS:
479             modeStr = kAtcModeHbmStr;
480             break;
481         case LbeState::POWER_SAVE:
482             modeStr = kAtcModePowerSaveStr;
483             break;
484         case LbeState::HIGH_BRIGHTNESS_ENHANCE:
485             modeStr = kAtcModeHbmStr;
486             enhanced_hbm = true;
487             break;
488         default:
489             ALOGE("Lbe state not support");
490             return;
491     }
492 
493     if (fullHdrLayer && state != LbeState::OFF) checkAtcHdrMode();
494     else if (setAtcMode(modeStr) != NO_ERROR) return;
495 
496     mBrightnessController->processEnhancedHbm(enhanced_hbm);
497     mBrightnessController->setOutdoorVisibility(state);
498 
499     if (mCurrentLbeState != state) {
500         mCurrentLbeState = state;
501         mDevice->onRefresh(mDisplayId);
502     }
503     ALOGI("Lbe state %hhd", mCurrentLbeState);
504 }
505 
setLbeAmbientLight(int value)506 void ExynosPrimaryDisplayModule::setLbeAmbientLight(int value) {
507     if (!mAtcInit) return;
508 
509     auto it = mAtcModeSetting.find(mCurrentAtcModeName);
510     if (it == mAtcModeSetting.end()) {
511         ALOGE("Atc mode not found");
512         return;
513     }
514     atc_mode mode = it->second;
515 
516     uint32_t index = getAtcLuxMapIndex(mode.lux_map, value);
517     if (setAtcAmbientLight(mode.lux_map[index].al) != NO_ERROR) {
518         ALOGE("Failed to set atc ambient light");
519         return;
520     }
521 
522     if (setAtcStDimming(mode.lux_map[index].st) != NO_ERROR) {
523         ALOGE("Failed to set atc st dimming");
524         return;
525     }
526 
527     if (mAtcLuxMapIndex != index) {
528         mAtcLuxMapIndex = index;
529         mDevice->onRefresh(mDisplayId);
530     }
531     mCurrentLux = value;
532 }
533 
getLbeState()534 LbeState ExynosPrimaryDisplayModule::getLbeState() {
535     return mCurrentLbeState;
536 }
537 
getPanelCalibrationStatus()538 PanelCalibrationStatus ExynosPrimaryDisplayModule::getPanelCalibrationStatus() {
539     auto displayColorInterface = getDisplayColorInterface();
540     if (displayColorInterface == nullptr) {
541         return PanelCalibrationStatus::UNCALIBRATED;
542     }
543 
544     auto displayType = getDcDisplayType();
545     auto calibrationInfo = displayColorInterface->GetCalibrationInfo(displayType);
546 
547     if (calibrationInfo.factory_cal_loaded) {
548         return PanelCalibrationStatus::ORIGINAL;
549     } else if (calibrationInfo.golden_cal_loaded) {
550         return PanelCalibrationStatus::GOLDEN;
551     } else {
552         return PanelCalibrationStatus::UNCALIBRATED;
553     }
554 }
555 
setAtcStDimming(uint32_t value)556 int32_t ExynosPrimaryDisplayModule::setAtcStDimming(uint32_t value) {
557     Mutex::Autolock lock(mAtcStMutex);
558     int32_t strength = mAtcStrength.value.get();
559     if (mAtcStTarget != value) {
560         mAtcStTarget = value;
561         uint32_t step = mAtcStTarget > strength ? mAtcStUpStep : mAtcStDownStep;
562 
563         int diff = value - strength;
564         uint32_t count = (std::abs(diff) + step - 1) / step;
565         mAtcStStepCount = count;
566         ALOGI("setup atc st dimming=%d, count=%d, step=%d", value, count, step);
567     }
568 
569     if (mAtcStStepCount == 0 && !mAtcStrength.value.is_dirty()) return NO_ERROR;
570 
571     if ((strength + mAtcStUpStep) < mAtcStTarget) {
572         strength = strength + mAtcStUpStep;
573     } else if (strength > (mAtcStTarget + mAtcStDownStep)) {
574         strength = strength - mAtcStDownStep;
575     } else {
576         strength = mAtcStTarget;
577     }
578 
579     if (setAtcStrength(strength) != NO_ERROR) {
580         ALOGE("Failed to set atc st");
581         return -EPERM;
582     }
583 
584     if (mAtcStStepCount > 0) mAtcStStepCount--;
585     return NO_ERROR;
586 }
587 
setAtcEnable(bool enable)588 int32_t ExynosPrimaryDisplayModule::setAtcEnable(bool enable) {
589     mAtcEnable.value.store(enable);
590     if (mAtcEnable.value.is_dirty()) {
591         if (writeIntToFile(mAtcEnable.node.c_str(), enable) != NO_ERROR) return -EPERM;
592         mAtcEnable.value.clear_dirty();
593     }
594     return NO_ERROR;
595 }
596 
checkAtcAnimation()597 void ExynosPrimaryDisplayModule::checkAtcAnimation() {
598     if (!isInAtcAnimation()) return;
599 
600     if (setAtcStDimming(mAtcStTarget) != NO_ERROR) {
601         ALOGE("Failed to set atc st dimming");
602         return;
603     }
604 
605     if (mPendingAtcOff && mAtcStStepCount == 0) {
606         if (setAtcEnable(false) != NO_ERROR) {
607             ALOGE("Failed to set atc enable to off");
608             return;
609         }
610         mPendingAtcOff = false;
611         ALOGI("atc enable is off (pending off=false)");
612     }
613 
614     mDevice->onRefresh(mDisplayId);
615 }
616 
setPowerMode(int32_t mode)617 int32_t ExynosPrimaryDisplayModule::setPowerMode(int32_t mode) {
618     hwc2_power_mode_t prevPowerModeState = mPowerModeState.value_or(HWC2_POWER_MODE_OFF);
619     int32_t ret;
620 
621     ret = ExynosPrimaryDisplay::setPowerMode(mode);
622 
623     if ((ret == HWC2_ERROR_NONE) && isDisplaySwitched(mode, prevPowerModeState)) {
624         ExynosDeviceModule* device = static_cast<ExynosDeviceModule*>(mDevice);
625 
626         device->setActiveDisplay(mIndex);
627         setForceColorUpdate(true);
628     }
629     return ret;
630 }
631 
isDisplaySwitched(int32_t mode,int32_t prevMode)632 bool ExynosPrimaryDisplayModule::isDisplaySwitched(int32_t mode, int32_t prevMode) {
633     ExynosDeviceModule* device = static_cast<ExynosDeviceModule*>(mDevice);
634 
635     return (device->getActiveDisplay() != mIndex) && (prevMode == HWC_POWER_MODE_OFF) &&
636             (mode != HWC_POWER_MODE_OFF);
637 }
638 
checkAtcHdrMode()639 void ExynosPrimaryDisplayModule::checkAtcHdrMode() {
640     ATRACE_CALL();
641     if (!mAtcInit) return;
642 
643     auto it = mAtcModeSetting.find(kAtcModeHdrStr);
644     if (it == mAtcModeSetting.end()) {
645         return;
646     }
647 
648     bool hdrModeActive = (mCurrentAtcModeName == kAtcModeHdrStr);
649     bool fullHdrLayer = isFullScreenHdrLayer();
650 
651     if (fullHdrLayer) {
652         if (!hdrModeActive && (mCurrentLbeState != LbeState::OFF)) {
653             setAtcMode(kAtcModeHdrStr);
654             ALOGI("HdrLayer on to set atc hdr mode");
655         }
656     } else {
657         if (hdrModeActive) {
658             setLbeState(mCurrentLbeState);
659             ALOGI("HdrLayer off to restore Lbe State");
660         }
661     }
662 }
663 
isFullScreenHdrLayer()664 bool ExynosPrimaryDisplayModule::isFullScreenHdrLayer() {
665     return mBrightnessController->getHdrLayerState() == HdrLayerState::kHdrLarge;
666 }
667