blob: 6379a08bf4dba9926a4da36b9858f1e379c856fa [file] [log] [blame]
Dan Stozaeb03fd32016-01-11 15:21:07 -08001/*
2 * Copyright 2016 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#ifndef ANDROID_UI_GRALLOC_1_ON_0_ADAPTER_H
18#define ANDROID_UI_GRALLOC_1_ON_0_ADAPTER_H
19
Mathias Agopiana9347642017-02-13 16:42:28 -080020#include <log/log.h>
Dan Stozaeb03fd32016-01-11 15:21:07 -080021
Mathias Agopiana9347642017-02-13 16:42:28 -080022#include <ui/Fence.h>
23
24#include <hardware/gralloc.h>
Dan Stozaeb03fd32016-01-11 15:21:07 -080025#include <hardware/gralloc1.h>
26
27#include <mutex>
28#include <string>
29#include <unordered_map>
30#include <vector>
31
Mathias Agopiana9347642017-02-13 16:42:28 -080032namespace android {
33class GraphicBuffer;
34} // namespace android
35
Dan Stozaeb03fd32016-01-11 15:21:07 -080036struct gralloc_module_t;
37
Dan Stozaeb03fd32016-01-11 15:21:07 -080038namespace android {
39
40class Gralloc1On0Adapter : public gralloc1_device_t
41{
42public:
43 Gralloc1On0Adapter(const hw_module_t* module);
44 ~Gralloc1On0Adapter();
45
46 gralloc1_device_t* getDevice() {
47 return static_cast<gralloc1_device_t*>(this);
48 }
49
50private:
51 static inline Gralloc1On0Adapter* getAdapter(gralloc1_device_t* device) {
52 return static_cast<Gralloc1On0Adapter*>(device);
53 }
54
55 // getCapabilities
56
57 void doGetCapabilities(uint32_t* outCount,
58 int32_t* /*gralloc1_capability_t*/ outCapabilities);
59 static void getCapabilitiesHook(gralloc1_device_t* device,
60 uint32_t* outCount,
61 int32_t* /*gralloc1_capability_t*/ outCapabilities) {
62 getAdapter(device)->doGetCapabilities(outCount, outCapabilities);
Colin Cross17576de2016-09-26 13:07:06 -070063 }
Dan Stozaeb03fd32016-01-11 15:21:07 -080064
65 // getFunction
66
67 gralloc1_function_pointer_t doGetFunction(
68 int32_t /*gralloc1_function_descriptor_t*/ descriptor);
69 static gralloc1_function_pointer_t getFunctionHook(
70 gralloc1_device_t* device,
71 int32_t /*gralloc1_function_descriptor_t*/ descriptor) {
72 return getAdapter(device)->doGetFunction(descriptor);
73 }
74
75 // dump
76
77 void dump(uint32_t* outSize, char* outBuffer);
78 static void dumpHook(gralloc1_device_t* device, uint32_t* outSize,
79 char* outBuffer) {
80 return getAdapter(device)->dump(outSize, outBuffer);
81 }
82 std::string mCachedDump;
83
84 // Buffer descriptor lifecycle functions
85
Colin Crossa2362b42016-09-26 13:48:25 -070086 struct Descriptor;
Dan Stozaeb03fd32016-01-11 15:21:07 -080087
88 gralloc1_error_t createDescriptor(
89 gralloc1_buffer_descriptor_t* outDescriptor);
90 static int32_t createDescriptorHook(gralloc1_device_t* device,
91 gralloc1_buffer_descriptor_t* outDescriptor) {
92 auto error = getAdapter(device)->createDescriptor(outDescriptor);
93 return static_cast<int32_t>(error);
94 }
95
96 gralloc1_error_t destroyDescriptor(gralloc1_buffer_descriptor_t descriptor);
97 static int32_t destroyDescriptorHook(gralloc1_device_t* device,
98 gralloc1_buffer_descriptor_t descriptor) {
99 auto error = getAdapter(device)->destroyDescriptor(descriptor);
100 return static_cast<int32_t>(error);
101 }
102
103 // Buffer descriptor modification functions
104
105 struct Descriptor : public std::enable_shared_from_this<Descriptor> {
Colin Cross382ecd32016-09-26 13:33:59 -0700106 Descriptor(Gralloc1On0Adapter* _adapter,
107 gralloc1_buffer_descriptor_t _id)
108 : adapter(_adapter),
109 id(_id),
Dan Stozaeb03fd32016-01-11 15:21:07 -0800110 width(0),
111 height(0),
112 format(HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED),
Craig Donner6ebc46a2016-10-21 15:23:44 -0700113 layerCount(1),
Dan Stozaeb03fd32016-01-11 15:21:07 -0800114 producerUsage(GRALLOC1_PRODUCER_USAGE_NONE),
115 consumerUsage(GRALLOC1_CONSUMER_USAGE_NONE) {}
116
117 gralloc1_error_t setDimensions(uint32_t w, uint32_t h) {
118 width = w;
119 height = h;
120 return GRALLOC1_ERROR_NONE;
121 }
122
123 gralloc1_error_t setFormat(int32_t f) {
124 format = f;
125 return GRALLOC1_ERROR_NONE;
126 }
127
Craig Donner6ebc46a2016-10-21 15:23:44 -0700128 gralloc1_error_t setLayerCount(uint32_t lc) {
129 layerCount = lc;
130 return GRALLOC1_ERROR_NONE;
131 }
132
Dan Stozaeb03fd32016-01-11 15:21:07 -0800133 gralloc1_error_t setProducerUsage(gralloc1_producer_usage_t usage) {
134 producerUsage = usage;
135 return GRALLOC1_ERROR_NONE;
136 }
137
138 gralloc1_error_t setConsumerUsage(gralloc1_consumer_usage_t usage) {
139 consumerUsage = usage;
140 return GRALLOC1_ERROR_NONE;
141 }
142
143 Gralloc1On0Adapter* const adapter;
144 const gralloc1_buffer_descriptor_t id;
145
146 uint32_t width;
147 uint32_t height;
148 int32_t format;
Craig Donner6ebc46a2016-10-21 15:23:44 -0700149 uint32_t layerCount;
Dan Stozaeb03fd32016-01-11 15:21:07 -0800150 gralloc1_producer_usage_t producerUsage;
151 gralloc1_consumer_usage_t consumerUsage;
152 };
153
154 template <typename ...Args>
155 static int32_t callDescriptorFunction(gralloc1_device_t* device,
156 gralloc1_buffer_descriptor_t descriptorId,
157 gralloc1_error_t (Descriptor::*member)(Args...), Args... args) {
158 auto descriptor = getAdapter(device)->getDescriptor(descriptorId);
159 if (!descriptor) {
160 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_DESCRIPTOR);
161 }
162 auto error = ((*descriptor).*member)(std::forward<Args>(args)...);
163 return static_cast<int32_t>(error);
164 }
165
166 static int32_t setConsumerUsageHook(gralloc1_device_t* device,
167 gralloc1_buffer_descriptor_t descriptorId, uint64_t intUsage) {
168 auto usage = static_cast<gralloc1_consumer_usage_t>(intUsage);
169 return callDescriptorFunction(device, descriptorId,
170 &Descriptor::setConsumerUsage, usage);
171 }
172
173 static int32_t setDimensionsHook(gralloc1_device_t* device,
174 gralloc1_buffer_descriptor_t descriptorId, uint32_t width,
175 uint32_t height) {
176 return callDescriptorFunction(device, descriptorId,
177 &Descriptor::setDimensions, width, height);
178 }
179
180 static int32_t setFormatHook(gralloc1_device_t* device,
181 gralloc1_buffer_descriptor_t descriptorId, int32_t format) {
182 return callDescriptorFunction(device, descriptorId,
183 &Descriptor::setFormat, format);
184 }
185
Craig Donner6ebc46a2016-10-21 15:23:44 -0700186 static int32_t setLayerCountHook(gralloc1_device_t* device,
187 gralloc1_buffer_descriptor_t descriptorId, uint32_t layerCount) {
188 return callDescriptorFunction(device, descriptorId,
189 &Descriptor::setLayerCount, layerCount);
190 }
191
Dan Stozaeb03fd32016-01-11 15:21:07 -0800192 static int32_t setProducerUsageHook(gralloc1_device_t* device,
193 gralloc1_buffer_descriptor_t descriptorId, uint64_t intUsage) {
194 auto usage = static_cast<gralloc1_producer_usage_t>(intUsage);
195 return callDescriptorFunction(device, descriptorId,
196 &Descriptor::setProducerUsage, usage);
197 }
198
199 // Buffer handle query functions
200
201 class Buffer {
202 public:
203 Buffer(buffer_handle_t handle, gralloc1_backing_store_t store,
204 const Descriptor& descriptor, uint32_t stride,
205 bool wasAllocated);
206
207 buffer_handle_t getHandle() const { return mHandle; }
208
209 void retain() { ++mReferenceCount; }
210
211 // Returns true if the reference count has dropped to 0, indicating that
212 // the buffer needs to be released
213 bool release() { return --mReferenceCount == 0; }
214
215 bool wasAllocated() const { return mWasAllocated; }
216
217 gralloc1_error_t getBackingStore(
218 gralloc1_backing_store_t* outStore) const {
219 *outStore = mStore;
220 return GRALLOC1_ERROR_NONE;
221 }
222
223 gralloc1_error_t getConsumerUsage(
224 gralloc1_consumer_usage_t* outUsage) const {
225 *outUsage = mDescriptor.consumerUsage;
226 return GRALLOC1_ERROR_NONE;
227 }
228
229 gralloc1_error_t getDimensions(uint32_t* outWidth,
230 uint32_t* outHeight) const {
231 *outWidth = mDescriptor.width;
232 *outHeight = mDescriptor.height;
233 return GRALLOC1_ERROR_NONE;
234 }
235
236 gralloc1_error_t getFormat(int32_t* outFormat) const {
237 *outFormat = mDescriptor.format;
238 return GRALLOC1_ERROR_NONE;
239 }
240
Craig Donner6ebc46a2016-10-21 15:23:44 -0700241 gralloc1_error_t getLayerCount(uint32_t* outLayerCount) const {
242 *outLayerCount = mDescriptor.layerCount;
243 return GRALLOC1_ERROR_NONE;
244 }
245
Dan Stozaeb03fd32016-01-11 15:21:07 -0800246 gralloc1_error_t getNumFlexPlanes(uint32_t* outNumPlanes) const {
247 // TODO: This is conservative, and we could do better by examining
248 // the format, but it won't hurt anything for now
249 *outNumPlanes = 4;
250 return GRALLOC1_ERROR_NONE;
251 }
252
253 gralloc1_error_t getProducerUsage(
254 gralloc1_producer_usage_t* outUsage) const {
255 *outUsage = mDescriptor.producerUsage;
256 return GRALLOC1_ERROR_NONE;
257 }
258
259 gralloc1_error_t getStride(uint32_t* outStride) const {
260 *outStride = mStride;
261 return GRALLOC1_ERROR_NONE;
262 }
263
264 private:
265
266 const buffer_handle_t mHandle;
267 size_t mReferenceCount;
268
269 // Since we're adapting to gralloc0, there will always be a 1:1
270 // correspondence between buffer handles and backing stores, and the
271 // backing store ID will be the same as the GraphicBuffer unique ID
272 const gralloc1_backing_store_t mStore;
273
274 const Descriptor mDescriptor;
275 const uint32_t mStride;
276
277 // Whether this buffer allocated in this process (as opposed to just
278 // being retained here), which determines whether to free or unregister
279 // the buffer when this Buffer is released
280 const bool mWasAllocated;
281 };
282
283 template <typename ...Args>
284 static int32_t callBufferFunction(gralloc1_device_t* device,
285 buffer_handle_t bufferHandle,
286 gralloc1_error_t (Buffer::*member)(Args...) const, Args... args) {
287 auto buffer = getAdapter(device)->getBuffer(bufferHandle);
288 if (!buffer) {
289 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_HANDLE);
290 }
291 auto error = ((*buffer).*member)(std::forward<Args>(args)...);
292 return static_cast<int32_t>(error);
293 }
294
295 template <typename MF, MF memFunc, typename ...Args>
296 static int32_t bufferHook(gralloc1_device_t* device,
297 buffer_handle_t bufferHandle, Args... args) {
298 return Gralloc1On0Adapter::callBufferFunction(device, bufferHandle,
299 memFunc, std::forward<Args>(args)...);
300 }
301
302 static int32_t getConsumerUsageHook(gralloc1_device_t* device,
303 buffer_handle_t bufferHandle, uint64_t* outUsage) {
304 auto usage = GRALLOC1_CONSUMER_USAGE_NONE;
305 auto error = callBufferFunction(device, bufferHandle,
306 &Buffer::getConsumerUsage, &usage);
Craig Donner58a1ef22017-02-02 12:40:05 -0800307 if (error == GRALLOC1_ERROR_NONE) {
Dan Stozaeb03fd32016-01-11 15:21:07 -0800308 *outUsage = static_cast<uint64_t>(usage);
309 }
310 return error;
311 }
312
313 static int32_t getProducerUsageHook(gralloc1_device_t* device,
314 buffer_handle_t bufferHandle, uint64_t* outUsage) {
315 auto usage = GRALLOC1_PRODUCER_USAGE_NONE;
316 auto error = callBufferFunction(device, bufferHandle,
317 &Buffer::getProducerUsage, &usage);
Craig Donner58a1ef22017-02-02 12:40:05 -0800318 if (error == GRALLOC1_ERROR_NONE) {
Dan Stozaeb03fd32016-01-11 15:21:07 -0800319 *outUsage = static_cast<uint64_t>(usage);
320 }
321 return error;
322 }
323
324 // Buffer management functions
325
326 // We don't provide GRALLOC1_FUNCTION_ALLOCATE, since this should always be
327 // called through GRALLOC1_FUNCTION_ALLOCATE_WITH_ID
328 gralloc1_error_t allocate(
329 const std::shared_ptr<Descriptor>& descriptor,
330 gralloc1_backing_store_t id,
331 buffer_handle_t* outBufferHandle);
332 static gralloc1_error_t allocateWithIdHook(gralloc1_device_t* device,
333 gralloc1_buffer_descriptor_t descriptors,
334 gralloc1_backing_store_t id, buffer_handle_t* outBuffer);
335
336 gralloc1_error_t retain(const std::shared_ptr<Buffer>& buffer);
337 gralloc1_error_t release(const std::shared_ptr<Buffer>& buffer);
338
339 // Member function pointer 'member' will either be retain or release
340 template <gralloc1_error_t (Gralloc1On0Adapter::*member)(
341 const std::shared_ptr<Buffer>& buffer)>
342 static int32_t managementHook(gralloc1_device_t* device,
343 buffer_handle_t bufferHandle) {
344 auto adapter = getAdapter(device);
345
346 auto buffer = adapter->getBuffer(bufferHandle);
347 if (!buffer) {
348 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_HANDLE);
349 }
350
351 auto error = ((*adapter).*member)(buffer);
352 return static_cast<int32_t>(error);
353 }
354
355 gralloc1_error_t retain(const GraphicBuffer* buffer);
356 static gralloc1_error_t retainGraphicBufferHook(gralloc1_device_t* device,
357 const GraphicBuffer* buffer) {
358 auto adapter = getAdapter(device);
359 return adapter->retain(buffer);
360 }
361
362 // Buffer access functions
363
364 gralloc1_error_t lock(const std::shared_ptr<Buffer>& buffer,
365 gralloc1_producer_usage_t producerUsage,
366 gralloc1_consumer_usage_t consumerUsage,
367 const gralloc1_rect_t& accessRegion, void** outData,
368 const sp<Fence>& acquireFence);
369 gralloc1_error_t lockFlex(const std::shared_ptr<Buffer>& buffer,
370 gralloc1_producer_usage_t producerUsage,
371 gralloc1_consumer_usage_t consumerUsage,
372 const gralloc1_rect_t& accessRegion,
373 struct android_flex_layout* outFlex,
374 const sp<Fence>& acquireFence);
375 gralloc1_error_t lockYCbCr(const std::shared_ptr<Buffer>& buffer,
376 gralloc1_producer_usage_t producerUsage,
377 gralloc1_consumer_usage_t consumerUsage,
378 const gralloc1_rect_t& accessRegion,
379 struct android_ycbcr* outFlex,
380 const sp<Fence>& acquireFence);
381
382 template <typename OUT, gralloc1_error_t (Gralloc1On0Adapter::*member)(
383 const std::shared_ptr<Buffer>&, gralloc1_producer_usage_t,
384 gralloc1_consumer_usage_t, const gralloc1_rect_t&, OUT*,
385 const sp<Fence>&)>
386 static int32_t lockHook(gralloc1_device_t* device,
387 buffer_handle_t bufferHandle,
388 uint64_t /*gralloc1_producer_usage_t*/ uintProducerUsage,
389 uint64_t /*gralloc1_consumer_usage_t*/ uintConsumerUsage,
390 const gralloc1_rect_t* accessRegion, OUT* outData,
391 int32_t acquireFenceFd) {
392 auto adapter = getAdapter(device);
393
394 // Exactly one of producer and consumer usage must be *_USAGE_NONE,
395 // but we can't check this until the upper levels of the framework
396 // correctly distinguish between producer and consumer usage
397 /*
398 bool hasProducerUsage =
399 uintProducerUsage != GRALLOC1_PRODUCER_USAGE_NONE;
400 bool hasConsumerUsage =
401 uintConsumerUsage != GRALLOC1_CONSUMER_USAGE_NONE;
402 if (hasProducerUsage && hasConsumerUsage ||
403 !hasProducerUsage && !hasConsumerUsage) {
404 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_VALUE);
405 }
406 */
407
408 auto producerUsage =
409 static_cast<gralloc1_producer_usage_t>(uintProducerUsage);
410 auto consumerUsage =
411 static_cast<gralloc1_consumer_usage_t>(uintConsumerUsage);
412
413 if (!outData) {
414 const auto producerCpuUsage = GRALLOC1_PRODUCER_USAGE_CPU_READ |
415 GRALLOC1_PRODUCER_USAGE_CPU_WRITE;
Colin Cross27224162016-09-27 14:09:07 -0700416 if ((producerUsage & producerCpuUsage) != 0) {
Dan Stozaeb03fd32016-01-11 15:21:07 -0800417 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_VALUE);
418 }
Colin Cross27224162016-09-27 14:09:07 -0700419 if ((consumerUsage & GRALLOC1_CONSUMER_USAGE_CPU_READ) != 0) {
Dan Stozaeb03fd32016-01-11 15:21:07 -0800420 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_VALUE);
421 }
422 }
423
424 auto buffer = adapter->getBuffer(bufferHandle);
425 if (!buffer) {
426 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_HANDLE);
427 }
428
429 if (!accessRegion) {
430 ALOGE("accessRegion is null");
431 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_VALUE);
432 }
433
434 sp<Fence> acquireFence{new Fence(acquireFenceFd)};
435 auto error = ((*adapter).*member)(buffer, producerUsage, consumerUsage,
436 *accessRegion, outData, acquireFence);
437 return static_cast<int32_t>(error);
438 }
439
440 gralloc1_error_t unlock(const std::shared_ptr<Buffer>& buffer,
441 sp<Fence>* outReleaseFence);
442 static int32_t unlockHook(gralloc1_device_t* device,
443 buffer_handle_t bufferHandle, int32_t* outReleaseFenceFd) {
444 auto adapter = getAdapter(device);
445
446 auto buffer = adapter->getBuffer(bufferHandle);
447 if (!buffer) {
448 return static_cast<int32_t>(GRALLOC1_ERROR_BAD_HANDLE);
449 }
450
451 sp<Fence> releaseFence = Fence::NO_FENCE;
452 auto error = adapter->unlock(buffer, &releaseFence);
453 if (error == GRALLOC1_ERROR_NONE) {
454 *outReleaseFenceFd = releaseFence->dup();
455 }
456 return static_cast<int32_t>(error);
457 }
458
459 // Adapter internals
460 const gralloc_module_t* mModule;
461 uint8_t mMinorVersion;
462 alloc_device_t* mDevice;
463
464 std::shared_ptr<Descriptor> getDescriptor(
465 gralloc1_buffer_descriptor_t descriptorId);
466 std::shared_ptr<Buffer> getBuffer(buffer_handle_t bufferHandle);
467
468 static std::atomic<gralloc1_buffer_descriptor_t> sNextBufferDescriptorId;
469 std::mutex mDescriptorMutex;
470 std::unordered_map<gralloc1_buffer_descriptor_t,
471 std::shared_ptr<Descriptor>> mDescriptors;
472 std::mutex mBufferMutex;
473 std::unordered_map<buffer_handle_t, std::shared_ptr<Buffer>> mBuffers;
474};
475
476} // namespace android
477
478#endif