1*d95af8dfSAndroid Build Coastguard Worker /*
2*d95af8dfSAndroid Build Coastguard Worker * Copyright 2022 The Chromium OS Authors. All rights reserved.
3*d95af8dfSAndroid Build Coastguard Worker * Use of this source code is governed by a BSD-style license that can be
4*d95af8dfSAndroid Build Coastguard Worker * found in the LICENSE file.
5*d95af8dfSAndroid Build Coastguard Worker */
6*d95af8dfSAndroid Build Coastguard Worker
7*d95af8dfSAndroid Build Coastguard Worker #include <aidl/android/hardware/graphics/allocator/BufferDescriptorInfo.h>
8*d95af8dfSAndroid Build Coastguard Worker #include <aidl/android/hardware/graphics/common/BufferUsage.h>
9*d95af8dfSAndroid Build Coastguard Worker #include <aidl/android/hardware/graphics/common/PixelFormat.h>
10*d95af8dfSAndroid Build Coastguard Worker #include <aidl/android/hardware/graphics/common/StandardMetadataType.h>
11*d95af8dfSAndroid Build Coastguard Worker #include <android-base/unique_fd.h>
12*d95af8dfSAndroid Build Coastguard Worker #include <android/hardware/graphics/mapper/IMapper.h>
13*d95af8dfSAndroid Build Coastguard Worker #include <android/hardware/graphics/mapper/utils/IMapperMetadataTypes.h>
14*d95af8dfSAndroid Build Coastguard Worker #include <android/hardware/graphics/mapper/utils/IMapperProvider.h>
15*d95af8dfSAndroid Build Coastguard Worker #include <cutils/native_handle.h>
16*d95af8dfSAndroid Build Coastguard Worker #include <gralloctypes/Gralloc4.h>
17*d95af8dfSAndroid Build Coastguard Worker
18*d95af8dfSAndroid Build Coastguard Worker #include <memory>
19*d95af8dfSAndroid Build Coastguard Worker
20*d95af8dfSAndroid Build Coastguard Worker #include "cros_gralloc/cros_gralloc_driver.h"
21*d95af8dfSAndroid Build Coastguard Worker #include "cros_gralloc/cros_gralloc_handle.h"
22*d95af8dfSAndroid Build Coastguard Worker #include "cros_gralloc/gralloc4/CrosGralloc4Utils.h"
23*d95af8dfSAndroid Build Coastguard Worker
24*d95af8dfSAndroid Build Coastguard Worker using namespace ::aidl::android::hardware::graphics::common;
25*d95af8dfSAndroid Build Coastguard Worker using namespace ::android::hardware::graphics::mapper;
26*d95af8dfSAndroid Build Coastguard Worker using ::aidl::android::hardware::graphics::allocator::BufferDescriptorInfo;
27*d95af8dfSAndroid Build Coastguard Worker using ::android::base::unique_fd;
28*d95af8dfSAndroid Build Coastguard Worker
29*d95af8dfSAndroid Build Coastguard Worker #define REQUIRE_DRIVER() \
30*d95af8dfSAndroid Build Coastguard Worker if (!mDriver) { \
31*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to %s. Driver is uninitialized.", __func__); \
32*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NO_RESOURCES; \
33*d95af8dfSAndroid Build Coastguard Worker }
34*d95af8dfSAndroid Build Coastguard Worker
35*d95af8dfSAndroid Build Coastguard Worker #define VALIDATE_BUFFER_HANDLE(bufferHandle) \
36*d95af8dfSAndroid Build Coastguard Worker if (!(bufferHandle)) { \
37*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to %s. Null buffer_handle_t.", __func__); \
38*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER; \
39*d95af8dfSAndroid Build Coastguard Worker }
40*d95af8dfSAndroid Build Coastguard Worker
41*d95af8dfSAndroid Build Coastguard Worker #define VALIDATE_DRIVER_AND_BUFFER_HANDLE(bufferHandle) \
42*d95af8dfSAndroid Build Coastguard Worker REQUIRE_DRIVER() \
43*d95af8dfSAndroid Build Coastguard Worker VALIDATE_BUFFER_HANDLE(bufferHandle)
44*d95af8dfSAndroid Build Coastguard Worker
45*d95af8dfSAndroid Build Coastguard Worker static_assert(CROS_GRALLOC_BUFFER_METADATA_MAX_NAME_SIZE >=
46*d95af8dfSAndroid Build Coastguard Worker decltype(std::declval<BufferDescriptorInfo>().name){}.size(),
47*d95af8dfSAndroid Build Coastguard Worker "Metadata name storage too small to fit a BufferDescriptorInfo::name");
48*d95af8dfSAndroid Build Coastguard Worker
49*d95af8dfSAndroid Build Coastguard Worker constexpr const char* STANDARD_METADATA_NAME =
50*d95af8dfSAndroid Build Coastguard Worker "android.hardware.graphics.common.StandardMetadataType";
51*d95af8dfSAndroid Build Coastguard Worker
isStandardMetadata(AIMapper_MetadataType metadataType)52*d95af8dfSAndroid Build Coastguard Worker static bool isStandardMetadata(AIMapper_MetadataType metadataType) {
53*d95af8dfSAndroid Build Coastguard Worker return strcmp(STANDARD_METADATA_NAME, metadataType.name) == 0;
54*d95af8dfSAndroid Build Coastguard Worker }
55*d95af8dfSAndroid Build Coastguard Worker
56*d95af8dfSAndroid Build Coastguard Worker class CrosGrallocMapperV5 final : public vendor::mapper::IMapperV5Impl {
57*d95af8dfSAndroid Build Coastguard Worker private:
58*d95af8dfSAndroid Build Coastguard Worker std::shared_ptr<cros_gralloc_driver> mDriver = cros_gralloc_driver::get_instance();
59*d95af8dfSAndroid Build Coastguard Worker
60*d95af8dfSAndroid Build Coastguard Worker public:
61*d95af8dfSAndroid Build Coastguard Worker explicit CrosGrallocMapperV5() = default;
62*d95af8dfSAndroid Build Coastguard Worker ~CrosGrallocMapperV5() override = default;
63*d95af8dfSAndroid Build Coastguard Worker
64*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error importBuffer(const native_handle_t* _Nonnull handle,
65*d95af8dfSAndroid Build Coastguard Worker buffer_handle_t _Nullable* _Nonnull outBufferHandle) override;
66*d95af8dfSAndroid Build Coastguard Worker
67*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error freeBuffer(buffer_handle_t _Nonnull buffer) override;
68*d95af8dfSAndroid Build Coastguard Worker
69*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error getTransportSize(buffer_handle_t _Nonnull buffer, uint32_t* _Nonnull outNumFds,
70*d95af8dfSAndroid Build Coastguard Worker uint32_t* _Nonnull outNumInts) override;
71*d95af8dfSAndroid Build Coastguard Worker
72*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error lock(buffer_handle_t _Nonnull buffer, uint64_t cpuUsage, ARect accessRegion,
73*d95af8dfSAndroid Build Coastguard Worker int acquireFence, void* _Nullable* _Nonnull outData) override;
74*d95af8dfSAndroid Build Coastguard Worker
75*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error unlock(buffer_handle_t _Nonnull buffer, int* _Nonnull releaseFence) override;
76*d95af8dfSAndroid Build Coastguard Worker
77*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error flushLockedBuffer(buffer_handle_t _Nonnull buffer) override;
78*d95af8dfSAndroid Build Coastguard Worker
79*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error rereadLockedBuffer(buffer_handle_t _Nonnull buffer) override;
80*d95af8dfSAndroid Build Coastguard Worker
81*d95af8dfSAndroid Build Coastguard Worker int32_t getMetadata(buffer_handle_t _Nonnull buffer, AIMapper_MetadataType metadataType,
82*d95af8dfSAndroid Build Coastguard Worker void* _Nonnull outData, size_t outDataSize) override;
83*d95af8dfSAndroid Build Coastguard Worker
84*d95af8dfSAndroid Build Coastguard Worker int32_t getStandardMetadata(buffer_handle_t _Nonnull buffer, int64_t standardMetadataType,
85*d95af8dfSAndroid Build Coastguard Worker void* _Nonnull outData, size_t outDataSize) override;
86*d95af8dfSAndroid Build Coastguard Worker
87*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error setMetadata(buffer_handle_t _Nonnull buffer, AIMapper_MetadataType metadataType,
88*d95af8dfSAndroid Build Coastguard Worker const void* _Nonnull metadata, size_t metadataSize) override;
89*d95af8dfSAndroid Build Coastguard Worker
90*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error setStandardMetadata(buffer_handle_t _Nonnull buffer,
91*d95af8dfSAndroid Build Coastguard Worker int64_t standardMetadataType, const void* _Nonnull metadata,
92*d95af8dfSAndroid Build Coastguard Worker size_t metadataSize) override;
93*d95af8dfSAndroid Build Coastguard Worker
94*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error listSupportedMetadataTypes(
95*d95af8dfSAndroid Build Coastguard Worker const AIMapper_MetadataTypeDescription* _Nullable* _Nonnull outDescriptionList,
96*d95af8dfSAndroid Build Coastguard Worker size_t* _Nonnull outNumberOfDescriptions) override;
97*d95af8dfSAndroid Build Coastguard Worker
98*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error dumpBuffer(buffer_handle_t _Nonnull bufferHandle,
99*d95af8dfSAndroid Build Coastguard Worker AIMapper_DumpBufferCallback _Nonnull dumpBufferCallback,
100*d95af8dfSAndroid Build Coastguard Worker void* _Null_unspecified context) override;
101*d95af8dfSAndroid Build Coastguard Worker
102*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error dumpAllBuffers(AIMapper_BeginDumpBufferCallback _Nonnull beginDumpBufferCallback,
103*d95af8dfSAndroid Build Coastguard Worker AIMapper_DumpBufferCallback _Nonnull dumpBufferCallback,
104*d95af8dfSAndroid Build Coastguard Worker void* _Null_unspecified context) override;
105*d95af8dfSAndroid Build Coastguard Worker
106*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error getReservedRegion(buffer_handle_t _Nonnull buffer,
107*d95af8dfSAndroid Build Coastguard Worker void* _Nullable* _Nonnull outReservedRegion,
108*d95af8dfSAndroid Build Coastguard Worker uint64_t* _Nonnull outReservedSize) override;
109*d95af8dfSAndroid Build Coastguard Worker
110*d95af8dfSAndroid Build Coastguard Worker private:
111*d95af8dfSAndroid Build Coastguard Worker template <typename F, StandardMetadataType TYPE>
112*d95af8dfSAndroid Build Coastguard Worker int32_t getStandardMetadata(const cros_gralloc_buffer* crosBuffer, F&& provide,
113*d95af8dfSAndroid Build Coastguard Worker StandardMetadata<TYPE>);
114*d95af8dfSAndroid Build Coastguard Worker
115*d95af8dfSAndroid Build Coastguard Worker template <StandardMetadataType TYPE>
116*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error setStandardMetadata(cros_gralloc_buffer* crosBuffer,
117*d95af8dfSAndroid Build Coastguard Worker typename StandardMetadata<TYPE>::value_type&& value);
118*d95af8dfSAndroid Build Coastguard Worker
119*d95af8dfSAndroid Build Coastguard Worker void dumpBuffer(
120*d95af8dfSAndroid Build Coastguard Worker const cros_gralloc_buffer* crosBuffer,
121*d95af8dfSAndroid Build Coastguard Worker std::function<void(AIMapper_MetadataType, const std::vector<uint8_t>&)> callback);
122*d95af8dfSAndroid Build Coastguard Worker };
123*d95af8dfSAndroid Build Coastguard Worker
importBuffer(const native_handle_t * _Nonnull bufferHandle,buffer_handle_t _Nullable * _Nonnull outBufferHandle)124*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::importBuffer(
125*d95af8dfSAndroid Build Coastguard Worker const native_handle_t* _Nonnull bufferHandle,
126*d95af8dfSAndroid Build Coastguard Worker buffer_handle_t _Nullable* _Nonnull outBufferHandle) {
127*d95af8dfSAndroid Build Coastguard Worker REQUIRE_DRIVER()
128*d95af8dfSAndroid Build Coastguard Worker
129*d95af8dfSAndroid Build Coastguard Worker if (!bufferHandle || bufferHandle->numFds == 0) {
130*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to importBuffer. Bad handle.");
131*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
132*d95af8dfSAndroid Build Coastguard Worker }
133*d95af8dfSAndroid Build Coastguard Worker
134*d95af8dfSAndroid Build Coastguard Worker native_handle_t* importedBufferHandle = native_handle_clone(bufferHandle);
135*d95af8dfSAndroid Build Coastguard Worker if (!importedBufferHandle) {
136*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to importBuffer. Handle clone failed: %s.", strerror(errno));
137*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NO_RESOURCES;
138*d95af8dfSAndroid Build Coastguard Worker }
139*d95af8dfSAndroid Build Coastguard Worker
140*d95af8dfSAndroid Build Coastguard Worker int ret = mDriver->retain(importedBufferHandle);
141*d95af8dfSAndroid Build Coastguard Worker if (ret) {
142*d95af8dfSAndroid Build Coastguard Worker native_handle_close(importedBufferHandle);
143*d95af8dfSAndroid Build Coastguard Worker native_handle_delete(importedBufferHandle);
144*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NO_RESOURCES;
145*d95af8dfSAndroid Build Coastguard Worker }
146*d95af8dfSAndroid Build Coastguard Worker
147*d95af8dfSAndroid Build Coastguard Worker *outBufferHandle = importedBufferHandle;
148*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
149*d95af8dfSAndroid Build Coastguard Worker }
150*d95af8dfSAndroid Build Coastguard Worker
freeBuffer(buffer_handle_t _Nonnull buffer)151*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::freeBuffer(buffer_handle_t _Nonnull buffer) {
152*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(buffer)
153*d95af8dfSAndroid Build Coastguard Worker
154*d95af8dfSAndroid Build Coastguard Worker int ret = mDriver->release(buffer);
155*d95af8dfSAndroid Build Coastguard Worker if (ret) {
156*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
157*d95af8dfSAndroid Build Coastguard Worker }
158*d95af8dfSAndroid Build Coastguard Worker
159*d95af8dfSAndroid Build Coastguard Worker native_handle_close(buffer);
160*d95af8dfSAndroid Build Coastguard Worker native_handle_delete(const_cast<native_handle_t*>(buffer));
161*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
162*d95af8dfSAndroid Build Coastguard Worker }
163*d95af8dfSAndroid Build Coastguard Worker
getTransportSize(buffer_handle_t _Nonnull bufferHandle,uint32_t * _Nonnull outNumFds,uint32_t * _Nonnull outNumInts)164*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::getTransportSize(buffer_handle_t _Nonnull bufferHandle,
165*d95af8dfSAndroid Build Coastguard Worker uint32_t* _Nonnull outNumFds,
166*d95af8dfSAndroid Build Coastguard Worker uint32_t* _Nonnull outNumInts) {
167*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(bufferHandle)
168*d95af8dfSAndroid Build Coastguard Worker
169*d95af8dfSAndroid Build Coastguard Worker // No local process data is currently stored on the native handle.
170*d95af8dfSAndroid Build Coastguard Worker *outNumFds = bufferHandle->numFds;
171*d95af8dfSAndroid Build Coastguard Worker *outNumInts = bufferHandle->numInts;
172*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
173*d95af8dfSAndroid Build Coastguard Worker }
174*d95af8dfSAndroid Build Coastguard Worker
lock(buffer_handle_t _Nonnull bufferHandle,uint64_t cpuUsage,ARect region,int acquireFenceRawFd,void * _Nullable * _Nonnull outData)175*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::lock(buffer_handle_t _Nonnull bufferHandle, uint64_t cpuUsage,
176*d95af8dfSAndroid Build Coastguard Worker ARect region, int acquireFenceRawFd,
177*d95af8dfSAndroid Build Coastguard Worker void* _Nullable* _Nonnull outData) {
178*d95af8dfSAndroid Build Coastguard Worker // We take ownership of the FD in all cases, even for errors
179*d95af8dfSAndroid Build Coastguard Worker unique_fd acquireFence(acquireFenceRawFd);
180*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(bufferHandle)
181*d95af8dfSAndroid Build Coastguard Worker if (cpuUsage == 0) {
182*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to lock. Bad cpu usage: %" PRIu64 ".", cpuUsage);
183*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
184*d95af8dfSAndroid Build Coastguard Worker }
185*d95af8dfSAndroid Build Coastguard Worker
186*d95af8dfSAndroid Build Coastguard Worker uint32_t mapUsage = cros_gralloc_convert_map_usage(cpuUsage);
187*d95af8dfSAndroid Build Coastguard Worker
188*d95af8dfSAndroid Build Coastguard Worker cros_gralloc_handle_t crosHandle = cros_gralloc_convert_handle(bufferHandle);
189*d95af8dfSAndroid Build Coastguard Worker if (crosHandle == nullptr) {
190*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to lock. Invalid handle.");
191*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
192*d95af8dfSAndroid Build Coastguard Worker }
193*d95af8dfSAndroid Build Coastguard Worker
194*d95af8dfSAndroid Build Coastguard Worker struct rectangle rect;
195*d95af8dfSAndroid Build Coastguard Worker
196*d95af8dfSAndroid Build Coastguard Worker // An access region of all zeros means the entire buffer.
197*d95af8dfSAndroid Build Coastguard Worker if (region.left == 0 && region.top == 0 && region.right == 0 && region.bottom == 0) {
198*d95af8dfSAndroid Build Coastguard Worker rect = {0, 0, crosHandle->width, crosHandle->height};
199*d95af8dfSAndroid Build Coastguard Worker } else {
200*d95af8dfSAndroid Build Coastguard Worker if (region.left < 0 || region.top < 0 || region.right <= region.left ||
201*d95af8dfSAndroid Build Coastguard Worker region.bottom <= region.top) {
202*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to lock. Invalid accessRegion: [%d, %d, %d, %d]", region.left, region.top,
203*d95af8dfSAndroid Build Coastguard Worker region.right, region.bottom);
204*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
205*d95af8dfSAndroid Build Coastguard Worker }
206*d95af8dfSAndroid Build Coastguard Worker
207*d95af8dfSAndroid Build Coastguard Worker if (region.right > crosHandle->width) {
208*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to lock. Invalid region: width greater than buffer width (%d vs %d).",
209*d95af8dfSAndroid Build Coastguard Worker region.right, crosHandle->width);
210*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
211*d95af8dfSAndroid Build Coastguard Worker }
212*d95af8dfSAndroid Build Coastguard Worker
213*d95af8dfSAndroid Build Coastguard Worker if (region.bottom > crosHandle->height) {
214*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to lock. Invalid region: height greater than buffer height (%d vs "
215*d95af8dfSAndroid Build Coastguard Worker "%d).",
216*d95af8dfSAndroid Build Coastguard Worker region.bottom, crosHandle->height);
217*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
218*d95af8dfSAndroid Build Coastguard Worker }
219*d95af8dfSAndroid Build Coastguard Worker
220*d95af8dfSAndroid Build Coastguard Worker rect = {static_cast<uint32_t>(region.left), static_cast<uint32_t>(region.top),
221*d95af8dfSAndroid Build Coastguard Worker static_cast<uint32_t>(region.right - region.left),
222*d95af8dfSAndroid Build Coastguard Worker static_cast<uint32_t>(region.bottom - region.top)};
223*d95af8dfSAndroid Build Coastguard Worker }
224*d95af8dfSAndroid Build Coastguard Worker
225*d95af8dfSAndroid Build Coastguard Worker uint8_t* addr[DRV_MAX_PLANES];
226*d95af8dfSAndroid Build Coastguard Worker int32_t status = mDriver->lock(bufferHandle, acquireFence.get(),
227*d95af8dfSAndroid Build Coastguard Worker /*close_acquire_fence=*/false, &rect, mapUsage, addr);
228*d95af8dfSAndroid Build Coastguard Worker if (status) {
229*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
230*d95af8dfSAndroid Build Coastguard Worker }
231*d95af8dfSAndroid Build Coastguard Worker
232*d95af8dfSAndroid Build Coastguard Worker *outData = addr[0];
233*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
234*d95af8dfSAndroid Build Coastguard Worker }
235*d95af8dfSAndroid Build Coastguard Worker
unlock(buffer_handle_t _Nonnull buffer,int * _Nonnull releaseFence)236*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::unlock(buffer_handle_t _Nonnull buffer,
237*d95af8dfSAndroid Build Coastguard Worker int* _Nonnull releaseFence) {
238*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(buffer)
239*d95af8dfSAndroid Build Coastguard Worker int ret = mDriver->unlock(buffer, releaseFence);
240*d95af8dfSAndroid Build Coastguard Worker if (ret) {
241*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to unlock.");
242*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
243*d95af8dfSAndroid Build Coastguard Worker }
244*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
245*d95af8dfSAndroid Build Coastguard Worker }
246*d95af8dfSAndroid Build Coastguard Worker
flushLockedBuffer(buffer_handle_t _Nonnull buffer)247*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::flushLockedBuffer(buffer_handle_t _Nonnull buffer) {
248*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(buffer)
249*d95af8dfSAndroid Build Coastguard Worker int ret = mDriver->flush(buffer);
250*d95af8dfSAndroid Build Coastguard Worker if (ret) {
251*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to flushLockedBuffer. Flush failed.");
252*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
253*d95af8dfSAndroid Build Coastguard Worker }
254*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
255*d95af8dfSAndroid Build Coastguard Worker }
256*d95af8dfSAndroid Build Coastguard Worker
rereadLockedBuffer(buffer_handle_t _Nonnull buffer)257*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::rereadLockedBuffer(buffer_handle_t _Nonnull buffer) {
258*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(buffer)
259*d95af8dfSAndroid Build Coastguard Worker int ret = mDriver->invalidate(buffer);
260*d95af8dfSAndroid Build Coastguard Worker if (ret) {
261*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to rereadLockedBuffer. Failed to invalidate.");
262*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
263*d95af8dfSAndroid Build Coastguard Worker }
264*d95af8dfSAndroid Build Coastguard Worker
265*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
266*d95af8dfSAndroid Build Coastguard Worker }
267*d95af8dfSAndroid Build Coastguard Worker
getMetadata(buffer_handle_t _Nonnull buffer,AIMapper_MetadataType metadataType,void * _Nonnull outData,size_t outDataSize)268*d95af8dfSAndroid Build Coastguard Worker int32_t CrosGrallocMapperV5::getMetadata(buffer_handle_t _Nonnull buffer,
269*d95af8dfSAndroid Build Coastguard Worker AIMapper_MetadataType metadataType, void* _Nonnull outData,
270*d95af8dfSAndroid Build Coastguard Worker size_t outDataSize) {
271*d95af8dfSAndroid Build Coastguard Worker // We don't have any vendor-specific metadata, so divert to getStandardMetadata after validating
272*d95af8dfSAndroid Build Coastguard Worker // that this is a standard metadata request
273*d95af8dfSAndroid Build Coastguard Worker if (isStandardMetadata(metadataType)) {
274*d95af8dfSAndroid Build Coastguard Worker return getStandardMetadata(buffer, metadataType.value, outData, outDataSize);
275*d95af8dfSAndroid Build Coastguard Worker }
276*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_UNSUPPORTED;
277*d95af8dfSAndroid Build Coastguard Worker }
278*d95af8dfSAndroid Build Coastguard Worker
getStandardMetadata(buffer_handle_t _Nonnull bufferHandle,int64_t standardType,void * _Nonnull outData,size_t outDataSize)279*d95af8dfSAndroid Build Coastguard Worker int32_t CrosGrallocMapperV5::getStandardMetadata(buffer_handle_t _Nonnull bufferHandle,
280*d95af8dfSAndroid Build Coastguard Worker int64_t standardType, void* _Nonnull outData,
281*d95af8dfSAndroid Build Coastguard Worker size_t outDataSize) {
282*d95af8dfSAndroid Build Coastguard Worker // Can't use VALIDATE_DRIVER_AND_BUFFER_HANDLE because we need to negate the error
283*d95af8dfSAndroid Build Coastguard Worker // for this call
284*d95af8dfSAndroid Build Coastguard Worker if (!mDriver) {
285*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to %s. Driver is uninitialized.", __func__);
286*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_NO_RESOURCES;
287*d95af8dfSAndroid Build Coastguard Worker }
288*d95af8dfSAndroid Build Coastguard Worker if (!(bufferHandle)) {
289*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to %s. Null buffer_handle_t.", __func__);
290*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_BAD_BUFFER;
291*d95af8dfSAndroid Build Coastguard Worker }
292*d95af8dfSAndroid Build Coastguard Worker
293*d95af8dfSAndroid Build Coastguard Worker cros_gralloc_handle_t crosHandle = cros_gralloc_convert_handle(bufferHandle);
294*d95af8dfSAndroid Build Coastguard Worker if (!crosHandle) {
295*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to get. Invalid handle.");
296*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_BAD_BUFFER;
297*d95af8dfSAndroid Build Coastguard Worker }
298*d95af8dfSAndroid Build Coastguard Worker
299*d95af8dfSAndroid Build Coastguard Worker int32_t retValue = -AIMAPPER_ERROR_UNSUPPORTED;
300*d95af8dfSAndroid Build Coastguard Worker mDriver->with_buffer(crosHandle, [&](cros_gralloc_buffer* crosBuffer) {
301*d95af8dfSAndroid Build Coastguard Worker auto provider = [&]<StandardMetadataType T>(auto&& provide) -> int32_t {
302*d95af8dfSAndroid Build Coastguard Worker return getStandardMetadata(crosBuffer, provide, StandardMetadata<T>{});
303*d95af8dfSAndroid Build Coastguard Worker };
304*d95af8dfSAndroid Build Coastguard Worker retValue = provideStandardMetadata(static_cast<StandardMetadataType>(standardType), outData,
305*d95af8dfSAndroid Build Coastguard Worker outDataSize, provider);
306*d95af8dfSAndroid Build Coastguard Worker });
307*d95af8dfSAndroid Build Coastguard Worker return retValue;
308*d95af8dfSAndroid Build Coastguard Worker }
309*d95af8dfSAndroid Build Coastguard Worker
310*d95af8dfSAndroid Build Coastguard Worker template <typename F, StandardMetadataType metadataType>
getStandardMetadata(const cros_gralloc_buffer * crosBuffer,F && provide,StandardMetadata<metadataType>)311*d95af8dfSAndroid Build Coastguard Worker int32_t CrosGrallocMapperV5::getStandardMetadata(const cros_gralloc_buffer* crosBuffer, F&& provide,
312*d95af8dfSAndroid Build Coastguard Worker StandardMetadata<metadataType>) {
313*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::BUFFER_ID) {
314*d95af8dfSAndroid Build Coastguard Worker return provide(crosBuffer->get_id());
315*d95af8dfSAndroid Build Coastguard Worker }
316*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::NAME) {
317*d95af8dfSAndroid Build Coastguard Worker std::optional<std::string> name;
318*d95af8dfSAndroid Build Coastguard Worker if (crosBuffer->get_name(&name)) {
319*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_NO_RESOURCES;
320*d95af8dfSAndroid Build Coastguard Worker } else {
321*d95af8dfSAndroid Build Coastguard Worker return provide(*name);
322*d95af8dfSAndroid Build Coastguard Worker }
323*d95af8dfSAndroid Build Coastguard Worker }
324*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::WIDTH) {
325*d95af8dfSAndroid Build Coastguard Worker return provide(crosBuffer->get_width());
326*d95af8dfSAndroid Build Coastguard Worker }
327*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::STRIDE) {
328*d95af8dfSAndroid Build Coastguard Worker return provide(crosBuffer->get_pixel_stride());
329*d95af8dfSAndroid Build Coastguard Worker }
330*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::HEIGHT) {
331*d95af8dfSAndroid Build Coastguard Worker return provide(crosBuffer->get_height());
332*d95af8dfSAndroid Build Coastguard Worker }
333*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::LAYER_COUNT) {
334*d95af8dfSAndroid Build Coastguard Worker return provide(1);
335*d95af8dfSAndroid Build Coastguard Worker }
336*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::PIXEL_FORMAT_REQUESTED) {
337*d95af8dfSAndroid Build Coastguard Worker return provide(static_cast<PixelFormat>(crosBuffer->get_android_format()));
338*d95af8dfSAndroid Build Coastguard Worker }
339*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::PIXEL_FORMAT_FOURCC) {
340*d95af8dfSAndroid Build Coastguard Worker return provide(drv_get_standard_fourcc(crosBuffer->get_format()));
341*d95af8dfSAndroid Build Coastguard Worker }
342*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::PIXEL_FORMAT_MODIFIER) {
343*d95af8dfSAndroid Build Coastguard Worker return provide(crosBuffer->get_format_modifier());
344*d95af8dfSAndroid Build Coastguard Worker }
345*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::USAGE) {
346*d95af8dfSAndroid Build Coastguard Worker return provide(static_cast<BufferUsage>(crosBuffer->get_android_usage()));
347*d95af8dfSAndroid Build Coastguard Worker }
348*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::ALLOCATION_SIZE) {
349*d95af8dfSAndroid Build Coastguard Worker return provide(crosBuffer->get_total_size());
350*d95af8dfSAndroid Build Coastguard Worker }
351*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::PROTECTED_CONTENT) {
352*d95af8dfSAndroid Build Coastguard Worker uint64_t hasProtectedContent =
353*d95af8dfSAndroid Build Coastguard Worker crosBuffer->get_android_usage() & static_cast<int64_t>(BufferUsage::PROTECTED) ? 1
354*d95af8dfSAndroid Build Coastguard Worker : 0;
355*d95af8dfSAndroid Build Coastguard Worker return provide(hasProtectedContent);
356*d95af8dfSAndroid Build Coastguard Worker }
357*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::COMPRESSION) {
358*d95af8dfSAndroid Build Coastguard Worker return provide(android::gralloc4::Compression_None);
359*d95af8dfSAndroid Build Coastguard Worker }
360*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::INTERLACED) {
361*d95af8dfSAndroid Build Coastguard Worker return provide(android::gralloc4::Interlaced_None);
362*d95af8dfSAndroid Build Coastguard Worker }
363*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::CHROMA_SITING) {
364*d95af8dfSAndroid Build Coastguard Worker return provide(android::gralloc4::ChromaSiting_None);
365*d95af8dfSAndroid Build Coastguard Worker }
366*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::PLANE_LAYOUTS) {
367*d95af8dfSAndroid Build Coastguard Worker std::vector<PlaneLayout> planeLayouts;
368*d95af8dfSAndroid Build Coastguard Worker getPlaneLayouts(crosBuffer->get_format(), &planeLayouts);
369*d95af8dfSAndroid Build Coastguard Worker
370*d95af8dfSAndroid Build Coastguard Worker for (size_t plane = 0; plane < planeLayouts.size(); plane++) {
371*d95af8dfSAndroid Build Coastguard Worker PlaneLayout& planeLayout = planeLayouts[plane];
372*d95af8dfSAndroid Build Coastguard Worker planeLayout.offsetInBytes = crosBuffer->get_plane_offset(plane);
373*d95af8dfSAndroid Build Coastguard Worker planeLayout.strideInBytes = crosBuffer->get_plane_stride(plane);
374*d95af8dfSAndroid Build Coastguard Worker planeLayout.totalSizeInBytes = crosBuffer->get_plane_size(plane);
375*d95af8dfSAndroid Build Coastguard Worker planeLayout.widthInSamples =
376*d95af8dfSAndroid Build Coastguard Worker crosBuffer->get_width() / planeLayout.horizontalSubsampling;
377*d95af8dfSAndroid Build Coastguard Worker planeLayout.heightInSamples =
378*d95af8dfSAndroid Build Coastguard Worker crosBuffer->get_height() / planeLayout.verticalSubsampling;
379*d95af8dfSAndroid Build Coastguard Worker }
380*d95af8dfSAndroid Build Coastguard Worker
381*d95af8dfSAndroid Build Coastguard Worker return provide(planeLayouts);
382*d95af8dfSAndroid Build Coastguard Worker }
383*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::CROP) {
384*d95af8dfSAndroid Build Coastguard Worker const uint32_t numPlanes = crosBuffer->get_num_planes();
385*d95af8dfSAndroid Build Coastguard Worker const uint32_t w = crosBuffer->get_width();
386*d95af8dfSAndroid Build Coastguard Worker const uint32_t h = crosBuffer->get_height();
387*d95af8dfSAndroid Build Coastguard Worker std::vector<aidl::android::hardware::graphics::common::Rect> crops;
388*d95af8dfSAndroid Build Coastguard Worker for (uint32_t plane = 0; plane < numPlanes; plane++) {
389*d95af8dfSAndroid Build Coastguard Worker aidl::android::hardware::graphics::common::Rect crop;
390*d95af8dfSAndroid Build Coastguard Worker crop.left = 0;
391*d95af8dfSAndroid Build Coastguard Worker crop.top = 0;
392*d95af8dfSAndroid Build Coastguard Worker crop.right = w;
393*d95af8dfSAndroid Build Coastguard Worker crop.bottom = h;
394*d95af8dfSAndroid Build Coastguard Worker crops.push_back(crop);
395*d95af8dfSAndroid Build Coastguard Worker }
396*d95af8dfSAndroid Build Coastguard Worker
397*d95af8dfSAndroid Build Coastguard Worker return provide(crops);
398*d95af8dfSAndroid Build Coastguard Worker }
399*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::DATASPACE) {
400*d95af8dfSAndroid Build Coastguard Worker std::optional<Dataspace> dataspace;
401*d95af8dfSAndroid Build Coastguard Worker if (crosBuffer->get_dataspace(&dataspace)) {
402*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_NO_RESOURCES;
403*d95af8dfSAndroid Build Coastguard Worker } else {
404*d95af8dfSAndroid Build Coastguard Worker return provide(*dataspace);
405*d95af8dfSAndroid Build Coastguard Worker }
406*d95af8dfSAndroid Build Coastguard Worker }
407*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::BLEND_MODE) {
408*d95af8dfSAndroid Build Coastguard Worker std::optional<BlendMode> blend;
409*d95af8dfSAndroid Build Coastguard Worker if (crosBuffer->get_blend_mode(&blend)) {
410*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_NO_RESOURCES;
411*d95af8dfSAndroid Build Coastguard Worker } else {
412*d95af8dfSAndroid Build Coastguard Worker return provide(*blend);
413*d95af8dfSAndroid Build Coastguard Worker }
414*d95af8dfSAndroid Build Coastguard Worker }
415*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::SMPTE2086) {
416*d95af8dfSAndroid Build Coastguard Worker std::optional<Smpte2086> smpte;
417*d95af8dfSAndroid Build Coastguard Worker if (crosBuffer->get_smpte2086(&smpte)) {
418*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_NO_RESOURCES;
419*d95af8dfSAndroid Build Coastguard Worker } else {
420*d95af8dfSAndroid Build Coastguard Worker return smpte ? provide(*smpte) : 0;
421*d95af8dfSAndroid Build Coastguard Worker }
422*d95af8dfSAndroid Build Coastguard Worker }
423*d95af8dfSAndroid Build Coastguard Worker if constexpr (metadataType == StandardMetadataType::CTA861_3) {
424*d95af8dfSAndroid Build Coastguard Worker std::optional<Cta861_3> cta;
425*d95af8dfSAndroid Build Coastguard Worker if (crosBuffer->get_cta861_3(&cta)) {
426*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_NO_RESOURCES;
427*d95af8dfSAndroid Build Coastguard Worker } else {
428*d95af8dfSAndroid Build Coastguard Worker return cta ? provide(*cta) : 0;
429*d95af8dfSAndroid Build Coastguard Worker }
430*d95af8dfSAndroid Build Coastguard Worker }
431*d95af8dfSAndroid Build Coastguard Worker return -AIMAPPER_ERROR_UNSUPPORTED;
432*d95af8dfSAndroid Build Coastguard Worker }
433*d95af8dfSAndroid Build Coastguard Worker
setMetadata(buffer_handle_t _Nonnull buffer,AIMapper_MetadataType metadataType,const void * _Nonnull metadata,size_t metadataSize)434*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::setMetadata(buffer_handle_t _Nonnull buffer,
435*d95af8dfSAndroid Build Coastguard Worker AIMapper_MetadataType metadataType,
436*d95af8dfSAndroid Build Coastguard Worker const void* _Nonnull metadata,
437*d95af8dfSAndroid Build Coastguard Worker size_t metadataSize) {
438*d95af8dfSAndroid Build Coastguard Worker // We don't have any vendor-specific metadata, so divert to setStandardMetadata after validating
439*d95af8dfSAndroid Build Coastguard Worker // that this is a standard metadata request
440*d95af8dfSAndroid Build Coastguard Worker if (isStandardMetadata(metadataType)) {
441*d95af8dfSAndroid Build Coastguard Worker return setStandardMetadata(buffer, metadataType.value, metadata, metadataSize);
442*d95af8dfSAndroid Build Coastguard Worker }
443*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_UNSUPPORTED;
444*d95af8dfSAndroid Build Coastguard Worker }
445*d95af8dfSAndroid Build Coastguard Worker
setStandardMetadata(buffer_handle_t _Nonnull bufferHandle,int64_t standardTypeRaw,const void * _Nonnull metadata,size_t metadataSize)446*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::setStandardMetadata(buffer_handle_t _Nonnull bufferHandle,
447*d95af8dfSAndroid Build Coastguard Worker int64_t standardTypeRaw,
448*d95af8dfSAndroid Build Coastguard Worker const void* _Nonnull metadata,
449*d95af8dfSAndroid Build Coastguard Worker size_t metadataSize) {
450*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(bufferHandle)
451*d95af8dfSAndroid Build Coastguard Worker
452*d95af8dfSAndroid Build Coastguard Worker cros_gralloc_handle_t crosHandle = cros_gralloc_convert_handle(bufferHandle);
453*d95af8dfSAndroid Build Coastguard Worker if (!crosHandle) {
454*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to get. Invalid handle.");
455*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
456*d95af8dfSAndroid Build Coastguard Worker }
457*d95af8dfSAndroid Build Coastguard Worker
458*d95af8dfSAndroid Build Coastguard Worker auto standardType = static_cast<StandardMetadataType>(standardTypeRaw);
459*d95af8dfSAndroid Build Coastguard Worker
460*d95af8dfSAndroid Build Coastguard Worker switch (standardType) {
461*d95af8dfSAndroid Build Coastguard Worker // Read-only values
462*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::BUFFER_ID:
463*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::NAME:
464*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::WIDTH:
465*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::HEIGHT:
466*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::LAYER_COUNT:
467*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::PIXEL_FORMAT_REQUESTED:
468*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::USAGE:
469*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_VALUE;
470*d95af8dfSAndroid Build Coastguard Worker
471*d95af8dfSAndroid Build Coastguard Worker // Supported to set
472*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::BLEND_MODE:
473*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::CTA861_3:
474*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::DATASPACE:
475*d95af8dfSAndroid Build Coastguard Worker case StandardMetadataType::SMPTE2086:
476*d95af8dfSAndroid Build Coastguard Worker break;
477*d95af8dfSAndroid Build Coastguard Worker
478*d95af8dfSAndroid Build Coastguard Worker // Everything else unsupported
479*d95af8dfSAndroid Build Coastguard Worker default:
480*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_UNSUPPORTED;
481*d95af8dfSAndroid Build Coastguard Worker }
482*d95af8dfSAndroid Build Coastguard Worker
483*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error status = AIMAPPER_ERROR_UNSUPPORTED;
484*d95af8dfSAndroid Build Coastguard Worker mDriver->with_buffer(crosHandle, [&](cros_gralloc_buffer* crosBuffer) {
485*d95af8dfSAndroid Build Coastguard Worker auto applier = [&]<StandardMetadataType T>(auto&& value) -> AIMapper_Error {
486*d95af8dfSAndroid Build Coastguard Worker return setStandardMetadata<T>(crosBuffer, std::forward<decltype(value)>(value));
487*d95af8dfSAndroid Build Coastguard Worker };
488*d95af8dfSAndroid Build Coastguard Worker
489*d95af8dfSAndroid Build Coastguard Worker status = applyStandardMetadata(standardType, metadata, metadataSize, applier);
490*d95af8dfSAndroid Build Coastguard Worker });
491*d95af8dfSAndroid Build Coastguard Worker return status;
492*d95af8dfSAndroid Build Coastguard Worker }
493*d95af8dfSAndroid Build Coastguard Worker
494*d95af8dfSAndroid Build Coastguard Worker template <StandardMetadataType TYPE>
setStandardMetadata(cros_gralloc_buffer * crosBuffer,typename StandardMetadata<TYPE>::value_type && value)495*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::setStandardMetadata(
496*d95af8dfSAndroid Build Coastguard Worker cros_gralloc_buffer* crosBuffer, typename StandardMetadata<TYPE>::value_type&& value) {
497*d95af8dfSAndroid Build Coastguard Worker int ret = 0;
498*d95af8dfSAndroid Build Coastguard Worker if constexpr (TYPE == StandardMetadataType::BLEND_MODE) {
499*d95af8dfSAndroid Build Coastguard Worker ret = crosBuffer->set_blend_mode(value);
500*d95af8dfSAndroid Build Coastguard Worker }
501*d95af8dfSAndroid Build Coastguard Worker if constexpr (TYPE == StandardMetadataType::CTA861_3) {
502*d95af8dfSAndroid Build Coastguard Worker ret = crosBuffer->set_cta861_3(value);
503*d95af8dfSAndroid Build Coastguard Worker }
504*d95af8dfSAndroid Build Coastguard Worker if constexpr (TYPE == StandardMetadataType::DATASPACE) {
505*d95af8dfSAndroid Build Coastguard Worker ret = crosBuffer->set_dataspace(value);
506*d95af8dfSAndroid Build Coastguard Worker }
507*d95af8dfSAndroid Build Coastguard Worker if constexpr (TYPE == StandardMetadataType::SMPTE2086) {
508*d95af8dfSAndroid Build Coastguard Worker ret = crosBuffer->set_smpte2086(value);
509*d95af8dfSAndroid Build Coastguard Worker }
510*d95af8dfSAndroid Build Coastguard Worker
511*d95af8dfSAndroid Build Coastguard Worker if (ret) {
512*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NO_RESOURCES;
513*d95af8dfSAndroid Build Coastguard Worker }
514*d95af8dfSAndroid Build Coastguard Worker
515*d95af8dfSAndroid Build Coastguard Worker // Unsupported metadatas were already filtered before we reached this point
516*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
517*d95af8dfSAndroid Build Coastguard Worker }
518*d95af8dfSAndroid Build Coastguard Worker
describeStandard(StandardMetadataType type,bool isGettable,bool isSettable)519*d95af8dfSAndroid Build Coastguard Worker constexpr AIMapper_MetadataTypeDescription describeStandard(StandardMetadataType type,
520*d95af8dfSAndroid Build Coastguard Worker bool isGettable, bool isSettable) {
521*d95af8dfSAndroid Build Coastguard Worker return {{STANDARD_METADATA_NAME, static_cast<int64_t>(type)},
522*d95af8dfSAndroid Build Coastguard Worker nullptr,
523*d95af8dfSAndroid Build Coastguard Worker isGettable,
524*d95af8dfSAndroid Build Coastguard Worker isSettable,
525*d95af8dfSAndroid Build Coastguard Worker {0}};
526*d95af8dfSAndroid Build Coastguard Worker }
527*d95af8dfSAndroid Build Coastguard Worker
listSupportedMetadataTypes(const AIMapper_MetadataTypeDescription * _Nullable * _Nonnull outDescriptionList,size_t * _Nonnull outNumberOfDescriptions)528*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::listSupportedMetadataTypes(
529*d95af8dfSAndroid Build Coastguard Worker const AIMapper_MetadataTypeDescription* _Nullable* _Nonnull outDescriptionList,
530*d95af8dfSAndroid Build Coastguard Worker size_t* _Nonnull outNumberOfDescriptions) {
531*d95af8dfSAndroid Build Coastguard Worker static constexpr std::array<AIMapper_MetadataTypeDescription, 22> sSupportedMetadaTypes{
532*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::BUFFER_ID, true, false),
533*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::NAME, true, false),
534*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::WIDTH, true, false),
535*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::HEIGHT, true, false),
536*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::LAYER_COUNT, true, false),
537*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::PIXEL_FORMAT_REQUESTED, true, false),
538*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::PIXEL_FORMAT_FOURCC, true, false),
539*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::PIXEL_FORMAT_MODIFIER, true, false),
540*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::USAGE, true, false),
541*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::ALLOCATION_SIZE, true, false),
542*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::PROTECTED_CONTENT, true, false),
543*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::COMPRESSION, true, false),
544*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::INTERLACED, true, false),
545*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::CHROMA_SITING, true, false),
546*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::PLANE_LAYOUTS, true, false),
547*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::CROP, true, false),
548*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::DATASPACE, true, true),
549*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::COMPRESSION, true, false),
550*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::BLEND_MODE, true, true),
551*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::SMPTE2086, true, true),
552*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::CTA861_3, true, true),
553*d95af8dfSAndroid Build Coastguard Worker describeStandard(StandardMetadataType::STRIDE, true, false),
554*d95af8dfSAndroid Build Coastguard Worker };
555*d95af8dfSAndroid Build Coastguard Worker *outDescriptionList = sSupportedMetadaTypes.data();
556*d95af8dfSAndroid Build Coastguard Worker *outNumberOfDescriptions = sSupportedMetadaTypes.size();
557*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
558*d95af8dfSAndroid Build Coastguard Worker }
559*d95af8dfSAndroid Build Coastguard Worker
dumpBuffer(const cros_gralloc_buffer * crosBuffer,std::function<void (AIMapper_MetadataType,const std::vector<uint8_t> &)> callback)560*d95af8dfSAndroid Build Coastguard Worker void CrosGrallocMapperV5::dumpBuffer(
561*d95af8dfSAndroid Build Coastguard Worker const cros_gralloc_buffer* crosBuffer,
562*d95af8dfSAndroid Build Coastguard Worker std::function<void(AIMapper_MetadataType, const std::vector<uint8_t>&)> callback) {
563*d95af8dfSAndroid Build Coastguard Worker // Temp buffer of ~10kb, should be large enough for any of the metadata we want to dump
564*d95af8dfSAndroid Build Coastguard Worker std::vector<uint8_t> tempBuffer;
565*d95af8dfSAndroid Build Coastguard Worker tempBuffer.resize(10000);
566*d95af8dfSAndroid Build Coastguard Worker AIMapper_MetadataType metadataType;
567*d95af8dfSAndroid Build Coastguard Worker metadataType.name = STANDARD_METADATA_NAME;
568*d95af8dfSAndroid Build Coastguard Worker
569*d95af8dfSAndroid Build Coastguard Worker // Take an instance of the empty StandardMetadat<T> class just to allow auto-deduction
570*d95af8dfSAndroid Build Coastguard Worker // to happen as explicit template invocation on lambdas is ugly
571*d95af8dfSAndroid Build Coastguard Worker auto dump = [&]<StandardMetadataType T>(StandardMetadata<T>) {
572*d95af8dfSAndroid Build Coastguard Worker // Nested templated lambdas! Woo! But the cleanness of the result is worth it
573*d95af8dfSAndroid Build Coastguard Worker // The outer lambda exists basically just to capture the StandardMetadataType that's
574*d95af8dfSAndroid Build Coastguard Worker // being dumped, as the `provider` parameter of getStandardMetadata only knows
575*d95af8dfSAndroid Build Coastguard Worker // the value_type that the enum maps to but not the enum value itself, which we need to
576*d95af8dfSAndroid Build Coastguard Worker // construct the `AIMapper_MetadataType` to pass to the dump callback
577*d95af8dfSAndroid Build Coastguard Worker auto dumpInner = [&](const typename StandardMetadata<T>::value_type& value) -> int32_t {
578*d95af8dfSAndroid Build Coastguard Worker int32_t size =
579*d95af8dfSAndroid Build Coastguard Worker StandardMetadata<T>::value::encode(value, tempBuffer.data(), tempBuffer.size());
580*d95af8dfSAndroid Build Coastguard Worker // The initial size should always be large enough, but just in case...
581*d95af8dfSAndroid Build Coastguard Worker if (size > tempBuffer.size()) {
582*d95af8dfSAndroid Build Coastguard Worker tempBuffer.resize(size * 2);
583*d95af8dfSAndroid Build Coastguard Worker size = StandardMetadata<T>::value::encode(value, tempBuffer.data(),
584*d95af8dfSAndroid Build Coastguard Worker tempBuffer.size());
585*d95af8dfSAndroid Build Coastguard Worker }
586*d95af8dfSAndroid Build Coastguard Worker // If the first resize failed _somehow_, just give up. Also don't notify if any
587*d95af8dfSAndroid Build Coastguard Worker // errors occurred during encoding.
588*d95af8dfSAndroid Build Coastguard Worker if (size >= 0 && size <= tempBuffer.size()) {
589*d95af8dfSAndroid Build Coastguard Worker metadataType.value = static_cast<int64_t>(T);
590*d95af8dfSAndroid Build Coastguard Worker callback(metadataType, tempBuffer);
591*d95af8dfSAndroid Build Coastguard Worker }
592*d95af8dfSAndroid Build Coastguard Worker // We don't actually care about the return value in this case, but why not use the
593*d95af8dfSAndroid Build Coastguard Worker // real value anyway
594*d95af8dfSAndroid Build Coastguard Worker return size;
595*d95af8dfSAndroid Build Coastguard Worker };
596*d95af8dfSAndroid Build Coastguard Worker getStandardMetadata(crosBuffer, dumpInner, StandardMetadata<T>{});
597*d95af8dfSAndroid Build Coastguard Worker };
598*d95af8dfSAndroid Build Coastguard Worker
599*d95af8dfSAndroid Build Coastguard Worker // So clean. So pretty.
600*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::BUFFER_ID>{});
601*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::NAME>{});
602*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::WIDTH>{});
603*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::HEIGHT>{});
604*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::LAYER_COUNT>{});
605*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::PIXEL_FORMAT_REQUESTED>{});
606*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::PIXEL_FORMAT_FOURCC>{});
607*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::PIXEL_FORMAT_MODIFIER>{});
608*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::USAGE>{});
609*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::ALLOCATION_SIZE>{});
610*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::PROTECTED_CONTENT>{});
611*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::COMPRESSION>{});
612*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::INTERLACED>{});
613*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::CHROMA_SITING>{});
614*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::PLANE_LAYOUTS>{});
615*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::DATASPACE>{});
616*d95af8dfSAndroid Build Coastguard Worker dump(StandardMetadata<StandardMetadataType::BLEND_MODE>{});
617*d95af8dfSAndroid Build Coastguard Worker }
618*d95af8dfSAndroid Build Coastguard Worker
dumpBuffer(buffer_handle_t _Nonnull bufferHandle,AIMapper_DumpBufferCallback _Nonnull dumpBufferCallback,void * _Null_unspecified context)619*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::dumpBuffer(
620*d95af8dfSAndroid Build Coastguard Worker buffer_handle_t _Nonnull bufferHandle,
621*d95af8dfSAndroid Build Coastguard Worker AIMapper_DumpBufferCallback _Nonnull dumpBufferCallback, void* _Null_unspecified context) {
622*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(bufferHandle)
623*d95af8dfSAndroid Build Coastguard Worker cros_gralloc_handle_t crosHandle = cros_gralloc_convert_handle(bufferHandle);
624*d95af8dfSAndroid Build Coastguard Worker if (!crosHandle) {
625*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to get. Invalid handle.");
626*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
627*d95af8dfSAndroid Build Coastguard Worker }
628*d95af8dfSAndroid Build Coastguard Worker auto callback = [&](AIMapper_MetadataType type, const std::vector<uint8_t>& buffer) {
629*d95af8dfSAndroid Build Coastguard Worker dumpBufferCallback(context, type, buffer.data(), buffer.size());
630*d95af8dfSAndroid Build Coastguard Worker };
631*d95af8dfSAndroid Build Coastguard Worker mDriver->with_buffer(
632*d95af8dfSAndroid Build Coastguard Worker crosHandle, [&](cros_gralloc_buffer* crosBuffer) { dumpBuffer(crosBuffer, callback); });
633*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
634*d95af8dfSAndroid Build Coastguard Worker }
635*d95af8dfSAndroid Build Coastguard Worker
dumpAllBuffers(AIMapper_BeginDumpBufferCallback _Nonnull beginDumpBufferCallback,AIMapper_DumpBufferCallback _Nonnull dumpBufferCallback,void * _Null_unspecified context)636*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::dumpAllBuffers(
637*d95af8dfSAndroid Build Coastguard Worker AIMapper_BeginDumpBufferCallback _Nonnull beginDumpBufferCallback,
638*d95af8dfSAndroid Build Coastguard Worker AIMapper_DumpBufferCallback _Nonnull dumpBufferCallback, void* _Null_unspecified context) {
639*d95af8dfSAndroid Build Coastguard Worker REQUIRE_DRIVER()
640*d95af8dfSAndroid Build Coastguard Worker auto callback = [&](AIMapper_MetadataType type, const std::vector<uint8_t>& buffer) {
641*d95af8dfSAndroid Build Coastguard Worker dumpBufferCallback(context, type, buffer.data(), buffer.size());
642*d95af8dfSAndroid Build Coastguard Worker };
643*d95af8dfSAndroid Build Coastguard Worker mDriver->with_each_buffer([&](cros_gralloc_buffer* crosBuffer) {
644*d95af8dfSAndroid Build Coastguard Worker beginDumpBufferCallback(context);
645*d95af8dfSAndroid Build Coastguard Worker dumpBuffer(crosBuffer, callback);
646*d95af8dfSAndroid Build Coastguard Worker });
647*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
648*d95af8dfSAndroid Build Coastguard Worker }
649*d95af8dfSAndroid Build Coastguard Worker
getReservedRegion(buffer_handle_t _Nonnull buffer,void * _Nullable * _Nonnull outReservedRegion,uint64_t * _Nonnull outReservedSize)650*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error CrosGrallocMapperV5::getReservedRegion(buffer_handle_t _Nonnull buffer,
651*d95af8dfSAndroid Build Coastguard Worker void* _Nullable* _Nonnull outReservedRegion,
652*d95af8dfSAndroid Build Coastguard Worker uint64_t* _Nonnull outReservedSize) {
653*d95af8dfSAndroid Build Coastguard Worker VALIDATE_DRIVER_AND_BUFFER_HANDLE(buffer)
654*d95af8dfSAndroid Build Coastguard Worker cros_gralloc_handle_t crosHandle = cros_gralloc_convert_handle(buffer);
655*d95af8dfSAndroid Build Coastguard Worker if (!crosHandle) {
656*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to getReservedRegion. Invalid handle.");
657*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
658*d95af8dfSAndroid Build Coastguard Worker }
659*d95af8dfSAndroid Build Coastguard Worker
660*d95af8dfSAndroid Build Coastguard Worker void* reservedRegionAddr = nullptr;
661*d95af8dfSAndroid Build Coastguard Worker uint64_t reservedRegionSize = 0;
662*d95af8dfSAndroid Build Coastguard Worker
663*d95af8dfSAndroid Build Coastguard Worker AIMapper_Error error = AIMAPPER_ERROR_NONE;
664*d95af8dfSAndroid Build Coastguard Worker mDriver->with_buffer(crosHandle, [&](cros_gralloc_buffer* crosBuffer) {
665*d95af8dfSAndroid Build Coastguard Worker int ret = crosBuffer->get_client_reserved_region(&reservedRegionAddr, &reservedRegionSize);
666*d95af8dfSAndroid Build Coastguard Worker if (ret) {
667*d95af8dfSAndroid Build Coastguard Worker reservedRegionAddr = nullptr;
668*d95af8dfSAndroid Build Coastguard Worker reservedRegionSize = 0;
669*d95af8dfSAndroid Build Coastguard Worker error = AIMAPPER_ERROR_NO_RESOURCES;
670*d95af8dfSAndroid Build Coastguard Worker }
671*d95af8dfSAndroid Build Coastguard Worker });
672*d95af8dfSAndroid Build Coastguard Worker
673*d95af8dfSAndroid Build Coastguard Worker if (error != AIMAPPER_ERROR_NONE) {
674*d95af8dfSAndroid Build Coastguard Worker ALOGE("Failed to getReservedRegion. Failed to getReservedRegion.");
675*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_BAD_BUFFER;
676*d95af8dfSAndroid Build Coastguard Worker }
677*d95af8dfSAndroid Build Coastguard Worker
678*d95af8dfSAndroid Build Coastguard Worker return AIMAPPER_ERROR_NONE;
679*d95af8dfSAndroid Build Coastguard Worker }
680*d95af8dfSAndroid Build Coastguard Worker
681*d95af8dfSAndroid Build Coastguard Worker extern "C" uint32_t ANDROID_HAL_MAPPER_VERSION = AIMAPPER_VERSION_5;
682*d95af8dfSAndroid Build Coastguard Worker
AIMapper_loadIMapper(AIMapper * _Nullable * _Nonnull outImplementation)683*d95af8dfSAndroid Build Coastguard Worker extern "C" AIMapper_Error AIMapper_loadIMapper(AIMapper* _Nullable* _Nonnull outImplementation) {
684*d95af8dfSAndroid Build Coastguard Worker static vendor::mapper::IMapperProvider<CrosGrallocMapperV5> provider;
685*d95af8dfSAndroid Build Coastguard Worker return provider.load(outImplementation);
686*d95af8dfSAndroid Build Coastguard Worker }