1 /*
2 * Copyright (C) 2007 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 "GraphicBufferMapper"
18 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
19 //#define LOG_NDEBUG 0
20
21 #include <ui/GraphicBufferMapper.h>
22
23 #include <grallocusage/GrallocUsageConversion.h>
24
25 // We would eliminate the non-conforming zero-length array, but we can't since
26 // this is effectively included from the Linux kernel
27 #pragma clang diagnostic push
28 #pragma clang diagnostic ignored "-Wzero-length-array"
29 #include <sync/sync.h>
30 #pragma clang diagnostic pop
31
32 #include <utils/Log.h>
33 #include <utils/Trace.h>
34
35 #include <ui/Gralloc.h>
36 #include <ui/Gralloc2.h>
37 #include <ui/Gralloc3.h>
38 #include <ui/Gralloc4.h>
39 #include <ui/Gralloc5.h>
40 #include <ui/GraphicBuffer.h>
41
42 #include <system/graphics.h>
43
44 using unique_fd = ::android::base::unique_fd;
45
46 namespace android {
47 // ---------------------------------------------------------------------------
48
49 using LockResult = GraphicBufferMapper::LockResult;
50
ANDROID_SINGLETON_STATIC_INSTANCE(GraphicBufferMapper)51 ANDROID_SINGLETON_STATIC_INSTANCE( GraphicBufferMapper )
52
53 void GraphicBufferMapper::preloadHal() {
54 Gralloc2Mapper::preload();
55 Gralloc3Mapper::preload();
56 Gralloc4Mapper::preload();
57 Gralloc5Mapper::preload();
58 }
59
GraphicBufferMapper()60 GraphicBufferMapper::GraphicBufferMapper() {
61 mMapper = std::make_unique<const Gralloc5Mapper>();
62 if (mMapper->isLoaded()) {
63 mMapperVersion = Version::GRALLOC_5;
64 return;
65 }
66 mMapper = std::make_unique<const Gralloc4Mapper>();
67 if (mMapper->isLoaded()) {
68 mMapperVersion = Version::GRALLOC_4;
69 return;
70 }
71 mMapper = std::make_unique<const Gralloc3Mapper>();
72 if (mMapper->isLoaded()) {
73 mMapperVersion = Version::GRALLOC_3;
74 return;
75 }
76 mMapper = std::make_unique<const Gralloc2Mapper>();
77 if (mMapper->isLoaded()) {
78 mMapperVersion = Version::GRALLOC_2;
79 return;
80 }
81
82 LOG_ALWAYS_FATAL("gralloc-mapper is missing");
83 }
84
dumpBuffer(buffer_handle_t bufferHandle,std::string & result,bool less) const85 void GraphicBufferMapper::dumpBuffer(buffer_handle_t bufferHandle, std::string& result,
86 bool less) const {
87 result.append(mMapper->dumpBuffer(bufferHandle, less));
88 }
89
dumpBufferToSystemLog(buffer_handle_t bufferHandle,bool less)90 void GraphicBufferMapper::dumpBufferToSystemLog(buffer_handle_t bufferHandle, bool less) {
91 std::string s;
92 GraphicBufferMapper::getInstance().dumpBuffer(bufferHandle, s, less);
93 ALOGD("%s", s.c_str());
94 }
95
importBuffer(const native_handle_t * rawHandle,uint32_t width,uint32_t height,uint32_t layerCount,PixelFormat format,uint64_t usage,uint32_t stride,buffer_handle_t * outHandle)96 status_t GraphicBufferMapper::importBuffer(const native_handle_t* rawHandle, uint32_t width,
97 uint32_t height, uint32_t layerCount, PixelFormat format,
98 uint64_t usage, uint32_t stride,
99 buffer_handle_t* outHandle) {
100 ATRACE_CALL();
101
102 buffer_handle_t bufferHandle;
103 status_t error = mMapper->importBuffer(rawHandle, &bufferHandle);
104 if (error != NO_ERROR) {
105 ALOGW("importBuffer(%p) failed: %d", rawHandle, error);
106 return error;
107 }
108
109 error = mMapper->validateBufferSize(bufferHandle, width, height, format, layerCount, usage,
110 stride);
111 if (error != NO_ERROR) {
112 ALOGE("validateBufferSize(%p) failed: %d", rawHandle, error);
113 freeBuffer(bufferHandle);
114 return static_cast<status_t>(error);
115 }
116
117 *outHandle = bufferHandle;
118
119 return NO_ERROR;
120 }
121
importBufferNoValidate(const native_handle_t * rawHandle,buffer_handle_t * outHandle)122 status_t GraphicBufferMapper::importBufferNoValidate(const native_handle_t* rawHandle,
123 buffer_handle_t* outHandle) {
124 return mMapper->importBuffer(rawHandle, outHandle);
125 }
126
getTransportSize(buffer_handle_t handle,uint32_t * outTransportNumFds,uint32_t * outTransportNumInts)127 void GraphicBufferMapper::getTransportSize(buffer_handle_t handle,
128 uint32_t* outTransportNumFds, uint32_t* outTransportNumInts)
129 {
130 mMapper->getTransportSize(handle, outTransportNumFds, outTransportNumInts);
131 }
132
freeBuffer(buffer_handle_t handle)133 status_t GraphicBufferMapper::freeBuffer(buffer_handle_t handle)
134 {
135 ATRACE_CALL();
136
137 mMapper->freeBuffer(handle);
138
139 return NO_ERROR;
140 }
141
lock(buffer_handle_t handle,int64_t usage,const Rect & bounds,unique_fd && acquireFence)142 ui::Result<LockResult> GraphicBufferMapper::lock(buffer_handle_t handle, int64_t usage,
143 const Rect& bounds, unique_fd&& acquireFence) {
144 ATRACE_CALL();
145
146 LockResult result;
147 status_t status = mMapper->lock(handle, usage, bounds, acquireFence.release(), &result.address,
148 &result.bytesPerPixel, &result.bytesPerStride);
149 if (status != OK) {
150 return base::unexpected(ui::Error::statusToCode(status));
151 } else {
152 return result;
153 }
154 }
155
lockYCbCr(buffer_handle_t handle,int64_t usage,const Rect & bounds,base::unique_fd && acquireFence)156 ui::Result<android_ycbcr> GraphicBufferMapper::lockYCbCr(buffer_handle_t handle, int64_t usage,
157 const Rect& bounds,
158 base::unique_fd&& acquireFence) {
159 ATRACE_CALL();
160
161 android_ycbcr result = {};
162 status_t status = mMapper->lock(handle, usage, bounds, acquireFence.release(), &result);
163 if (status != OK) {
164 return base::unexpected(ui::Error::statusToCode(status));
165 } else {
166 return result;
167 }
168 }
169
unlock(buffer_handle_t handle,base::unique_fd * outFence)170 status_t GraphicBufferMapper::unlock(buffer_handle_t handle, base::unique_fd* outFence) {
171 ATRACE_CALL();
172 int fence = mMapper->unlock(handle);
173 if (outFence) {
174 *outFence = unique_fd{fence};
175 } else {
176 sync_wait(fence, -1);
177 close(fence);
178 }
179 return OK;
180 }
181
lock(buffer_handle_t handle,uint32_t usage,const Rect & bounds,void ** vaddr)182 status_t GraphicBufferMapper::lock(buffer_handle_t handle, uint32_t usage, const Rect& bounds,
183 void** vaddr) {
184 auto result = lock(handle, static_cast<int64_t>(usage), bounds);
185 if (!result.has_value()) return result.asStatus();
186 auto val = result.value();
187 *vaddr = val.address;
188 return OK;
189 }
190
lockYCbCr(buffer_handle_t handle,uint32_t usage,const Rect & bounds,android_ycbcr * ycbcr)191 status_t GraphicBufferMapper::lockYCbCr(buffer_handle_t handle, uint32_t usage, const Rect& bounds,
192 android_ycbcr* ycbcr) {
193 auto result = lockYCbCr(handle, static_cast<int64_t>(usage), bounds);
194 if (!result.has_value()) return result.asStatus();
195 *ycbcr = result.value();
196 return OK;
197 }
198
lockAsync(buffer_handle_t handle,uint32_t usage,const Rect & bounds,void ** vaddr,int fenceFd)199 status_t GraphicBufferMapper::lockAsync(buffer_handle_t handle, uint32_t usage, const Rect& bounds,
200 void** vaddr, int fenceFd) {
201 auto result = lock(handle, static_cast<int64_t>(usage), bounds, unique_fd{fenceFd});
202 if (!result.has_value()) return result.asStatus();
203 auto val = result.value();
204 *vaddr = val.address;
205 return OK;
206 }
207
lockAsync(buffer_handle_t handle,uint64_t producerUsage,uint64_t consumerUsage,const Rect & bounds,void ** vaddr,int fenceFd)208 status_t GraphicBufferMapper::lockAsync(buffer_handle_t handle, uint64_t producerUsage,
209 uint64_t consumerUsage, const Rect& bounds, void** vaddr,
210 int fenceFd) {
211 return lockAsync(handle,
212 ANDROID_NATIVE_UNSIGNED_CAST(
213 android_convertGralloc1To0Usage(producerUsage, consumerUsage)),
214 bounds, vaddr, fenceFd);
215 }
216
lockAsyncYCbCr(buffer_handle_t handle,uint32_t usage,const Rect & bounds,android_ycbcr * ycbcr,int fenceFd)217 status_t GraphicBufferMapper::lockAsyncYCbCr(buffer_handle_t handle, uint32_t usage,
218 const Rect& bounds, android_ycbcr* ycbcr,
219 int fenceFd) {
220 auto result = lockYCbCr(handle, static_cast<int64_t>(usage), bounds, unique_fd{fenceFd});
221 if (!result.has_value()) return result.asStatus();
222 *ycbcr = result.value();
223 return OK;
224 }
225
isSupported(uint32_t width,uint32_t height,android::PixelFormat format,uint32_t layerCount,uint64_t usage,bool * outSupported)226 status_t GraphicBufferMapper::isSupported(uint32_t width, uint32_t height,
227 android::PixelFormat format, uint32_t layerCount,
228 uint64_t usage, bool* outSupported) {
229 return mMapper->isSupported(width, height, format, layerCount, usage, outSupported);
230 }
231
getBufferId(buffer_handle_t bufferHandle,uint64_t * outBufferId)232 status_t GraphicBufferMapper::getBufferId(buffer_handle_t bufferHandle, uint64_t* outBufferId) {
233 return mMapper->getBufferId(bufferHandle, outBufferId);
234 }
235
getName(buffer_handle_t bufferHandle,std::string * outName)236 status_t GraphicBufferMapper::getName(buffer_handle_t bufferHandle, std::string* outName) {
237 return mMapper->getName(bufferHandle, outName);
238 }
239
getWidth(buffer_handle_t bufferHandle,uint64_t * outWidth)240 status_t GraphicBufferMapper::getWidth(buffer_handle_t bufferHandle, uint64_t* outWidth) {
241 return mMapper->getWidth(bufferHandle, outWidth);
242 }
243
getHeight(buffer_handle_t bufferHandle,uint64_t * outHeight)244 status_t GraphicBufferMapper::getHeight(buffer_handle_t bufferHandle, uint64_t* outHeight) {
245 return mMapper->getHeight(bufferHandle, outHeight);
246 }
247
getLayerCount(buffer_handle_t bufferHandle,uint64_t * outLayerCount)248 status_t GraphicBufferMapper::getLayerCount(buffer_handle_t bufferHandle, uint64_t* outLayerCount) {
249 return mMapper->getLayerCount(bufferHandle, outLayerCount);
250 }
251
getPixelFormatRequested(buffer_handle_t bufferHandle,ui::PixelFormat * outPixelFormatRequested)252 status_t GraphicBufferMapper::getPixelFormatRequested(buffer_handle_t bufferHandle,
253 ui::PixelFormat* outPixelFormatRequested) {
254 return mMapper->getPixelFormatRequested(bufferHandle, outPixelFormatRequested);
255 }
256
getPixelFormatFourCC(buffer_handle_t bufferHandle,uint32_t * outPixelFormatFourCC)257 status_t GraphicBufferMapper::getPixelFormatFourCC(buffer_handle_t bufferHandle,
258 uint32_t* outPixelFormatFourCC) {
259 return mMapper->getPixelFormatFourCC(bufferHandle, outPixelFormatFourCC);
260 }
261
getPixelFormatModifier(buffer_handle_t bufferHandle,uint64_t * outPixelFormatModifier)262 status_t GraphicBufferMapper::getPixelFormatModifier(buffer_handle_t bufferHandle,
263 uint64_t* outPixelFormatModifier) {
264 return mMapper->getPixelFormatModifier(bufferHandle, outPixelFormatModifier);
265 }
266
getUsage(buffer_handle_t bufferHandle,uint64_t * outUsage)267 status_t GraphicBufferMapper::getUsage(buffer_handle_t bufferHandle, uint64_t* outUsage) {
268 return mMapper->getUsage(bufferHandle, outUsage);
269 }
270
getAllocationSize(buffer_handle_t bufferHandle,uint64_t * outAllocationSize)271 status_t GraphicBufferMapper::getAllocationSize(buffer_handle_t bufferHandle,
272 uint64_t* outAllocationSize) {
273 return mMapper->getAllocationSize(bufferHandle, outAllocationSize);
274 }
275
getProtectedContent(buffer_handle_t bufferHandle,uint64_t * outProtectedContent)276 status_t GraphicBufferMapper::getProtectedContent(buffer_handle_t bufferHandle,
277 uint64_t* outProtectedContent) {
278 return mMapper->getProtectedContent(bufferHandle, outProtectedContent);
279 }
280
getCompression(buffer_handle_t bufferHandle,aidl::android::hardware::graphics::common::ExtendableType * outCompression)281 status_t GraphicBufferMapper::getCompression(
282 buffer_handle_t bufferHandle,
283 aidl::android::hardware::graphics::common::ExtendableType* outCompression) {
284 return mMapper->getCompression(bufferHandle, outCompression);
285 }
286
getCompression(buffer_handle_t bufferHandle,ui::Compression * outCompression)287 status_t GraphicBufferMapper::getCompression(buffer_handle_t bufferHandle,
288 ui::Compression* outCompression) {
289 return mMapper->getCompression(bufferHandle, outCompression);
290 }
291
getInterlaced(buffer_handle_t bufferHandle,aidl::android::hardware::graphics::common::ExtendableType * outInterlaced)292 status_t GraphicBufferMapper::getInterlaced(
293 buffer_handle_t bufferHandle,
294 aidl::android::hardware::graphics::common::ExtendableType* outInterlaced) {
295 return mMapper->getInterlaced(bufferHandle, outInterlaced);
296 }
297
getInterlaced(buffer_handle_t bufferHandle,ui::Interlaced * outInterlaced)298 status_t GraphicBufferMapper::getInterlaced(buffer_handle_t bufferHandle,
299 ui::Interlaced* outInterlaced) {
300 return mMapper->getInterlaced(bufferHandle, outInterlaced);
301 }
302
getChromaSiting(buffer_handle_t bufferHandle,aidl::android::hardware::graphics::common::ExtendableType * outChromaSiting)303 status_t GraphicBufferMapper::getChromaSiting(
304 buffer_handle_t bufferHandle,
305 aidl::android::hardware::graphics::common::ExtendableType* outChromaSiting) {
306 return mMapper->getChromaSiting(bufferHandle, outChromaSiting);
307 }
308
getChromaSiting(buffer_handle_t bufferHandle,ui::ChromaSiting * outChromaSiting)309 status_t GraphicBufferMapper::getChromaSiting(buffer_handle_t bufferHandle,
310 ui::ChromaSiting* outChromaSiting) {
311 return mMapper->getChromaSiting(bufferHandle, outChromaSiting);
312 }
313
getPlaneLayouts(buffer_handle_t bufferHandle,std::vector<ui::PlaneLayout> * outPlaneLayouts)314 status_t GraphicBufferMapper::getPlaneLayouts(buffer_handle_t bufferHandle,
315 std::vector<ui::PlaneLayout>* outPlaneLayouts) {
316 return mMapper->getPlaneLayouts(bufferHandle, outPlaneLayouts);
317 }
318
getPlaneLayouts(buffer_handle_t bufferHandle)319 ui::Result<std::vector<ui::PlaneLayout>> GraphicBufferMapper::getPlaneLayouts(
320 buffer_handle_t bufferHandle) {
321 std::vector<ui::PlaneLayout> temp;
322 status_t status = mMapper->getPlaneLayouts(bufferHandle, &temp);
323 if (status == OK) {
324 return std::move(temp);
325 } else {
326 return base::unexpected(ui::Error::statusToCode(status));
327 }
328 }
329
getDataspace(buffer_handle_t bufferHandle,ui::Dataspace * outDataspace)330 status_t GraphicBufferMapper::getDataspace(buffer_handle_t bufferHandle,
331 ui::Dataspace* outDataspace) {
332 return mMapper->getDataspace(bufferHandle, outDataspace);
333 }
334
setDataspace(buffer_handle_t bufferHandle,ui::Dataspace dataspace)335 status_t GraphicBufferMapper::setDataspace(buffer_handle_t bufferHandle, ui::Dataspace dataspace) {
336 return mMapper->setDataspace(bufferHandle, dataspace);
337 }
338
getBlendMode(buffer_handle_t bufferHandle,ui::BlendMode * outBlendMode)339 status_t GraphicBufferMapper::getBlendMode(buffer_handle_t bufferHandle,
340 ui::BlendMode* outBlendMode) {
341 return mMapper->getBlendMode(bufferHandle, outBlendMode);
342 }
343
getSmpte2086(buffer_handle_t bufferHandle,std::optional<ui::Smpte2086> * outSmpte2086)344 status_t GraphicBufferMapper::getSmpte2086(buffer_handle_t bufferHandle,
345 std::optional<ui::Smpte2086>* outSmpte2086) {
346 return mMapper->getSmpte2086(bufferHandle, outSmpte2086);
347 }
348
setSmpte2086(buffer_handle_t bufferHandle,std::optional<ui::Smpte2086> smpte2086)349 status_t GraphicBufferMapper::setSmpte2086(buffer_handle_t bufferHandle,
350 std::optional<ui::Smpte2086> smpte2086) {
351 return mMapper->setSmpte2086(bufferHandle, smpte2086);
352 }
353
getCta861_3(buffer_handle_t bufferHandle,std::optional<ui::Cta861_3> * outCta861_3)354 status_t GraphicBufferMapper::getCta861_3(buffer_handle_t bufferHandle,
355 std::optional<ui::Cta861_3>* outCta861_3) {
356 return mMapper->getCta861_3(bufferHandle, outCta861_3);
357 }
358
setCta861_3(buffer_handle_t bufferHandle,std::optional<ui::Cta861_3> cta861_3)359 status_t GraphicBufferMapper::setCta861_3(buffer_handle_t bufferHandle,
360 std::optional<ui::Cta861_3> cta861_3) {
361 return mMapper->setCta861_3(bufferHandle, cta861_3);
362 }
363
getSmpte2094_40(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> * outSmpte2094_40)364 status_t GraphicBufferMapper::getSmpte2094_40(
365 buffer_handle_t bufferHandle, std::optional<std::vector<uint8_t>>* outSmpte2094_40) {
366 return mMapper->getSmpte2094_40(bufferHandle, outSmpte2094_40);
367 }
368
setSmpte2094_40(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> smpte2094_40)369 status_t GraphicBufferMapper::setSmpte2094_40(buffer_handle_t bufferHandle,
370 std::optional<std::vector<uint8_t>> smpte2094_40) {
371 return mMapper->setSmpte2094_40(bufferHandle, smpte2094_40);
372 }
373
getSmpte2094_10(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> * outSmpte2094_10)374 status_t GraphicBufferMapper::getSmpte2094_10(
375 buffer_handle_t bufferHandle, std::optional<std::vector<uint8_t>>* outSmpte2094_10) {
376 return mMapper->getSmpte2094_10(bufferHandle, outSmpte2094_10);
377 }
378
setSmpte2094_10(buffer_handle_t bufferHandle,std::optional<std::vector<uint8_t>> smpte2094_10)379 status_t GraphicBufferMapper::setSmpte2094_10(buffer_handle_t bufferHandle,
380 std::optional<std::vector<uint8_t>> smpte2094_10) {
381 return mMapper->setSmpte2094_10(bufferHandle, smpte2094_10);
382 }
383
384 // ---------------------------------------------------------------------------
385 }; // namespace android
386