1 /*
2 * Copyright (c) 2021-2022 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.h"
17
18 #include <algorithm>
19 #include <cinttypes>
20
21 #include "graphic_feature_param_manager.h"
22 #include "pipeline/main_thread/rs_main_thread.h"
23 #include "platform/common/rs_log.h"
24 #include "platform/common/rs_system_properties.h"
25 #include "rs_trace.h"
26 #include "string_utils.h"
27 #include "hisysevent.h"
28 #include "hgm_core.h"
29 #include "platform/common/rs_hisysevent.h"
30
31 #undef LOG_TAG
32 #define LOG_TAG "RSScreen"
33
34 namespace OHOS {
35 namespace Rosen {
36 using namespace HiviewDFX;
37
38 namespace impl {
39 std::map<GraphicColorGamut, GraphicCM_ColorSpaceType> RSScreen::RS_TO_COMMON_COLOR_SPACE_TYPE_MAP {
40 {GRAPHIC_COLOR_GAMUT_STANDARD_BT601, GRAPHIC_CM_BT601_EBU_FULL},
41 {GRAPHIC_COLOR_GAMUT_STANDARD_BT709, GRAPHIC_CM_BT709_FULL},
42 {GRAPHIC_COLOR_GAMUT_SRGB, GRAPHIC_CM_SRGB_FULL},
43 {GRAPHIC_COLOR_GAMUT_ADOBE_RGB, GRAPHIC_CM_ADOBERGB_FULL},
44 {GRAPHIC_COLOR_GAMUT_DISPLAY_P3, GRAPHIC_CM_P3_FULL},
45 {GRAPHIC_COLOR_GAMUT_BT2020, GRAPHIC_CM_DISPLAY_BT2020_SRGB},
46 {GRAPHIC_COLOR_GAMUT_BT2100_PQ, GRAPHIC_CM_BT2020_PQ_FULL},
47 {GRAPHIC_COLOR_GAMUT_BT2100_HLG, GRAPHIC_CM_BT2020_HLG_FULL},
48 {GRAPHIC_COLOR_GAMUT_DISPLAY_BT2020, GRAPHIC_CM_DISPLAY_BT2020_SRGB},
49 };
50 std::map<GraphicCM_ColorSpaceType, GraphicColorGamut> RSScreen::COMMON_COLOR_SPACE_TYPE_TO_RS_MAP {
51 {GRAPHIC_CM_BT601_EBU_FULL, GRAPHIC_COLOR_GAMUT_STANDARD_BT601},
52 {GRAPHIC_CM_BT709_FULL, GRAPHIC_COLOR_GAMUT_STANDARD_BT709},
53 {GRAPHIC_CM_SRGB_FULL, GRAPHIC_COLOR_GAMUT_SRGB},
54 {GRAPHIC_CM_ADOBERGB_FULL, GRAPHIC_COLOR_GAMUT_ADOBE_RGB},
55 {GRAPHIC_CM_P3_FULL, GRAPHIC_COLOR_GAMUT_DISPLAY_P3},
56 {GRAPHIC_CM_DISPLAY_BT2020_SRGB, GRAPHIC_COLOR_GAMUT_BT2020},
57 {GRAPHIC_CM_BT2020_PQ_FULL, GRAPHIC_COLOR_GAMUT_BT2100_PQ},
58 {GRAPHIC_CM_BT2020_HLG_FULL, GRAPHIC_COLOR_GAMUT_BT2100_HLG},
59 {GRAPHIC_CM_DISPLAY_BT2020_SRGB, GRAPHIC_COLOR_GAMUT_DISPLAY_BT2020},
60 };
61 std::map<GraphicHDRFormat, ScreenHDRFormat> RSScreen::HDI_HDR_FORMAT_TO_RS_MAP {
62 {GRAPHIC_NOT_SUPPORT_HDR, NOT_SUPPORT_HDR},
63 {GRAPHIC_DOLBY_VISION, NOT_SUPPORT_HDR},
64 {GRAPHIC_HDR10, VIDEO_HDR10},
65 {GRAPHIC_HLG, VIDEO_HLG},
66 {GRAPHIC_HDR10_PLUS, NOT_SUPPORT_HDR},
67 {GRAPHIC_HDR_VIVID, VIDEO_HDR_VIVID},
68 };
69 std::map<ScreenHDRFormat, GraphicHDRFormat> RSScreen::RS_TO_HDI_HDR_FORMAT_MAP {
70 {NOT_SUPPORT_HDR, GRAPHIC_NOT_SUPPORT_HDR},
71 {VIDEO_HLG, GRAPHIC_HLG},
72 {VIDEO_HDR10, GRAPHIC_HDR10},
73 {VIDEO_HDR_VIVID, GRAPHIC_HDR_VIVID},
74 {IMAGE_HDR_VIVID_DUAL, GRAPHIC_HDR_VIVID},
75 {IMAGE_HDR_VIVID_SINGLE, GRAPHIC_HDR_VIVID},
76 {IMAGE_HDR_ISO_DUAL, GRAPHIC_NOT_SUPPORT_HDR},
77 {IMAGE_HDR_ISO_SINGLE, GRAPHIC_NOT_SUPPORT_HDR},
78 };
79
80 constexpr int MAX_LUM = 1000;
81
RSScreen(ScreenId id,bool isVirtual,std::shared_ptr<HdiOutput> output,sptr<Surface> surface)82 RSScreen::RSScreen(ScreenId id,
83 bool isVirtual,
84 std::shared_ptr<HdiOutput> output,
85 sptr<Surface> surface)
86 : id_(id),
87 isVirtual_(isVirtual),
88 hdiOutput_(std::move(output)),
89 producerSurface_(std::move(surface))
90 {
91 if (!IsVirtual()) {
92 hdrCapability_.formatCount = 0;
93 name_ = "Screen_" + std::to_string(id_);
94 PhysicalScreenInit();
95 RS_LOGW("init physical: {id: %{public}" PRIu64 ", w * h: [%{public}u * %{public}u], "
96 "screenType: %{public}u}", id_, width_, height_, screenType_);
97 }
98 capability_.props.clear();
99 }
100
RSScreen(const VirtualScreenConfigs & configs)101 RSScreen::RSScreen(const VirtualScreenConfigs &configs)
102 : id_(configs.id),
103 mirrorId_(configs.mirrorId),
104 name_(configs.name),
105 width_(configs.width),
106 height_(configs.height),
107 isVirtual_(true),
108 producerSurface_(configs.surface),
109 pixelFormat_(configs.pixelFormat),
110 screenType_(RSScreenType::VIRTUAL_TYPE_SCREEN),
111 whiteList_(configs.whiteList)
112 {
113 VirtualScreenInit();
114 RS_LOGW("init virtual: {id: %{public}" PRIu64 ", mirrorId: %{public}" PRIu64
115 ", w * h: [%{public}u * %{public}u], name: %{public}s, screenType: %{public}u}",
116 id_, mirrorId_, width_, height_, name_.c_str(), screenType_);
117 }
118
~RSScreen()119 RSScreen::~RSScreen() noexcept
120 {
121 }
122
VirtualScreenInit()123 void RSScreen::VirtualScreenInit() noexcept
124 {
125 hdrCapability_.formatCount = 0;
126 for (auto item : supportedVirtualHDRFormats_) {
127 hdrCapability_.formats.emplace_back(RS_TO_HDI_HDR_FORMAT_MAP[item]);
128 ++hdrCapability_.formatCount;
129 }
130 }
131
PhysicalScreenInit()132 void RSScreen::PhysicalScreenInit() noexcept
133 {
134 hdiScreen_ = HdiScreen::CreateHdiScreen(ScreenPhysicalId(id_));
135 if (hdiScreen_ == nullptr) {
136 RS_LOGE("%{public}s: RSScreen(id %{public}" PRIu64 ") failed to CreateHdiScreens.",
137 __func__, id_);
138 return;
139 }
140
141 hdiScreen_->Init();
142 if (hdiScreen_->GetScreenSupportedModes(supportedModes_) < 0) {
143 RS_LOGE("%{public}s: RSScreen(id %{public}" PRIu64 ") failed to GetScreenSupportedModes.",
144 __func__, id_);
145 }
146
147 if (hdiScreen_->GetHDRCapabilityInfos(hdrCapability_) < 0) {
148 RS_LOGE("%{public}s: RSScreen(id %{public}" PRIu64 ") failed to GetHDRCapabilityInfos.",
149 __func__, id_);
150 }
151 std::transform(hdrCapability_.formats.begin(), hdrCapability_.formats.end(),
152 back_inserter(supportedPhysicalHDRFormats_),
153 [](GraphicHDRFormat item) -> ScreenHDRFormat {return HDI_HDR_FORMAT_TO_RS_MAP[item];});
154 auto status = GraphicDispPowerStatus::GRAPHIC_POWER_STATUS_ON;
155 auto multiScreenFeatureParam = std::static_pointer_cast<MultiScreenParam>(
156 GraphicFeatureParamManager::GetInstance().GetFeatureParam(FEATURE_CONFIGS[MULTISCREEN]));
157 if (!multiScreenFeatureParam) {
158 RS_LOGE("%{public}s multiScreenFeatureParam is null", __func__);
159 return;
160 }
161 if (multiScreenFeatureParam->IsRsSetScreenPowerStatus() || id_ == 0) {
162 RS_LOGI("%{public}s: RSScreen(id %{public}" PRIu64 ") start SetScreenPowerStatus to On",
163 __func__, id_);
164 if (hdiScreen_->SetScreenPowerStatus(status) < 0) {
165 RS_LOGE("%{public}s: RSScreen(id %{public}" PRIu64 ") failed to SetScreenPowerStatus.",
166 __func__, id_);
167 } else {
168 RS_LOGI("%{public}s: RSScreen(id %{public}" PRIu64 ") end SetScreenPowerStatus to On",
169 __func__, id_);
170 }
171 }
172 auto activeMode = GetActiveMode();
173 if (activeMode) {
174 phyWidth_ = activeMode->width;
175 phyHeight_ = activeMode->height;
176 width_ = phyWidth_;
177 height_ = phyHeight_;
178 }
179 if (hdiScreen_->GetScreenPowerStatus(status) < 0) {
180 RS_LOGE("%{public}s: RSScreen(id %{public}" PRIu64 ") failed to GetScreenPowerStatus.",
181 __func__, id_);
182 powerStatus_ = ScreenPowerStatus::INVALID_POWER_STATUS;
183 } else {
184 powerStatus_ = static_cast<ScreenPowerStatus>(status);
185 }
186 if (capability_.type == GraphicInterfaceType::GRAPHIC_DISP_INTF_MIPI) {
187 screenType_ = RSScreenType::BUILT_IN_TYPE_SCREEN;
188 } else {
189 screenType_ = RSScreenType::EXTERNAL_TYPE_SCREEN;
190 }
191 ScreenCapabilityInit();
192
193 std::vector<GraphicColorGamut> supportedColorGamuts;
194 if (hdiScreen_->GetScreenSupportedColorGamuts(supportedColorGamuts) != GRAPHIC_DISPLAY_SUCCESS) {
195 RS_LOGE("%{public}s: RSScreen(id %{public}" PRIu64 ") failed to GetScreenSupportedColorGamuts.",
196 __func__, id_);
197 } else {
198 int index = 0;
199 for (auto item : supportedColorGamuts) {
200 supportedPhysicalColorGamuts_.push_back(static_cast<ScreenColorGamut>(item));
201 if (item == GraphicColorGamut::GRAPHIC_COLOR_GAMUT_SRGB) {
202 currentPhysicalColorGamutIdx_ = index;
203 }
204 ++index;
205 }
206 }
207 screenBacklightLevel_ = GetScreenBacklight();
208 }
209
ScreenCapabilityInit()210 void RSScreen::ScreenCapabilityInit() noexcept
211 {
212 if (!hdiScreen_) {
213 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
214 return;
215 }
216 int32_t ret = hdiScreen_->GetScreenCapability(capability_);
217 if (ret != GRAPHIC_DISPLAY_SUCCESS) {
218 RS_LOGE("%{public}s: get display capability failed, ret is %{public}d, use the default"
219 " display capability.", __func__, ret);
220 capability_ = {
221 .name = "test1",
222 .type = GRAPHIC_DISP_INTF_HDMI,
223 .phyWidth = 1921,
224 .phyHeight = 1081,
225 .supportLayers = 0,
226 .virtualDispCount = 0,
227 .supportWriteBack = true,
228 .propertyCount = 0
229 };
230 }
231 }
232
Id() const233 ScreenId RSScreen::Id() const
234 {
235 return id_;
236 }
237
MirrorId() const238 ScreenId RSScreen::MirrorId() const
239 {
240 return mirrorId_;
241 }
242
SetMirror(ScreenId mirrorId)243 void RSScreen::SetMirror(ScreenId mirrorId)
244 {
245 mirrorId_ = mirrorId;
246 }
247
Name() const248 const std::string& RSScreen::Name() const
249 {
250 return name_;
251 }
252
Width() const253 uint32_t RSScreen::Width() const
254 {
255 std::shared_lock<std::shared_mutex> lock(screenMutex_);
256 return width_;
257 }
258
Height() const259 uint32_t RSScreen::Height() const
260 {
261 std::shared_lock<std::shared_mutex> lock(screenMutex_);
262 return height_;
263 }
264
PhyWidth() const265 uint32_t RSScreen::PhyWidth() const
266 {
267 std::shared_lock<std::shared_mutex> lock(screenMutex_);
268 return phyWidth_;
269 }
270
PhyHeight() const271 uint32_t RSScreen::PhyHeight() const
272 {
273 std::shared_lock<std::shared_mutex> lock(screenMutex_);
274 return phyHeight_;
275 }
276
IsSamplingOn() const277 bool RSScreen::IsSamplingOn() const
278 {
279 std::shared_lock<std::shared_mutex> lock(screenMutex_);
280 return isSamplingOn_;
281 }
282
GetSamplingTranslateX() const283 float RSScreen::GetSamplingTranslateX() const
284 {
285 std::shared_lock<std::shared_mutex> lock(screenMutex_);
286 return samplingTranslateX_;
287 }
288
GetSamplingTranslateY() const289 float RSScreen::GetSamplingTranslateY() const
290 {
291 std::shared_lock<std::shared_mutex> lock(screenMutex_);
292 return samplingTranslateY_;
293 }
294
GetSamplingScale() const295 float RSScreen::GetSamplingScale() const
296 {
297 std::shared_lock<std::shared_mutex> lock(screenMutex_);
298 return samplingScale_;
299 }
300
GetActiveRect() const301 RectI RSScreen::GetActiveRect() const
302 {
303 std::shared_lock<std::shared_mutex> lock(screenMutex_);
304 return activeRect_;
305 }
306
GetMaskRect() const307 RectI RSScreen::GetMaskRect() const
308 {
309 std::shared_lock<std::shared_mutex> lock(screenMutex_);
310 return maskRect_;
311 }
312
GetReviseRect() const313 RectI RSScreen::GetReviseRect() const
314 {
315 std::shared_lock<std::shared_mutex> lock(screenMutex_);
316 return reviseRect_;
317 }
318
IsEnable() const319 bool RSScreen::IsEnable() const
320 {
321 if (id_ == INVALID_SCREEN_ID) {
322 return false;
323 }
324
325 if (!hdiOutput_ && !producerSurface_) {
326 return false;
327 }
328
329 // [PLANNING]: maybe need more information to judge whether this screen is enable.
330 return true;
331 }
332
IsVirtual() const333 bool RSScreen::IsVirtual() const
334 {
335 return isVirtual_;
336 }
337
WriteHisyseventEpsLcdInfo(GraphicDisplayModeInfo & activeMode)338 void RSScreen::WriteHisyseventEpsLcdInfo(GraphicDisplayModeInfo& activeMode)
339 {
340 auto frameRateMgr = HgmCore::Instance().GetFrameRateMgr();
341 if (frameRateMgr != nullptr && frameRateMgr->IsLtpo()) {
342 RS_LOGW_IF(DEBUG_SCREEN, "RSScreen LTPO mode");
343 return;
344 }
345 static GraphicDisplayModeInfo modeInfo;
346 if ((modeInfo.freshRate != activeMode.freshRate)
347 || modeInfo.width != activeMode.width || modeInfo.height != activeMode.height) {
348 RS_TRACE_NAME("RSScreen::WriteHisyseventEpsLcdInfo HiSysEventWrite");
349 RSHiSysEvent::EventWrite(RSEventName::EPS_LCD_FREQ, RSEventType::RS_STATISTIC,
350 "SOURCERATE", modeInfo.freshRate, "TARGETRATE", activeMode.freshRate, "WIDTH", activeMode.width,
351 "HEIGHT", activeMode.height);
352 modeInfo = activeMode;
353 }
354 }
355
SetActiveMode(uint32_t modeId)356 uint32_t RSScreen::SetActiveMode(uint32_t modeId)
357 {
358 if (IsVirtual()) {
359 RS_LOGW("%{public}s: virtual screen not support SetActiveMode.", __func__);
360 return StatusCode::VIRTUAL_SCREEN;
361 }
362 if (!hdiScreen_) {
363 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
364 return StatusCode::SCREEN_NOT_FOUND;
365 }
366
367 if (modeId >= supportedModes_.size()) {
368 RS_LOGE("%{public}s: set fails because the index is out of bounds.", __func__);
369 return StatusCode::INVALID_ARGUMENTS;
370 }
371 RS_LOGW_IF(DEBUG_SCREEN, "RSScreen set active mode: %{public}u", modeId);
372 int32_t selectModeId = supportedModes_[modeId].id;
373 if (hdiScreen_->SetScreenMode(static_cast<uint32_t>(selectModeId)) < 0) {
374 RS_LOGE("%{public}s: Hdi SetScreenMode fails.", __func__);
375 return StatusCode::SET_RATE_ERROR;
376 }
377 auto activeMode = GetActiveMode();
378 if (activeMode) {
379 std::unique_lock<std::shared_mutex> lock(screenMutex_);
380 phyWidth_ = activeMode->width;
381 phyHeight_ = activeMode->height;
382 lock.unlock();
383 WriteHisyseventEpsLcdInfo(activeMode.value());
384 }
385 return StatusCode::SUCCESS;
386 }
387
SetScreenActiveRect(const GraphicIRect & activeRect)388 uint32_t RSScreen::SetScreenActiveRect(const GraphicIRect& activeRect)
389 {
390 if (IsVirtual()) {
391 RS_LOGW("%{public}s failed: virtual screen not support", __func__);
392 return StatusCode::HDI_ERROR;
393 }
394 if (hdiScreen_ == nullptr) {
395 RS_LOGE("%{public}s failed: hdiScreen_ is nullptr", __func__);
396 return StatusCode::HDI_ERROR;
397 }
398 if (activeRect.x < 0 || activeRect.y < 0 || activeRect.w <= 0 || activeRect.h <= 0 ||
399 static_cast<uint32_t>(activeRect.x + activeRect.w) > width_ ||
400 static_cast<uint32_t>(activeRect.y + activeRect.h) > height_) {
401 RS_LOGW("%{public}s failed:, for activeRect: "
402 "(%{public}" PRId32 ", %{public}" PRId32 ", %{public}" PRId32 ", %{public}" PRId32 ")",
403 __func__, activeRect.x, activeRect.y, activeRect.w, activeRect.h);
404 return StatusCode::INVALID_ARGUMENTS;
405 }
406
407 std::unique_lock<std::shared_mutex> lock(screenMutex_);
408 activeRect_ = RectI(activeRect.x, activeRect.y, activeRect.w, activeRect.h);
409 RS_LOGI("%{public}s success, activeRect: (%{public}" PRId32 ", %{public}" PRId32 ", "
410 "%{public}" PRId32 ", %{public}" PRId32 ")", __func__, activeRect.x, activeRect.y, activeRect.w, activeRect.h);
411 GraphicIRect reviseRect = activeRect;
412 if (!CalculateMaskRectAndReviseRect(activeRect, reviseRect)) {
413 RS_LOGW("CalculateMaskRect failed or not need");
414 }
415 reviseRect_ = RectI(reviseRect.x, reviseRect.y, reviseRect.w, reviseRect.h);
416 lock.unlock();
417
418 if (hdiScreen_->SetScreenActiveRect(reviseRect) < 0) {
419 RS_LOGE("%{public}s failed: hdi SetScreenActiveRect failed, activeRect with revise:"
420 "(%{public}" PRId32 ", %{public}" PRId32 ", %{public}" PRId32 ", %{public}" PRId32 ")",
421 __func__, reviseRect.x, reviseRect.y, reviseRect.w, reviseRect.h);
422 return StatusCode::HDI_ERROR;
423 }
424 RS_LOGI("%{public}s success, reviseRect: (%{public}" PRId32 ", %{public}" PRId32 ", "
425 "%{public}" PRId32 ", %{public}" PRId32 ")", __func__, reviseRect.x, reviseRect.y, reviseRect.w, reviseRect.h);
426 return StatusCode::SUCCESS;
427 }
428
CalculateMaskRectAndReviseRect(const GraphicIRect & activeRect,GraphicIRect & reviseRect)429 bool RSScreen::CalculateMaskRectAndReviseRect(const GraphicIRect& activeRect, GraphicIRect& reviseRect)
430 {
431 if (!RSSystemProperties::IsSuperFoldDisplay()) {
432 RS_LOGE("device is not super fold display");
433 return false;
434 }
435 if (activeRect.w > 0 && activeRect.h > 0) {
436 // neet tobe configuration item
437 static RectI rect[2] = {{0, 0, 0, 0}, {0, 1008, 2232, 128}};
438 maskRect_ = (static_cast<uint32_t>(activeRect.h) == height_) ? rect[0] : rect[1];
439 // Take the minimum rectangular area containing two rectangles
440 reviseRect.x = std::clamp(activeRect.x, 0, std::min(activeRect.x, maskRect_.left_));
441 reviseRect.y = std::clamp(activeRect.y, 0, std::min(activeRect.y, maskRect_.top_));
442 reviseRect.w = std::max(activeRect.x + activeRect.w, maskRect_.left_ + maskRect_.width_) - reviseRect.x;
443 reviseRect.h = std::max(activeRect.y + activeRect.h, maskRect_.top_ + maskRect_.height_) - reviseRect.y;
444 RS_LOGI("%{public}s success, maskRect: %{public}s", __func__, maskRect_.ToString().c_str());
445 return true;
446 }
447 return false;
448 }
449
SetRogResolution(uint32_t width,uint32_t height)450 void RSScreen::SetRogResolution(uint32_t width, uint32_t height)
451 {
452 if (!hdiScreen_) {
453 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
454 return;
455 }
456
457 std::shared_lock<std::shared_mutex> sharedLock(screenMutex_);
458 if ((width == 0 || height == 0) ||
459 (width == width_ && height == height_) ||
460 (width > phyWidth_ || height > phyHeight_)) {
461 RS_LOGD("%{public}s: width: %{public}d, height: %{public}d.", __func__, width, height);
462 return;
463 }
464 sharedLock.unlock();
465
466 if (hdiScreen_->SetScreenOverlayResolution(width, height) < 0) {
467 RS_LOGE("%{public}s: hdi set screen rog resolution failed.", __func__);
468 }
469 std::lock_guard<std::shared_mutex> lock(screenMutex_);
470 width_ = width;
471 height_ = height;
472 RS_LOGI("%{public}s: RSScreen(id %{public}" PRIu64 "), width: %{public}d,"
473 " height: %{public}d, phywidth: %{public}d, phyHeight: %{public}d.",
474 __func__, id_, width_, height_, phyWidth_, phyHeight_);
475 }
476
SetResolution(uint32_t width,uint32_t height)477 int32_t RSScreen::SetResolution(uint32_t width, uint32_t height)
478 {
479 RS_LOGI("%{public}s width: %{public}u height: %{public}u", __func__, width, height);
480 std::lock_guard<std::shared_mutex> lock(screenMutex_);
481 if (IsVirtual()) {
482 width_ = width;
483 height_ = height;
484 return StatusCode::SUCCESS;
485 }
486 if (width < phyWidth_ || height < phyHeight_) {
487 RS_LOGE("%{public}s phyWidth: %{public}u phyHeight: %{public}u", __func__, phyWidth_, phyHeight_);
488 return StatusCode::INVALID_ARGUMENTS;
489 }
490 width_ = width;
491 height_ = height;
492 isSamplingOn_ = width > phyWidth_ || height > phyHeight_;
493 if (isSamplingOn_ && width_ > 0 && height_ > 0) {
494 samplingScale_ = std::min(static_cast<float>(phyWidth_) / width_,
495 static_cast<float>(phyHeight_) / height_);
496 samplingTranslateX_ = (phyWidth_ - width_ * samplingScale_) / 2.f;
497 samplingTranslateY_ = (phyHeight_ - height_ * samplingScale_) / 2.f;
498 RS_LOGI("%{public}s: sampling is enable. "
499 "scale: %{public}f, translateX: %{public}f, translateY: %{public}f",
500 __func__, samplingScale_, samplingTranslateX_, samplingTranslateY_);
501 }
502 return StatusCode::SUCCESS;
503 }
504
GetActiveModePosByModeId(int32_t modeId) const505 int32_t RSScreen::GetActiveModePosByModeId(int32_t modeId) const
506 {
507 decltype(supportedModes_.size()) modeIndex = 0;
508 for (; modeIndex < supportedModes_.size(); ++modeIndex) {
509 if (supportedModes_[modeIndex].id == modeId) {
510 return static_cast<int32_t>(modeIndex);
511 }
512 }
513 return -1;
514 }
515
SetPowerStatus(uint32_t powerStatus)516 int32_t RSScreen::SetPowerStatus(uint32_t powerStatus)
517 {
518 if (!hdiScreen_) {
519 RS_LOGE("[UL_POWER] %{public}s failed, hdiScreen_ is nullptr", __func__);
520 return StatusCode::HDI_ERROR;
521 }
522
523 RS_LOGW("[UL_POWER]RSScreen_%{public}" PRIu64 " SetPowerStatus: %{public}u.", id_, powerStatus);
524 RS_TRACE_NAME_FMT("[UL_POWER]Screen_%llu SetPowerStatus %u", id_, powerStatus);
525 if (hdiScreen_->SetScreenPowerStatus(static_cast<GraphicDispPowerStatus>(powerStatus)) < 0) {
526 RS_LOGW("[UL_POWER] %{public}s failed to set power status", __func__);
527 powerStatus_ = ScreenPowerStatus::INVALID_POWER_STATUS;
528 return StatusCode::HDI_ERROR;
529 }
530 powerStatus_ = static_cast<ScreenPowerStatus>(powerStatus);
531
532 RS_LOGW("[UL_POWER]RSScreen_%{public}" PRIu64 " SetPowerStatus: %{public}u done.", id_, powerStatus);
533 return StatusCode::SUCCESS;
534 }
535
GetActiveMode() const536 std::optional<GraphicDisplayModeInfo> RSScreen::GetActiveMode() const
537 {
538 if (IsVirtual()) {
539 RS_LOGW("%{public}s: virtual screen not support GetActiveMode.", __func__);
540 return {};
541 }
542
543 uint32_t modeId = 0;
544
545 if (hdiScreen_ == nullptr) {
546 RS_LOGE("%{public}s: id: %{public}" PRIu64 " hdiScreen is null.", __func__, id_);
547 return {};
548 }
549
550 if (hdiScreen_->GetScreenMode(modeId) < 0) {
551 RS_LOGE("%{public}s: id: %{public}" PRIu64 " GetScreenMode failed.", __func__, id_);
552 return {};
553 }
554
555 auto iter = std::find_if(supportedModes_.cbegin(), supportedModes_.cend(),
556 [modeId](const auto &mode) { return static_cast<uint32_t>(mode.id) == modeId; });
557 if (iter == supportedModes_.cend()) {
558 return {};
559 }
560
561 return *iter;
562 }
563
GetSupportedModes() const564 const std::vector<GraphicDisplayModeInfo>& RSScreen::GetSupportedModes() const
565 {
566 return supportedModes_;
567 }
568
GetCapability() const569 const GraphicDisplayCapability& RSScreen::GetCapability() const
570 {
571 return capability_;
572 }
573
GetPowerStatus()574 uint32_t RSScreen::GetPowerStatus()
575 {
576 if (IsVirtual()) {
577 RS_LOGW("%{public}s: virtual screen not support GetPowerStatus.", __func__);
578 return ScreenPowerStatus::INVALID_POWER_STATUS;
579 }
580 if (!hdiScreen_) {
581 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
582 return INVALID_POWER_STATUS;
583 }
584
585 if (powerStatus_ != ScreenPowerStatus::INVALID_POWER_STATUS) {
586 return static_cast<uint32_t>(powerStatus_);
587 }
588
589 auto status = GraphicDispPowerStatus::GRAPHIC_POWER_STATUS_ON;
590 if (hdiScreen_->GetScreenPowerStatus(status) < 0) {
591 powerStatus_ = ScreenPowerStatus::INVALID_POWER_STATUS;
592 RS_LOGE("%{public}s failed to get screen powerStatus", __func__);
593 return INVALID_POWER_STATUS;
594 }
595 powerStatus_ = static_cast<ScreenPowerStatus>(status);
596 RS_LOGW("%{public}s cached powerStatus is INVALID_POWER_STATUS and GetScreenPowerStatus %{public}d",
597 __func__, static_cast<uint32_t>(status));
598 return static_cast<uint32_t>(status);
599 }
600
GetOutput() const601 std::shared_ptr<HdiOutput> RSScreen::GetOutput() const
602 {
603 return hdiOutput_;
604 }
605
GetProducerSurface() const606 sptr<Surface> RSScreen::GetProducerSurface() const
607 {
608 return producerSurface_;
609 }
610
SetProducerSurface(sptr<Surface> producerSurface)611 void RSScreen::SetProducerSurface(sptr<Surface> producerSurface)
612 {
613 producerSurface_ = producerSurface;
614 isVirtualSurfaceUpdateFlag_ = true;
615 }
616
GetAndResetVirtualSurfaceUpdateFlag()617 bool RSScreen::GetAndResetVirtualSurfaceUpdateFlag()
618 {
619 if (isVirtualSurfaceUpdateFlag_) {
620 isVirtualSurfaceUpdateFlag_ = false;
621 return true;
622 }
623 return false;
624 }
625
ModeInfoDump(std::string & dumpString)626 void RSScreen::ModeInfoDump(std::string& dumpString)
627 {
628 decltype(supportedModes_.size()) modeIndex = 0;
629 for (; modeIndex < supportedModes_.size(); ++modeIndex) {
630 AppendFormat(dumpString, " supportedMode[%d]: %dx%d, refreshrate=%d\n",
631 modeIndex, supportedModes_[modeIndex].width,
632 supportedModes_[modeIndex].height, supportedModes_[modeIndex].freshRate);
633 }
634 std::optional<GraphicDisplayModeInfo> activeMode = GetActiveMode();
635 if (activeMode) {
636 AppendFormat(dumpString, " activeMode: %dx%d, refreshrate=%d\n",
637 activeMode->width, activeMode->height, activeMode->freshRate);
638 }
639 }
640
CapabilityTypeDump(GraphicInterfaceType capabilityType,std::string & dumpString)641 void RSScreen::CapabilityTypeDump(GraphicInterfaceType capabilityType, std::string& dumpString)
642 {
643 dumpString += "type=";
644 switch (capabilityType) {
645 case GRAPHIC_DISP_INTF_HDMI: {
646 dumpString += "DISP_INTF_HDMI, ";
647 break;
648 }
649 case GRAPHIC_DISP_INTF_LCD: {
650 dumpString += "DISP_INTF_LCD, ";
651 break;
652 }
653 case GRAPHIC_DISP_INTF_BT1120: {
654 dumpString += "DISP_INTF_BT1120, ";
655 break;
656 }
657 case GRAPHIC_DISP_INTF_BT656: {
658 dumpString += "DISP_INTF_BT656, ";
659 break;
660 }
661 default:
662 dumpString += "INVILID_DISP_INTF, ";
663 break;
664 }
665 }
666
CapabilityDump(std::string & dumpString)667 void RSScreen::CapabilityDump(std::string& dumpString)
668 {
669 AppendFormat(dumpString, " capability: name=%s, phywidth=%d, phyheight=%d,"
670 "supportlayers=%d, virtualDispCount=%d, propCount=%d, ",
671 capability_.name.c_str(), capability_.phyWidth, capability_.phyHeight,
672 capability_.supportLayers, capability_.virtualDispCount, capability_.propertyCount);
673 CapabilityTypeDump(capability_.type, dumpString);
674 dumpString += "supportWriteBack=";
675 dumpString += (capability_.supportWriteBack) ? "true" : "false";
676 dumpString += "\n";
677 PropDump(dumpString);
678 }
679
PropDump(std::string & dumpString)680 void RSScreen::PropDump(std::string& dumpString)
681 {
682 decltype(capability_.propertyCount) propIndex = 0;
683 for (; propIndex < capability_.propertyCount; ++propIndex) {
684 AppendFormat(dumpString, "prop[%u]: name=%s, propid=%d, value=%d\n",
685 propIndex, capability_.props[propIndex].name.c_str(), capability_.props[propIndex].propId,
686 capability_.props[propIndex].value);
687 }
688 }
689
PowerStatusDump(std::string & dumpString)690 void RSScreen::PowerStatusDump(std::string& dumpString)
691 {
692 dumpString += "powerstatus=";
693 switch (GetPowerStatus()) {
694 case GRAPHIC_POWER_STATUS_ON: {
695 dumpString += "POWER_STATUS_ON";
696 break;
697 }
698 case GRAPHIC_POWER_STATUS_STANDBY: {
699 dumpString += "POWER_STATUS_STANDBY";
700 break;
701 }
702 case GRAPHIC_POWER_STATUS_SUSPEND: {
703 dumpString += "POWER_STATUS_SUSPEND";
704 break;
705 }
706 case GRAPHIC_POWER_STATUS_OFF: {
707 dumpString += "POWER_STATUS_OFF";
708 break;
709 }
710 case GRAPHIC_POWER_STATUS_OFF_FAKE: {
711 dumpString += "POWER_STATUS_OFF_FAKE";
712 break;
713 }
714 case GRAPHIC_POWER_STATUS_BUTT: {
715 dumpString += "POWER_STATUS_BUTT";
716 break;
717 }
718 case GRAPHIC_POWER_STATUS_ON_ADVANCED: {
719 dumpString += "POWER_STATUS_ON_ADVANCED";
720 break;
721 }
722 case GRAPHIC_POWER_STATUS_OFF_ADVANCED: {
723 dumpString += "POWER_STATUS_OFF_ADVANCED";
724 break;
725 }
726 default: {
727 dumpString += "INVALID_POWER_STATUS";
728 break;
729 }
730 }
731 }
732
733
DisplayDump(int32_t screenIndex,std::string & dumpString)734 void RSScreen::DisplayDump(int32_t screenIndex, std::string& dumpString)
735 {
736 dumpString += "-- ScreenInfo\n";
737 if (IsVirtual()) {
738 dumpString += "screen[" + std::to_string(screenIndex) + "]: ";
739 dumpString += "id=";
740 dumpString += (id_ == INVALID_SCREEN_ID) ? "INVALID_SCREEN_ID" : std::to_string(id_);
741 dumpString += ", ";
742 dumpString += "mirrorId=";
743 dumpString += (mirrorId_ == INVALID_SCREEN_ID) ? "INVALID_SCREEN_ID" : std::to_string(mirrorId_);
744 dumpString += ", ";
745 std::shared_lock<std::shared_mutex> screenLock(screenMutex_, std::defer_lock);
746 std::shared_lock<std::shared_mutex> skipFrameLock(skipFrameMutex_, std::defer_lock);
747 std::lock(screenLock, skipFrameLock);
748 AppendFormat(dumpString, ", render size: %dx%d, isvirtual=true, skipFrameInterval_:%d"
749 ", expectedRefreshRate_:%d, skipFrameStrategy_:%d\n",
750 width_, height_, skipFrameInterval_, expectedRefreshRate_, skipFrameStrategy_);
751 } else {
752 dumpString += "screen[" + std::to_string(screenIndex) + "]: ";
753 dumpString += "id=";
754 dumpString += (id_ == INVALID_SCREEN_ID) ? "INVALID_SCREEN_ID" : std::to_string(id_);
755 dumpString += ", ";
756 PowerStatusDump(dumpString);
757 dumpString += ", ";
758 dumpString += "backlight=" + std::to_string(GetScreenBacklight());
759 dumpString += ", ";
760 ScreenTypeDump(dumpString);
761 std::shared_lock<std::shared_mutex> screenLock(screenMutex_, std::defer_lock);
762 std::shared_lock<std::shared_mutex> skipFrameLock(skipFrameMutex_, std::defer_lock);
763 std::lock(screenLock, skipFrameLock);
764 AppendFormat(dumpString,
765 ", render size: %dx%d, physical screen resolution: %dx%d, isvirtual=false, skipFrameInterval_:%d"
766 ", expectedRefreshRate_:%d, skipFrameStrategy_:%d\n",
767 width_, height_, phyWidth_, phyHeight_, skipFrameInterval_, expectedRefreshRate_, skipFrameStrategy_);
768 screenLock.unlock();
769 skipFrameLock.unlock();
770 dumpString += "\n";
771 ModeInfoDump(dumpString);
772 CapabilityDump(dumpString);
773 }
774 }
775
ScreenTypeDump(std::string & dumpString)776 void RSScreen::ScreenTypeDump(std::string& dumpString)
777 {
778 dumpString += "screenType=";
779 switch (screenType_) {
780 case RSScreenType::BUILT_IN_TYPE_SCREEN: {
781 dumpString += "BUILT_IN_TYPE";
782 break;
783 }
784 case RSScreenType::EXTERNAL_TYPE_SCREEN: {
785 dumpString += "EXTERNAL_TYPE";
786 break;
787 }
788 case RSScreenType::VIRTUAL_TYPE_SCREEN: {
789 dumpString += "VIRTUAL_TYPE";
790 break;
791 }
792 default: {
793 dumpString += "UNKNOWN_TYPE";
794 break;
795 }
796 }
797 }
798
SurfaceDump(int32_t screenIndex,std::string & dumpString)799 void RSScreen::SurfaceDump(int32_t screenIndex, std::string& dumpString)
800 {
801 if (hdiOutput_ == nullptr) {
802 RS_LOGW("%{public}s: hdiOutput_ is nullptr.", __func__);
803 return;
804 }
805 hdiOutput_->Dump(dumpString);
806 }
807
FpsDump(int32_t screenIndex,std::string & dumpString,std::string & arg)808 void RSScreen::FpsDump(int32_t screenIndex, std::string& dumpString, std::string& arg)
809 {
810 if (hdiOutput_ == nullptr) {
811 RS_LOGW("%{public}s: hdiOutput_ is nullptr.", __func__);
812 return;
813 }
814 hdiOutput_->DumpFps(dumpString, arg);
815 }
816
ClearFpsDump(int32_t screenIndex,std::string & dumpString,std::string & arg)817 void RSScreen::ClearFpsDump(int32_t screenIndex, std::string& dumpString, std::string& arg)
818 {
819 if (hdiOutput_ == nullptr) {
820 RS_LOGW("%{public}s: hdiOutput_ is nullptr.", __func__);
821 return;
822 }
823 hdiOutput_->ClearFpsDump(dumpString, arg);
824 }
825
HitchsDump(int32_t screenIndex,std::string & dumpString,std::string & arg)826 void RSScreen::HitchsDump(int32_t screenIndex, std::string& dumpString, std::string& arg)
827 {
828 if (hdiOutput_ == nullptr) {
829 RS_LOGW("%{public}s: hdiOutput_ is nullptr.", __func__);
830 return;
831 }
832 hdiOutput_->DumpHitchs(dumpString, arg);
833 }
834
ResizeVirtualScreen(uint32_t width,uint32_t height)835 void RSScreen::ResizeVirtualScreen(uint32_t width, uint32_t height)
836 {
837 if (!IsVirtual()) {
838 RS_LOGW("%{public}s: physical screen not support ResizeVirtualScreen.", __func__);
839 return;
840 }
841 std::lock_guard<std::shared_mutex> lock(screenMutex_);
842 width_ = width;
843 height_ = height;
844 }
845
SetScreenBacklight(uint32_t level)846 void RSScreen::SetScreenBacklight(uint32_t level)
847 {
848 if (!hdiScreen_) {
849 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
850 return;
851 }
852 if (IsVirtual()) {
853 RS_LOGW("%{public}s: virtual screen not support SetScreenBacklight.", __func__);
854 return;
855 }
856
857 RS_LOGD("%{public}s id: %{public}" PRIu64 ", level is %{public}u", __func__, id_, level);
858 if (hdiScreen_->SetScreenBacklight(level) < 0) {
859 RS_LOGE("RSScreen_%{public}" PRIu64 " SetScreenBacklight error.", id_);
860 return;
861 }
862 std::lock_guard<std::shared_mutex> lock(screenMutex_);
863 screenBacklightLevel_ = static_cast<int32_t>(level);
864 }
865
GetScreenBacklight() const866 int32_t RSScreen::GetScreenBacklight() const
867 {
868 if (IsVirtual()) {
869 RS_LOGW("%{public}s: virtual screen not support GetScreenBacklight.", __func__);
870 return INVALID_BACKLIGHT_VALUE;
871 }
872 uint32_t level = 0;
873 if (std::shared_lock<std::shared_mutex> lock(screenMutex_);
874 screenBacklightLevel_ != INVALID_BACKLIGHT_VALUE) {
875 return screenBacklightLevel_;
876 }
877 if (!hdiScreen_) {
878 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
879 return INVALID_BACKLIGHT_VALUE;
880 }
881 if (hdiScreen_->GetScreenBacklight(level) < 0) {
882 RS_LOGE("%{public}s failed, level is invalid", __func__);
883 return INVALID_BACKLIGHT_VALUE;
884 }
885 return static_cast<int32_t>(level);
886 }
887
GetScreenSupportedColorGamuts(std::vector<ScreenColorGamut> & mode) const888 int32_t RSScreen::GetScreenSupportedColorGamuts(std::vector<ScreenColorGamut> &mode) const
889 {
890 mode.clear();
891 if (IsVirtual()) {
892 mode = supportedVirtualColorGamuts_;
893 } else {
894 mode = supportedPhysicalColorGamuts_;
895 }
896 if (mode.size() == 0) {
897 return StatusCode::HDI_ERROR;
898 }
899 return StatusCode::SUCCESS;
900 }
901
GetScreenSupportedMetaDataKeys(std::vector<ScreenHDRMetadataKey> & keys) const902 int32_t RSScreen::GetScreenSupportedMetaDataKeys(std::vector<ScreenHDRMetadataKey> &keys) const
903 {
904 if (IsVirtual()) {
905 RS_LOGW("%{public}s: virtual screen not support GetScreenSupportedMetaDataKeys.", __func__);
906 return INVALID_BACKLIGHT_VALUE;
907 }
908
909 // ScreenHDRMetadataKey now is mock data.
910 keys.push_back(ScreenHDRMetadataKey::MATAKEY_RED_PRIMARY_X);
911 keys.push_back(ScreenHDRMetadataKey::MATAKEY_RED_PRIMARY_Y);
912 keys.push_back(ScreenHDRMetadataKey::MATAKEY_GREEN_PRIMARY_X);
913 keys.push_back(ScreenHDRMetadataKey::MATAKEY_GREEN_PRIMARY_Y);
914 keys.push_back(ScreenHDRMetadataKey::MATAKEY_BLUE_PRIMARY_X);
915 keys.push_back(ScreenHDRMetadataKey::MATAKEY_BLUE_PRIMARY_Y);
916 keys.push_back(ScreenHDRMetadataKey::MATAKEY_WHITE_PRIMARY_X);
917 keys.push_back(ScreenHDRMetadataKey::MATAKEY_WHITE_PRIMARY_Y);
918 keys.push_back(ScreenHDRMetadataKey::MATAKEY_MAX_LUMINANCE);
919 keys.push_back(ScreenHDRMetadataKey::MATAKEY_MIN_LUMINANCE);
920 keys.push_back(ScreenHDRMetadataKey::MATAKEY_MAX_CONTENT_LIGHT_LEVEL);
921 keys.push_back(ScreenHDRMetadataKey::MATAKEY_MAX_FRAME_AVERAGE_LIGHT_LEVEL);
922 keys.push_back(ScreenHDRMetadataKey::MATAKEY_HDR10_PLUS);
923 keys.push_back(ScreenHDRMetadataKey::MATAKEY_HDR_VIVID);
924 return StatusCode::SUCCESS;
925 }
926
GetScreenColorGamut(ScreenColorGamut & mode) const927 int32_t RSScreen::GetScreenColorGamut(ScreenColorGamut &mode) const
928 {
929 if (IsVirtual()) {
930 mode = supportedVirtualColorGamuts_[currentVirtualColorGamutIdx_];
931 return StatusCode::SUCCESS;
932 }
933 if (supportedPhysicalColorGamuts_.size() == 0) {
934 RS_LOGE("%{public}s failed", __func__);
935 return StatusCode::HDI_ERROR;
936 }
937 mode = supportedPhysicalColorGamuts_[currentPhysicalColorGamutIdx_];
938 return StatusCode::SUCCESS;
939 }
940
SetScreenColorGamut(int32_t modeIdx)941 int32_t RSScreen::SetScreenColorGamut(int32_t modeIdx)
942 {
943 if (modeIdx < 0) {
944 return StatusCode::INVALID_ARGUMENTS;
945 }
946 if (IsVirtual()) {
947 if (modeIdx >= static_cast<int32_t>(supportedVirtualColorGamuts_.size())) {
948 return StatusCode::INVALID_ARGUMENTS;
949 }
950 currentVirtualColorGamutIdx_ = modeIdx;
951 return StatusCode::SUCCESS;
952 }
953 if (!hdiScreen_) {
954 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
955 return StatusCode::HDI_ERROR;
956 }
957 std::vector<GraphicColorGamut> hdiMode;
958 if (hdiScreen_->GetScreenSupportedColorGamuts(hdiMode) != GRAPHIC_DISPLAY_SUCCESS) {
959 return StatusCode::HDI_ERROR;
960 }
961 if (modeIdx >= static_cast<int32_t>(hdiMode.size())) {
962 return StatusCode::INVALID_ARGUMENTS;
963 }
964 int32_t result = hdiScreen_->SetScreenColorGamut(hdiMode[modeIdx]);
965 if (result == GRAPHIC_DISPLAY_SUCCESS) {
966 currentPhysicalColorGamutIdx_ = modeIdx;
967 return StatusCode::SUCCESS;
968 }
969 return StatusCode::HDI_ERROR;
970 }
971
SetScreenGamutMap(ScreenGamutMap mode)972 int32_t RSScreen::SetScreenGamutMap(ScreenGamutMap mode)
973 {
974 if (IsVirtual()) {
975 currentVirtualGamutMap_ = mode;
976 return StatusCode::SUCCESS;
977 }
978 if (!hdiScreen_) {
979 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
980 return StatusCode::HDI_ERROR;
981 }
982 int32_t result = hdiScreen_->SetScreenGamutMap(static_cast<GraphicGamutMap>(mode));
983 if (result == GRAPHIC_DISPLAY_SUCCESS) {
984 return StatusCode::SUCCESS;
985 }
986 return StatusCode::HDI_ERROR;
987 }
988
SetScreenCorrection(ScreenRotation screenRotation)989 void RSScreen::SetScreenCorrection(ScreenRotation screenRotation)
990 {
991 RS_LOGI("%{public}s: RSScreen(id %{public}" PRIu64 ") ,ScreenRotation: %{public}d.", __func__,
992 id_, static_cast<uint32_t>(screenRotation));
993 screenRotation_ = screenRotation;
994 }
995
GetScreenCorrection() const996 ScreenRotation RSScreen::GetScreenCorrection() const
997 {
998 return screenRotation_;
999 }
1000
GetScreenGamutMap(ScreenGamutMap & mode) const1001 int32_t RSScreen::GetScreenGamutMap(ScreenGamutMap &mode) const
1002 {
1003 if (IsVirtual()) {
1004 mode = currentVirtualGamutMap_;
1005 return StatusCode::SUCCESS;
1006 }
1007 if (!hdiScreen_) {
1008 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
1009 return StatusCode::HDI_ERROR;
1010 }
1011 GraphicGamutMap hdiMode;
1012 int32_t result = hdiScreen_->GetScreenGamutMap(hdiMode);
1013 if (result == GRAPHIC_DISPLAY_SUCCESS) {
1014 mode = static_cast<ScreenGamutMap>(hdiMode);
1015 return StatusCode::SUCCESS;
1016 }
1017 return StatusCode::HDI_ERROR;
1018 }
1019
GetHDRCapability()1020 const GraphicHDRCapability& RSScreen::GetHDRCapability()
1021 {
1022 hdrCapability_.maxLum = MAX_LUM; // mock data
1023 return hdrCapability_;
1024 }
1025
GetScreenType() const1026 const RSScreenType& RSScreen::GetScreenType() const
1027 {
1028 return screenType_;
1029 }
1030
SetScreenSkipFrameInterval(uint32_t skipFrameInterval)1031 void RSScreen::SetScreenSkipFrameInterval(uint32_t skipFrameInterval)
1032 {
1033 std::lock_guard<std::shared_mutex> lock(skipFrameMutex_);
1034 skipFrameInterval_ = skipFrameInterval;
1035 skipFrameStrategy_ = SKIP_FRAME_BY_INTERVAL;
1036 }
1037
SetScreenExpectedRefreshRate(uint32_t expectedRefreshRate)1038 void RSScreen::SetScreenExpectedRefreshRate(uint32_t expectedRefreshRate)
1039 {
1040 std::lock_guard<std::shared_mutex> lock(skipFrameMutex_);
1041 expectedRefreshRate_ = expectedRefreshRate;
1042 skipFrameStrategy_ = SKIP_FRAME_BY_REFRESH_RATE;
1043 }
1044
SetEqualVsyncPeriod(bool isEqualVsyncPeriod)1045 void RSScreen::SetEqualVsyncPeriod(bool isEqualVsyncPeriod)
1046 {
1047 std::lock_guard<std::shared_mutex> lock(skipFrameMutex_);
1048 isEqualVsyncPeriod_ = isEqualVsyncPeriod;
1049 }
1050
GetScreenSkipFrameInterval() const1051 uint32_t RSScreen::GetScreenSkipFrameInterval() const
1052 {
1053 std::shared_lock<std::shared_mutex> lock(skipFrameMutex_);
1054 return skipFrameInterval_;
1055 }
1056
GetScreenExpectedRefreshRate() const1057 uint32_t RSScreen::GetScreenExpectedRefreshRate() const
1058 {
1059 std::shared_lock<std::shared_mutex> lock(skipFrameMutex_);
1060 return expectedRefreshRate_;
1061 }
1062
GetScreenSkipFrameStrategy() const1063 SkipFrameStrategy RSScreen::GetScreenSkipFrameStrategy() const
1064 {
1065 std::shared_lock<std::shared_mutex> lock(skipFrameMutex_);
1066 return skipFrameStrategy_;
1067 }
1068
GetEqualVsyncPeriod() const1069 bool RSScreen::GetEqualVsyncPeriod() const
1070 {
1071 std::shared_lock<std::shared_mutex> lock(skipFrameMutex_);
1072 return isEqualVsyncPeriod_;
1073 }
1074
SetScreenVsyncEnabled(bool enabled) const1075 void RSScreen::SetScreenVsyncEnabled(bool enabled) const
1076 {
1077 if (IsVirtual()) {
1078 return;
1079 }
1080 if (hdiScreen_ != nullptr) {
1081 hdiScreen_->SetScreenVsyncEnabled(enabled);
1082 }
1083 }
1084
SetVirtualMirrorScreenCanvasRotation(bool canvasRotation)1085 bool RSScreen::SetVirtualMirrorScreenCanvasRotation(bool canvasRotation)
1086 {
1087 if (IsVirtual()) {
1088 canvasRotation_ = canvasRotation;
1089 return true;
1090 }
1091 return false;
1092 }
1093
GetCanvasRotation() const1094 bool RSScreen::GetCanvasRotation() const
1095 {
1096 return canvasRotation_;
1097 }
1098
SetVirtualMirrorScreenScaleMode(ScreenScaleMode scaleMode)1099 bool RSScreen::SetVirtualMirrorScreenScaleMode(ScreenScaleMode scaleMode)
1100 {
1101 if (IsVirtual()) {
1102 scaleMode_ = scaleMode;
1103 return true;
1104 }
1105 return false;
1106 }
1107
GetScaleMode() const1108 ScreenScaleMode RSScreen::GetScaleMode() const
1109 {
1110 return scaleMode_;
1111 }
1112
GetScreenSupportedHDRFormats(std::vector<ScreenHDRFormat> & hdrFormats) const1113 int32_t RSScreen::GetScreenSupportedHDRFormats(std::vector<ScreenHDRFormat>& hdrFormats) const
1114 {
1115 hdrFormats.clear();
1116 if (IsVirtual()) {
1117 hdrFormats = supportedVirtualHDRFormats_;
1118 } else {
1119 hdrFormats = supportedPhysicalHDRFormats_;
1120 }
1121 if (hdrFormats.size() == 0) {
1122 return StatusCode::HDI_ERROR;
1123 }
1124 return StatusCode::SUCCESS;
1125 }
1126
GetScreenHDRFormat(ScreenHDRFormat & hdrFormat) const1127 int32_t RSScreen::GetScreenHDRFormat(ScreenHDRFormat& hdrFormat) const
1128 {
1129 if (IsVirtual()) {
1130 hdrFormat = supportedVirtualHDRFormats_[currentVirtualHDRFormatIdx_];
1131 return StatusCode::SUCCESS;
1132 } else {
1133 if (supportedPhysicalHDRFormats_.size() == 0) {
1134 return StatusCode::HDI_ERROR;
1135 }
1136 hdrFormat = supportedPhysicalHDRFormats_[currentPhysicalHDRFormatIdx_];
1137 return StatusCode::SUCCESS;
1138 }
1139 return StatusCode::HDI_ERROR;
1140 }
1141
SetScreenHDRFormat(int32_t modeIdx)1142 int32_t RSScreen::SetScreenHDRFormat(int32_t modeIdx)
1143 {
1144 if (modeIdx < 0) {
1145 return StatusCode::INVALID_ARGUMENTS;
1146 }
1147 if (IsVirtual()) {
1148 if (modeIdx >= static_cast<int32_t>(supportedVirtualHDRFormats_.size())) {
1149 return StatusCode::INVALID_ARGUMENTS;
1150 }
1151 currentVirtualHDRFormatIdx_ = modeIdx;
1152 return StatusCode::SUCCESS;
1153 } else {
1154 // There should be some hdi operation
1155 if (modeIdx >= static_cast<int32_t>(hdrCapability_.formats.size())) {
1156 return StatusCode::INVALID_ARGUMENTS;
1157 }
1158 currentPhysicalHDRFormatIdx_ = modeIdx;
1159 return StatusCode::SUCCESS;
1160 }
1161 return StatusCode::HDI_ERROR;
1162 }
1163
GetPixelFormat(GraphicPixelFormat & pixelFormat) const1164 int32_t RSScreen::GetPixelFormat(GraphicPixelFormat& pixelFormat) const
1165 {
1166 pixelFormat = pixelFormat_;
1167 return StatusCode::SUCCESS;
1168 }
1169
SetPixelFormat(GraphicPixelFormat pixelFormat)1170 int32_t RSScreen::SetPixelFormat(GraphicPixelFormat pixelFormat)
1171 {
1172 pixelFormat_ = pixelFormat;
1173 return StatusCode::SUCCESS;
1174 }
1175
GetScreenSupportedColorSpaces(std::vector<GraphicCM_ColorSpaceType> & colorSpaces) const1176 int32_t RSScreen::GetScreenSupportedColorSpaces(std::vector<GraphicCM_ColorSpaceType>& colorSpaces) const
1177 {
1178 colorSpaces.clear();
1179 if (IsVirtual()) {
1180 std::transform(supportedVirtualColorGamuts_.begin(), supportedVirtualColorGamuts_.end(),
1181 back_inserter(colorSpaces),
1182 [](ScreenColorGamut item) -> GraphicCM_ColorSpaceType {
1183 return RS_TO_COMMON_COLOR_SPACE_TYPE_MAP[static_cast<GraphicColorGamut>(item)];
1184 });
1185 } else {
1186 std::transform(supportedPhysicalColorGamuts_.begin(), supportedPhysicalColorGamuts_.end(),
1187 back_inserter(colorSpaces),
1188 [](ScreenColorGamut item) -> GraphicCM_ColorSpaceType {
1189 return RS_TO_COMMON_COLOR_SPACE_TYPE_MAP[static_cast<GraphicColorGamut>(item)];
1190 });
1191 }
1192 if (colorSpaces.size() == 0) {
1193 return StatusCode::HDI_ERROR;
1194 }
1195 return StatusCode::SUCCESS;
1196 }
1197
GetScreenColorSpace(GraphicCM_ColorSpaceType & colorSpace) const1198 int32_t RSScreen::GetScreenColorSpace(GraphicCM_ColorSpaceType& colorSpace) const
1199 {
1200 ScreenColorGamut curGamut;
1201 int32_t result = GetScreenColorGamut(curGamut);
1202 colorSpace = RS_TO_COMMON_COLOR_SPACE_TYPE_MAP[static_cast<GraphicColorGamut>(curGamut)];
1203 return result;
1204 }
1205
SetScreenColorSpace(GraphicCM_ColorSpaceType colorSpace)1206 int32_t RSScreen::SetScreenColorSpace(GraphicCM_ColorSpaceType colorSpace)
1207 {
1208 auto iter = COMMON_COLOR_SPACE_TYPE_TO_RS_MAP.find(colorSpace);
1209 if (iter == COMMON_COLOR_SPACE_TYPE_TO_RS_MAP.end()) {
1210 return StatusCode::INVALID_ARGUMENTS;
1211 }
1212 ScreenColorGamut dstColorGamut = static_cast<ScreenColorGamut>(iter->second);
1213 int32_t curIdx;
1214 if (IsVirtual()) {
1215 auto it = std::find(supportedVirtualColorGamuts_.begin(), supportedVirtualColorGamuts_.end(), dstColorGamut);
1216 if (it == supportedVirtualColorGamuts_.end()) {
1217 return StatusCode::INVALID_ARGUMENTS;
1218 }
1219 curIdx = std::distance(supportedVirtualColorGamuts_.begin(), it);
1220 currentVirtualColorGamutIdx_ = curIdx;
1221 return StatusCode::SUCCESS;
1222 }
1223 if (!hdiScreen_) {
1224 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
1225 return StatusCode::HDI_ERROR;
1226 }
1227 std::vector<GraphicColorGamut> hdiMode;
1228 if (hdiScreen_->GetScreenSupportedColorGamuts(hdiMode) != GRAPHIC_DISPLAY_SUCCESS) {
1229 return StatusCode::HDI_ERROR;
1230 }
1231 auto it = std::find(hdiMode.begin(), hdiMode.end(), static_cast<GraphicColorGamut>(dstColorGamut));
1232 if (it == hdiMode.end()) {
1233 return StatusCode::INVALID_ARGUMENTS;
1234 }
1235 curIdx = std::distance(hdiMode.begin(), it);
1236 int32_t result = hdiScreen_->SetScreenColorGamut(hdiMode[curIdx]);
1237 if (result == GRAPHIC_DISPLAY_SUCCESS) {
1238 currentPhysicalColorGamutIdx_ = curIdx;
1239 return StatusCode::SUCCESS;
1240 }
1241 return StatusCode::HDI_ERROR;
1242 }
GetWhiteList() const1243 const std::unordered_set<uint64_t>& RSScreen::GetWhiteList() const
1244 {
1245 return whiteList_;
1246 }
1247
SetBlackList(const std::unordered_set<uint64_t> & blackList)1248 void RSScreen::SetBlackList(const std::unordered_set<uint64_t>& blackList)
1249 {
1250 blackList_ = blackList;
1251 }
1252
AddBlackList(const std::vector<uint64_t> & blackList)1253 void RSScreen::AddBlackList(const std::vector<uint64_t>& blackList)
1254 {
1255 for (auto& list : blackList) {
1256 blackList_.emplace(list);
1257 }
1258 }
1259
RemoveBlackList(const std::vector<uint64_t> & blackList)1260 void RSScreen::RemoveBlackList(const std::vector<uint64_t>& blackList)
1261 {
1262 for (auto& list : blackList) {
1263 blackList_.erase(list);
1264 }
1265 }
1266
SetCastScreenEnableSkipWindow(bool enable)1267 void RSScreen::SetCastScreenEnableSkipWindow(bool enable)
1268 {
1269 skipWindow_ = enable;
1270 }
1271
GetCastScreenEnableSkipWindow()1272 bool RSScreen::GetCastScreenEnableSkipWindow()
1273 {
1274 return skipWindow_;
1275 }
1276
GetBlackList() const1277 const std::unordered_set<uint64_t>& RSScreen::GetBlackList() const
1278 {
1279 return blackList_;
1280 }
1281
SetScreenConstraint(uint64_t frameId,uint64_t timestamp,ScreenConstraintType type)1282 int32_t RSScreen::SetScreenConstraint(uint64_t frameId, uint64_t timestamp, ScreenConstraintType type)
1283 {
1284 if (IsVirtual()) {
1285 return StatusCode::SUCCESS;
1286 }
1287 if (hdiScreen_ != nullptr) {
1288 int32_t result = hdiScreen_->SetScreenConstraint(frameId, timestamp, static_cast<uint32_t>(type));
1289 if (result == GRAPHIC_DISPLAY_SUCCESS) {
1290 return StatusCode::SUCCESS;
1291 }
1292 }
1293 return StatusCode::HDI_ERROR;
1294 }
1295
SetVirtualScreenStatus(VirtualScreenStatus screenStatus)1296 bool RSScreen::SetVirtualScreenStatus(VirtualScreenStatus screenStatus)
1297 {
1298 if (IsVirtual()) {
1299 screenStatus_ = screenStatus;
1300 return true;
1301 }
1302 return false;
1303 }
1304
GetVirtualScreenStatus() const1305 VirtualScreenStatus RSScreen::GetVirtualScreenStatus() const
1306 {
1307 return screenStatus_;
1308 }
1309
SetSecurityExemptionList(const std::vector<uint64_t> & securityExemptionList)1310 void RSScreen::SetSecurityExemptionList(const std::vector<uint64_t>& securityExemptionList)
1311 {
1312 securityExemptionList_ = securityExemptionList;
1313 }
1314
GetSecurityExemptionList() const1315 const std::vector<uint64_t>& RSScreen::GetSecurityExemptionList() const
1316 {
1317 return securityExemptionList_;
1318 }
1319
SetSecurityMask(std::shared_ptr<Media::PixelMap> securityMask)1320 int32_t RSScreen::SetSecurityMask(std::shared_ptr<Media::PixelMap> securityMask)
1321 {
1322 if (!IsVirtual()) {
1323 RS_LOGW("%{public}s not virtual screen", __func__);
1324 return SCREEN_NOT_FOUND;
1325 }
1326 securityMask_ = std::move(securityMask);
1327 return SUCCESS;
1328 }
1329
GetSecurityMask() const1330 std::shared_ptr<Media::PixelMap> RSScreen::GetSecurityMask() const
1331 {
1332 return securityMask_;
1333 }
1334
SetEnableVisibleRect(bool enable)1335 void RSScreen::SetEnableVisibleRect(bool enable)
1336 {
1337 enableVisibleRect_ = enable;
1338 }
1339
GetEnableVisibleRect() const1340 bool RSScreen::GetEnableVisibleRect() const
1341 {
1342 return enableVisibleRect_;
1343 }
1344
SetMainScreenVisibleRect(const Rect & mainScreenRect)1345 void RSScreen::SetMainScreenVisibleRect(const Rect& mainScreenRect)
1346 {
1347 mainScreenVisibleRect_ = mainScreenRect;
1348 }
1349
GetMainScreenVisibleRect() const1350 Rect RSScreen::GetMainScreenVisibleRect() const
1351 {
1352 return mainScreenVisibleRect_;
1353 }
1354
GetDisplayPropertyForHardCursor()1355 bool RSScreen::GetDisplayPropertyForHardCursor()
1356 {
1357 std::call_once(hardCursorSupportedFlag_, [this]() {
1358 if (hdiScreen_) {
1359 isHardCursorSupport_ = hdiScreen_->GetDisplayPropertyForHardCursor(id_);
1360 }
1361 RS_LOGI("%{public}s, RSScreen(id %{public}" PRIu64 ", isHardCursorSupport:%{public}d)",
1362 __func__, id_, isHardCursorSupport_);
1363 });
1364 return isHardCursorSupport_;
1365 }
1366
SetHasProtectedLayer(bool hasProtectedLayer)1367 void RSScreen::SetHasProtectedLayer(bool hasProtectedLayer)
1368 {
1369 hasProtectedLayer_ = hasProtectedLayer;
1370 }
1371
GetHasProtectedLayer()1372 bool RSScreen::GetHasProtectedLayer()
1373 {
1374 return hasProtectedLayer_;
1375 }
1376
GetVisibleRectSupportRotation() const1377 bool RSScreen::GetVisibleRectSupportRotation() const
1378 {
1379 return isSupportRotation_;
1380 }
1381
SetVisibleRectSupportRotation(bool supportRotation)1382 void RSScreen::SetVisibleRectSupportRotation(bool supportRotation)
1383 {
1384 isSupportRotation_ = supportRotation;
1385 }
1386
GetDisplayIdentificationData(uint8_t & outPort,std::vector<uint8_t> & edidData) const1387 int32_t RSScreen::GetDisplayIdentificationData(uint8_t& outPort, std::vector<uint8_t>& edidData) const
1388 {
1389 if (hdiScreen_ == nullptr) {
1390 RS_LOGE("%{public}s: id: %{public}" PRIu64 " is not physical display", __func__, id_);
1391 return HDI_ERROR;
1392 }
1393
1394 int32_t ret = hdiScreen_->GetDisplayIdentificationData(outPort, edidData);
1395 if (ret != GRAPHIC_DISPLAY_SUCCESS) {
1396 RS_LOGE("%{public}s: id %{public}" PRIu64 " call hid interface failed(%{public}d)",
1397 __func__, id_, ret);
1398 return HDI_ERROR;
1399 }
1400 RS_LOGD("%{public}s:: EdidSize: %{public}zu", __func__, edidData.size());
1401 return SUCCESS;
1402 }
1403
SetScreenLinearMatrix(const std::vector<float> & matrix)1404 int32_t RSScreen::SetScreenLinearMatrix(const std::vector<float> &matrix)
1405 {
1406 if (IsVirtual()) {
1407 RS_LOGW("%{public}s: virtual screen not support SetScreenLinearMatrix.", __func__);
1408 return StatusCode::VIRTUAL_SCREEN;
1409 }
1410 if (!hdiScreen_) {
1411 RS_LOGE("%{public}s failed, hdiScreen_ is nullptr", __func__);
1412 return StatusCode::HDI_ERROR;
1413 }
1414 if (std::shared_lock<std::shared_mutex> lock(linearMatrixMutex_);
1415 linearMatrix_ == matrix) {
1416 return StatusCode::SUCCESS;
1417 }
1418 if (hdiScreen_->SetScreenLinearMatrix(matrix) < 0) {
1419 RS_LOGI("%{public}s failed, matrix is invalid", __func__);
1420 return StatusCode::INVALID_ARGUMENTS;
1421 }
1422
1423 std::lock_guard<std::shared_mutex> lock(linearMatrixMutex_);
1424 linearMatrix_ = matrix;
1425 return StatusCode::SUCCESS;
1426 }
1427 } // namespace impl
1428 } // namespace Rosen
1429 } // namespace OHOS
1430