blob: 67127fd005b95fe1ccd250123146b1a75c049888 [file] [log] [blame]
John Stultz16100f62017-05-03 11:12:18 -07001/*
2 * Copyright (C) 2016 ARM Limited. All rights reserved.
3 *
4 * Copyright (C) 2008 The Android Open Source Project
5 *
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 */
18
19#include <string.h>
20#include <dlfcn.h>
21#include <hardware/gralloc.h>
22#include <inttypes.h>
23#include <cutils/log.h>
24
25#include "mali_gralloc_formats.h"
26#include "gralloc_priv.h"
27
28static mali_gralloc_format_caps dpu_runtime_caps;
29static mali_gralloc_format_caps vpu_runtime_caps;
30static mali_gralloc_format_caps gpu_runtime_caps;
31static mali_gralloc_format_caps cam_runtime_caps;
32static pthread_mutex_t caps_init_mutex = PTHREAD_MUTEX_INITIALIZER;
33static bool runtime_caps_read = false;
34
35#define MALI_GRALLOC_GPU_LIB_NAME "libGLES_mali.so"
36#if defined(__LP64__)
37#define MALI_GRALLOC_GPU_LIBRARY_PATH1 "/vendor/lib64/egl/"
38#define MALI_GRALLOC_GPU_LIBRARY_PATH2 "/system/lib64/egl/"
39#else
40#define MALI_GRALLOC_GPU_LIBRARY_PATH1 "/vendor/lib/egl/"
41#define MALI_GRALLOC_GPU_LIBRARY_PATH2 "/system/lib/egl/"
42#endif
43
44static bool get_block_capabilities(bool hal_module, const char *name, mali_gralloc_format_caps *block_caps)
45{
46 void *dso_handle = NULL;
47 bool rval = false;
48
49 /* Look for MALI_GRALLOC_FORMATCAPS_SYM_NAME_STR symbol in user-space drivers
50 * to determine hw format capabilities.
51 */
52 if(!hal_module)
53 {
54 dso_handle = dlopen(name, RTLD_LAZY);
55 }
56 else
57 {
58 /* libhardware does some heuristics to find hal modules
59 * and then stores the dso handle internally. Use this.
60 */
61 const struct hw_module_t *module = {NULL};
62
63 if(hw_get_module(name, &module) >= 0)
64 {
65 dso_handle = module->dso;
66 }
67 }
68
69 if(dso_handle)
70 {
71 void *sym = dlsym(dso_handle, MALI_GRALLOC_FORMATCAPS_SYM_NAME_STR);
72
73 if(sym)
74 {
75 memcpy((void*) block_caps, sym, sizeof(mali_gralloc_format_caps));
76 rval = true;
77 }
78
79 if(!hal_module)
80 {
81 dlclose(dso_handle);
82 }
83 }
84
85 return rval;
86}
87
88static int map_flex_formats(int req_format, uint64_t *producer_runtime_mask)
89{
90 /* Map Android flexible formats to internal base formats */
91 if(req_format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED ||
92 req_format == HAL_PIXEL_FORMAT_YCbCr_420_888)
93 {
94 req_format = MALI_GRALLOC_FORMAT_INTERNAL_NV12;
95
96 /*
97 * We disable AFBC for NV12 since neither VPU or DPU DDKs support
98 * them currently.
99 */
100 *producer_runtime_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
101 }
John Stultz16100f62017-05-03 11:12:18 -0700102 return req_format;
103}
104
105static bool is_afbc_supported(int req_format_mapped)
106{
107 bool rval = true;
108
109 /* These base formats we currently don't support with compression */
110 switch(req_format_mapped)
111 {
112 case MALI_GRALLOC_FORMAT_INTERNAL_RAW16:
113 case MALI_GRALLOC_FORMAT_INTERNAL_RAW12:
114 case MALI_GRALLOC_FORMAT_INTERNAL_RAW10:
115 case MALI_GRALLOC_FORMAT_INTERNAL_BLOB:
116 case MALI_GRALLOC_FORMAT_INTERNAL_P010:
117 case MALI_GRALLOC_FORMAT_INTERNAL_P210:
118 case MALI_GRALLOC_FORMAT_INTERNAL_Y410:
119 case HAL_PIXEL_FORMAT_YCbCr_422_I:
120 rval = false;
121 break;
122 }
123 return rval;
124}
125
126static bool is_android_yuv_format(int req_format)
127{
128 bool rval = false;
129
130 switch(req_format)
131 {
132 case HAL_PIXEL_FORMAT_YV12:
133 case HAL_PIXEL_FORMAT_Y8:
134 case HAL_PIXEL_FORMAT_Y16:
135 case HAL_PIXEL_FORMAT_YCbCr_420_888:
136 case HAL_PIXEL_FORMAT_YCbCr_422_888:
137 case HAL_PIXEL_FORMAT_YCbCr_444_888:
138 rval = true;
139 break;
140 }
141 return rval;
142}
143
144static bool is_afbc_allowed(int buffer_size)
145{
146 bool afbc_allowed = false;
147
148 (void) buffer_size;
149
150#if GRALLOC_DISP_W != 0 && GRALLOC_DISP_H != 0
151 afbc_allowed = ((buffer_size*100) / (GRALLOC_DISP_W*GRALLOC_DISP_H)) >= GRALLOC_AFBC_MIN_SIZE;
152
153#else
154 /* If display size is not valid then always allow AFBC */
155 afbc_allowed = true;
156
157#endif
158
159 return afbc_allowed;
160}
161
162static bool is_afbc_format(uint64_t internal_format)
163{
164 return (internal_format & MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK) != 0;
165}
166
167static uint64_t determine_best_format(int req_format, mali_gralloc_producer_type producer, mali_gralloc_consumer_type consumer,
168 uint64_t producer_runtime_mask, uint64_t consumer_runtime_mask)
169{
170 /* Default is to return the requested format */
171 uint64_t internal_format = req_format;
172 uint64_t dpu_mask = dpu_runtime_caps.caps_mask;
173 uint64_t gpu_mask = gpu_runtime_caps.caps_mask;
174 uint64_t vpu_mask = vpu_runtime_caps.caps_mask;
175 uint64_t cam_mask = cam_runtime_caps.caps_mask;
176
177 if(producer == MALI_GRALLOC_PRODUCER_GPU && gpu_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT)
178 {
179 gpu_mask &= producer_runtime_mask;
180
181 if(consumer == MALI_GRALLOC_CONSUMER_GPU_OR_DISPLAY)
182 {
183 gpu_mask &= consumer_runtime_mask;
184 dpu_mask &= consumer_runtime_mask;
185
186 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK &&
187 dpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK)
188 {
189 internal_format |= MALI_GRALLOC_INTFMT_AFBC_SPLITBLK;
190 }
191 else if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC &&
192 dpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC)
193 {
194 internal_format |= MALI_GRALLOC_INTFMT_AFBC_BASIC;
195
196 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS &&
197 dpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS)
198 {
199 internal_format |= MALI_GRALLOC_INTFMT_AFBC_TILED_HEADERS;
200 }
201 }
202 }
203 else if(consumer == MALI_GRALLOC_CONSUMER_GPU_EXCL)
204 {
205 gpu_mask &= consumer_runtime_mask;
206
207 /* When GPU acts as both producer and consumer it prefers 16x16 superblocks */
208 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC)
209 {
210 internal_format |= MALI_GRALLOC_INTFMT_AFBC_BASIC;
211 }
212
213 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS)
214 {
215 internal_format |= MALI_GRALLOC_INTFMT_AFBC_TILED_HEADERS;
216 }
217 }
218 else if(consumer == MALI_GRALLOC_CONSUMER_VIDEO_ENCODER)
219 {
220 vpu_mask &= consumer_runtime_mask;
221
222 if(req_format == HAL_PIXEL_FORMAT_YV12)
223 {
224 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC &&
225 vpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC)
226 {
227 internal_format |= MALI_GRALLOC_INTFMT_AFBC_BASIC;
228 }
229
230 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS &&
231 vpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS)
232 {
233 internal_format |= MALI_GRALLOC_INTFMT_AFBC_TILED_HEADERS;
234 }
235 }
236 }
237 }
238 else if(producer == MALI_GRALLOC_PRODUCER_VIDEO_DECODER && vpu_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT)
239 {
240 vpu_mask &= producer_runtime_mask;
241
242 if(consumer == MALI_GRALLOC_CONSUMER_GPU_OR_DISPLAY)
243 {
244 gpu_mask &= consumer_runtime_mask;
245 dpu_mask &= consumer_runtime_mask;
246
247 if(internal_format == HAL_PIXEL_FORMAT_YV12)
248 {
249 if(vpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC &&
250 gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC &&
251 dpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC)
252 {
253 internal_format |= MALI_GRALLOC_INTFMT_AFBC_BASIC;
254 }
255
256 if(vpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS &&
257 gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS &&
258 dpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS)
259 {
260 internal_format |= MALI_GRALLOC_INTFMT_AFBC_TILED_HEADERS;
261 }
262 }
263 }
264 else if(consumer == MALI_GRALLOC_CONSUMER_GPU_EXCL)
265 {
266 gpu_mask &= consumer_runtime_mask;
267
268 if(internal_format == HAL_PIXEL_FORMAT_YV12)
269 {
270 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC &&
271 vpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC)
272 {
273 internal_format |= MALI_GRALLOC_INTFMT_AFBC_BASIC;
274 }
275
276 if(gpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS &&
277 vpu_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS)
278 {
279 internal_format |= MALI_GRALLOC_INTFMT_AFBC_TILED_HEADERS;
280 }
281 }
282 }
283 else if(consumer == MALI_GRALLOC_CONSUMER_VIDEO_ENCODER)
284 {
285 /* Fall-through. To be decided.*/
286 }
287 }
288 else if(producer == MALI_GRALLOC_PRODUCER_CAMERA && cam_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT)
289 {
290 if(consumer == MALI_GRALLOC_CONSUMER_GPU_OR_DISPLAY)
291 {
292 /* Fall-through. To be decided.*/
293 }
294 else if(consumer == MALI_GRALLOC_CONSUMER_GPU_EXCL)
295 {
296 /* Fall-through. To be decided.*/
297 }
298 else if(consumer == MALI_GRALLOC_CONSUMER_VIDEO_ENCODER)
299 {
300 /* Fall-through. To be decided.*/
301 }
302 }
303 return internal_format;
304}
305
306static uint64_t decode_internal_format(int req_format)
307{
308 uint64_t internal_format, me_mask, base_format, mapped_base_format;
309 uint64_t ignore_mask;
310
311 internal_format = GRALLOC_PRIVATE_FORMAT_UNWRAP(req_format);
312
313 me_mask = internal_format & MALI_GRALLOC_INTFMT_ME_EXT_MASK;
314 if(me_mask > 0 && ((me_mask - 1) & me_mask) != 0)
315 {
316 ALOGE("Internal format contains multiple mutually exclusive modifier bits: %" PRIx64, internal_format);
317 internal_format = 0;
318 goto out;
319 }
320
321 base_format = internal_format & MALI_GRALLOC_INTFMT_FMT_MASK;
322
323 /* Even though private format allocations are intended to be for specific
324 * formats, certain test cases uses the flexible formats that needs to be mapped
325 * to internal ones.
326 */
327 mapped_base_format = map_flex_formats((uint32_t ) base_format, &ignore_mask);
328
329 /* Validate the internal base format passed in */
330 switch(mapped_base_format)
331 {
332 case MALI_GRALLOC_FORMAT_INTERNAL_RGBA_8888:
333 case MALI_GRALLOC_FORMAT_INTERNAL_RGBX_8888:
334 case MALI_GRALLOC_FORMAT_INTERNAL_RGB_888:
335 case MALI_GRALLOC_FORMAT_INTERNAL_RGB_565:
336 case MALI_GRALLOC_FORMAT_INTERNAL_BGRA_8888:
337 case MALI_GRALLOC_FORMAT_INTERNAL_YV12:
338 case MALI_GRALLOC_FORMAT_INTERNAL_Y8:
339 case MALI_GRALLOC_FORMAT_INTERNAL_Y16:
340 case MALI_GRALLOC_FORMAT_INTERNAL_RAW16:
341 case MALI_GRALLOC_FORMAT_INTERNAL_RAW12:
342 case MALI_GRALLOC_FORMAT_INTERNAL_RAW10:
343 case MALI_GRALLOC_FORMAT_INTERNAL_BLOB:
344 case MALI_GRALLOC_FORMAT_INTERNAL_NV12:
345 case MALI_GRALLOC_FORMAT_INTERNAL_NV21:
346 case MALI_GRALLOC_FORMAT_INTERNAL_YUV422_8BIT:
347 case MALI_GRALLOC_FORMAT_INTERNAL_Y0L2:
348 case MALI_GRALLOC_FORMAT_INTERNAL_P010:
349 case MALI_GRALLOC_FORMAT_INTERNAL_P210:
350 case MALI_GRALLOC_FORMAT_INTERNAL_Y210:
351 case MALI_GRALLOC_FORMAT_INTERNAL_Y410:
352 if(mapped_base_format != base_format)
353 {
354 internal_format = (internal_format & MALI_GRALLOC_INTFMT_EXT_MASK) | mapped_base_format;
355 }
356 break;
357
358 default:
359 ALOGE("Internal base format requested is unrecognized: %" PRIx64 ,internal_format);
360 internal_format = 0;
361 break;
362 }
363out:
364 return internal_format;
365}
366
367static bool determine_producer(mali_gralloc_producer_type *producer, uint64_t *producer_runtime_mask, int req_format, int usage)
368{
369 bool rval = true;
370
371 /* Default to GPU */
372 *producer = MALI_GRALLOC_PRODUCER_GPU;
373
374 if(usage & (GRALLOC_USAGE_SW_READ_MASK | GRALLOC_USAGE_SW_WRITE_MASK))
375 {
376 rval = false;
377 }
378 else if(usage & GRALLOC_USAGE_HW_RENDER)
379 {
380 if(is_android_yuv_format(req_format))
381 {
382 if(gpu_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_YUV_NOWRITE)
383 {
384 *producer_runtime_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
385 }
386 else
387 {
388 /* All GPUs that can write YUV AFBC can only do it in 16x16, optionally with tiled */
389 *producer_runtime_mask &= ~(MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK | MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_WIDEBLK);
390 }
391 }
392 *producer = MALI_GRALLOC_PRODUCER_GPU;
393 }
394 else if(usage & GRALLOC_USAGE_HW_CAMERA_MASK)
395 {
396 *producer = MALI_GRALLOC_PRODUCER_CAMERA;
397 }
398 /* HW_TEXTURE+HW_COMPOSER+EXTERNAL_DISP is a definition set by
399 * stagefright for "video decoder". We check for it here.
400 */
401 else if((usage & (GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_HW_COMPOSER | GRALLOC_USAGE_EXTERNAL_DISP)) ==
402 (GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_HW_COMPOSER | GRALLOC_USAGE_EXTERNAL_DISP))
403 {
404 *producer = MALI_GRALLOC_PRODUCER_VIDEO_DECODER;
405 }
406
407 return rval;
408}
409
410static bool determine_consumer(mali_gralloc_consumer_type *consumer, uint64_t *consumer_runtime_mask, int req_format, int usage)
411{
412 bool rval = true;
413
414 /* Default to GPU */
415 *consumer = MALI_GRALLOC_CONSUMER_GPU_EXCL;
416
417 if(usage & (GRALLOC_USAGE_SW_READ_MASK | GRALLOC_USAGE_SW_WRITE_MASK))
418 {
419 rval = false;
420 }
421 /* When usage explicitly targets a consumer, as it does with GRALLOC_USAGE_HW_FB,
422 * we pick DPU even if there are no runtime capabilities present.
423 */
424 else if( usage & GRALLOC_USAGE_HW_FB )
425 {
426 *consumer = MALI_GRALLOC_CONSUMER_GPU_OR_DISPLAY;
427 }
428 else if(usage & GRALLOC_USAGE_HW_VIDEO_ENCODER)
429 {
430 if((vpu_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_YUV_NOREAD) &&
431 is_android_yuv_format(req_format))
432 {
433 *consumer_runtime_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
434 }
435 *consumer = MALI_GRALLOC_CONSUMER_VIDEO_ENCODER;
436 }
437 /* GRALLOC_USAGE_HW_COMPOSER is by default applied by SurfaceFlinger so we can't exclusively rely on it
438 * to determine consumer. When a buffer is targeted for either we reject the DPU when it lacks
439 * runtime capabilities, in favor of the more capable GPU.
440 */
441 else if((usage & (GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_HW_COMPOSER )) == (GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_HW_COMPOSER ) &&
442 dpu_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT)
443 {
444 *consumer = MALI_GRALLOC_CONSUMER_GPU_OR_DISPLAY;
445 }
446 else if(usage & GRALLOC_USAGE_HW_TEXTURE)
447 {
448 *consumer = MALI_GRALLOC_CONSUMER_GPU_EXCL;
449 }
450 return rval;
451}
452
453/*
454 * Here we determine format capabilities for the 4 IPs we support.
455 * For now these are controlled by build defines, but in the future
456 * they should be read out from each user-space driver.
457 */
458static void determine_format_capabilities()
459{
460 /* Loading libraries can take some time and
461 * we may see many allocations at boot.
462 */
463 pthread_mutex_lock(&caps_init_mutex);
464
465 if(runtime_caps_read)
466 {
467 goto already_init;
468 }
469
470 memset((void*) &dpu_runtime_caps,0,sizeof(dpu_runtime_caps));
471 memset((void*) &vpu_runtime_caps,0,sizeof(vpu_runtime_caps));
472 memset((void*) &gpu_runtime_caps,0,sizeof(gpu_runtime_caps));
473 memset((void*) &cam_runtime_caps,0,sizeof(cam_runtime_caps));
474
475 /* Determine DPU format capabilities */
476 if(!get_block_capabilities(true, "hwcomposer", &dpu_runtime_caps))
477 {
478#if MALI_DISPLAY_VERSION >= 500
479 dpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT;
480 dpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC;
481
482#if MALI_DISPLAY_VERSION >= 550
483 dpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK;
484#endif
485#endif
486 }
487
488 /* Determine GPU format capabilities */
489 if(access(MALI_GRALLOC_GPU_LIBRARY_PATH1 MALI_GRALLOC_GPU_LIB_NAME,R_OK) == 0)
490 {
491 get_block_capabilities(false, MALI_GRALLOC_GPU_LIBRARY_PATH1 MALI_GRALLOC_GPU_LIB_NAME, &gpu_runtime_caps);
492 }
493 else if(access(MALI_GRALLOC_GPU_LIBRARY_PATH2 MALI_GRALLOC_GPU_LIB_NAME,R_OK) == 0)
494 {
495 get_block_capabilities(false, MALI_GRALLOC_GPU_LIBRARY_PATH2 MALI_GRALLOC_GPU_LIB_NAME, &gpu_runtime_caps);
496 }
497
498 if((gpu_runtime_caps.caps_mask & MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT) == 0)
499 {
500 ALOGW("Failed to find GPU block configuration in %s. Using static build configuration.", MALI_GRALLOC_GPU_LIB_NAME);
501
502#if MALI_GPU_SUPPORT_AFBC_BASIC == 1
503 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT;
504 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC;
505
506 /* Need to verify when to remove this */
507 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_YUV_NOWRITE;
508
509#if MALI_SUPPORT_AFBC_SPLITBLK == 1
510 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK;
511#endif
512
513#if MALI_SUPPORT_AFBC_WIDEBLK == 1
514 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK;
515 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_WIDEBLK;
516#endif
517
518#if MALI_USE_YUV_AFBC_WIDEBLK != 1
519 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_WIDEBLK_YUV_DISABLE;
520#endif
521
522#if MALI_SUPPORT_AFBC_TILED_HEADERS == 1
523 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_SPLITBLK;
524 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_WIDEBLK;
525 gpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS;
526#endif
527#endif /* MALI_GPU_SUPPORT_AFBC_BASIC == 1 */
528 }
529
530 /* Determine VPU format capabilities */
531#if MALI_VIDEO_VERSION == 500 || MALI_VIDEO_VERSION == 550
532 vpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT;
533 vpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC;
534 vpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_YUV_NOREAD;
535#endif
536
537#if MALI_VIDEO_VERSION == 61
538 vpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_OPTIONS_PRESENT;
539 vpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_BASIC;
540 vpu_runtime_caps.caps_mask |= MALI_GRALLOC_FORMAT_CAPABILITY_AFBC_TILED_HEADERS;
541#endif
542
543
544 /* Build specific capability changes */
545#if GRALLOC_ARM_NO_EXTERNAL_AFBC == 1
546 {
547 dpu_runtime_caps.caps_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
548 gpu_runtime_caps.caps_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
549 vpu_runtime_caps.caps_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
550 cam_runtime_caps.caps_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
551 }
552#endif
553
554 runtime_caps_read = true;
555
556already_init:
557 pthread_mutex_unlock(&caps_init_mutex);
558
559 ALOGV("GPU format capabilities 0x%" PRIx64 , gpu_runtime_caps.caps_mask);
560 ALOGV("DPU format capabilities 0x%" PRIx64 , dpu_runtime_caps.caps_mask);
561 ALOGV("VPU format capabilities 0x%" PRIx64 , vpu_runtime_caps.caps_mask);
562 ALOGV("CAM format capabilities 0x%" PRIx64 , cam_runtime_caps.caps_mask);
563}
564
565uint64_t mali_gralloc_select_format(int req_format, int usage, int buffer_size)
566{
567 uint64_t internal_format = 0;
568 mali_gralloc_consumer_type consumer;
569 mali_gralloc_producer_type producer;
570 uint64_t producer_runtime_mask = ~(0ULL);
571 uint64_t consumer_runtime_mask = ~(0ULL);
572 int req_format_mapped=0;
573
574 if(!runtime_caps_read)
575 {
576 /*
577 * It is better to initialize these when needed because
578 * not all processes allocates memory.
579 */
580 determine_format_capabilities();
581 }
582
583 /* A unique usage specifies that an internal format is in req_format */
584 if(usage & MALI_GRALLOC_USAGE_PRIVATE_FORMAT)
585 {
586 internal_format = decode_internal_format(req_format);
587 goto out;
588 }
589
590 /* Re-map special Android formats */
591 req_format_mapped = map_flex_formats(req_format, &producer_runtime_mask);
592
593 /* Determine producer/consumer */
594 if(!determine_producer(&producer, &producer_runtime_mask, req_format, usage) ||
595 !determine_consumer(&consumer, &consumer_runtime_mask, req_format, usage))
596 {
597 /* Failing to determine producer/consumer usually means
598 * client has requested sw rendering.
599 */
600 internal_format = req_format_mapped;
601 goto out;
602 }
603
604 /*
605 * Determine runtime capability limitations
606 */
607
608 /* Disable AFBC based on unique usage */
609 if ((usage & MALI_GRALLOC_USAGE_NO_AFBC) == MALI_GRALLOC_USAGE_NO_AFBC)
610 {
611 if(is_android_yuv_format(req_format_mapped))
612 {
613 ALOGE("It is invalid to specify NO_AFBC usage flags when allocating YUV formats.\
614 Requested fmt: 0x%08X Re-Mapped fmt: 0x%08X",req_format,req_format_mapped);
615 internal_format = 0;
616 goto out;
617 }
618 producer_runtime_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
619 }
620 /* Disable AFBC based on buffer dimensions */
621 else if(!is_afbc_allowed(buffer_size))
622 {
623 producer_runtime_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
624 }
625 else if(!is_afbc_supported(req_format_mapped))
626 {
627 producer_runtime_mask &= ~MALI_GRALLOC_FORMAT_CAPABILITY_AFBCENABLE_MASK;
628 }
629
630 /* Automatically select format in case producer/consumer identified */
631 internal_format = determine_best_format(req_format_mapped, producer, consumer, producer_runtime_mask, consumer_runtime_mask);
632
633out:
634 ALOGV("mali_gralloc_select_format: req_format=0x%08X req_fmt_mapped=0x%08X internal_format=0x%" PRIx64 " usage=0x%08X",req_format, req_format_mapped, internal_format, usage);
635
636 return internal_format;
637}
638
639extern "C"
640{
641void mali_gralloc_get_gpu_caps(struct mali_gralloc_format_caps *gpu_caps)
642{
643 if(gpu_caps != NULL)
644 {
645 if(!runtime_caps_read)
646 {
647 determine_format_capabilities();
648 }
649 memcpy(gpu_caps,(void*) &gpu_runtime_caps,sizeof(struct mali_gralloc_format_caps));
650 }
651}
652}