• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2022 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #define LOG_TAG "Gralloc5"
18 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
19 
20 #include <ui/Gralloc5.h>
21 
22 #include <aidlcommonsupport/NativeHandle.h>
23 #include <android/binder_manager.h>
24 #include <android/hardware/graphics/mapper/utils/IMapperMetadataTypes.h>
25 #include <binder/IPCThreadState.h>
26 #include <dlfcn.h>
27 #include <ui/FatVector.h>
28 #include <vndksupport/linker.h>
29 
30 using namespace aidl::android::hardware::graphics::allocator;
31 using namespace aidl::android::hardware::graphics::common;
32 using namespace ::android::hardware::graphics::mapper;
33 
34 namespace android {
35 
36 static const auto kIAllocatorServiceName = IAllocator::descriptor + std::string("/default");
37 static const auto kIAllocatorMinimumVersion = 2;
38 
39 // TODO(b/72323293, b/72703005): Remove these invalid bits from callers
40 static constexpr uint64_t kRemovedUsageBits = static_cast<uint64_t>((1 << 10) | (1 << 13));
41 
42 typedef AIMapper_Error (*AIMapper_loadIMapperFn)(AIMapper *_Nullable *_Nonnull outImplementation);
43 
44 struct Gralloc5 {
45     std::shared_ptr<IAllocator> allocator;
46     AIMapper *mapper = nullptr;
47 };
48 
waitForAllocator()49 static std::shared_ptr<IAllocator> waitForAllocator() {
50     if (__builtin_available(android 31, *)) {
51         if (!AServiceManager_isDeclared(kIAllocatorServiceName.c_str())) {
52             return nullptr;
53         }
54         auto allocator = IAllocator::fromBinder(
55                 ndk::SpAIBinder(AServiceManager_waitForService(kIAllocatorServiceName.c_str())));
56         if (!allocator) {
57             ALOGE("AIDL IAllocator declared but failed to get service");
58             return nullptr;
59         }
60 
61         int32_t version = 0;
62         if (!allocator->getInterfaceVersion(&version).isOk()) {
63             ALOGE("Failed to query interface version");
64             return nullptr;
65         }
66         if (version < kIAllocatorMinimumVersion) {
67             return nullptr;
68         }
69         return allocator;
70     } else {
71         // TODO: LOG_ALWAYS_FATAL("libui is not backwards compatible");
72         return nullptr;
73     }
74 }
75 
loadIMapperLibrary()76 static void *loadIMapperLibrary() {
77     static void *imapperLibrary = []() -> void * {
78         auto allocator = waitForAllocator();
79         std::string mapperSuffix;
80         auto status = allocator->getIMapperLibrarySuffix(&mapperSuffix);
81         if (!status.isOk()) {
82             ALOGE("Failed to get IMapper library suffix");
83             return nullptr;
84         }
85 
86         std::string lib_name = "mapper." + mapperSuffix + ".so";
87         void *so = android_load_sphal_library(lib_name.c_str(), RTLD_LOCAL | RTLD_NOW);
88         if (!so) {
89             ALOGE("Failed to load %s", lib_name.c_str());
90         }
91         return so;
92     }();
93     return imapperLibrary;
94 }
95 
getInstance()96 static const Gralloc5 &getInstance() {
97     static Gralloc5 instance = []() {
98         auto allocator = waitForAllocator();
99         if (!allocator) {
100             return Gralloc5{};
101         }
102         void *so = loadIMapperLibrary();
103         if (!so) {
104             return Gralloc5{};
105         }
106         auto loadIMapper = (AIMapper_loadIMapperFn)dlsym(so, "AIMapper_loadIMapper");
107         AIMapper *mapper = nullptr;
108         AIMapper_Error error = loadIMapper(&mapper);
109         if (error != AIMAPPER_ERROR_NONE) {
110             ALOGE("AIMapper_loadIMapper failed %d", error);
111             return Gralloc5{};
112         }
113         return Gralloc5{std::move(allocator), mapper};
114     }();
115     return instance;
116 }
117 
118 template <StandardMetadataType T>
getStandardMetadata(AIMapper * mapper,buffer_handle_t bufferHandle)119 static auto getStandardMetadata(AIMapper *mapper, buffer_handle_t bufferHandle)
120         -> decltype(StandardMetadata<T>::value::decode(nullptr, 0)) {
121     using Value = typename StandardMetadata<T>::value;
122     // TODO: Tune for common-case better
123     FatVector<uint8_t, 128> buffer;
124     int32_t sizeRequired = mapper->v5.getStandardMetadata(bufferHandle, static_cast<int64_t>(T),
125                                                           buffer.data(), buffer.size());
126     if (sizeRequired < 0) {
127         ALOGW_IF(-AIMAPPER_ERROR_UNSUPPORTED != sizeRequired,
128                  "Unexpected error %d from valid getStandardMetadata call", -sizeRequired);
129         return std::nullopt;
130     }
131     if ((size_t)sizeRequired > buffer.size()) {
132         buffer.resize(sizeRequired);
133         sizeRequired = mapper->v5.getStandardMetadata(bufferHandle, static_cast<int64_t>(T),
134                                                       buffer.data(), buffer.size());
135     }
136     if (sizeRequired < 0 || (size_t)sizeRequired > buffer.size()) {
137         ALOGW("getStandardMetadata failed, received %d with buffer size %zd", sizeRequired,
138               buffer.size());
139         // Generate a fail type
140         return std::nullopt;
141     }
142     return Value::decode(buffer.data(), sizeRequired);
143 }
144 
145 template <StandardMetadataType T>
setStandardMetadata(AIMapper * mapper,buffer_handle_t bufferHandle,const typename StandardMetadata<T>::value_type & value)146 static AIMapper_Error setStandardMetadata(AIMapper *mapper, buffer_handle_t bufferHandle,
147                                           const typename StandardMetadata<T>::value_type &value) {
148     using Value = typename StandardMetadata<T>::value;
149     int32_t sizeRequired = Value::encode(value, nullptr, 0);
150     if (sizeRequired < 0) {
151         ALOGW("Failed to calculate required size");
152         return static_cast<AIMapper_Error>(-sizeRequired);
153     }
154     FatVector<uint8_t, 128> buffer;
155     buffer.resize(sizeRequired);
156     sizeRequired = Value::encode(value, buffer.data(), buffer.size());
157     if (sizeRequired < 0 || (size_t)sizeRequired > buffer.size()) {
158         ALOGW("Failed to encode with calculated size %d; buffer size %zd", sizeRequired,
159               buffer.size());
160         return static_cast<AIMapper_Error>(-sizeRequired);
161     }
162     return mapper->v5.setStandardMetadata(bufferHandle, static_cast<int64_t>(T), buffer.data(),
163                                           sizeRequired);
164 }
165 
Gralloc5Allocator(const Gralloc5Mapper & mapper)166 Gralloc5Allocator::Gralloc5Allocator(const Gralloc5Mapper &mapper) : mMapper(mapper) {
167     mAllocator = getInstance().allocator;
168 }
169 
isLoaded() const170 bool Gralloc5Allocator::isLoaded() const {
171     return mAllocator != nullptr;
172 }
173 
getValidUsageBits()174 static uint64_t getValidUsageBits() {
175     static const uint64_t validUsageBits = []() -> uint64_t {
176         uint64_t bits = 0;
177         for (const auto bit : ndk::enum_range<BufferUsage>{}) {
178             bits |= static_cast<int64_t>(bit);
179         }
180         return bits;
181     }();
182     return validUsageBits | kRemovedUsageBits;
183 }
184 
makeDescriptor(std::string requestorName,uint32_t width,uint32_t height,PixelFormat format,uint32_t layerCount,uint64_t usage)185 static std::optional<BufferDescriptorInfo> makeDescriptor(std::string requestorName, uint32_t width,
186                                                           uint32_t height, PixelFormat format,
187                                                           uint32_t layerCount, uint64_t usage) {
188     uint64_t validUsageBits = getValidUsageBits();
189     if (usage & ~validUsageBits) {
190         ALOGE("buffer descriptor contains invalid usage bits 0x%" PRIx64, usage & ~validUsageBits);
191         return std::nullopt;
192     }
193 
194     BufferDescriptorInfo descriptorInfo{
195             .width = static_cast<int32_t>(width),
196             .height = static_cast<int32_t>(height),
197             .layerCount = static_cast<int32_t>(layerCount),
198             .format = static_cast<::aidl::android::hardware::graphics::common::PixelFormat>(format),
199             .usage = static_cast<BufferUsage>(usage),
200     };
201     auto nameLength = std::min(requestorName.length(), descriptorInfo.name.size() - 1);
202     memcpy(descriptorInfo.name.data(), requestorName.data(), nameLength);
203     requestorName.data()[nameLength] = 0;
204     return descriptorInfo;
205 }
206 
dumpDebugInfo(bool less) const207 std::string Gralloc5Allocator::dumpDebugInfo(bool less) const {
208     return mMapper.dumpBuffers(less);
209 }
210 
allocate(std::string requestorName,uint32_t width,uint32_t height,android::PixelFormat format,uint32_t layerCount,uint64_t usage,uint32_t bufferCount,uint32_t * outStride,buffer_handle_t * outBufferHandles,bool importBuffers) const211 status_t Gralloc5Allocator::allocate(std::string requestorName, uint32_t width, uint32_t height,
212                                      android::PixelFormat format, uint32_t layerCount,
213                                      uint64_t usage, uint32_t bufferCount, uint32_t *outStride,
214                                      buffer_handle_t *outBufferHandles, bool importBuffers) const {
215     auto descriptorInfo = makeDescriptor(requestorName, width, height, format, layerCount, usage);
216     if (!descriptorInfo) {
217         return BAD_VALUE;
218     }
219 
220     AllocationResult result;
221     auto status = mAllocator->allocate2(*descriptorInfo, bufferCount, &result);
222     if (!status.isOk()) {
223         auto error = status.getExceptionCode();
224         if (error == EX_SERVICE_SPECIFIC) {
225             error = status.getServiceSpecificError();
226         }
227         if (error == OK) {
228             error = UNKNOWN_ERROR;
229         }
230         return error;
231     }
232 
233     if (importBuffers) {
234         for (uint32_t i = 0; i < bufferCount; i++) {
235             auto handle = makeFromAidl(result.buffers[i]);
236             auto error = mMapper.importBuffer(handle, &outBufferHandles[i]);
237             native_handle_delete(handle);
238             if (error != NO_ERROR) {
239                 for (uint32_t j = 0; j < i; j++) {
240                     mMapper.freeBuffer(outBufferHandles[j]);
241                     outBufferHandles[j] = nullptr;
242                 }
243                 return error;
244             }
245         }
246     } else {
247         for (uint32_t i = 0; i < bufferCount; i++) {
248             outBufferHandles[i] = dupFromAidl(result.buffers[i]);
249             if (!outBufferHandles[i]) {
250                 for (uint32_t j = 0; j < i; j++) {
251                     auto buffer = const_cast<native_handle_t *>(outBufferHandles[j]);
252                     native_handle_close(buffer);
253                     native_handle_delete(buffer);
254                     outBufferHandles[j] = nullptr;
255                 }
256                 return NO_MEMORY;
257             }
258         }
259     }
260 
261     *outStride = result.stride;
262 
263     // Release all the resources held by AllocationResult (specifically any remaining FDs)
264     result = {};
265     // make sure the kernel driver sees BC_FREE_BUFFER and closes the fds now
266     // TODO: Re-enable this at some point if it's necessary. We can't do it now because libui
267     // is marked apex_available (b/214400477) and libbinder isn't (which of course is correct)
268     // IPCThreadState::self()->flushCommands();
269 
270     return OK;
271 }
272 
preload()273 void Gralloc5Mapper::preload() {
274     // TODO(b/261858155): Implement. We can't bounce off of IAllocator for this because zygote can't
275     // use binder. So when an alternate strategy of retrieving the library prefix is available,
276     // use that here.
277 }
278 
Gralloc5Mapper()279 Gralloc5Mapper::Gralloc5Mapper() {
280     mMapper = getInstance().mapper;
281 }
282 
isLoaded() const283 bool Gralloc5Mapper::isLoaded() const {
284     return mMapper != nullptr && mMapper->version >= AIMAPPER_VERSION_5;
285 }
286 
dumpBuffer(buffer_handle_t bufferHandle,bool less) const287 std::string Gralloc5Mapper::dumpBuffer(buffer_handle_t bufferHandle, bool less) const {
288     // TODO(b/261858392): Implement
289     (void)bufferHandle;
290     (void)less;
291     return {};
292 }
293 
dumpBuffers(bool less) const294 std::string Gralloc5Mapper::dumpBuffers(bool less) const {
295     // TODO(b/261858392): Implement
296     (void)less;
297     return {};
298 }
299 
importBuffer(const native_handle_t * rawHandle,buffer_handle_t * outBufferHandle) const300 status_t Gralloc5Mapper::importBuffer(const native_handle_t *rawHandle,
301                                       buffer_handle_t *outBufferHandle) const {
302     return mMapper->v5.importBuffer(rawHandle, outBufferHandle);
303 }
304 
freeBuffer(buffer_handle_t bufferHandle) const305 void Gralloc5Mapper::freeBuffer(buffer_handle_t bufferHandle) const {
306     mMapper->v5.freeBuffer(bufferHandle);
307 }
308 
validateBufferSize(buffer_handle_t bufferHandle,uint32_t width,uint32_t height,PixelFormat format,uint32_t layerCount,uint64_t usage,uint32_t stride) const309 status_t Gralloc5Mapper::validateBufferSize(buffer_handle_t bufferHandle, uint32_t width,
310                                             uint32_t height, PixelFormat format,
311                                             uint32_t layerCount, uint64_t usage,
312                                             uint32_t stride) const {
313     {
314         auto value = getStandardMetadata<StandardMetadataType::WIDTH>(mMapper, bufferHandle);
315         if (width != value) {
316             ALOGW("Width didn't match, expected %d got %" PRId64, width, value.value_or(-1));
317             return BAD_VALUE;
318         }
319     }
320     {
321         auto value = getStandardMetadata<StandardMetadataType::HEIGHT>(mMapper, bufferHandle);
322         if (height != value) {
323             ALOGW("Height didn't match, expected %d got %" PRId64, height, value.value_or(-1));
324             return BAD_VALUE;
325         }
326     }
327     {
328         auto value =
329                 getStandardMetadata<StandardMetadataType::PIXEL_FORMAT_REQUESTED>(mMapper,
330                                                                                   bufferHandle);
331         if (static_cast<::aidl::android::hardware::graphics::common::PixelFormat>(format) !=
332             value) {
333             ALOGW("Format didn't match, expected %d got %s", format,
334                   value.has_value() ? toString(*value).c_str() : "<null>");
335             return BAD_VALUE;
336         }
337     }
338     {
339         auto value = getStandardMetadata<StandardMetadataType::LAYER_COUNT>(mMapper, bufferHandle);
340         if (layerCount != value) {
341             ALOGW("Layer count didn't match, expected %d got %" PRId64, layerCount,
342                   value.value_or(-1));
343             return BAD_VALUE;
344         }
345     }
346     // TODO: This can false-positive fail if the allocator adjusted the USAGE bits internally
347     //       Investigate further & re-enable or remove, but for now ignoring usage should be OK
348     (void)usage;
349     // {
350     //     auto value = getStandardMetadata<StandardMetadataType::USAGE>(mMapper, bufferHandle);
351     //     if (static_cast<BufferUsage>(usage) != value) {
352     //         ALOGW("Usage didn't match, expected %" PRIu64 " got %" PRId64, usage,
353     //               static_cast<int64_t>(value.value_or(BufferUsage::CPU_READ_NEVER)));
354     //         return BAD_VALUE;
355     //     }
356     // }
357     {
358         auto value = getStandardMetadata<StandardMetadataType::STRIDE>(mMapper, bufferHandle);
359         if (stride != value) {
360             ALOGW("Stride didn't match, expected %" PRIu32 " got %" PRId32, stride,
361                   value.value_or(-1));
362             return BAD_VALUE;
363         }
364     }
365     return OK;
366 }
367 
getTransportSize(buffer_handle_t bufferHandle,uint32_t * outNumFds,uint32_t * outNumInts) const368 void Gralloc5Mapper::getTransportSize(buffer_handle_t bufferHandle, uint32_t *outNumFds,
369                                       uint32_t *outNumInts) const {
370     mMapper->v5.getTransportSize(bufferHandle, outNumFds, outNumInts);
371 }
372 
lock(buffer_handle_t bufferHandle,uint64_t usage,const Rect & bounds,int acquireFence,void ** outData,int32_t * outBytesPerPixel,int32_t * outBytesPerStride) const373 status_t Gralloc5Mapper::lock(buffer_handle_t bufferHandle, uint64_t usage, const Rect &bounds,
374                               int acquireFence, void **outData, int32_t *outBytesPerPixel,
375                               int32_t *outBytesPerStride) const {
376     std::vector<ui::PlaneLayout> planeLayouts;
377     status_t err = getPlaneLayouts(bufferHandle, &planeLayouts);
378 
379     if (err == NO_ERROR && !planeLayouts.empty()) {
380         if (outBytesPerPixel) {
381             int32_t bitsPerPixel = planeLayouts.front().sampleIncrementInBits;
382             for (const auto &planeLayout : planeLayouts) {
383                 if (bitsPerPixel != planeLayout.sampleIncrementInBits) {
384                     bitsPerPixel = -1;
385                 }
386             }
387             if (bitsPerPixel >= 0 && bitsPerPixel % 8 == 0) {
388                 *outBytesPerPixel = bitsPerPixel / 8;
389             } else {
390                 *outBytesPerPixel = -1;
391             }
392         }
393         if (outBytesPerStride) {
394             int32_t bytesPerStride = planeLayouts.front().strideInBytes;
395             for (const auto &planeLayout : planeLayouts) {
396                 if (bytesPerStride != planeLayout.strideInBytes) {
397                     bytesPerStride = -1;
398                 }
399             }
400             if (bytesPerStride >= 0) {
401                 *outBytesPerStride = bytesPerStride;
402             } else {
403                 *outBytesPerStride = -1;
404             }
405         }
406     }
407 
408     auto status = mMapper->v5.lock(bufferHandle, usage, bounds, acquireFence, outData);
409 
410     ALOGW_IF(status != AIMAPPER_ERROR_NONE, "lock(%p, ...) failed: %d", bufferHandle, status);
411     return static_cast<status_t>(status);
412 }
413 
lock(buffer_handle_t bufferHandle,uint64_t usage,const Rect & bounds,int acquireFence,android_ycbcr * outYcbcr) const414 status_t Gralloc5Mapper::lock(buffer_handle_t bufferHandle, uint64_t usage, const Rect &bounds,
415                               int acquireFence, android_ycbcr *outYcbcr) const {
416     if (!outYcbcr) {
417         return BAD_VALUE;
418     }
419 
420     // TODO(b/262279301): Change the return type of ::unlock to unique_fd instead of int so that
421     //  ignoring the return value "just works" instead
422     auto unlock = [this](buffer_handle_t bufferHandle) {
423         int fence = this->unlock(bufferHandle);
424         if (fence != -1) {
425             ::close(fence);
426         }
427     };
428 
429     std::vector<ui::PlaneLayout> planeLayouts;
430     status_t error = getPlaneLayouts(bufferHandle, &planeLayouts);
431     if (error != NO_ERROR) {
432         return error;
433     }
434 
435     void *data = nullptr;
436     error = lock(bufferHandle, usage, bounds, acquireFence, &data, nullptr, nullptr);
437     if (error != NO_ERROR) {
438         return error;
439     }
440 
441     android_ycbcr ycbcr;
442 
443     ycbcr.y = nullptr;
444     ycbcr.cb = nullptr;
445     ycbcr.cr = nullptr;
446     ycbcr.ystride = 0;
447     ycbcr.cstride = 0;
448     ycbcr.chroma_step = 0;
449 
450     for (const auto &planeLayout : planeLayouts) {
451         for (const auto &planeLayoutComponent : planeLayout.components) {
452             if (!gralloc4::isStandardPlaneLayoutComponentType(planeLayoutComponent.type)) {
453                 continue;
454             }
455 
456             uint8_t *tmpData = static_cast<uint8_t *>(data) + planeLayout.offsetInBytes;
457 
458             // Note that `offsetInBits` may not be a multiple of 8 for packed formats (e.g. P010)
459             // but we still want to point to the start of the first byte.
460             tmpData += (planeLayoutComponent.offsetInBits / 8);
461 
462             uint64_t sampleIncrementInBytes;
463 
464             auto type = static_cast<PlaneLayoutComponentType>(planeLayoutComponent.type.value);
465             switch (type) {
466                 case PlaneLayoutComponentType::Y:
467                     if ((ycbcr.y != nullptr) || (planeLayout.sampleIncrementInBits % 8 != 0)) {
468                         unlock(bufferHandle);
469                         return BAD_VALUE;
470                     }
471                     ycbcr.y = tmpData;
472                     ycbcr.ystride = planeLayout.strideInBytes;
473                     break;
474 
475                 case PlaneLayoutComponentType::CB:
476                 case PlaneLayoutComponentType::CR:
477                     if (planeLayout.sampleIncrementInBits % 8 != 0) {
478                         unlock(bufferHandle);
479                         return BAD_VALUE;
480                     }
481 
482                     sampleIncrementInBytes = planeLayout.sampleIncrementInBits / 8;
483                     if ((sampleIncrementInBytes != 1) && (sampleIncrementInBytes != 2) &&
484                         (sampleIncrementInBytes != 4)) {
485                         unlock(bufferHandle);
486                         return BAD_VALUE;
487                     }
488 
489                     if (ycbcr.cstride == 0 && ycbcr.chroma_step == 0) {
490                         ycbcr.cstride = planeLayout.strideInBytes;
491                         ycbcr.chroma_step = sampleIncrementInBytes;
492                     } else {
493                         if ((static_cast<int64_t>(ycbcr.cstride) != planeLayout.strideInBytes) ||
494                             (ycbcr.chroma_step != sampleIncrementInBytes)) {
495                             unlock(bufferHandle);
496                             return BAD_VALUE;
497                         }
498                     }
499 
500                     if (type == PlaneLayoutComponentType::CB) {
501                         if (ycbcr.cb != nullptr) {
502                             unlock(bufferHandle);
503                             return BAD_VALUE;
504                         }
505                         ycbcr.cb = tmpData;
506                     } else {
507                         if (ycbcr.cr != nullptr) {
508                             unlock(bufferHandle);
509                             return BAD_VALUE;
510                         }
511                         ycbcr.cr = tmpData;
512                     }
513                     break;
514                 default:
515                     break;
516             };
517         }
518     }
519 
520     *outYcbcr = ycbcr;
521     return OK;
522 }
523 
unlock(buffer_handle_t bufferHandle) const524 int Gralloc5Mapper::unlock(buffer_handle_t bufferHandle) const {
525     int fence = -1;
526     AIMapper_Error error = mMapper->v5.unlock(bufferHandle, &fence);
527     if (error != AIMAPPER_ERROR_NONE) {
528         ALOGW("unlock failed with error %d", error);
529     }
530     return fence;
531 }
532 
isSupported(uint32_t width,uint32_t height,PixelFormat format,uint32_t layerCount,uint64_t usage,bool * outSupported) const533 status_t Gralloc5Mapper::isSupported(uint32_t width, uint32_t height, PixelFormat format,
534                                      uint32_t layerCount, uint64_t usage,
535                                      bool *outSupported) const {
536     auto descriptorInfo = makeDescriptor("", width, height, format, layerCount, usage);
537     if (!descriptorInfo) {
538         *outSupported = false;
539         return OK;
540     }
541     auto status = getInstance().allocator->isSupported(*descriptorInfo, outSupported);
542     if (!status.isOk()) {
543         ALOGW("IAllocator::isSupported error %d (%s)", status.getStatus(), status.getMessage());
544         *outSupported = false;
545     }
546     return OK;
547 }
548 
getBufferId(buffer_handle_t bufferHandle,uint64_t * outBufferId) const549 status_t Gralloc5Mapper::getBufferId(buffer_handle_t bufferHandle, uint64_t *outBufferId) const {
550     auto value = getStandardMetadata<StandardMetadataType::BUFFER_ID>(mMapper, bufferHandle);
551     if (value.has_value()) {
552         *outBufferId = *value;
553         return OK;
554     }
555     return UNKNOWN_TRANSACTION;
556 }
557 
getName(buffer_handle_t bufferHandle,std::string * outName) const558 status_t Gralloc5Mapper::getName(buffer_handle_t bufferHandle, std::string *outName) const {
559     auto value = getStandardMetadata<StandardMetadataType::NAME>(mMapper, bufferHandle);
560     if (value.has_value()) {
561         *outName = *value;
562         return OK;
563     }
564     return UNKNOWN_TRANSACTION;
565 }
566 
getWidth(buffer_handle_t bufferHandle,uint64_t * outWidth) const567 status_t Gralloc5Mapper::getWidth(buffer_handle_t bufferHandle, uint64_t *outWidth) const {
568     auto value = getStandardMetadata<StandardMetadataType::WIDTH>(mMapper, bufferHandle);
569     if (value.has_value()) {
570         *outWidth = *value;
571         return OK;
572     }
573     return UNKNOWN_TRANSACTION;
574 }
575 
getHeight(buffer_handle_t bufferHandle,uint64_t * outHeight) const576 status_t Gralloc5Mapper::getHeight(buffer_handle_t bufferHandle, uint64_t *outHeight) const {
577     auto value = getStandardMetadata<StandardMetadataType::HEIGHT>(mMapper, bufferHandle);
578     if (value.has_value()) {
579         *outHeight = *value;
580         return OK;
581     }
582     return UNKNOWN_TRANSACTION;
583 }
584 
getLayerCount(buffer_handle_t bufferHandle,uint64_t * outLayerCount) const585 status_t Gralloc5Mapper::getLayerCount(buffer_handle_t bufferHandle,
586                                        uint64_t *outLayerCount) const {
587     auto value = getStandardMetadata<StandardMetadataType::LAYER_COUNT>(mMapper, bufferHandle);
588     if (value.has_value()) {
589         *outLayerCount = *value;
590         return OK;
591     }
592     return UNKNOWN_TRANSACTION;
593 }
594 
getPixelFormatRequested(buffer_handle_t bufferHandle,ui::PixelFormat * outPixelFormatRequested) const595 status_t Gralloc5Mapper::getPixelFormatRequested(buffer_handle_t bufferHandle,
596                                                  ui::PixelFormat *outPixelFormatRequested) const {
597     auto value = getStandardMetadata<StandardMetadataType::PIXEL_FORMAT_REQUESTED>(mMapper,
598                                                                                    bufferHandle);
599     if (value.has_value()) {
600         *outPixelFormatRequested = static_cast<ui::PixelFormat>(*value);
601         return OK;
602     }
603     return UNKNOWN_TRANSACTION;
604 }
605 
getPixelFormatFourCC(buffer_handle_t bufferHandle,uint32_t * outPixelFormatFourCC) const606 status_t Gralloc5Mapper::getPixelFormatFourCC(buffer_handle_t bufferHandle,
607                                               uint32_t *outPixelFormatFourCC) const {
608     auto value =
609             getStandardMetadata<StandardMetadataType::PIXEL_FORMAT_FOURCC>(mMapper, bufferHandle);
610     if (value.has_value()) {
611         *outPixelFormatFourCC = *value;
612         return OK;
613     }
614     return UNKNOWN_TRANSACTION;
615 }
616 
getPixelFormatModifier(buffer_handle_t bufferHandle,uint64_t * outPixelFormatModifier) const617 status_t Gralloc5Mapper::getPixelFormatModifier(buffer_handle_t bufferHandle,
618                                                 uint64_t *outPixelFormatModifier) const {
619     auto value =
620             getStandardMetadata<StandardMetadataType::PIXEL_FORMAT_MODIFIER>(mMapper, bufferHandle);
621     if (value.has_value()) {
622         *outPixelFormatModifier = *value;
623         return OK;
624     }
625     return UNKNOWN_TRANSACTION;
626 }
627 
getUsage(buffer_handle_t bufferHandle,uint64_t * outUsage) const628 status_t Gralloc5Mapper::getUsage(buffer_handle_t bufferHandle, uint64_t *outUsage) const {
629     auto value = getStandardMetadata<StandardMetadataType::USAGE>(mMapper, bufferHandle);
630     if (value.has_value()) {
631         *outUsage = static_cast<uint64_t>(*value);
632         return OK;
633     }
634     return UNKNOWN_TRANSACTION;
635 }
636 
getAllocationSize(buffer_handle_t bufferHandle,uint64_t * outAllocationSize) const637 status_t Gralloc5Mapper::getAllocationSize(buffer_handle_t bufferHandle,
638                                            uint64_t *outAllocationSize) const {
639     auto value = getStandardMetadata<StandardMetadataType::ALLOCATION_SIZE>(mMapper, bufferHandle);
640     if (value.has_value()) {
641         *outAllocationSize = *value;
642         return OK;
643     }
644     return UNKNOWN_TRANSACTION;
645 }
646 
getProtectedContent(buffer_handle_t bufferHandle,uint64_t * outProtectedContent) const647 status_t Gralloc5Mapper::getProtectedContent(buffer_handle_t bufferHandle,
648                                              uint64_t *outProtectedContent) const {
649     auto value =
650             getStandardMetadata<StandardMetadataType::PROTECTED_CONTENT>(mMapper, bufferHandle);
651     if (value.has_value()) {
652         *outProtectedContent = *value;
653         return OK;
654     }
655     return UNKNOWN_TRANSACTION;
656 }
657 
getCompression(buffer_handle_t bufferHandle,aidl::android::hardware::graphics::common::ExtendableType * outCompression) const658 status_t Gralloc5Mapper::getCompression(
659         buffer_handle_t bufferHandle,
660         aidl::android::hardware::graphics::common::ExtendableType *outCompression) const {
661     auto value = getStandardMetadata<StandardMetadataType::COMPRESSION>(mMapper, bufferHandle);
662     if (value.has_value()) {
663         *outCompression = *value;
664         return OK;
665     }
666     return UNKNOWN_TRANSACTION;
667 }
668 
getCompression(buffer_handle_t bufferHandle,ui::Compression * outCompression) const669 status_t Gralloc5Mapper::getCompression(buffer_handle_t bufferHandle,
670                                         ui::Compression *outCompression) const {
671     auto value = getStandardMetadata<StandardMetadataType::COMPRESSION>(mMapper, bufferHandle);
672     if (!value.has_value()) {
673         return UNKNOWN_TRANSACTION;
674     }
675     if (!gralloc4::isStandardCompression(*value)) {
676         return BAD_TYPE;
677     }
678     *outCompression = gralloc4::getStandardCompressionValue(*value);
679     return OK;
680 }
681 
getInterlaced(buffer_handle_t bufferHandle,aidl::android::hardware::graphics::common::ExtendableType * outInterlaced) const682 status_t Gralloc5Mapper::getInterlaced(
683         buffer_handle_t bufferHandle,
684         aidl::android::hardware::graphics::common::ExtendableType *outInterlaced) const {
685     auto value = getStandardMetadata<StandardMetadataType::INTERLACED>(mMapper, bufferHandle);
686     if (value.has_value()) {
687         *outInterlaced = *value;
688         return OK;
689     }
690     return UNKNOWN_TRANSACTION;
691 }
692 
getInterlaced(buffer_handle_t bufferHandle,ui::Interlaced * outInterlaced) const693 status_t Gralloc5Mapper::getInterlaced(buffer_handle_t bufferHandle,
694                                        ui::Interlaced *outInterlaced) const {
695     if (!outInterlaced) {
696         return BAD_VALUE;
697     }
698     ExtendableType interlaced;
699     status_t error = getInterlaced(bufferHandle, &interlaced);
700     if (error) {
701         return error;
702     }
703     if (!gralloc4::isStandardInterlaced(interlaced)) {
704         return BAD_TYPE;
705     }
706     *outInterlaced = gralloc4::getStandardInterlacedValue(interlaced);
707     return NO_ERROR;
708 }
709 
getChromaSiting(buffer_handle_t bufferHandle,aidl::android::hardware::graphics::common::ExtendableType * outChromaSiting) const710 status_t Gralloc5Mapper::getChromaSiting(
711         buffer_handle_t bufferHandle,
712         aidl::android::hardware::graphics::common::ExtendableType *outChromaSiting) const {
713     auto value = getStandardMetadata<StandardMetadataType::CHROMA_SITING>(mMapper, bufferHandle);
714     if (value.has_value()) {
715         *outChromaSiting = *value;
716         return OK;
717     }
718     return UNKNOWN_TRANSACTION;
719 }
720 
getChromaSiting(buffer_handle_t bufferHandle,ui::ChromaSiting * outChromaSiting) const721 status_t Gralloc5Mapper::getChromaSiting(buffer_handle_t bufferHandle,
722                                          ui::ChromaSiting *outChromaSiting) const {
723     if (!outChromaSiting) {
724         return BAD_VALUE;
725     }
726     ExtendableType chromaSiting;
727     status_t error = getChromaSiting(bufferHandle, &chromaSiting);
728     if (error) {
729         return error;
730     }
731     if (!gralloc4::isStandardChromaSiting(chromaSiting)) {
732         return BAD_TYPE;
733     }
734     *outChromaSiting = gralloc4::getStandardChromaSitingValue(chromaSiting);
735     return NO_ERROR;
736 }
737 
getPlaneLayouts(buffer_handle_t bufferHandle,std::vector<ui::PlaneLayout> * outPlaneLayouts) const738 status_t Gralloc5Mapper::getPlaneLayouts(buffer_handle_t bufferHandle,
739                                          std::vector<ui::PlaneLayout> *outPlaneLayouts) const {
740     auto value = getStandardMetadata<StandardMetadataType::PLANE_LAYOUTS>(mMapper, bufferHandle);
741     if (value.has_value()) {
742         *outPlaneLayouts = *value;
743         return OK;
744     }
745     return UNKNOWN_TRANSACTION;
746 }
747 
getDataspace(buffer_handle_t bufferHandle,ui::Dataspace * outDataspace) const748 status_t Gralloc5Mapper::getDataspace(buffer_handle_t bufferHandle,
749                                       ui::Dataspace *outDataspace) const {
750     auto value = getStandardMetadata<StandardMetadataType::DATASPACE>(mMapper, bufferHandle);
751     if (value.has_value()) {
752         *outDataspace = static_cast<ui::Dataspace>(*value);
753         return OK;
754     }
755     return UNKNOWN_TRANSACTION;
756 }
757 
setDataspace(buffer_handle_t bufferHandle,ui::Dataspace dataspace) const758 status_t Gralloc5Mapper::setDataspace(buffer_handle_t bufferHandle, ui::Dataspace dataspace) const {
759     return setStandardMetadata<StandardMetadataType::DATASPACE>(mMapper, bufferHandle,
760                                                                 static_cast<Dataspace>(dataspace));
761 }
762 
getBlendMode(buffer_handle_t bufferHandle,ui::BlendMode * outBlendMode) const763 status_t Gralloc5Mapper::getBlendMode(buffer_handle_t bufferHandle,
764                                       ui::BlendMode *outBlendMode) const {
765     auto value = getStandardMetadata<StandardMetadataType::BLEND_MODE>(mMapper, bufferHandle);
766     if (value.has_value()) {
767         *outBlendMode = static_cast<ui::BlendMode>(*value);
768         return OK;
769     }
770     return UNKNOWN_TRANSACTION;
771 }
772 
getSmpte2086(buffer_handle_t bufferHandle,std::optional<ui::Smpte2086> * outSmpte2086) const773 status_t Gralloc5Mapper::getSmpte2086(buffer_handle_t bufferHandle,
774                                       std::optional<ui::Smpte2086> *outSmpte2086) const {
775     auto value = getStandardMetadata<StandardMetadataType::SMPTE2086>(mMapper, bufferHandle);
776     if (value.has_value()) {
777         *outSmpte2086 = *value;
778         return OK;
779     }
780     return UNKNOWN_TRANSACTION;
781 }
782 
setSmpte2086(buffer_handle_t bufferHandle,std::optional<ui::Smpte2086> smpte2086) const783 status_t Gralloc5Mapper::setSmpte2086(buffer_handle_t bufferHandle,
784                                       std::optional<ui::Smpte2086> smpte2086) const {
785     return setStandardMetadata<StandardMetadataType::SMPTE2086>(mMapper, bufferHandle, smpte2086);
786 }
787 
getCta861_3(buffer_handle_t bufferHandle,std::optional<ui::Cta861_3> * outCta861_3) const788 status_t Gralloc5Mapper::getCta861_3(buffer_handle_t bufferHandle,
789                                      std::optional<ui::Cta861_3> *outCta861_3) const {
790     auto value = getStandardMetadata<StandardMetadataType::CTA861_3>(mMapper, bufferHandle);
791     if (value.has_value()) {
792         *outCta861_3 = *value;
793         return OK;
794     }
795     return UNKNOWN_TRANSACTION;
796 }
797 
setCta861_3(buffer_handle_t bufferHandle,std::optional<ui::Cta861_3> cta861_3) const798 status_t Gralloc5Mapper::setCta861_3(buffer_handle_t bufferHandle,
799                                      std::optional<ui::Cta861_3> cta861_3) const {
800     return setStandardMetadata<StandardMetadataType::CTA861_3>(mMapper, bufferHandle, cta861_3);
801 }
802 
getSmpte2094_40(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> * outSmpte2094_40) const803 status_t Gralloc5Mapper::getSmpte2094_40(
804         buffer_handle_t bufferHandle, std::optional<std::vector<uint8_t>> *outSmpte2094_40) const {
805     auto value = getStandardMetadata<StandardMetadataType::SMPTE2094_40>(mMapper, bufferHandle);
806     if (value.has_value()) {
807         *outSmpte2094_40 = std::move(*value);
808         return OK;
809     }
810     return UNKNOWN_TRANSACTION;
811 }
812 
setSmpte2094_40(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> smpte2094_40) const813 status_t Gralloc5Mapper::setSmpte2094_40(buffer_handle_t bufferHandle,
814                                          std::optional<std::vector<uint8_t>> smpte2094_40) const {
815     return setStandardMetadata<StandardMetadataType::SMPTE2094_40>(mMapper, bufferHandle,
816                                                                    smpte2094_40);
817 }
818 
getSmpte2094_10(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> * outSmpte2094_10) const819 status_t Gralloc5Mapper::getSmpte2094_10(
820         buffer_handle_t bufferHandle, std::optional<std::vector<uint8_t>> *outSmpte2094_10) const {
821     auto value = getStandardMetadata<StandardMetadataType::SMPTE2094_10>(mMapper, bufferHandle);
822     if (value.has_value()) {
823         *outSmpte2094_10 = std::move(*value);
824         return OK;
825     }
826     return UNKNOWN_TRANSACTION;
827 }
828 
setSmpte2094_10(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> smpte2094_10) const829 status_t Gralloc5Mapper::setSmpte2094_10(buffer_handle_t bufferHandle,
830                                          std::optional<std::vector<uint8_t>> smpte2094_10) const {
831     return setStandardMetadata<StandardMetadataType::SMPTE2094_10>(mMapper, bufferHandle,
832                                                                    smpte2094_10);
833 }
834 
835 } // namespace android