blob: d5f65c62119d4bf3fc9a313440e7a01333259c55 [file] [log] [blame]
Dan Stoza651bf312015-10-23 17:03:17 -07001/*
2 * Copyright 2015 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Ady Abrahamb0dbdaa2020-01-06 16:19:42 -080017// TODO(b/129481165): remove the #pragma below and fix conversion issues
18#pragma clang diagnostic push
19#pragma clang diagnostic ignored "-Wconversion"
20
Dan Stoza651bf312015-10-23 17:03:17 -070021// #define LOG_NDEBUG 0
22
23#undef LOG_TAG
24#define LOG_TAG "HWC2"
25#define ATRACE_TAG ATRACE_TAG_GRAPHICS
26
27#include "HWC2.h"
28
Dominik Laskowski4e2b71f2020-11-10 15:05:32 -080029#include <android/configuration.h>
Dominik Laskowski88096872023-12-08 15:26:04 -050030#include <common/FlagManager.h>
Dan Stoza651bf312015-10-23 17:03:17 -070031#include <ui/Fence.h>
Dan Stoza5a423ea2017-02-16 14:10:39 -080032#include <ui/FloatRect.h>
Dan Stoza651bf312015-10-23 17:03:17 -070033#include <ui/GraphicBuffer.h>
Dan Stoza651bf312015-10-23 17:03:17 -070034
Lloyd Pique3c085a02018-05-09 19:38:32 -070035#include <algorithm>
Dominik Laskowski4e2b71f2020-11-10 15:05:32 -080036#include <cinttypes>
Lloyd Pique3c085a02018-05-09 19:38:32 -070037#include <iterator>
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -070038#include <set>
Dan Stoza651bf312015-10-23 17:03:17 -070039
Ady Abraham6e60b142022-01-06 18:10:35 -080040using aidl::android::hardware::graphics::composer3::Color;
Leon Scroggins III2e1aa182021-12-01 17:33:12 -050041using aidl::android::hardware::graphics::composer3::Composition;
Ady Abrahamde549d42022-01-26 19:19:17 -080042using AidlCapability = aidl::android::hardware::graphics::composer3::Capability;
Leon Scroggins III5967aec2021-12-29 11:14:22 -050043using aidl::android::hardware::graphics::composer3::DisplayCapability;
Sally Qi492cec32024-06-28 14:34:47 -070044using aidl::android::hardware::graphics::composer3::Lut;
Sally Qi0cbd08b2022-08-17 12:12:28 -070045using aidl::android::hardware::graphics::composer3::OverlayProperties;
Leon Scroggins III2e1aa182021-12-01 17:33:12 -050046
Peiyong Line9d809e2020-04-14 13:10:48 -070047namespace android {
48
Dan Stoza651bf312015-10-23 17:03:17 -070049using android::Fence;
Dan Stoza5a423ea2017-02-16 14:10:39 -080050using android::FloatRect;
Dan Stoza651bf312015-10-23 17:03:17 -070051using android::GraphicBuffer;
Dan Stoza7d7ae732016-03-16 12:23:40 -070052using android::HdrCapabilities;
Courtney Goeltzenleuchterf9c98e52018-02-12 07:23:17 -070053using android::HdrMetadata;
Dan Stoza651bf312015-10-23 17:03:17 -070054using android::Rect;
55using android::Region;
56using android::sp;
57
58namespace HWC2 {
59
Peiyong Line9d809e2020-04-14 13:10:48 -070060using namespace android::hardware::graphics::composer::hal;
61
Chia-I Wuaab99f52016-10-05 12:59:58 +080062namespace Hwc2 = android::Hwc2;
63
Steven Thomas94e35b92017-07-26 18:48:28 -070064namespace {
65
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -070066inline bool hasMetadataKey(const std::set<Hwc2::PerFrameMetadataKey>& keys,
67 const Hwc2::PerFrameMetadataKey& key) {
68 return keys.find(key) != keys.end();
69}
70
Steven Thomas94e35b92017-07-26 18:48:28 -070071} // namespace anonymous
72
Dan Stoza651bf312015-10-23 17:03:17 -070073// Display methods
Ana Krulec4593b692019-01-11 22:07:25 -080074Display::~Display() = default;
Dan Stoza651bf312015-10-23 17:03:17 -070075
Ana Krulec4593b692019-01-11 22:07:25 -080076namespace impl {
Dominik Laskowski55c85402020-01-21 16:25:47 -080077
Peiyong Lin74ca2f42019-01-14 19:36:57 -080078Display::Display(android::Hwc2::Composer& composer,
Ady Abrahamde549d42022-01-26 19:19:17 -080079 const std::unordered_set<AidlCapability>& capabilities, HWDisplayId id,
Lloyd Piquebc792092018-01-17 11:52:30 -080080 DisplayType type)
Peiyong Line9d809e2020-04-14 13:10:48 -070081 : mComposer(composer), mCapabilities(capabilities), mId(id), mType(type) {
Dan Stoza651bf312015-10-23 17:03:17 -070082 ALOGV("Created display %" PRIu64, id);
HyunKyounga264a352024-04-24 18:51:33 +090083 if (mType == hal::DisplayType::VIRTUAL) {
84 loadDisplayCapabilities();
85 }
Dan Stoza651bf312015-10-23 17:03:17 -070086}
87
Steven Thomas94e35b92017-07-26 18:48:28 -070088Display::~Display() {
Lloyd Piquea516c002021-05-07 14:36:58 -070089 // Note: The calls to onOwningDisplayDestroyed() are allowed (and expected)
90 // to call Display::onLayerDestroyed(). As that call removes entries from
91 // mLayers, we do not want to have a for loop directly over it here. Since
92 // the end goal is an empty mLayers anyway, we just go ahead and swap an
93 // initially empty local container with mLayers, and then enumerate
94 // the contents of the local container.
95 Layers destroyingLayers;
96 std::swap(mLayers, destroyingLayers);
97 for (const auto& [_, weakLayer] : destroyingLayers) {
98 if (std::shared_ptr layer = weakLayer.lock()) {
99 layer->onOwningDisplayDestroyed();
100 }
101 }
Steven Thomas94e35b92017-07-26 18:48:28 -0700102
Peiyong Line9d809e2020-04-14 13:10:48 -0700103 Error error = Error::NONE;
Dominik Laskowski55c85402020-01-21 16:25:47 -0800104 const char* msg;
105 switch (mType) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700106 case DisplayType::PHYSICAL:
107 error = setVsyncEnabled(HWC2::Vsync::DISABLE);
Dominik Laskowski55c85402020-01-21 16:25:47 -0800108 msg = "disable VSYNC for";
109 break;
110
Peiyong Line9d809e2020-04-14 13:10:48 -0700111 case DisplayType::VIRTUAL:
Dominik Laskowski55c85402020-01-21 16:25:47 -0800112 error = static_cast<Error>(mComposer.destroyVirtualDisplay(mId));
113 msg = "destroy virtual";
114 break;
115
Peiyong Line9d809e2020-04-14 13:10:48 -0700116 case DisplayType::INVALID: // Used in unit tests.
Dominik Laskowski55c85402020-01-21 16:25:47 -0800117 break;
Dan Stoza651bf312015-10-23 17:03:17 -0700118 }
Dominik Laskowski55c85402020-01-21 16:25:47 -0800119
Peiyong Line9d809e2020-04-14 13:10:48 -0700120 ALOGE_IF(error != Error::NONE, "%s: Failed to %s display %" PRIu64 ": %d", __FUNCTION__, msg,
121 mId, static_cast<int32_t>(error));
Dominik Laskowski55c85402020-01-21 16:25:47 -0800122
123 ALOGV("Destroyed display %" PRIu64, mId);
Dan Stoza651bf312015-10-23 17:03:17 -0700124}
125
Dan Stoza651bf312015-10-23 17:03:17 -0700126// Required by HWC2 display
Dan Stoza651bf312015-10-23 17:03:17 -0700127Error Display::acceptChanges()
128{
Steven Thomas94e35b92017-07-26 18:48:28 -0700129 auto intError = mComposer.acceptDisplayChanges(mId);
Dan Stoza651bf312015-10-23 17:03:17 -0700130 return static_cast<Error>(intError);
131}
132
Lloyd Piquea516c002021-05-07 14:36:58 -0700133base::expected<std::shared_ptr<HWC2::Layer>, hal::Error> Display::createLayer() {
Peiyong Line9d809e2020-04-14 13:10:48 -0700134 HWLayerId layerId = 0;
Steven Thomas94e35b92017-07-26 18:48:28 -0700135 auto intError = mComposer.createLayer(mId, &layerId);
Dan Stoza651bf312015-10-23 17:03:17 -0700136 auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700137 if (error != Error::NONE) {
Lloyd Piquea516c002021-05-07 14:36:58 -0700138 return base::unexpected(error);
Dan Stoza651bf312015-10-23 17:03:17 -0700139 }
140
Lloyd Piquea516c002021-05-07 14:36:58 -0700141 auto layer = std::make_shared<impl::Layer>(mComposer, mCapabilities, *this, layerId);
142 mLayers.emplace(layerId, layer);
143 return layer;
Steven Thomas94e35b92017-07-26 18:48:28 -0700144}
145
Lloyd Piquea516c002021-05-07 14:36:58 -0700146void Display::onLayerDestroyed(hal::HWLayerId layerId) {
147 mLayers.erase(layerId);
Dan Stoza651bf312015-10-23 17:03:17 -0700148}
149
Ady Abraham7159f572019-10-11 11:10:18 -0700150bool Display::isVsyncPeriodSwitchSupported() const {
151 ALOGV("[%" PRIu64 "] isVsyncPeriodSwitchSupported()", mId);
152
Ady Abraham4d211cf2021-12-14 16:19:03 -0800153 return mComposer.isSupported(android::Hwc2::Composer::OptionalFeature::RefreshRateSwitching);
Ady Abraham7159f572019-10-11 11:10:18 -0700154}
155
ramindani32cf0602022-03-02 02:30:29 +0000156bool Display::hasDisplayIdleTimerCapability() const {
157 bool isCapabilitySupported = false;
158 return mComposer.hasDisplayIdleTimerCapability(mId, &isCapabilitySupported) == Error::NONE &&
159 isCapabilitySupported;
160}
161
ramindani06e518e2022-03-14 18:47:53 +0000162Error Display::getPhysicalDisplayOrientation(Hwc2::AidlTransform* outTransform) const {
163 auto error = mComposer.getPhysicalDisplayOrientation(mId, outTransform);
164 return static_cast<Error>(error);
165}
166
Lloyd Pique35d58242018-12-18 16:33:25 -0800167Error Display::getChangedCompositionTypes(std::unordered_map<HWC2::Layer*, Composition>* outTypes) {
Chia-I Wuaab99f52016-10-05 12:59:58 +0800168 std::vector<Hwc2::Layer> layerIds;
Leon Scroggins III2e1aa182021-12-01 17:33:12 -0500169 std::vector<Composition> types;
Steven Thomas94e35b92017-07-26 18:48:28 -0700170 auto intError = mComposer.getChangedCompositionTypes(
171 mId, &layerIds, &types);
Chia-I Wuaab99f52016-10-05 12:59:58 +0800172 uint32_t numElements = layerIds.size();
linkaid1bb3142023-12-20 10:18:16 +0800173 const auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700174 if (error != Error::NONE) {
Dan Stoza651bf312015-10-23 17:03:17 -0700175 return error;
176 }
177
178 outTypes->clear();
179 outTypes->reserve(numElements);
180 for (uint32_t element = 0; element < numElements; ++element) {
181 auto layer = getLayerById(layerIds[element]);
182 if (layer) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700183 auto type = types[element];
Dan Stoza651bf312015-10-23 17:03:17 -0700184 ALOGV("getChangedCompositionTypes: adding %" PRIu64 " %s",
185 layer->getId(), to_string(type).c_str());
Lloyd Piquea516c002021-05-07 14:36:58 -0700186 outTypes->emplace(layer.get(), type);
Dan Stoza651bf312015-10-23 17:03:17 -0700187 } else {
188 ALOGE("getChangedCompositionTypes: invalid layer %" PRIu64 " found"
189 " on display %" PRIu64, layerIds[element], mId);
190 }
191 }
192
Peiyong Line9d809e2020-04-14 13:10:48 -0700193 return Error::NONE;
Dan Stoza651bf312015-10-23 17:03:17 -0700194}
195
Peiyong Lin34beb7a2018-03-28 11:57:12 -0700196Error Display::getColorModes(std::vector<ColorMode>* outModes) const
Dan Stoza076ac672016-03-14 10:47:53 -0700197{
Peiyong Linfd997e02018-03-28 15:29:00 -0700198 auto intError = mComposer.getColorModes(mId, outModes);
199 return static_cast<Error>(intError);
Dan Stoza076ac672016-03-14 10:47:53 -0700200}
201
Chia-I Wud7e01d72018-06-21 13:39:09 +0800202int32_t Display::getSupportedPerFrameMetadata() const
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700203{
Chia-I Wud7e01d72018-06-21 13:39:09 +0800204 int32_t supportedPerFrameMetadata = 0;
205
206 std::vector<Hwc2::PerFrameMetadataKey> tmpKeys = mComposer.getPerFrameMetadataKeys(mId);
207 std::set<Hwc2::PerFrameMetadataKey> keys(tmpKeys.begin(), tmpKeys.end());
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700208
209 // Check whether a specific metadata type is supported. A metadata type is considered
210 // supported if and only if all required fields are supported.
211
212 // SMPTE2086
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700213 if (hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::DISPLAY_RED_PRIMARY_X) &&
214 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::DISPLAY_RED_PRIMARY_Y) &&
215 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::DISPLAY_GREEN_PRIMARY_X) &&
216 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::DISPLAY_GREEN_PRIMARY_Y) &&
217 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::DISPLAY_BLUE_PRIMARY_X) &&
218 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::DISPLAY_BLUE_PRIMARY_Y) &&
219 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::WHITE_POINT_X) &&
220 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::WHITE_POINT_Y) &&
221 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::MAX_LUMINANCE) &&
222 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::MIN_LUMINANCE)) {
Chia-I Wud7e01d72018-06-21 13:39:09 +0800223 supportedPerFrameMetadata |= HdrMetadata::Type::SMPTE2086;
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700224 }
225 // CTA861_3
226 if (hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::MAX_CONTENT_LIGHT_LEVEL) &&
227 hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::MAX_FRAME_AVERAGE_LIGHT_LEVEL)) {
Chia-I Wud7e01d72018-06-21 13:39:09 +0800228 supportedPerFrameMetadata |= HdrMetadata::Type::CTA861_3;
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700229 }
230
Valerie Haue9e843a2018-12-18 13:39:23 -0800231 // HDR10PLUS
232 if (hasMetadataKey(keys, Hwc2::PerFrameMetadataKey::HDR10_PLUS_SEI)) {
233 supportedPerFrameMetadata |= HdrMetadata::Type::HDR10PLUS;
234 }
235
Chia-I Wud7e01d72018-06-21 13:39:09 +0800236 return supportedPerFrameMetadata;
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700237}
238
Peiyong Lin0e7a7912018-04-05 14:36:36 -0700239Error Display::getRenderIntents(ColorMode colorMode,
240 std::vector<RenderIntent>* outRenderIntents) const
241{
242 auto intError = mComposer.getRenderIntents(mId, colorMode, outRenderIntents);
243 return static_cast<Error>(intError);
244}
245
246Error Display::getDataspaceSaturationMatrix(Dataspace dataspace, android::mat4* outMatrix)
247{
248 auto intError = mComposer.getDataspaceSaturationMatrix(dataspace, outMatrix);
249 return static_cast<Error>(intError);
250}
251
Dan Stoza651bf312015-10-23 17:03:17 -0700252Error Display::getName(std::string* outName) const
253{
Steven Thomas94e35b92017-07-26 18:48:28 -0700254 auto intError = mComposer.getDisplayName(mId, outName);
Chia-I Wuaab99f52016-10-05 12:59:58 +0800255 return static_cast<Error>(intError);
Dan Stoza651bf312015-10-23 17:03:17 -0700256}
257
258Error Display::getRequests(HWC2::DisplayRequest* outDisplayRequests,
Lloyd Pique35d58242018-12-18 16:33:25 -0800259 std::unordered_map<HWC2::Layer*, LayerRequest>* outLayerRequests) {
Lloyd Piquee9eff972020-05-05 12:36:44 -0700260 uint32_t intDisplayRequests = 0;
Chia-I Wuaab99f52016-10-05 12:59:58 +0800261 std::vector<Hwc2::Layer> layerIds;
262 std::vector<uint32_t> layerRequests;
Steven Thomas94e35b92017-07-26 18:48:28 -0700263 auto intError = mComposer.getDisplayRequests(
264 mId, &intDisplayRequests, &layerIds, &layerRequests);
Chia-I Wuaab99f52016-10-05 12:59:58 +0800265 uint32_t numElements = layerIds.size();
266 auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700267 if (error != Error::NONE) {
Dan Stoza651bf312015-10-23 17:03:17 -0700268 return error;
269 }
270
271 *outDisplayRequests = static_cast<DisplayRequest>(intDisplayRequests);
272 outLayerRequests->clear();
273 outLayerRequests->reserve(numElements);
274 for (uint32_t element = 0; element < numElements; ++element) {
275 auto layer = getLayerById(layerIds[element]);
276 if (layer) {
277 auto layerRequest =
278 static_cast<LayerRequest>(layerRequests[element]);
Lloyd Piquea516c002021-05-07 14:36:58 -0700279 outLayerRequests->emplace(layer.get(), layerRequest);
Dan Stoza651bf312015-10-23 17:03:17 -0700280 } else {
281 ALOGE("getRequests: invalid layer %" PRIu64 " found on display %"
282 PRIu64, layerIds[element], mId);
283 }
284 }
285
Peiyong Line9d809e2020-04-14 13:10:48 -0700286 return Error::NONE;
Dan Stoza651bf312015-10-23 17:03:17 -0700287}
288
Dominik Laskowski969cdcb2024-02-08 16:35:29 -0500289ftl::Expected<ui::DisplayConnectionType, hal::Error> Display::getConnectionType() const {
290 if (!mConnectionType) {
291 mConnectionType = [this]() -> decltype(mConnectionType) {
292 if (mType != DisplayType::PHYSICAL) {
293 return ftl::Unexpected(Error::BAD_DISPLAY);
294 }
Dominik Laskowski55c85402020-01-21 16:25:47 -0800295
Dominik Laskowski969cdcb2024-02-08 16:35:29 -0500296 using ConnectionType = Hwc2::IComposerClient::DisplayConnectionType;
297 ConnectionType connectionType;
298
299 if (const auto error = static_cast<Error>(
300 mComposer.getDisplayConnectionType(mId, &connectionType));
301 error != Error::NONE) {
302 return ftl::Unexpected(error);
303 }
304
305 return connectionType == ConnectionType::INTERNAL ? ui::DisplayConnectionType::Internal
306 : ui::DisplayConnectionType::External;
307 }();
Dominik Laskowski55c85402020-01-21 16:25:47 -0800308 }
309
Dominik Laskowski969cdcb2024-02-08 16:35:29 -0500310 return *mConnectionType;
Dan Stoza651bf312015-10-23 17:03:17 -0700311}
312
Leon Scroggins III5967aec2021-12-29 11:14:22 -0500313bool Display::hasCapability(DisplayCapability capability) const {
Ady Abraham27fbcc72021-09-20 14:54:57 -0700314 std::scoped_lock lock(mDisplayCapabilitiesMutex);
315 if (mDisplayCapabilities) {
316 return mDisplayCapabilities->count(capability) > 0;
317 }
318
Leon Scroggins III515f0382021-12-29 11:17:04 -0500319 ALOGW("Can't query capability %s."
Ady Abraham27fbcc72021-09-20 14:54:57 -0700320 " Display Capabilities were not queried from HWC yet",
Leon Scroggins III515f0382021-12-29 11:17:04 -0500321 to_string(capability).c_str());
Ady Abraham27fbcc72021-09-20 14:54:57 -0700322
323 return false;
324}
325
Peiyong Lined531a32018-10-26 18:27:56 -0700326Error Display::supportsDoze(bool* outSupport) const {
Leon Scroggins III689c80f2023-06-05 17:49:32 -0400327 {
328 std::scoped_lock lock(mDisplayCapabilitiesMutex);
329 if (!mDisplayCapabilities) {
330 // The display has not turned on since boot, so DOZE support is unknown.
331 ALOGW("%s: haven't queried capabilities yet!", __func__);
332 return Error::NO_RESOURCES;
333 }
334 }
Ady Abraham27fbcc72021-09-20 14:54:57 -0700335 *outSupport = hasCapability(DisplayCapability::DOZE);
Peiyong Line9d809e2020-04-14 13:10:48 -0700336 return Error::NONE;
Dan Stoza651bf312015-10-23 17:03:17 -0700337}
338
Peiyong Lin62665892018-04-16 11:07:44 -0700339Error Display::getHdrCapabilities(HdrCapabilities* outCapabilities) const
Dan Stoza7d7ae732016-03-16 12:23:40 -0700340{
Dan Stoza7d7ae732016-03-16 12:23:40 -0700341 float maxLuminance = -1.0f;
342 float maxAverageLuminance = -1.0f;
343 float minLuminance = -1.0f;
Marc Kassisbdf7e4b2022-11-04 17:26:48 +0100344 std::vector<Hwc2::Hdr> hdrTypes;
345 auto intError = mComposer.getHdrCapabilities(mId, &hdrTypes, &maxLuminance,
346 &maxAverageLuminance, &minLuminance);
Chia-I Wuaab99f52016-10-05 12:59:58 +0800347 auto error = static_cast<HWC2::Error>(intError);
348
Peiyong Line9d809e2020-04-14 13:10:48 -0700349 if (error != Error::NONE) {
Dan Stoza7d7ae732016-03-16 12:23:40 -0700350 return error;
351 }
352
Marc Kassisbdf7e4b2022-11-04 17:26:48 +0100353 *outCapabilities =
354 HdrCapabilities(std::move(hdrTypes), maxLuminance, maxAverageLuminance, minLuminance);
Peiyong Line9d809e2020-04-14 13:10:48 -0700355 return Error::NONE;
Dan Stoza7d7ae732016-03-16 12:23:40 -0700356}
357
Sally Qibb866c12022-10-17 11:31:20 -0700358Error Display::getOverlaySupport(OverlayProperties* outProperties) const {
359 auto intError = mComposer.getOverlaySupport(outProperties);
360 return static_cast<Error>(intError);
Sally Qi0cbd08b2022-08-17 12:12:28 -0700361}
362
Peiyong Line9d809e2020-04-14 13:10:48 -0700363Error Display::getDisplayedContentSamplingAttributes(hal::PixelFormat* outFormat,
Kevin DuBois9c0a1762018-10-16 13:32:31 -0700364 Dataspace* outDataspace,
365 uint8_t* outComponentMask) const {
366 auto intError = mComposer.getDisplayedContentSamplingAttributes(mId, outFormat, outDataspace,
367 outComponentMask);
368 return static_cast<Error>(intError);
369}
370
Kevin DuBois74e53772018-11-19 10:52:38 -0800371Error Display::setDisplayContentSamplingEnabled(bool enabled, uint8_t componentMask,
372 uint64_t maxFrames) const {
373 auto intError =
374 mComposer.setDisplayContentSamplingEnabled(mId, enabled, componentMask, maxFrames);
375 return static_cast<Error>(intError);
376}
377
Kevin DuBois1d4249a2018-08-29 10:45:14 -0700378Error Display::getDisplayedContentSample(uint64_t maxFrames, uint64_t timestamp,
379 android::DisplayedFrameStats* outStats) const {
380 auto intError = mComposer.getDisplayedContentSample(mId, maxFrames, timestamp, outStats);
381 return static_cast<Error>(intError);
382}
383
Lloyd Pique35d58242018-12-18 16:33:25 -0800384Error Display::getReleaseFences(std::unordered_map<HWC2::Layer*, sp<Fence>>* outFences) const {
Chia-I Wuaab99f52016-10-05 12:59:58 +0800385 std::vector<Hwc2::Layer> layerIds;
386 std::vector<int> fenceFds;
Steven Thomas94e35b92017-07-26 18:48:28 -0700387 auto intError = mComposer.getReleaseFences(mId, &layerIds, &fenceFds);
Chia-I Wuaab99f52016-10-05 12:59:58 +0800388 auto error = static_cast<Error>(intError);
389 uint32_t numElements = layerIds.size();
Peiyong Line9d809e2020-04-14 13:10:48 -0700390 if (error != Error::NONE) {
Dan Stoza651bf312015-10-23 17:03:17 -0700391 return error;
392 }
393
Lloyd Pique35d58242018-12-18 16:33:25 -0800394 std::unordered_map<HWC2::Layer*, sp<Fence>> releaseFences;
Dan Stoza651bf312015-10-23 17:03:17 -0700395 releaseFences.reserve(numElements);
396 for (uint32_t element = 0; element < numElements; ++element) {
397 auto layer = getLayerById(layerIds[element]);
398 if (layer) {
Ady Abrahamd11bade2022-08-01 16:18:03 -0700399 sp<Fence> fence(sp<Fence>::make(fenceFds[element]));
Lloyd Piquea516c002021-05-07 14:36:58 -0700400 releaseFences.emplace(layer.get(), fence);
Dan Stoza651bf312015-10-23 17:03:17 -0700401 } else {
402 ALOGE("getReleaseFences: invalid layer %" PRIu64
403 " found on display %" PRIu64, layerIds[element], mId);
Chia-I Wu5e74c652017-05-17 13:43:16 -0700404 for (; element < numElements; ++element) {
405 close(fenceFds[element]);
406 }
Peiyong Line9d809e2020-04-14 13:10:48 -0700407 return Error::BAD_LAYER;
Dan Stoza651bf312015-10-23 17:03:17 -0700408 }
409 }
410
411 *outFences = std::move(releaseFences);
Peiyong Line9d809e2020-04-14 13:10:48 -0700412 return Error::NONE;
Dan Stoza651bf312015-10-23 17:03:17 -0700413}
414
Fabien Sanglard11d0fc32016-12-01 15:43:01 -0800415Error Display::present(sp<Fence>* outPresentFence)
Dan Stoza651bf312015-10-23 17:03:17 -0700416{
Naseer Ahmed847650b2016-06-17 11:14:25 -0400417 int32_t presentFenceFd = -1;
Steven Thomas94e35b92017-07-26 18:48:28 -0700418 auto intError = mComposer.presentDisplay(mId, &presentFenceFd);
Dan Stoza651bf312015-10-23 17:03:17 -0700419 auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700420 if (error != Error::NONE) {
Dan Stoza651bf312015-10-23 17:03:17 -0700421 return error;
422 }
423
Ady Abrahamd11bade2022-08-01 16:18:03 -0700424 *outPresentFence = sp<Fence>::make(presentFenceFd);
Peiyong Line9d809e2020-04-14 13:10:48 -0700425 return Error::NONE;
Dan Stoza651bf312015-10-23 17:03:17 -0700426}
427
Marin Shalamanov3ea1d602020-12-16 19:59:39 +0100428Error Display::setActiveConfigWithConstraints(hal::HWConfigId configId,
429 const VsyncPeriodChangeConstraints& constraints,
430 VsyncPeriodChangeTimeline* outTimeline) {
Ady Abraham7159f572019-10-11 11:10:18 -0700431 ALOGV("[%" PRIu64 "] setActiveConfigWithConstraints", mId);
Ady Abraham7159f572019-10-11 11:10:18 -0700432
Dominik Laskowski88096872023-12-08 15:26:04 -0500433 // FIXME (b/319505580): At least the first config set on an external display must be
434 // `setActiveConfig`, so skip over the block that calls `setActiveConfigWithConstraints`
435 // for simplicity.
Dominik Laskowski88096872023-12-08 15:26:04 -0500436 const bool connected_display = FlagManager::getInstance().connected_display();
Dominik Laskowski88096872023-12-08 15:26:04 -0500437
438 if (isVsyncPeriodSwitchSupported() &&
Dominik Laskowski969cdcb2024-02-08 16:35:29 -0500439 (!connected_display ||
440 getConnectionType().value_opt() != ui::DisplayConnectionType::External)) {
Ady Abraham7159f572019-10-11 11:10:18 -0700441 Hwc2::IComposerClient::VsyncPeriodChangeConstraints hwc2Constraints;
442 hwc2Constraints.desiredTimeNanos = constraints.desiredTimeNanos;
443 hwc2Constraints.seamlessRequired = constraints.seamlessRequired;
444
445 Hwc2::VsyncPeriodChangeTimeline vsyncPeriodChangeTimeline = {};
Marin Shalamanov3ea1d602020-12-16 19:59:39 +0100446 auto intError = mComposer.setActiveConfigWithConstraints(mId, configId, hwc2Constraints,
447 &vsyncPeriodChangeTimeline);
Ady Abraham7159f572019-10-11 11:10:18 -0700448 outTimeline->newVsyncAppliedTimeNanos = vsyncPeriodChangeTimeline.newVsyncAppliedTimeNanos;
449 outTimeline->refreshRequired = vsyncPeriodChangeTimeline.refreshRequired;
450 outTimeline->refreshTimeNanos = vsyncPeriodChangeTimeline.refreshTimeNanos;
451 return static_cast<Error>(intError);
452 }
453
454 // Use legacy setActiveConfig instead
455 ALOGV("fallback to legacy setActiveConfig");
456 const auto now = systemTime();
457 if (constraints.desiredTimeNanos > now || constraints.seamlessRequired) {
458 ALOGE("setActiveConfigWithConstraints received constraints that can't be satisfied");
459 }
460
Marin Shalamanov3ea1d602020-12-16 19:59:39 +0100461 auto intError_2_4 = mComposer.setActiveConfig(mId, configId);
Ady Abraham7159f572019-10-11 11:10:18 -0700462 outTimeline->newVsyncAppliedTimeNanos = std::max(now, constraints.desiredTimeNanos);
463 outTimeline->refreshRequired = true;
464 outTimeline->refreshTimeNanos = now;
465 return static_cast<Error>(intError_2_4);
466}
467
Daniel Nicoara1f42e3a2017-04-10 13:27:32 -0400468Error Display::setClientTarget(uint32_t slot, const sp<GraphicBuffer>& target,
Alec Mourif97df4d2023-09-06 02:10:05 +0000469 const sp<Fence>& acquireFence, Dataspace dataspace,
470 float hdrSdrRatio) {
Dan Stoza5cf424b2016-05-20 14:02:39 -0700471 // TODO: Properly encode client target surface damage
Dan Stoza651bf312015-10-23 17:03:17 -0700472 int32_t fenceFd = acquireFence->dup();
Alec Mourif97df4d2023-09-06 02:10:05 +0000473 auto intError =
474 mComposer.setClientTarget(mId, slot, target, fenceFd, dataspace,
475 std::vector<Hwc2::IComposerClient::Rect>(), hdrSdrRatio);
Dan Stoza651bf312015-10-23 17:03:17 -0700476 return static_cast<Error>(intError);
477}
478
Peiyong Lin0e7a7912018-04-05 14:36:36 -0700479Error Display::setColorMode(ColorMode mode, RenderIntent renderIntent)
Dan Stoza076ac672016-03-14 10:47:53 -0700480{
Peiyong Lin0e7a7912018-04-05 14:36:36 -0700481 auto intError = mComposer.setColorMode(mId, mode, renderIntent);
Dan Stoza076ac672016-03-14 10:47:53 -0700482 return static_cast<Error>(intError);
483}
484
Ady Abrahamdc011a92021-12-21 14:06:44 -0800485Error Display::setColorTransform(const android::mat4& matrix) {
486 auto intError = mComposer.setColorTransform(mId, matrix.asArray());
Dan Stoza5df2a862016-03-24 16:19:37 -0700487 return static_cast<Error>(intError);
488}
489
Dan Stoza651bf312015-10-23 17:03:17 -0700490Error Display::setOutputBuffer(const sp<GraphicBuffer>& buffer,
491 const sp<Fence>& releaseFence)
492{
493 int32_t fenceFd = releaseFence->dup();
494 auto handle = buffer->getNativeBuffer()->handle;
Steven Thomas94e35b92017-07-26 18:48:28 -0700495 auto intError = mComposer.setOutputBuffer(mId, handle, fenceFd);
Dan Stoza38628982016-07-13 15:48:58 -0700496 close(fenceFd);
Dan Stoza651bf312015-10-23 17:03:17 -0700497 return static_cast<Error>(intError);
498}
499
500Error Display::setPowerMode(PowerMode mode)
501{
Chia-I Wucd8d7f02016-11-16 11:02:31 +0800502 auto intMode = static_cast<Hwc2::IComposerClient::PowerMode>(mode);
Steven Thomas94e35b92017-07-26 18:48:28 -0700503 auto intError = mComposer.setPowerMode(mId, intMode);
Peiyong Lin1336e6e2019-05-28 09:23:50 -0700504
Peiyong Line9d809e2020-04-14 13:10:48 -0700505 if (mode == PowerMode::ON) {
HyunKyounga264a352024-04-24 18:51:33 +0900506 loadDisplayCapabilities();
Peiyong Lin1336e6e2019-05-28 09:23:50 -0700507 }
508
Dan Stoza651bf312015-10-23 17:03:17 -0700509 return static_cast<Error>(intError);
510}
511
512Error Display::setVsyncEnabled(Vsync enabled)
513{
Chia-I Wucd8d7f02016-11-16 11:02:31 +0800514 auto intEnabled = static_cast<Hwc2::IComposerClient::Vsync>(enabled);
Steven Thomas94e35b92017-07-26 18:48:28 -0700515 auto intError = mComposer.setVsyncEnabled(mId, intEnabled);
Dan Stoza651bf312015-10-23 17:03:17 -0700516 return static_cast<Error>(intError);
517}
518
ramindani09acbb82023-11-03 09:02:38 -0700519Error Display::validate(nsecs_t expectedPresentTime, int32_t frameIntervalNs, uint32_t* outNumTypes,
Ady Abraham43065bd2021-12-10 17:22:15 -0800520 uint32_t* outNumRequests) {
Dan Stoza651bf312015-10-23 17:03:17 -0700521 uint32_t numTypes = 0;
522 uint32_t numRequests = 0;
ramindani09acbb82023-11-03 09:02:38 -0700523 auto intError = mComposer.validateDisplay(mId, expectedPresentTime, frameIntervalNs, &numTypes,
524 &numRequests);
Dan Stoza651bf312015-10-23 17:03:17 -0700525 auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700526 if (error != Error::NONE && !hasChangesError(error)) {
Dan Stoza651bf312015-10-23 17:03:17 -0700527 return error;
528 }
529
530 *outNumTypes = numTypes;
531 *outNumRequests = numRequests;
532 return error;
533}
534
ramindani4aac32c2023-10-30 14:13:30 -0700535Error Display::presentOrValidate(nsecs_t expectedPresentTime, int32_t frameIntervalNs,
536 uint32_t* outNumTypes, uint32_t* outNumRequests,
537 sp<android::Fence>* outPresentFence, uint32_t* state) {
Fabien Sanglard249c0ae2017-06-19 19:22:36 -0700538 uint32_t numTypes = 0;
539 uint32_t numRequests = 0;
540 int32_t presentFenceFd = -1;
ramindani4aac32c2023-10-30 14:13:30 -0700541 auto intError =
542 mComposer.presentOrValidateDisplay(mId, expectedPresentTime, frameIntervalNs, &numTypes,
543 &numRequests, &presentFenceFd, state);
Fabien Sanglard249c0ae2017-06-19 19:22:36 -0700544 auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700545 if (error != Error::NONE && !hasChangesError(error)) {
Fabien Sanglard249c0ae2017-06-19 19:22:36 -0700546 return error;
547 }
548
549 if (*state == 1) {
Ady Abrahamd11bade2022-08-01 16:18:03 -0700550 *outPresentFence = sp<Fence>::make(presentFenceFd);
Fabien Sanglard249c0ae2017-06-19 19:22:36 -0700551 }
552
553 if (*state == 0) {
554 *outNumTypes = numTypes;
555 *outNumRequests = numRequests;
556 }
557 return error;
558}
Chia-I Wu0c6ce462017-06-22 10:48:28 -0700559
Dominik Laskowskib17c6212022-05-09 09:36:19 -0700560ftl::Future<Error> Display::setDisplayBrightness(
Alec Mouri4d8a05d2022-03-23 18:14:26 +0000561 float brightness, float brightnessNits,
562 const Hwc2::Composer::DisplayBrightnessOptions& options) {
563 return ftl::defer([composer = &mComposer, id = mId, brightness, brightnessNits, options] {
564 const auto intError =
565 composer->setDisplayBrightness(id, brightness, brightnessNits, options);
Dominik Laskowski5690bde2020-04-23 19:04:22 -0700566 return static_cast<Error>(intError);
567 });
Dan Gittik57e63c52019-01-18 16:37:54 +0000568}
569
Kriti Dang7defaf32021-11-15 11:55:43 +0100570Error Display::setBootDisplayConfig(hal::HWConfigId configId) {
571 auto intError = mComposer.setBootDisplayConfig(mId, configId);
572 return static_cast<Error>(intError);
573}
574
575Error Display::clearBootDisplayConfig() {
576 auto intError = mComposer.clearBootDisplayConfig(mId);
577 return static_cast<Error>(intError);
578}
579
580Error Display::getPreferredBootDisplayConfig(hal::HWConfigId* configId) const {
581 auto intError = mComposer.getPreferredBootDisplayConfig(mId, configId);
582 return static_cast<Error>(intError);
583}
584
Dominik Laskowski5690bde2020-04-23 19:04:22 -0700585Error Display::setAutoLowLatencyMode(bool on) {
Galia Peycheva5492cb52019-10-30 14:13:16 +0100586 auto intError = mComposer.setAutoLowLatencyMode(mId, on);
587 return static_cast<Error>(intError);
588}
589
590Error Display::getSupportedContentTypes(std::vector<ContentType>* outSupportedContentTypes) const {
591 std::vector<Hwc2::IComposerClient::ContentType> tmpSupportedContentTypes;
592 auto intError = mComposer.getSupportedContentTypes(mId, &tmpSupportedContentTypes);
593 for (Hwc2::IComposerClient::ContentType contentType : tmpSupportedContentTypes) {
594 outSupportedContentTypes->push_back(static_cast<ContentType>(contentType));
595 }
596 return static_cast<Error>(intError);
597}
598
Dominik Laskowski5690bde2020-04-23 19:04:22 -0700599Error Display::setContentType(ContentType contentType) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700600 auto intError = mComposer.setContentType(mId, contentType);
Galia Peycheva5492cb52019-10-30 14:13:16 +0100601 return static_cast<Error>(intError);
602}
603
Alec Mouri85065692022-03-18 00:58:26 +0000604Error Display::getClientTargetProperty(
605 aidl::android::hardware::graphics::composer3::ClientTargetPropertyWithBrightness*
606 outClientTargetProperty) {
607 const auto error = mComposer.getClientTargetProperty(mId, outClientTargetProperty);
Peiyong Lindfc3f7c2020-05-07 20:15:50 -0700608 return static_cast<Error>(error);
609}
610
Sally Qi492cec32024-06-28 14:34:47 -0700611Error Display::getDisplayLuts(std::vector<Lut>* outLuts) {
612 std::vector<Lut> tmpLuts;
613 const auto error = mComposer.getDisplayLuts(mId, &tmpLuts);
614 for (Lut& lut : tmpLuts) {
615 if (lut.pfd.get() >= 0) {
616 outLuts->push_back(
617 {lut.layer, ndk::ScopedFileDescriptor(lut.pfd.release()), lut.lutProperties});
618 }
619 }
620 return static_cast<Error>(error);
621}
622
Leon Scroggins IIIe7c51c62022-02-01 15:53:54 -0500623Error Display::getDisplayDecorationSupport(
624 std::optional<aidl::android::hardware::graphics::common::DisplayDecorationSupport>*
625 support) {
626 const auto error = mComposer.getDisplayDecorationSupport(mId, support);
627 return static_cast<Error>(error);
628}
629
ramindani32cf0602022-03-02 02:30:29 +0000630Error Display::setIdleTimerEnabled(std::chrono::milliseconds timeout) {
631 const auto error = mComposer.setIdleTimerEnabled(mId, timeout);
632 return static_cast<Error>(error);
633}
634
Dan Stoza651bf312015-10-23 17:03:17 -0700635// For use by Device
636
Steven Thomas94e35b92017-07-26 18:48:28 -0700637void Display::setConnected(bool connected) {
Steven Thomasb6c6ad42018-01-29 12:22:00 -0800638 if (!mIsConnected && connected) {
Steven Thomas94e35b92017-07-26 18:48:28 -0700639 mComposer.setClientTargetSlotCount(mId);
Steven Thomas94e35b92017-07-26 18:48:28 -0700640 }
641 mIsConnected = connected;
642}
643
Dan Stoza651bf312015-10-23 17:03:17 -0700644// Other Display methods
645
Lloyd Piquea516c002021-05-07 14:36:58 -0700646std::shared_ptr<HWC2::Layer> Display::getLayerById(HWLayerId id) const {
647 auto it = mLayers.find(id);
648 return it != mLayers.end() ? it->second.lock() : nullptr;
Dan Stoza651bf312015-10-23 17:03:17 -0700649}
HyunKyounga264a352024-04-24 18:51:33 +0900650
651void Display::loadDisplayCapabilities() {
652 std::call_once(mDisplayCapabilityQueryFlag, [this]() {
653 std::vector<DisplayCapability> tmpCapabilities;
654 auto error =
655 static_cast<Error>(mComposer.getDisplayCapabilities(mId, &tmpCapabilities));
656 if (error == Error::NONE) {
657 std::scoped_lock lock(mDisplayCapabilitiesMutex);
658 mDisplayCapabilities.emplace();
659 for (auto capability : tmpCapabilities) {
660 mDisplayCapabilities->emplace(capability);
661 }
662 } else if (error == Error::UNSUPPORTED) {
663 std::scoped_lock lock(mDisplayCapabilitiesMutex);
664 mDisplayCapabilities.emplace();
665 if (mCapabilities.count(AidlCapability::SKIP_CLIENT_COLOR_TRANSFORM)) {
666 mDisplayCapabilities->emplace(DisplayCapability::SKIP_CLIENT_COLOR_TRANSFORM);
667 }
668 bool dozeSupport = false;
669 error = static_cast<Error>(mComposer.getDozeSupport(mId, &dozeSupport));
670 if (error == Error::NONE && dozeSupport) {
671 mDisplayCapabilities->emplace(DisplayCapability::DOZE);
672 }
673 }
674 });
675}
Ana Krulec4593b692019-01-11 22:07:25 -0800676} // namespace impl
Dan Stoza651bf312015-10-23 17:03:17 -0700677
678// Layer methods
679
Leon Scroggins III4459bf42022-01-04 13:58:26 -0500680namespace {
681std::vector<Hwc2::IComposerClient::Rect> convertRegionToHwcRects(const Region& region) {
682 size_t rectCount = 0;
683 Rect const* rectArray = region.getArray(&rectCount);
684
685 std::vector<Hwc2::IComposerClient::Rect> hwcRects;
686 hwcRects.reserve(rectCount);
687 for (size_t rect = 0; rect < rectCount; ++rect) {
688 hwcRects.push_back({rectArray[rect].left, rectArray[rect].top, rectArray[rect].right,
689 rectArray[rect].bottom});
690 }
691 return hwcRects;
692}
693} // namespace
694
Lloyd Pique35d58242018-12-18 16:33:25 -0800695Layer::~Layer() = default;
696
697namespace impl {
698
Ady Abrahamde549d42022-01-26 19:19:17 -0800699Layer::Layer(android::Hwc2::Composer& composer,
700 const std::unordered_set<AidlCapability>& capabilities, HWC2::Display& display,
701 HWLayerId layerId)
Lloyd Pique4603f3c2020-02-11 12:06:56 -0800702 : mComposer(composer),
703 mCapabilities(capabilities),
Lloyd Piquea516c002021-05-07 14:36:58 -0700704 mDisplay(&display),
Lloyd Pique4603f3c2020-02-11 12:06:56 -0800705 mId(layerId),
706 mColorMatrix(android::mat4()) {
Lloyd Piquea516c002021-05-07 14:36:58 -0700707 ALOGV("Created layer %" PRIu64 " on display %" PRIu64, layerId, display.getId());
Dan Stoza651bf312015-10-23 17:03:17 -0700708}
709
710Layer::~Layer()
711{
Lloyd Piquea516c002021-05-07 14:36:58 -0700712 onOwningDisplayDestroyed();
713}
714
715void Layer::onOwningDisplayDestroyed() {
716 // Note: onOwningDisplayDestroyed() may be called to perform cleanup by
717 // either the Layer dtor or by the Display dtor and must be safe to call
718 // from either path. In particular, the call to Display::onLayerDestroyed()
719 // is expected to be safe to do,
720
721 if (CC_UNLIKELY(!mDisplay)) {
722 return;
723 }
724
725 mDisplay->onLayerDestroyed(mId);
726
727 // Note: If the HWC display was actually disconnected, these calls are will
728 // return an error. We always make them as there may be other reasons for
729 // the HWC2::Display to be destroyed.
730 auto intError = mComposer.destroyLayer(mDisplay->getId(), mId);
Steven Thomas94e35b92017-07-26 18:48:28 -0700731 auto error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -0700732 ALOGE_IF(error != Error::NONE,
733 "destroyLayer(%" PRIu64 ", %" PRIu64 ")"
734 " failed: %s (%d)",
Lloyd Piquea516c002021-05-07 14:36:58 -0700735 mDisplay->getId(), mId, to_string(error).c_str(), intError);
736
737 mDisplay = nullptr;
Steven Thomas94e35b92017-07-26 18:48:28 -0700738}
739
Dan Stoza651bf312015-10-23 17:03:17 -0700740Error Layer::setCursorPosition(int32_t x, int32_t y)
741{
Lloyd Piquea516c002021-05-07 14:36:58 -0700742 if (CC_UNLIKELY(!mDisplay)) {
743 return Error::BAD_DISPLAY;
744 }
745
746 auto intError = mComposer.setCursorPosition(mDisplay->getId(), mId, x, y);
Dan Stoza651bf312015-10-23 17:03:17 -0700747 return static_cast<Error>(intError);
748}
749
Daniel Nicoara1f42e3a2017-04-10 13:27:32 -0400750Error Layer::setBuffer(uint32_t slot, const sp<GraphicBuffer>& buffer,
Dan Stoza651bf312015-10-23 17:03:17 -0700751 const sp<Fence>& acquireFence)
752{
Lloyd Piquea516c002021-05-07 14:36:58 -0700753 if (CC_UNLIKELY(!mDisplay)) {
754 return Error::BAD_DISPLAY;
755 }
756
Yichi Chen8366f562019-03-25 19:44:06 +0800757 if (buffer == nullptr && mBufferSlot == slot) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700758 return Error::NONE;
Yichi Chen8366f562019-03-25 19:44:06 +0800759 }
760 mBufferSlot = slot;
761
Dan Stoza651bf312015-10-23 17:03:17 -0700762 int32_t fenceFd = acquireFence->dup();
Lloyd Piquea516c002021-05-07 14:36:58 -0700763 auto intError = mComposer.setLayerBuffer(mDisplay->getId(), mId, slot, buffer, fenceFd);
Dan Stoza651bf312015-10-23 17:03:17 -0700764 return static_cast<Error>(intError);
765}
766
Brian Lindahlb158a5c2022-12-15 15:21:13 -0700767Error Layer::setBufferSlotsToClear(const std::vector<uint32_t>& slotsToClear,
768 uint32_t activeBufferSlot) {
Brian Lindahl90553da2022-12-06 13:36:30 -0700769 if (CC_UNLIKELY(!mDisplay)) {
770 return Error::BAD_DISPLAY;
771 }
Brian Lindahlb158a5c2022-12-15 15:21:13 -0700772 auto intError = mComposer.setLayerBufferSlotsToClear(mDisplay->getId(), mId, slotsToClear,
773 activeBufferSlot);
Brian Lindahl90553da2022-12-06 13:36:30 -0700774 return static_cast<Error>(intError);
775}
776
Dan Stoza651bf312015-10-23 17:03:17 -0700777Error Layer::setSurfaceDamage(const Region& damage)
778{
Lloyd Piquea516c002021-05-07 14:36:58 -0700779 if (CC_UNLIKELY(!mDisplay)) {
780 return Error::BAD_DISPLAY;
781 }
782
Yichi Chen8366f562019-03-25 19:44:06 +0800783 if (damage.isRect() && mDamageRegion.isRect() &&
784 (damage.getBounds() == mDamageRegion.getBounds())) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700785 return Error::NONE;
Yichi Chen8366f562019-03-25 19:44:06 +0800786 }
787 mDamageRegion = damage;
788
Dan Stoza651bf312015-10-23 17:03:17 -0700789 // We encode default full-screen damage as INVALID_RECT upstream, but as 0
790 // rects for HWC
Chia-I Wuaab99f52016-10-05 12:59:58 +0800791 Hwc2::Error intError = Hwc2::Error::NONE;
Dan Stoza651bf312015-10-23 17:03:17 -0700792 if (damage.isRect() && damage.getBounds() == Rect::INVALID_RECT) {
Lloyd Piquea516c002021-05-07 14:36:58 -0700793 intError = mComposer.setLayerSurfaceDamage(mDisplay->getId(), mId,
794 std::vector<Hwc2::IComposerClient::Rect>());
Dan Stoza651bf312015-10-23 17:03:17 -0700795 } else {
Leon Scroggins III4459bf42022-01-04 13:58:26 -0500796 const auto hwcRects = convertRegionToHwcRects(damage);
Lloyd Piquea516c002021-05-07 14:36:58 -0700797 intError = mComposer.setLayerSurfaceDamage(mDisplay->getId(), mId, hwcRects);
Dan Stoza651bf312015-10-23 17:03:17 -0700798 }
799
800 return static_cast<Error>(intError);
801}
802
803Error Layer::setBlendMode(BlendMode mode)
804{
Lloyd Piquea516c002021-05-07 14:36:58 -0700805 if (CC_UNLIKELY(!mDisplay)) {
806 return Error::BAD_DISPLAY;
807 }
808
809 auto intError = mComposer.setLayerBlendMode(mDisplay->getId(), mId, mode);
Dan Stoza651bf312015-10-23 17:03:17 -0700810 return static_cast<Error>(intError);
811}
812
Peiyong Line9d809e2020-04-14 13:10:48 -0700813Error Layer::setColor(Color color) {
Lloyd Piquea516c002021-05-07 14:36:58 -0700814 if (CC_UNLIKELY(!mDisplay)) {
815 return Error::BAD_DISPLAY;
816 }
817
818 auto intError = mComposer.setLayerColor(mDisplay->getId(), mId, color);
Dan Stoza651bf312015-10-23 17:03:17 -0700819 return static_cast<Error>(intError);
820}
821
822Error Layer::setCompositionType(Composition type)
823{
Lloyd Piquea516c002021-05-07 14:36:58 -0700824 if (CC_UNLIKELY(!mDisplay)) {
825 return Error::BAD_DISPLAY;
826 }
827
828 auto intError = mComposer.setLayerCompositionType(mDisplay->getId(), mId, type);
Dan Stoza651bf312015-10-23 17:03:17 -0700829 return static_cast<Error>(intError);
830}
831
Peiyong Lin34beb7a2018-03-28 11:57:12 -0700832Error Layer::setDataspace(Dataspace dataspace)
Dan Stoza5df2a862016-03-24 16:19:37 -0700833{
Lloyd Piquea516c002021-05-07 14:36:58 -0700834 if (CC_UNLIKELY(!mDisplay)) {
835 return Error::BAD_DISPLAY;
836 }
837
Courtney Goeltzenleuchterc988ee42017-05-31 17:56:46 -0600838 if (dataspace == mDataSpace) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700839 return Error::NONE;
Courtney Goeltzenleuchterc988ee42017-05-31 17:56:46 -0600840 }
841 mDataSpace = dataspace;
Lloyd Piquea516c002021-05-07 14:36:58 -0700842 auto intError = mComposer.setLayerDataspace(mDisplay->getId(), mId, mDataSpace);
Dan Stoza5df2a862016-03-24 16:19:37 -0700843 return static_cast<Error>(intError);
844}
845
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700846Error Layer::setPerFrameMetadata(const int32_t supportedPerFrameMetadata,
847 const android::HdrMetadata& metadata)
848{
Lloyd Piquea516c002021-05-07 14:36:58 -0700849 if (CC_UNLIKELY(!mDisplay)) {
850 return Error::BAD_DISPLAY;
851 }
852
Courtney Goeltzenleuchterf9c98e52018-02-12 07:23:17 -0700853 if (metadata == mHdrMetadata) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700854 return Error::NONE;
Courtney Goeltzenleuchterf9c98e52018-02-12 07:23:17 -0700855 }
856
857 mHdrMetadata = metadata;
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700858 int validTypes = mHdrMetadata.validTypes & supportedPerFrameMetadata;
859 std::vector<Hwc2::PerFrameMetadata> perFrameMetadatas;
860 if (validTypes & HdrMetadata::SMPTE2086) {
861 perFrameMetadatas.insert(perFrameMetadatas.end(),
862 {{Hwc2::PerFrameMetadataKey::DISPLAY_RED_PRIMARY_X,
Valerie Haue9e843a2018-12-18 13:39:23 -0800863 mHdrMetadata.smpte2086.displayPrimaryRed.x},
864 {Hwc2::PerFrameMetadataKey::DISPLAY_RED_PRIMARY_Y,
865 mHdrMetadata.smpte2086.displayPrimaryRed.y},
866 {Hwc2::PerFrameMetadataKey::DISPLAY_GREEN_PRIMARY_X,
867 mHdrMetadata.smpte2086.displayPrimaryGreen.x},
868 {Hwc2::PerFrameMetadataKey::DISPLAY_GREEN_PRIMARY_Y,
869 mHdrMetadata.smpte2086.displayPrimaryGreen.y},
870 {Hwc2::PerFrameMetadataKey::DISPLAY_BLUE_PRIMARY_X,
871 mHdrMetadata.smpte2086.displayPrimaryBlue.x},
872 {Hwc2::PerFrameMetadataKey::DISPLAY_BLUE_PRIMARY_Y,
873 mHdrMetadata.smpte2086.displayPrimaryBlue.y},
874 {Hwc2::PerFrameMetadataKey::WHITE_POINT_X,
875 mHdrMetadata.smpte2086.whitePoint.x},
876 {Hwc2::PerFrameMetadataKey::WHITE_POINT_Y,
877 mHdrMetadata.smpte2086.whitePoint.y},
878 {Hwc2::PerFrameMetadataKey::MAX_LUMINANCE,
879 mHdrMetadata.smpte2086.maxLuminance},
880 {Hwc2::PerFrameMetadataKey::MIN_LUMINANCE,
881 mHdrMetadata.smpte2086.minLuminance}});
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700882 }
883
884 if (validTypes & HdrMetadata::CTA861_3) {
885 perFrameMetadatas.insert(perFrameMetadatas.end(),
886 {{Hwc2::PerFrameMetadataKey::MAX_CONTENT_LIGHT_LEVEL,
Valerie Haue9e843a2018-12-18 13:39:23 -0800887 mHdrMetadata.cta8613.maxContentLightLevel},
888 {Hwc2::PerFrameMetadataKey::MAX_FRAME_AVERAGE_LIGHT_LEVEL,
889 mHdrMetadata.cta8613.maxFrameAverageLightLevel}});
Peiyong Lin0ac5f4e2018-04-19 22:06:34 -0700890 }
891
Alec Mouri66d83482022-01-11 11:14:44 -0800892 const Error error = static_cast<Error>(
893 mComposer.setLayerPerFrameMetadata(mDisplay->getId(), mId, perFrameMetadatas));
894 if (error != Error::NONE) {
895 return error;
896 }
Valerie Haue9e843a2018-12-18 13:39:23 -0800897
Alec Mouri66d83482022-01-11 11:14:44 -0800898 std::vector<Hwc2::PerFrameMetadataBlob> perFrameMetadataBlobs;
Valerie Haue9e843a2018-12-18 13:39:23 -0800899 if (validTypes & HdrMetadata::HDR10PLUS) {
Yichi Chen1d5146d2020-06-12 18:50:11 +0800900 if (CC_UNLIKELY(mHdrMetadata.hdr10plus.size() == 0)) {
901 return Error::BAD_PARAMETER;
902 }
903
Valerie Haue9e843a2018-12-18 13:39:23 -0800904 perFrameMetadataBlobs.push_back(
905 {Hwc2::PerFrameMetadataKey::HDR10_PLUS_SEI, mHdrMetadata.hdr10plus});
Valerie Haue9e843a2018-12-18 13:39:23 -0800906 }
Alec Mouri66d83482022-01-11 11:14:44 -0800907
908 return static_cast<Error>(
909 mComposer.setLayerPerFrameMetadataBlobs(mDisplay->getId(), mId, perFrameMetadataBlobs));
Courtney Goeltzenleuchterf9c98e52018-02-12 07:23:17 -0700910}
911
Dan Stoza651bf312015-10-23 17:03:17 -0700912Error Layer::setDisplayFrame(const Rect& frame)
913{
Lloyd Piquea516c002021-05-07 14:36:58 -0700914 if (CC_UNLIKELY(!mDisplay)) {
915 return Error::BAD_DISPLAY;
916 }
917
Chia-I Wucd8d7f02016-11-16 11:02:31 +0800918 Hwc2::IComposerClient::Rect hwcRect{frame.left, frame.top,
Chia-I Wuaab99f52016-10-05 12:59:58 +0800919 frame.right, frame.bottom};
Lloyd Piquea516c002021-05-07 14:36:58 -0700920 auto intError = mComposer.setLayerDisplayFrame(mDisplay->getId(), mId, hwcRect);
Dan Stoza651bf312015-10-23 17:03:17 -0700921 return static_cast<Error>(intError);
922}
923
924Error Layer::setPlaneAlpha(float alpha)
925{
Lloyd Piquea516c002021-05-07 14:36:58 -0700926 if (CC_UNLIKELY(!mDisplay)) {
927 return Error::BAD_DISPLAY;
928 }
929
930 auto intError = mComposer.setLayerPlaneAlpha(mDisplay->getId(), mId, alpha);
Dan Stoza651bf312015-10-23 17:03:17 -0700931 return static_cast<Error>(intError);
932}
933
934Error Layer::setSidebandStream(const native_handle_t* stream)
935{
Lloyd Piquea516c002021-05-07 14:36:58 -0700936 if (CC_UNLIKELY(!mDisplay)) {
937 return Error::BAD_DISPLAY;
938 }
939
Ady Abrahamde549d42022-01-26 19:19:17 -0800940 if (mCapabilities.count(AidlCapability::SIDEBAND_STREAM) == 0) {
Dan Stoza09e7a272016-04-14 12:31:01 -0700941 ALOGE("Attempted to call setSidebandStream without checking that the "
942 "device supports sideband streams");
Peiyong Line9d809e2020-04-14 13:10:48 -0700943 return Error::UNSUPPORTED;
Dan Stoza09e7a272016-04-14 12:31:01 -0700944 }
Lloyd Piquea516c002021-05-07 14:36:58 -0700945 auto intError = mComposer.setLayerSidebandStream(mDisplay->getId(), mId, stream);
Dan Stoza651bf312015-10-23 17:03:17 -0700946 return static_cast<Error>(intError);
947}
948
949Error Layer::setSourceCrop(const FloatRect& crop)
950{
Lloyd Piquea516c002021-05-07 14:36:58 -0700951 if (CC_UNLIKELY(!mDisplay)) {
952 return Error::BAD_DISPLAY;
953 }
954
Chia-I Wucd8d7f02016-11-16 11:02:31 +0800955 Hwc2::IComposerClient::FRect hwcRect{
Chia-I Wuaab99f52016-10-05 12:59:58 +0800956 crop.left, crop.top, crop.right, crop.bottom};
Lloyd Piquea516c002021-05-07 14:36:58 -0700957 auto intError = mComposer.setLayerSourceCrop(mDisplay->getId(), mId, hwcRect);
Dan Stoza651bf312015-10-23 17:03:17 -0700958 return static_cast<Error>(intError);
959}
960
961Error Layer::setTransform(Transform transform)
962{
Lloyd Piquea516c002021-05-07 14:36:58 -0700963 if (CC_UNLIKELY(!mDisplay)) {
964 return Error::BAD_DISPLAY;
965 }
966
Chia-I Wuaab99f52016-10-05 12:59:58 +0800967 auto intTransform = static_cast<Hwc2::Transform>(transform);
Lloyd Piquea516c002021-05-07 14:36:58 -0700968 auto intError = mComposer.setLayerTransform(mDisplay->getId(), mId, intTransform);
Dan Stoza651bf312015-10-23 17:03:17 -0700969 return static_cast<Error>(intError);
970}
971
972Error Layer::setVisibleRegion(const Region& region)
973{
Lloyd Piquea516c002021-05-07 14:36:58 -0700974 if (CC_UNLIKELY(!mDisplay)) {
975 return Error::BAD_DISPLAY;
976 }
977
Yichi Chen8366f562019-03-25 19:44:06 +0800978 if (region.isRect() && mVisibleRegion.isRect() &&
979 (region.getBounds() == mVisibleRegion.getBounds())) {
Peiyong Line9d809e2020-04-14 13:10:48 -0700980 return Error::NONE;
Yichi Chen8366f562019-03-25 19:44:06 +0800981 }
982 mVisibleRegion = region;
Leon Scroggins III4459bf42022-01-04 13:58:26 -0500983 const auto hwcRects = convertRegionToHwcRects(region);
Lloyd Piquea516c002021-05-07 14:36:58 -0700984 auto intError = mComposer.setLayerVisibleRegion(mDisplay->getId(), mId, hwcRects);
Dan Stoza651bf312015-10-23 17:03:17 -0700985 return static_cast<Error>(intError);
986}
987
988Error Layer::setZOrder(uint32_t z)
989{
Lloyd Piquea516c002021-05-07 14:36:58 -0700990 if (CC_UNLIKELY(!mDisplay)) {
991 return Error::BAD_DISPLAY;
992 }
993
994 auto intError = mComposer.setLayerZOrder(mDisplay->getId(), mId, z);
Dan Stoza651bf312015-10-23 17:03:17 -0700995 return static_cast<Error>(intError);
996}
997
Peiyong Lin698147a2018-09-14 13:27:18 -0700998// Composer HAL 2.3
999Error Layer::setColorTransform(const android::mat4& matrix) {
Lloyd Piquea516c002021-05-07 14:36:58 -07001000 if (CC_UNLIKELY(!mDisplay)) {
1001 return Error::BAD_DISPLAY;
1002 }
1003
Peiyong Lin698147a2018-09-14 13:27:18 -07001004 if (matrix == mColorMatrix) {
Peiyong Line9d809e2020-04-14 13:10:48 -07001005 return Error::NONE;
Peiyong Lin698147a2018-09-14 13:27:18 -07001006 }
Lloyd Piquea516c002021-05-07 14:36:58 -07001007 auto intError = mComposer.setLayerColorTransform(mDisplay->getId(), mId, matrix.asArray());
Peiyong Lin04d25872019-04-18 10:26:19 -07001008 Error error = static_cast<Error>(intError);
Peiyong Line9d809e2020-04-14 13:10:48 -07001009 if (error != Error::NONE) {
Peiyong Lin04d25872019-04-18 10:26:19 -07001010 return error;
1011 }
1012 mColorMatrix = matrix;
1013 return error;
Peiyong Lin698147a2018-09-14 13:27:18 -07001014}
Lloyd Pique35d58242018-12-18 16:33:25 -08001015
Lloyd Pique4603f3c2020-02-11 12:06:56 -08001016// Composer HAL 2.4
1017Error Layer::setLayerGenericMetadata(const std::string& name, bool mandatory,
1018 const std::vector<uint8_t>& value) {
Lloyd Piquea516c002021-05-07 14:36:58 -07001019 if (CC_UNLIKELY(!mDisplay)) {
1020 return Error::BAD_DISPLAY;
1021 }
1022
1023 auto intError =
1024 mComposer.setLayerGenericMetadata(mDisplay->getId(), mId, name, mandatory, value);
Lloyd Pique4603f3c2020-02-11 12:06:56 -08001025 return static_cast<Error>(intError);
1026}
1027
Alec Mouricdf6cbc2021-11-01 17:21:15 -07001028// AIDL HAL
Alec Mouri6da0e272022-02-07 12:45:57 -08001029Error Layer::setBrightness(float brightness) {
Alec Mouricdf6cbc2021-11-01 17:21:15 -07001030 if (CC_UNLIKELY(!mDisplay)) {
1031 return Error::BAD_DISPLAY;
1032 }
1033
Alec Mouri6da0e272022-02-07 12:45:57 -08001034 auto intError = mComposer.setLayerBrightness(mDisplay->getId(), mId, brightness);
Alec Mouricdf6cbc2021-11-01 17:21:15 -07001035 return static_cast<Error>(intError);
1036}
1037
Leon Scroggins IIId77d3162022-01-05 10:42:28 -05001038Error Layer::setBlockingRegion(const Region& region) {
1039 if (CC_UNLIKELY(!mDisplay)) {
1040 return Error::BAD_DISPLAY;
1041 }
1042
1043 if (region.isRect() && mBlockingRegion.isRect() &&
1044 (region.getBounds() == mBlockingRegion.getBounds())) {
1045 return Error::NONE;
1046 }
1047 mBlockingRegion = region;
1048 const auto hwcRects = convertRegionToHwcRects(region);
1049 const auto intError = mComposer.setLayerBlockingRegion(mDisplay->getId(), mId, hwcRects);
1050 return static_cast<Error>(intError);
1051}
1052
Lloyd Pique35d58242018-12-18 16:33:25 -08001053} // namespace impl
Dan Stoza651bf312015-10-23 17:03:17 -07001054} // namespace HWC2
Peiyong Line9d809e2020-04-14 13:10:48 -07001055} // namespace android
Ady Abrahamb0dbdaa2020-01-06 16:19:42 -08001056
1057// TODO(b/129481165): remove the #pragma below and fix conversion issues
1058#pragma clang diagnostic pop // ignored "-Wconversion"