• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2023 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "rs_screen_manager.h"
17 
18 #include "hgm_core.h"
19 #include "pipeline/rs_display_render_node.h"
20 #include "pipeline/rs_main_thread.h"
21 #include "pipeline/rs_hardware_thread.h"
22 #include "platform/common/rs_log.h"
23 #include "vsync_sampler.h"
24 
25 namespace OHOS {
26 namespace Rosen {
27 using namespace HiviewDFX;
28 namespace impl {
29 std::once_flag RSScreenManager::createFlag_;
30 sptr<OHOS::Rosen::RSScreenManager> RSScreenManager::instance_ = nullptr;
31 
GetInstance()32 sptr<OHOS::Rosen::RSScreenManager> RSScreenManager::GetInstance() noexcept
33 {
34     std::call_once(createFlag_, []() {
35         instance_ = new RSScreenManager();
36     });
37 
38     return instance_;
39 }
40 
RSScreenManager()41 RSScreenManager::RSScreenManager()
42 {
43 }
44 
~RSScreenManager()45 RSScreenManager::~RSScreenManager() noexcept
46 {
47 }
48 
Init()49 bool RSScreenManager::Init() noexcept
50 {
51     composer_ = HdiBackend::GetInstance();
52     if (composer_ == nullptr) {
53         RS_LOGE("RSScreenManager %s: Failed to get composer.", __func__);
54         return false;
55     }
56 
57     if (composer_->RegScreenHotplug(&RSScreenManager::OnHotPlug, this) != 0) {
58         RS_LOGE("RSScreenManager %s: Failed to register OnHotPlug Func to composer.", __func__);
59         return false;
60     }
61 
62     if (composer_->RegHwcDeadListener(&RSScreenManager::OnHwcDead, this) != 0) {
63         RS_LOGE("RSScreenManager %s: Failed to register OnHwcDead Func to composer.", __func__);
64         return false;
65     }
66 
67     // call ProcessScreenHotPlugEvents() for primary screen immediately in main thread.
68     ProcessScreenHotPlugEvents();
69     RS_LOGI("RSScreenManager Init succeed");
70     return true;
71 }
72 
OnHotPlug(std::shared_ptr<HdiOutput> & output,bool connected,void * data)73 void RSScreenManager::OnHotPlug(std::shared_ptr<HdiOutput> &output, bool connected, void *data)
74 {
75     if (output == nullptr) {
76         RS_LOGE("RSScreenManager %s: output is nullptr.", __func__);
77         return;
78     }
79 
80     RSScreenManager *screenManager = nullptr;
81     if (data != nullptr) {
82         screenManager = static_cast<RSScreenManager *>(data);
83     } else {
84         screenManager = static_cast<RSScreenManager *>(RSScreenManager::GetInstance().GetRefPtr());
85     }
86 
87     if (screenManager == nullptr) {
88         RS_LOGE("RSScreenManager %s: Failed to find RSScreenManager instance.", __func__);
89         return;
90     }
91 
92     screenManager->OnHotPlugEvent(output, connected);
93 }
94 
OnHotPlugEvent(std::shared_ptr<HdiOutput> & output,bool connected)95 void RSScreenManager::OnHotPlugEvent(std::shared_ptr<HdiOutput> &output, bool connected)
96 {
97     {
98         std::lock_guard<std::mutex> lock(mutex_);
99         pendingHotPlugEvents_.emplace_back(ScreenHotPlugEvent{output, connected});
100     }
101 
102     // This func would be called in main thread first time immediately after calling composer_->RegScreenHotplug,
103     // but at this time the RSMainThread object would not be ready to handle this, so we need to call
104     // ProcessScreenHotPlugEvents() after this func in RSScreenManager::Init().
105 
106     // Normally, this func would be called in hdi's hw-ipc threads(but sometimes in main thread, maybe),
107     // so we should notify the RSMainThread to postTask to call ProcessScreenHotPlugEvents().
108     auto mainThread = RSMainThread::Instance();
109     if (mainThread == nullptr) {
110         return;
111     }
112     mainThread->RequestNextVSync();
113 }
114 
OnHwcDead(void * data)115 void RSScreenManager::OnHwcDead(void *data)
116 {
117     RS_LOGD("RSScreenManager %s: The composer_host is already dead.", __func__);
118     RSScreenManager *screenManager = static_cast<RSScreenManager *>(RSScreenManager::GetInstance().GetRefPtr());
119     if (screenManager == nullptr) {
120         RS_LOGE("RSScreenManager %s: Failed to find RSScreenManager instance.", __func__);
121         return;
122     }
123 
124     screenManager->OnHwcDeadEvent();
125 
126     // Automatically recover when composer host dies.
127     screenManager->Reinit();
128 }
129 
OnHwcDeadEvent()130 void RSScreenManager::OnHwcDeadEvent()
131 {
132     std::lock_guard<std::mutex> lock(mutex_);
133     for (const auto &[id, screen] : screens_) {
134         if (screen) {
135             for (auto &cb : screenChangeCallbacks_) {
136                 cb->OnScreenChanged(id, ScreenEvent::DISCONNECTED);
137                 RS_LOGD("RSScreenManager %s: The screen callback has been invoked.", __func__);
138             }
139             if (screenPowerStatus_.count(id) != 0) {
140                 screenPowerStatus_.erase(id);
141             }
142             if (screen->IsVirtual()) {
143                 continue;
144             } else {
145                 screen->GetOutput()->GetFrameBufferSurface()->CleanCache();
146             }
147         }
148     }
149     screens_.clear();
150     defaultScreenId_ = INVALID_SCREEN_ID;
151 }
152 
Reinit()153 void RSScreenManager::Reinit()
154 {
155     RSScreenManager *screenManager = static_cast<RSScreenManager *>(RSScreenManager::GetInstance().GetRefPtr());
156     if (screenManager == nullptr) {
157         RS_LOGE("RSScreenManager %s: Failed to find RSScreenManager instance.", __func__);
158         return;
159     }
160 
161     auto renderType = RSUniRenderJudgement::GetUniRenderEnabledType();
162     if (renderType != UniRenderEnabledType::UNI_RENDER_ENABLED_FOR_ALL) {
163         auto mainThread = RSMainThread::Instance();
164         if (mainThread == nullptr) {
165             RS_LOGE("RSScreenManager %s: Reinit failed, get RSMainThread failed.", __func__);
166             return;
167         }
168         mainThread->PostTask([screenManager, this]() {
169             composer_->ResetDevice();
170             if (!screenManager->Init()) {
171                 RS_LOGE("RSScreenManager %s: Reinit failed, screenManager init failed in mainThread.", __func__);
172                 return;
173             }
174         });
175     } else {
176         RSHardwareThread::Instance().PostTask([screenManager, this]() {
177             composer_->ResetDevice();
178             if (!screenManager->Init()) {
179                 RS_LOGE("RSScreenManager %s: Reinit failed, screenManager init failed in HardwareThread.", __func__);
180                 return;
181             }
182         });
183     }
184 }
185 
ProcessScreenHotPlugEvents()186 void RSScreenManager::ProcessScreenHotPlugEvents()
187 {
188     std::lock_guard<std::mutex> lock(mutex_);
189     for (auto &event : pendingHotPlugEvents_) {
190         if (event.connected) {
191             ProcessScreenConnectedLocked(event.output);
192             AddScreenToHgm(event.output);
193         } else {
194             ProcessScreenDisConnectedLocked(event.output);
195             RemoveScreenFromHgm(event.output);
196         }
197     }
198     for (auto id : connectedIds_) {
199         for (auto &cb : screenChangeCallbacks_) {
200             cb->OnScreenChanged(id, ScreenEvent::CONNECTED);
201         }
202     }
203     mipiCheckInFirstHotPlugEvent_ = true;
204     pendingHotPlugEvents_.clear();
205     connectedIds_.clear();
206 }
207 
AddScreenToHgm(std::shared_ptr<HdiOutput> & output)208 void RSScreenManager::AddScreenToHgm(std::shared_ptr<HdiOutput> &output)
209 {
210     if (output == nullptr) {
211         RS_LOGE("RSScreenManager %s: output is nullptr.", __func__);
212         return;
213     }
214     RS_LOGI("RSScreenManager AddScreenToHgm");
215     auto &hgmCore = OHOS::Rosen::HgmCore::Instance();
216     ScreenId thisId = ToScreenId(output->GetScreenId());
217     if (screens_.find(thisId) == screens_.end()) {
218         RS_LOGE("RSScreenManager invalid screen id, screen not found : %" PRIu64 "", thisId);
219         return;
220     }
221 
222     int32_t initModeId = 0;
223     auto initMode = screens_[thisId]->GetActiveMode();
224     if (!initMode) {
225         RS_LOGE("RSScreenManager failed to get initial mode");
226     } else {
227         initModeId = initMode->id;
228     }
229     if (hgmCore.AddScreen(thisId, initModeId)) {
230         RS_LOGW("RSScreenManager failed to add screen : %" PRIu64 "", thisId);
231         return;
232     }
233 
234     // for each supported mode, use the index as modeId to add the detailed mode to hgm
235     int32_t modeId = 0;
236     auto supportedModes = screens_[thisId]->GetSupportedModes();
237     for (auto mode = supportedModes.begin(); mode != supportedModes.end(); ++mode) {
238         if (!hgmCore.AddScreenInfo(thisId, (*mode).width, (*mode).height,
239             (*mode).freshRate, modeId)) {
240             RS_LOGW("RSScreenManager failed to add a screen profile to the screen : %" PRIu64 "", thisId);
241         }
242         modeId++;
243     }
244     const auto &screen = screens_.at(thisId);
245     const auto &capability = screens_.at(thisId)->GetCapability();
246     hgmCore.AddScreenProfile(thisId, screen->Width(), screen->Height(), capability.phyWidth, capability.phyHeight);
247 }
248 
RemoveScreenFromHgm(std::shared_ptr<HdiOutput> & output)249 void RSScreenManager::RemoveScreenFromHgm(std::shared_ptr<HdiOutput> &output)
250 {
251     if (output == nullptr) {
252         RS_LOGE("RSScreenManager %s: output is nullptr.", __func__);
253         return;
254     }
255 
256     RS_LOGI("RSScreenManager RemoveScreenFromHgm");
257     auto &hgmCore = OHOS::Rosen::HgmCore::Instance();
258     ScreenId id = ToScreenId(output->GetScreenId());
259     if (hgmCore.RemoveScreen(id)) {
260         RS_LOGW("RSScreenManager failed to remove screen : %" PRIu64 "", id);
261     }
262     hgmCore.RemoveScreenProfile(id);
263 }
264 
ProcessScreenConnectedLocked(std::shared_ptr<HdiOutput> & output)265 void RSScreenManager::ProcessScreenConnectedLocked(std::shared_ptr<HdiOutput> &output)
266 {
267     if (output == nullptr) {
268         RS_LOGE("RSScreenManager %s: output is nullptr.", __func__);
269         return;
270     }
271 
272     bool isVirtual = false;
273     ScreenId id = ToScreenId(output->GetScreenId());
274 
275     if (screens_.count(id) == 1) {
276         RS_LOGW("RSScreenManager %s The screen for id %" PRIu64 " already existed.", __func__, id);
277 
278         // [PLANNING]: should we erase it and create a new one?
279         for (auto &cb : screenChangeCallbacks_) {
280             cb->OnScreenChanged(id, ScreenEvent::DISCONNECTED);
281         }
282         screens_.erase(id);
283     }
284 
285     screens_[id] = std::make_unique<RSScreen>(id, isVirtual, output, nullptr);
286 
287     auto vsyncSampler = CreateVSyncSampler();
288     if (vsyncSampler != nullptr) {
289         auto renderType = RSUniRenderJudgement::GetUniRenderEnabledType();
290         if (renderType != UniRenderEnabledType::UNI_RENDER_ENABLED_FOR_ALL) {
291             vsyncSampler->RegSetScreenVsyncEnabledCallback([this, id](bool enabled) {
292                 auto mainThread = RSMainThread::Instance();
293                 if (mainThread == nullptr) {
294                     RS_LOGE("SetScreenVsyncEnabled:%{public}d failed, get RSMainThread failed", enabled);
295                     return;
296                 }
297                 mainThread->PostTask([this, id, enabled]() {
298                     if (screens_[id] == nullptr) {
299                         RS_LOGE("SetScreenVsyncEnabled:%{public}d failed, screen %{public}ld not found", enabled, id);
300                         return;
301                     }
302                     screens_[id]->SetScreenVsyncEnabled(enabled);
303                 });
304             });
305         } else {
306             vsyncSampler->RegSetScreenVsyncEnabledCallback([this, id](bool enabled) {
307                 RSHardwareThread::Instance().PostTask([this, id, enabled]() {
308                     if (screens_[id] == nullptr) {
309                         RS_LOGE("SetScreenVsyncEnabled:%{public}d failed, screen %{public}ld not found", enabled, id);
310                         return;
311                     }
312                     screens_[id]->SetScreenVsyncEnabled(enabled);
313                 });
314             });
315         }
316     } else {
317         RS_LOGE("RegSetScreenVsyncEnabledCallback failed, vsyncSampler is null");
318     }
319 
320     if (screens_[id]->GetCapability().type == GraphicInterfaceType::GRAPHIC_DISP_INTF_MIPI) {
321         if (!mipiCheckInFirstHotPlugEvent_) {
322             defaultScreenId_ = id;
323         }
324         mipiCheckInFirstHotPlugEvent_ = true;
325     } else if (defaultScreenId_ == INVALID_SCREEN_ID) {
326         defaultScreenId_ = id;
327     }
328 
329     RS_LOGI("RSScreenManager %s: A new screen(id %" PRIu64 ") connected.", __func__, id);
330     connectedIds_.emplace_back(id);
331 }
332 
ProcessScreenDisConnectedLocked(std::shared_ptr<HdiOutput> & output)333 void RSScreenManager::ProcessScreenDisConnectedLocked(std::shared_ptr<HdiOutput> &output)
334 {
335     ScreenId id = ToScreenId(output->GetScreenId());
336 
337     if (screens_.count(id) == 0) {
338         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64, __func__, id);
339     } else {
340         for (auto &cb : screenChangeCallbacks_) {
341             cb->OnScreenChanged(id, ScreenEvent::DISCONNECTED);
342         }
343         screens_.erase(id);
344         RS_LOGI("RSScreenManager %s: Screen(id %" PRIu64 ") disconnected.", __func__, id);
345     }
346     if (screenPowerStatus_.count(id) != 0) {
347         screenPowerStatus_.erase(id);
348     }
349     if (id == defaultScreenId_) {
350         HandleDefaultScreenDisConnectedLocked();
351     }
352 }
353 
354 // If the previous primary screen disconnected, we traversal the left screens
355 // and find the first physical screen to be the default screen.
356 // If there was no physical screen left, we set the first screen as default, no matter what type it is.
357 // At last, if no screen left, we set Default Screen Id to INVALID_SCREEN_ID.
HandleDefaultScreenDisConnectedLocked()358 void RSScreenManager::HandleDefaultScreenDisConnectedLocked()
359 {
360     defaultScreenId_ = INVALID_SCREEN_ID;
361     for (const auto &[id, screen] : screens_) {
362         if (!screen->IsVirtual()) {
363             defaultScreenId_ = id;
364             break;
365         }
366     }
367 
368     if (defaultScreenId_ == INVALID_SCREEN_ID) {
369         if (!screens_.empty()) {
370             defaultScreenId_ = screens_.cbegin()->first;
371         }
372     }
373 }
374 
SetDefaultScreenId(ScreenId id)375 void RSScreenManager::SetDefaultScreenId(ScreenId id)
376 {
377     std::lock_guard<std::mutex> lock(mutex_);
378     defaultScreenId_ = id;
379 }
380 
SetScreenMirror(ScreenId id,ScreenId toMirror)381 void RSScreenManager::SetScreenMirror(ScreenId id, ScreenId toMirror)
382 {
383     std::lock_guard<std::mutex> lock(mutex_);
384 
385     if (screens_.count(id) == 0) {
386         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
387         return;
388     }
389 
390     screens_[id]->SetMirror(toMirror);
391 }
392 
GenerateVirtualScreenIdLocked()393 ScreenId RSScreenManager::GenerateVirtualScreenIdLocked()
394 {
395     if (!freeVirtualScreenIds_.empty()) {
396         ScreenId id = freeVirtualScreenIds_.front();
397         freeVirtualScreenIds_.pop();
398         return id;
399     }
400 
401     // The left 32 bits is for virtual screen id.
402     return (static_cast<ScreenId>(maxVirtualScreenNum_++) << 32) | 0xffffffffu;
403 }
404 
ReuseVirtualScreenIdLocked(ScreenId id)405 void RSScreenManager::ReuseVirtualScreenIdLocked(ScreenId id)
406 {
407     freeVirtualScreenIds_.push(id);
408 }
409 
GetMirrorScreenId(ScreenId id)410 ScreenId RSScreenManager::GetMirrorScreenId(ScreenId id)
411 {
412     ScreenId mirroredId = INVALID_SCREEN_ID;
413     auto mainThread = RSMainThread::Instance();
414     if (mainThread == nullptr) {
415         return mirroredId;
416     }
417 
418     const auto& nodeMap = mainThread->GetContext().GetNodeMap();
419     nodeMap.TraversalNodes([&id, &mirroredId](const std::shared_ptr<RSBaseRenderNode>& node) {
420         if (node == nullptr || !node->IsInstanceOf<RSDisplayRenderNode>()) {
421             return;
422         }
423         RSDisplayRenderNode& displayNode = *(RSBaseRenderNode::ReinterpretCast<RSDisplayRenderNode>(node));
424         if (displayNode.GetScreenId() != id) {
425             return;
426         }
427         std::shared_ptr<RSDisplayRenderNode> mirroredNode = displayNode.GetMirrorSource().lock();
428         if (mirroredNode != nullptr) {
429             mirroredId = mirroredNode->GetScreenId();
430         }
431     });
432     return mirroredId;
433 }
434 
435 // The main screen resolution can be changed by the mirrored screen.
MirrorChangeDefaultScreenResolution(ScreenId id,uint32_t width,uint32_t height)436 void RSScreenManager::MirrorChangeDefaultScreenResolution(ScreenId id, uint32_t width, uint32_t height)
437 {
438     if (screens_.count(id) == 0) {
439         RS_LOGD("RSScreenManager %s: set fails because no screen access is currently available!", __func__);
440         return;
441     }
442 
443     ScreenId mirroredId = GetMirrorScreenId(id);
444     if (mirroredId == INVALID_SCREEN_ID) {
445         RS_LOGD("RSScreenManager %s: mirror screen is invalid.", __func__);
446         return;
447     }
448     ScreenId mainId = GetDefaultScreenId();
449     if (mirroredId == mainId) {
450         bool resolutionSetSuccess = false;
451         std::vector<GraphicDisplayModeInfo> mainMode = screens_.at(mainId)->GetSupportedModes();
452         for (uint32_t i = 0; i < mainMode.size(); i++) {
453             if (static_cast<uint32_t>(mainMode[i].width) == width &&
454                 static_cast<uint32_t>(mainMode[i].height) == height) {
455                 screens_.at(mainId)->SetActiveMode(i);
456                 resolutionSetSuccess = true;
457                 break;
458             }
459         }
460         if (!resolutionSetSuccess) {
461             RS_LOGD("RSScreenManager %s: not support the current resolution!", __func__);
462         }
463     }
464 }
465 
GetVirtualScreenResolutionLocked(ScreenId id,RSVirtualScreenResolution & virtualScreenResolution) const466 void RSScreenManager::GetVirtualScreenResolutionLocked(ScreenId id,
467     RSVirtualScreenResolution& virtualScreenResolution) const
468 {
469     if (screens_.count(id) == 0) {
470         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
471         return;
472     }
473 
474     virtualScreenResolution.SetVirtualScreenWidth(static_cast<uint32_t>(screens_.at(id)->Width()));
475     virtualScreenResolution.SetVirtualScreenHeight(static_cast<uint32_t>(screens_.at(id)->Height()));
476 }
477 
GetScreenActiveModeLocked(ScreenId id,RSScreenModeInfo & screenModeInfo) const478 void RSScreenManager::GetScreenActiveModeLocked(ScreenId id, RSScreenModeInfo& screenModeInfo) const
479 {
480     if (screens_.count(id) == 0) {
481         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
482         return;
483     }
484 
485     auto modeInfo = screens_.at(id)->GetActiveMode();
486     if (!modeInfo) {
487         RS_LOGE("RSScreenManager %s: Failed to get active mode for screen %" PRIu64 ".", __func__, id);
488         return;
489     }
490 
491     screenModeInfo.SetScreenWidth(modeInfo->width);
492     screenModeInfo.SetScreenHeight(modeInfo->height);
493     screenModeInfo.SetScreenRefreshRate(modeInfo->freshRate);
494     screenModeInfo.SetScreenModeId(screens_.at(id)->GetActiveModePosByModeId(modeInfo->id));
495 }
496 
GetScreenSupportedModesLocked(ScreenId id) const497 std::vector<RSScreenModeInfo> RSScreenManager::GetScreenSupportedModesLocked(ScreenId id) const
498 {
499     std::vector<RSScreenModeInfo> screenSupportedModes;
500     if (screens_.count(id) == 0) {
501         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
502         return screenSupportedModes;
503     }
504 
505     const auto& displaySupportedModes = screens_.at(id)->GetSupportedModes();
506     screenSupportedModes.resize(displaySupportedModes.size());
507     for (decltype(displaySupportedModes.size()) idx = 0; idx < displaySupportedModes.size(); ++idx) {
508         screenSupportedModes[idx].SetScreenWidth(displaySupportedModes[idx].width);
509         screenSupportedModes[idx].SetScreenHeight(displaySupportedModes[idx].height);
510         screenSupportedModes[idx].SetScreenRefreshRate(displaySupportedModes[idx].freshRate);
511         screenSupportedModes[idx].SetScreenModeId(displaySupportedModes[idx].id);
512     }
513     return screenSupportedModes;
514 }
515 
GetScreenCapabilityLocked(ScreenId id) const516 RSScreenCapability RSScreenManager::GetScreenCapabilityLocked(ScreenId id) const
517 {
518     RSScreenCapability screenCapability;
519     if (screens_.count(id) == 0) {
520         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
521         return screenCapability;
522     }
523     if (screens_.at(id)->IsVirtual()) {
524         RS_LOGW("RSScreenManager %s: only name attribute is valid for virtual screen.", __func__);
525         screenCapability.SetName(screens_.at(id)->Name());
526         return screenCapability;
527     }
528 
529     const auto& capability = screens_.at(id)->GetCapability();
530     std::vector<RSScreenProps> props;
531     uint32_t propCount = capability.propertyCount;
532     props.resize(propCount);
533     for (uint32_t propIndex = 0; propIndex < propCount; propIndex++) {
534         props[propIndex] = RSScreenProps(capability.props[propIndex].name, capability.props[propIndex].propId,
535             capability.props[propIndex].value);
536     }
537     screenCapability.SetName(capability.name);
538     screenCapability.SetType(static_cast<ScreenInterfaceType>(capability.type));
539     screenCapability.SetPhyWidth(capability.phyWidth);
540     screenCapability.SetPhyHeight(capability.phyHeight);
541     screenCapability.SetSupportLayers(capability.supportLayers);
542     screenCapability.SetVirtualDispCount(capability.virtualDispCount);
543     screenCapability.SetSupportWriteBack(capability.supportWriteBack);
544     screenCapability.SetProps(props);
545     return screenCapability;
546 }
547 
GetScreenPowerStatusLocked(ScreenId id) const548 ScreenPowerStatus RSScreenManager::GetScreenPowerStatusLocked(ScreenId id) const
549 {
550     if (screens_.count(id) == 0) {
551         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
552         return INVALID_POWER_STATUS;
553     }
554 
555     ScreenPowerStatus status = static_cast<ScreenPowerStatus>(screens_.at(id)->GetPowerStatus());
556     return status;
557 }
558 
GetAllScreenIds()559 std::vector<ScreenId> RSScreenManager::GetAllScreenIds()
560 {
561     std::vector<ScreenId> ids;
562     for (auto iter = screens_.begin(); iter != screens_.end(); ++iter) {
563         ids.emplace_back(iter->first);
564     }
565     return ids;
566 }
567 
CreateVirtualScreen(const std::string & name,uint32_t width,uint32_t height,sptr<Surface> surface,ScreenId mirrorId,int32_t flags)568 ScreenId RSScreenManager::CreateVirtualScreen(
569     const std::string &name,
570     uint32_t width,
571     uint32_t height,
572     sptr<Surface> surface,
573     ScreenId mirrorId,
574     int32_t flags
575     )
576 {
577     std::lock_guard<std::mutex> lock(mutex_);
578 
579     if (surface != nullptr) {
580         uint64_t surfaceId = surface->GetUniqueId();
581         for (auto &[_, screen] : screens_) {
582             if (!screen->IsVirtual()) {
583                 continue;
584             }
585             auto screenSurface = screen->GetProducerSurface();
586             if (screenSurface == nullptr) {
587                 continue;
588             }
589             if (screenSurface->GetUniqueId() == surfaceId) {
590                 RS_LOGW("RSScreenManager %s: surface %" PRIu64 " is used, create virtual screen failed!", __func__,
591                     surfaceId);
592                 return INVALID_SCREEN_ID;
593             }
594         }
595     } else {
596         RS_LOGD("RSScreenManager %s: surface is nullptr.", __func__);
597     }
598 
599     VirtualScreenConfigs configs;
600     ScreenId newId = GenerateVirtualScreenIdLocked();
601     configs.id = newId;
602     configs.mirrorId = mirrorId;
603     configs.name = name;
604     configs.width = width;
605     configs.height = height;
606     configs.surface = surface;
607     configs.flags = flags;
608 
609     screens_[newId] = std::make_unique<RSScreen>(configs);
610     RS_LOGD("RSScreenManager %s: create virtual screen(id %" PRIu64 ").", __func__, newId);
611     return newId;
612 }
613 
SetVirtualScreenSurface(ScreenId id,sptr<Surface> surface)614 int32_t RSScreenManager::SetVirtualScreenSurface(ScreenId id, sptr<Surface> surface)
615 {
616     std::lock_guard<std::mutex> lock(mutex_);
617     if (screens_.find(id) == screens_.end()) {
618         return SCREEN_NOT_FOUND;
619     }
620     uint64_t surfaceId = surface->GetUniqueId();
621     for (auto &[screenId, screen] : screens_) {
622         if (!screen->IsVirtual() || screenId == id) {
623             continue;
624         }
625         auto screenSurface = screen->GetProducerSurface();
626         if (screenSurface == nullptr) {
627             continue;
628         }
629         if (screenSurface->GetUniqueId() == surface->GetUniqueId()) {
630             RS_LOGE("RSScreenManager %s: surface %" PRIu64 " is used, set surface failed!", __func__, surfaceId);
631             return SURFACE_NOT_UNIQUE;
632         }
633     }
634     screens_.at(id)->SetProducerSurface(surface);
635     RS_LOGD("RSScreenManager %s: set virtual screen surface success!", __func__);
636     // if SetVirtualScreenSurface success, better to request the next vsync, avoiding prolong black screen
637     auto mainThread = RSMainThread::Instance();
638     if (mainThread != nullptr) {
639         mainThread->RequestNextVSync();
640     }
641     return SUCCESS;
642 }
643 
RemoveVirtualScreen(ScreenId id)644 void RSScreenManager::RemoveVirtualScreen(ScreenId id)
645 {
646     std::lock_guard<std::mutex> lock(mutex_);
647 
648     RemoveVirtualScreenLocked(id);
649 }
650 
RemoveVirtualScreenLocked(ScreenId id)651 void RSScreenManager::RemoveVirtualScreenLocked(ScreenId id)
652 {
653     if (screens_.count(id) == 0) {
654         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
655         return;
656     }
657 
658     screens_.erase(id);
659 
660     // Update other screens' mirrorId.
661     for (auto &[id, screen] : screens_) {
662         if (screen->MirrorId() == id) {
663             screen->SetMirror(INVALID_SCREEN_ID);
664         }
665     }
666     RS_LOGD("RSScreenManager %s: remove virtual screen(id %" PRIu64 ").", __func__, id);
667 
668     ReuseVirtualScreenIdLocked(id);
669 }
670 
SetScreenActiveMode(ScreenId id,uint32_t modeId)671 void RSScreenManager::SetScreenActiveMode(ScreenId id, uint32_t modeId)
672 {
673     std::lock_guard<std::mutex> lock(mutex_);
674 
675     if (screens_.count(id) == 0) {
676         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
677         return;
678     }
679     screens_.at(id)->SetActiveMode(modeId);
680 
681     // The main screen resolution can be changed on the mirrored physical screen.
682     auto supportedModes = screens_.at(id)->GetSupportedModes();
683     if (modeId >= supportedModes.size()) {
684         RS_LOGE("RSScreenManager %s: set fails because the index is out of bounds.", __func__);
685         return;
686     }
687     uint32_t width = supportedModes[modeId].width;
688     uint32_t height = supportedModes[modeId].height;
689     MirrorChangeDefaultScreenResolution(id, width, height);
690 }
691 
SetVirtualScreenResolution(ScreenId id,uint32_t width,uint32_t height)692 int32_t RSScreenManager::SetVirtualScreenResolution(ScreenId id, uint32_t width, uint32_t height)
693 {
694     std::lock_guard<std::mutex> lock(mutex_);
695 
696     if (screens_.count(id) == 0) {
697         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
698         return SCREEN_NOT_FOUND;
699     }
700     screens_.at(id)->SetResolution(width, height);
701     RS_LOGD("RSScreenManager %s: set virtual screen resolution success", __func__);
702 
703     // The main screen resolution can be changed by the mirrored virtual screen.
704     MirrorChangeDefaultScreenResolution(id, width, height);
705 
706     return SUCCESS;
707 }
708 
SetScreenPowerStatus(ScreenId id,ScreenPowerStatus status)709 void RSScreenManager::SetScreenPowerStatus(ScreenId id, ScreenPowerStatus status)
710 {
711     std::lock_guard<std::mutex> lock(mutex_);
712 
713     if (screens_.count(id) == 0) {
714         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
715         return;
716     }
717     screens_.at(id)->SetPowerStatus(static_cast<uint32_t>(status));
718 
719     /*
720      * If app adds the first frame when power on the screen, delete the code
721      */
722     if (status == ScreenPowerStatus::POWER_STATUS_ON) {
723         auto mainThread = RSMainThread::Instance();
724         if (mainThread == nullptr) {
725             return;
726         }
727         mainThread->SetDirtyFlag();
728         if (screenPowerStatus_.count(id) == 0 || screenPowerStatus_[id] == ScreenPowerStatus::POWER_STATUS_OFF) {
729             mainThread->ForceRefreshForUni();
730         } else {
731             mainThread->RequestNextVSync();
732         }
733 
734         RS_LOGI("RSScreenManager %s: Set system power on, request a frame", __func__);
735     }
736     screenPowerStatus_[id] = status;
737 }
738 
GetVirtualScreenResolution(ScreenId id,RSVirtualScreenResolution & virtualScreenResolution) const739 void RSScreenManager::GetVirtualScreenResolution(ScreenId id, RSVirtualScreenResolution& virtualScreenResolution) const
740 {
741     std::lock_guard<std::mutex> lock(mutex_);
742 
743     GetVirtualScreenResolutionLocked(id, virtualScreenResolution);
744 }
745 
GetScreenActiveMode(ScreenId id,RSScreenModeInfo & screenModeInfo) const746 void RSScreenManager::GetScreenActiveMode(ScreenId id, RSScreenModeInfo& screenModeInfo) const
747 {
748     std::lock_guard<std::mutex> lock(mutex_);
749 
750     GetScreenActiveModeLocked(id, screenModeInfo);
751 }
752 
GetScreenSupportedModes(ScreenId id) const753 std::vector<RSScreenModeInfo> RSScreenManager::GetScreenSupportedModes(ScreenId id) const
754 {
755     std::lock_guard<std::mutex> lock(mutex_);
756 
757     return GetScreenSupportedModesLocked(id);
758 }
759 
GetScreenCapability(ScreenId id) const760 RSScreenCapability RSScreenManager::GetScreenCapability(ScreenId id) const
761 {
762     std::lock_guard<std::mutex> lock(mutex_);
763 
764     return GetScreenCapabilityLocked(id);
765 }
766 
GetScreenPowerStatus(ScreenId id) const767 ScreenPowerStatus RSScreenManager::GetScreenPowerStatus(ScreenId id) const
768 {
769     std::lock_guard<std::mutex> lock(mutex_);
770 
771     return GetScreenPowerStatusLocked(id);
772 }
773 
GetScreenData(ScreenId id) const774 RSScreenData RSScreenManager::GetScreenData(ScreenId id) const
775 {
776     std::lock_guard<std::mutex> lock(mutex_);
777     RSScreenData screenData;
778     if (screens_.count(id) == 0) {
779         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
780         return screenData;
781     }
782     RSScreenCapability capability = GetScreenCapabilityLocked(id);
783     RSScreenModeInfo activeMode;
784     GetScreenActiveModeLocked(id, activeMode);
785     std::vector<RSScreenModeInfo> supportModes = GetScreenSupportedModesLocked(id);
786     ScreenPowerStatus powerStatus = GetScreenPowerStatusLocked(id);
787     screenData.SetCapability(capability);
788     screenData.SetActivityModeInfo(activeMode);
789     screenData.SetSupportModeInfo(supportModes);
790     screenData.SetPowerStatus(powerStatus);
791     return screenData;
792 }
793 
GetScreenBacklight(ScreenId id)794 int32_t RSScreenManager::GetScreenBacklight(ScreenId id)
795 {
796     std::lock_guard<std::mutex> lock(mutex_);
797     return GetScreenBacklightLocked(id);
798 }
799 
GetScreenBacklightLocked(ScreenId id) const800 int32_t RSScreenManager::GetScreenBacklightLocked(ScreenId id) const
801 {
802     if (screens_.count(id) == 0) {
803         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
804         return INVALID_BACKLIGHT_VALUE;
805     }
806 
807     int32_t level = screens_.at(id)->GetScreenBacklight();
808     return level;
809 }
810 
SetScreenBacklight(ScreenId id,uint32_t level)811 void RSScreenManager::SetScreenBacklight(ScreenId id, uint32_t level)
812 {
813     std::lock_guard<std::mutex> lock(mutex_);
814     if (screens_.count(id) == 0) {
815         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
816         return;
817     }
818     screens_.at(id)->SetScreenBacklight(level);
819 }
820 
QueryScreenInfo(ScreenId id) const821 ScreenInfo RSScreenManager::QueryScreenInfo(ScreenId id) const
822 {
823     std::lock_guard<std::mutex> lock(mutex_);
824 
825     ScreenInfo info;
826     if (screens_.count(id) == 0) {
827         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
828         return info;
829     }
830 
831     const auto &screen = screens_.at(id);
832     info.id = id;
833     info.width = screen->Width();
834     info.height = screen->Height();
835     auto ret = screen->GetScreenColorGamut(info.colorGamut);
836     if (ret != StatusCode::SUCCESS) {
837         info.colorGamut = COLOR_GAMUT_SRGB;
838     }
839 
840     if (!screen->IsEnable()) {
841         info.state = ScreenState::DISABLED;
842     } else if (!screen->IsVirtual()) {
843         info.state = ScreenState::HDI_OUTPUT_ENABLE;
844     } else {
845         info.state = ScreenState::PRODUCER_SURFACE_ENABLE;
846     }
847     info.skipFrameInterval = screen->GetScreenSkipFrameInterval();
848 
849     return info;
850 }
851 
GetProducerSurface(ScreenId id) const852 sptr<Surface> RSScreenManager::GetProducerSurface(ScreenId id) const
853 {
854     std::lock_guard<std::mutex> lock(mutex_);
855 
856     // assert screens_.count(id) == 1
857     if (screens_.count(id) == 0) {
858         RS_LOGW("RSScreenManager::GetProducerSurface: There is no screen for id %" PRIu64 ".", id);
859         return nullptr;
860     }
861     return screens_.at(id)->GetProducerSurface();
862 }
863 
GetOutput(ScreenId id) const864 std::shared_ptr<HdiOutput> RSScreenManager::GetOutput(ScreenId id) const
865 {
866     std::lock_guard<std::mutex> lock(mutex_);
867 
868     // assert screens_.count(id) == 1
869     if (screens_.count(id) == 0) {
870         RS_LOGW("RSScreenManager::GetOutput: There is no screen for id %" PRIu64 ".", id);
871         return nullptr;
872     }
873     return screens_.at(id)->GetOutput();
874 }
875 
AddScreenChangeCallback(const sptr<RSIScreenChangeCallback> & callback)876 int32_t RSScreenManager::AddScreenChangeCallback(const sptr<RSIScreenChangeCallback> &callback)
877 {
878     if (callback == nullptr) {
879         RS_LOGE("RSScreenManager %s: callback is NULL.", __func__);
880         return INVALID_ARGUMENTS;
881     }
882 
883     std::lock_guard<std::mutex> lock(mutex_);
884     // when the callback first registered, maybe there were some physical screens already connected,
885     // so notify to remote immediately.
886     for (const auto &[id, screen] : screens_) {
887         if (!screen->IsVirtual()) {
888             callback->OnScreenChanged(id, ScreenEvent::CONNECTED);
889         }
890     }
891     screenChangeCallbacks_.push_back(callback);
892     RS_LOGD("RSScreenManager %s: add a remote callback succeed.", __func__);
893     return SUCCESS;
894 }
895 
RemoveScreenChangeCallback(const sptr<RSIScreenChangeCallback> & callback)896 void RSScreenManager::RemoveScreenChangeCallback(const sptr<RSIScreenChangeCallback> &callback)
897 {
898     std::lock_guard<std::mutex> lock(mutex_);
899     for (auto it = screenChangeCallbacks_.begin(); it != screenChangeCallbacks_.end(); it++) {
900         if (*it == callback) {
901             screenChangeCallbacks_.erase(it);
902             RS_LOGD("RSScreenManager %s: remove a remote callback succeed.", __func__);
903             break;
904         }
905     }
906 }
907 
DisplayDump(std::string & dumpString)908 void RSScreenManager::DisplayDump(std::string& dumpString)
909 {
910     int32_t index = 0;
911     for (const auto &[id, screen] : screens_) {
912         screen->DisplayDump(index, dumpString);
913         index++;
914     }
915 }
916 
SurfaceDump(std::string & dumpString)917 void RSScreenManager::SurfaceDump(std::string& dumpString)
918 {
919     int32_t index = 0;
920     for (const auto &[id, screen] : screens_) {
921         screen->SurfaceDump(index, dumpString);
922         index++;
923     }
924 }
925 
FpsDump(std::string & dumpString,std::string & arg)926 void RSScreenManager::FpsDump(std::string& dumpString, std::string& arg)
927 {
928     int32_t index = 0;
929     dumpString += "\n-- The recently fps records info of screens:\n";
930     for (const auto &[id, screen] : screens_) {
931         screen->FpsDump(index, dumpString, arg);
932         index++;
933     }
934 }
935 
ClearFpsDump(std::string & dumpString,std::string & arg)936 void RSScreenManager::ClearFpsDump(std::string& dumpString, std::string& arg)
937 {
938     int32_t index = 0;
939     dumpString += "\n-- Clear fps records info of screens:\n";
940     for (const auto &[id, screen] : screens_) {
941         screen->ClearFpsDump(index, dumpString, arg);
942         index++;
943     }
944 }
945 
GetScreenSupportedColorGamutsLocked(ScreenId id,std::vector<ScreenColorGamut> & mode) const946 int32_t RSScreenManager::GetScreenSupportedColorGamutsLocked(ScreenId id, std::vector<ScreenColorGamut>& mode) const
947 {
948     if (screens_.count(id) == 0) {
949         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
950         return StatusCode::SCREEN_NOT_FOUND;
951     }
952     return screens_.at(id)->GetScreenSupportedColorGamuts(mode);
953 }
954 
GetScreenSupportedMetaDataKeysLocked(ScreenId id,std::vector<ScreenHDRMetadataKey> & keys) const955 int32_t RSScreenManager::GetScreenSupportedMetaDataKeysLocked(
956     ScreenId id, std::vector<ScreenHDRMetadataKey>& keys) const
957 {
958     if (screens_.count(id) == 0) {
959         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
960         return StatusCode::SCREEN_NOT_FOUND;
961     }
962     return screens_.at(id)->GetScreenSupportedMetaDataKeys(keys);
963 }
964 
GetScreenColorGamutLocked(ScreenId id,ScreenColorGamut & mode) const965 int32_t RSScreenManager::GetScreenColorGamutLocked(ScreenId id, ScreenColorGamut& mode) const
966 {
967     if (screens_.count(id) == 0) {
968         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
969         return StatusCode::SCREEN_NOT_FOUND;
970     }
971     return screens_.at(id)->GetScreenColorGamut(mode);
972 }
973 
SetScreenColorGamutLocked(ScreenId id,int32_t modeIdx)974 int32_t RSScreenManager::SetScreenColorGamutLocked(ScreenId id, int32_t modeIdx)
975 {
976     if (screens_.count(id) == 0) {
977         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
978         return StatusCode::SCREEN_NOT_FOUND;
979     }
980     return screens_.at(id)->SetScreenColorGamut(modeIdx);
981 }
982 
SetScreenGamutMapLocked(ScreenId id,ScreenGamutMap mode)983 int32_t RSScreenManager::SetScreenGamutMapLocked(ScreenId id, ScreenGamutMap mode)
984 {
985     if (screens_.count(id) == 0) {
986         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
987         return StatusCode::SCREEN_NOT_FOUND;
988     }
989     return screens_.at(id)->SetScreenGamutMap(mode);
990 }
991 
GetScreenGamutMapLocked(ScreenId id,ScreenGamutMap & mode) const992 int32_t RSScreenManager::GetScreenGamutMapLocked(ScreenId id, ScreenGamutMap &mode) const
993 {
994     if (screens_.count(id) == 0) {
995         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
996         return StatusCode::SCREEN_NOT_FOUND;
997     }
998     return screens_.at(id)->GetScreenGamutMap(mode);
999 }
1000 
GetScreenHDRCapabilityLocked(ScreenId id,RSScreenHDRCapability & screenHdrCapability) const1001 int32_t RSScreenManager::GetScreenHDRCapabilityLocked(ScreenId id, RSScreenHDRCapability& screenHdrCapability) const
1002 {
1003     if (screens_.count(id) == 0) {
1004         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
1005         return StatusCode::SCREEN_NOT_FOUND;
1006     }
1007     GraphicHDRCapability hdrCapability = screens_.at(id)->GetHDRCapability();
1008     std::vector<ScreenHDRFormat> hdrFormats;
1009     uint32_t formatCount = hdrCapability.formatCount;
1010     hdrFormats.resize(formatCount);
1011     for (uint32_t index = 0; index < formatCount; index++) {
1012         hdrFormats[index] = static_cast<ScreenHDRFormat>(hdrCapability.formats[index]);
1013     }
1014     screenHdrCapability.SetMaxLum(hdrCapability.maxLum);
1015     screenHdrCapability.SetMaxAverageLum(hdrCapability.maxAverageLum);
1016     screenHdrCapability.SetMinLum(hdrCapability.minLum);
1017     screenHdrCapability.SetHdrFormats(hdrFormats);
1018     return StatusCode::SUCCESS;
1019 }
1020 
GetScreenTypeLocked(ScreenId id,RSScreenType & type) const1021 int32_t RSScreenManager::GetScreenTypeLocked(ScreenId id, RSScreenType& type) const
1022 {
1023     if (screens_.count(id) == 0) {
1024         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
1025         return StatusCode::SCREEN_NOT_FOUND;
1026     }
1027 
1028     type = screens_.at(id)->GetScreenType();
1029     return StatusCode::SUCCESS;
1030 }
1031 
SetScreenSkipFrameIntervalLocked(ScreenId id,uint32_t skipFrameInterval)1032 int32_t RSScreenManager::SetScreenSkipFrameIntervalLocked(ScreenId id, uint32_t skipFrameInterval)
1033 {
1034     if (screens_.count(id) == 0) {
1035         RS_LOGW("RSScreenManager %s: There is no screen for id %" PRIu64 ".", __func__, id);
1036         return StatusCode::SCREEN_NOT_FOUND;
1037     }
1038     RSScreenModeInfo screenModeInfo;
1039     // use the refresh rate of the physical screen as the maximum refresh rate
1040     GetScreenActiveModeLocked(defaultScreenId_, screenModeInfo);
1041     // guaranteed screen refresh rate at least 1
1042     if (skipFrameInterval == 0 || (skipFrameInterval > screenModeInfo.GetScreenRefreshRate())) {
1043         return INVALID_ARGUMENTS;
1044     }
1045     screens_.at(id)->SetScreenSkipFrameInterval(skipFrameInterval);
1046     RS_LOGD("RSScreenManager %s: screen(id %" PRIu64 "), skipFrameInterval(%d).",
1047         __func__, id, skipFrameInterval);
1048     return StatusCode::SUCCESS;
1049 }
1050 
GetScreenSupportedColorGamuts(ScreenId id,std::vector<ScreenColorGamut> & mode) const1051 int32_t RSScreenManager::GetScreenSupportedColorGamuts(ScreenId id, std::vector<ScreenColorGamut>& mode) const
1052 {
1053     std::lock_guard<std::mutex> lock(mutex_);
1054     return GetScreenSupportedColorGamutsLocked(id, mode);
1055 }
1056 
GetScreenSupportedMetaDataKeys(ScreenId id,std::vector<ScreenHDRMetadataKey> & keys) const1057 int32_t RSScreenManager::GetScreenSupportedMetaDataKeys(ScreenId id, std::vector<ScreenHDRMetadataKey>& keys) const
1058 {
1059     std::lock_guard<std::mutex> lock(mutex_);
1060     return GetScreenSupportedMetaDataKeysLocked(id, keys);
1061 }
1062 
GetScreenColorGamut(ScreenId id,ScreenColorGamut & mode) const1063 int32_t RSScreenManager::GetScreenColorGamut(ScreenId id, ScreenColorGamut &mode) const
1064 {
1065     std::lock_guard<std::mutex> lock(mutex_);
1066     return GetScreenColorGamutLocked(id, mode);
1067 }
1068 
SetScreenColorGamut(ScreenId id,int32_t modeIdx)1069 int32_t RSScreenManager::SetScreenColorGamut(ScreenId id, int32_t modeIdx)
1070 {
1071     std::lock_guard<std::mutex> lock(mutex_);
1072     return SetScreenColorGamutLocked(id, modeIdx);
1073 }
1074 
SetScreenGamutMap(ScreenId id,ScreenGamutMap mode)1075 int32_t RSScreenManager::SetScreenGamutMap(ScreenId id, ScreenGamutMap mode)
1076 {
1077     std::lock_guard<std::mutex> lock(mutex_);
1078     return SetScreenGamutMapLocked(id, mode);
1079 }
1080 
GetScreenGamutMap(ScreenId id,ScreenGamutMap & mode) const1081 int32_t RSScreenManager::GetScreenGamutMap(ScreenId id, ScreenGamutMap &mode) const
1082 {
1083     std::lock_guard<std::mutex> lock(mutex_);
1084     return GetScreenGamutMapLocked(id, mode);
1085 }
1086 
GetScreenHDRCapability(ScreenId id,RSScreenHDRCapability & screenHdrCapability) const1087 int32_t RSScreenManager::GetScreenHDRCapability(ScreenId id, RSScreenHDRCapability& screenHdrCapability) const
1088 {
1089     std::lock_guard<std::mutex> lock(mutex_);
1090     return GetScreenHDRCapabilityLocked(id, screenHdrCapability);
1091 }
1092 
GetScreenType(ScreenId id,RSScreenType & type) const1093 int32_t RSScreenManager::GetScreenType(ScreenId id, RSScreenType& type) const
1094 {
1095     std::lock_guard<std::mutex> lock(mutex_);
1096     return GetScreenTypeLocked(id, type);
1097 }
1098 
SetScreenSkipFrameInterval(ScreenId id,uint32_t skipFrameInterval)1099 int32_t RSScreenManager::SetScreenSkipFrameInterval(ScreenId id, uint32_t skipFrameInterval)
1100 {
1101     std::lock_guard<std::mutex> lock(mutex_);
1102     return SetScreenSkipFrameIntervalLocked(id, skipFrameInterval);
1103 }
1104 } // namespace impl
1105 
CreateOrGetScreenManager()1106 sptr<RSScreenManager> CreateOrGetScreenManager()
1107 {
1108     return impl::RSScreenManager::GetInstance();
1109 }
1110 } // namespace Rosen
1111 } // namespace OHOS
1112