• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2008 VMware, Inc.
3  * Copyright (C) 2014 Broadcom
4  * Copyright (C) 2018 Alyssa Rosenzweig
5  * Copyright (C) 2019 Collabora, Ltd.
6  * Copyright (C) 2012 Rob Clark <robclark@freedesktop.org>
7  *
8  * Permission is hereby granted, free of charge, to any person obtaining a
9  * copy of this software and associated documentation files (the "Software"),
10  * to deal in the Software without restriction, including without limitation
11  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
12  * and/or sell copies of the Software, and to permit persons to whom the
13  * Software is furnished to do so, subject to the following conditions:
14  *
15  * The above copyright notice and this permission notice (including the next
16  * paragraph) shall be included in all copies or substantial portions of the
17  * Software.
18  *
19  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
22  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
25  * SOFTWARE.
26  *
27  */
28 
29 #include "draw/draw_context.h"
30 #include "pipe/p_defines.h"
31 #include "pipe/p_screen.h"
32 #include "util/format/u_format.h"
33 #include "util/format/u_format_s3tc.h"
34 #include "util/os_time.h"
35 #include "util/u_debug.h"
36 #include "util/u_memory.h"
37 #include "util/u_process.h"
38 #include "util/u_screen.h"
39 #include "util/u_video.h"
40 
41 #include <fcntl.h>
42 
43 #include "drm-uapi/drm_fourcc.h"
44 #include "drm-uapi/panfrost_drm.h"
45 
46 #include "decode.h"
47 #include "pan_bo.h"
48 #include "pan_fence.h"
49 #include "pan_public.h"
50 #include "pan_resource.h"
51 #include "pan_screen.h"
52 #include "pan_shader.h"
53 #include "pan_util.h"
54 
55 #include "pan_context.h"
56 
57 #define DEFAULT_MAX_AFBC_PACKING_RATIO 90
58 
59 /* clang-format off */
60 static const struct debug_named_value panfrost_debug_options[] = {
61    {"perf",       PAN_DBG_PERF,     "Enable performance warnings"},
62    {"trace",      PAN_DBG_TRACE,    "Trace the command stream"},
63    {"dirty",      PAN_DBG_DIRTY,    "Always re-emit all state"},
64    {"sync",       PAN_DBG_SYNC,     "Wait for each job's completion and abort on GPU faults"},
65    {"nofp16",     PAN_DBG_NOFP16,    "Disable 16-bit support"},
66    {"gl3",        PAN_DBG_GL3,      "Enable experimental GL 3.x implementation, up to 3.3"},
67    {"noafbc",     PAN_DBG_NO_AFBC,  "Disable AFBC support"},
68    {"crc",        PAN_DBG_CRC,      "Enable transaction elimination"},
69    {"msaa16",     PAN_DBG_MSAA16,   "Enable MSAA 8x and 16x support"},
70    {"linear",     PAN_DBG_LINEAR,   "Force linear textures"},
71    {"nocache",    PAN_DBG_NO_CACHE, "Disable BO cache"},
72    {"dump",       PAN_DBG_DUMP,     "Dump all graphics memory"},
73 #ifdef PAN_DBG_OVERFLOW
74    {"overflow",   PAN_DBG_OVERFLOW, "Check for buffer overflows in pool uploads"},
75 #endif
76    {"yuv",        PAN_DBG_YUV,      "Tint YUV textures with blue for 1-plane and green for 2-plane"},
77    {"forcepack",  PAN_DBG_FORCE_PACK,  "Force packing of AFBC textures on upload"},
78    DEBUG_NAMED_VALUE_END
79 };
80 /* clang-format on */
81 
82 static const char *
panfrost_get_name(struct pipe_screen * screen)83 panfrost_get_name(struct pipe_screen *screen)
84 {
85    return pan_device(screen)->model->name;
86 }
87 
88 static const char *
panfrost_get_vendor(struct pipe_screen * screen)89 panfrost_get_vendor(struct pipe_screen *screen)
90 {
91    return "Mesa";
92 }
93 
94 static const char *
panfrost_get_device_vendor(struct pipe_screen * screen)95 panfrost_get_device_vendor(struct pipe_screen *screen)
96 {
97    return "Arm";
98 }
99 
100 static int
panfrost_get_param(struct pipe_screen * screen,enum pipe_cap param)101 panfrost_get_param(struct pipe_screen *screen, enum pipe_cap param)
102 {
103    struct panfrost_device *dev = pan_device(screen);
104 
105    /* Our GL 3.x implementation is WIP */
106    bool is_gl3 = dev->debug & PAN_DBG_GL3;
107 
108    /* Native MRT is introduced with v5 */
109    bool has_mrt = (dev->arch >= 5);
110 
111    /* Only kernel drivers >= 1.1 can allocate HEAP BOs */
112    bool has_heap = panfrost_device_kmod_version_major(dev) > 1 ||
113                    panfrost_device_kmod_version_minor(dev) >= 1;
114 
115    switch (param) {
116    case PIPE_CAP_NPOT_TEXTURES:
117    case PIPE_CAP_MIXED_COLOR_DEPTH_BITS:
118    case PIPE_CAP_FRAGMENT_SHADER_TEXTURE_LOD:
119    case PIPE_CAP_VERTEX_COLOR_UNCLAMPED:
120    case PIPE_CAP_DEPTH_CLIP_DISABLE:
121    case PIPE_CAP_DEPTH_CLIP_DISABLE_SEPARATE:
122    case PIPE_CAP_MIXED_FRAMEBUFFER_SIZES:
123    case PIPE_CAP_FRONTEND_NOOP:
124    case PIPE_CAP_SAMPLE_SHADING:
125    case PIPE_CAP_FRAGMENT_SHADER_DERIVATIVES:
126    case PIPE_CAP_FRAMEBUFFER_NO_ATTACHMENT:
127    case PIPE_CAP_QUADS_FOLLOW_PROVOKING_VERTEX_CONVENTION:
128    case PIPE_CAP_SHADER_PACK_HALF_FLOAT:
129    case PIPE_CAP_HAS_CONST_BW:
130       return 1;
131 
132    case PIPE_CAP_MAX_RENDER_TARGETS:
133    case PIPE_CAP_FBFETCH:
134    case PIPE_CAP_FBFETCH_COHERENT:
135       return has_mrt ? 8 : 1;
136 
137    case PIPE_CAP_MAX_DUAL_SOURCE_RENDER_TARGETS:
138       return 1;
139 
140    case PIPE_CAP_OCCLUSION_QUERY:
141    case PIPE_CAP_PRIMITIVE_RESTART:
142    case PIPE_CAP_PRIMITIVE_RESTART_FIXED_INDEX:
143       return true;
144 
145    case PIPE_CAP_ANISOTROPIC_FILTER:
146       return panfrost_device_gpu_rev(dev) >= dev->model->min_rev_anisotropic;
147 
148    /* Compile side is done for Bifrost, Midgard TODO. Needs some kernel
149     * work to turn on, since CYCLE_COUNT_START needs to be issued. In
150     * kbase, userspace requests this via BASE_JD_REQ_PERMON. There is not
151     * yet way to request this with mainline TODO */
152    case PIPE_CAP_SHADER_CLOCK:
153       return 0;
154 
155    case PIPE_CAP_VS_INSTANCEID:
156    case PIPE_CAP_TEXTURE_MULTISAMPLE:
157    case PIPE_CAP_SURFACE_SAMPLE_COUNT:
158       return true;
159 
160    case PIPE_CAP_SAMPLER_VIEW_TARGET:
161    case PIPE_CAP_CLIP_HALFZ:
162    case PIPE_CAP_POLYGON_OFFSET_CLAMP:
163    case PIPE_CAP_TEXTURE_SWIZZLE:
164    case PIPE_CAP_TEXTURE_MIRROR_CLAMP_TO_EDGE:
165    case PIPE_CAP_VERTEX_ELEMENT_INSTANCE_DIVISOR:
166    case PIPE_CAP_BLEND_EQUATION_SEPARATE:
167    case PIPE_CAP_INDEP_BLEND_ENABLE:
168    case PIPE_CAP_INDEP_BLEND_FUNC:
169    case PIPE_CAP_GENERATE_MIPMAP:
170    case PIPE_CAP_ACCELERATED:
171    case PIPE_CAP_UMA:
172    case PIPE_CAP_TEXTURE_FLOAT_LINEAR:
173    case PIPE_CAP_TEXTURE_HALF_FLOAT_LINEAR:
174    case PIPE_CAP_SHADER_ARRAY_COMPONENTS:
175    case PIPE_CAP_TEXTURE_BUFFER_OBJECTS:
176    case PIPE_CAP_PACKED_UNIFORMS:
177    case PIPE_CAP_IMAGE_LOAD_FORMATTED:
178    case PIPE_CAP_CUBE_MAP_ARRAY:
179    case PIPE_CAP_COMPUTE:
180    case PIPE_CAP_INT64:
181       return 1;
182 
183    case PIPE_CAP_COPY_BETWEEN_COMPRESSED_AND_PLAIN_FORMATS:
184       return 1;
185 
186    case PIPE_CAP_MAX_STREAM_OUTPUT_BUFFERS:
187       return PIPE_MAX_SO_BUFFERS;
188 
189    case PIPE_CAP_MAX_STREAM_OUTPUT_SEPARATE_COMPONENTS:
190    case PIPE_CAP_MAX_STREAM_OUTPUT_INTERLEAVED_COMPONENTS:
191       return PIPE_MAX_SO_OUTPUTS;
192 
193    case PIPE_CAP_STREAM_OUTPUT_PAUSE_RESUME:
194    case PIPE_CAP_STREAM_OUTPUT_INTERLEAVE_BUFFERS:
195       return 1;
196 
197    case PIPE_CAP_MAX_TEXTURE_ARRAY_LAYERS:
198       return 2048;
199 
200    case PIPE_CAP_GLSL_FEATURE_LEVEL:
201    case PIPE_CAP_GLSL_FEATURE_LEVEL_COMPATIBILITY:
202       return is_gl3 ? 330 : 140;
203    case PIPE_CAP_ESSL_FEATURE_LEVEL:
204       return dev->arch >= 6 ? 320 : 310;
205 
206    case PIPE_CAP_CONSTANT_BUFFER_OFFSET_ALIGNMENT:
207       return 16;
208 
209    /* v7 (only) restricts component orders with AFBC. To workaround, we
210     * compose format swizzles with texture swizzles. pan_texture.c motsly
211     * handles this but we need to fix up the border colour.
212     */
213    case PIPE_CAP_TEXTURE_BORDER_COLOR_QUIRK:
214       if (dev->arch == 7)
215          return PIPE_QUIRK_TEXTURE_BORDER_COLOR_SWIZZLE_FREEDRENO;
216       else
217          return 0;
218 
219    case PIPE_CAP_MAX_TEXEL_BUFFER_ELEMENTS_UINT:
220       return 65536;
221 
222    /* Must be at least 64 for correct behaviour */
223    case PIPE_CAP_TEXTURE_BUFFER_OFFSET_ALIGNMENT:
224       return 64;
225 
226    case PIPE_CAP_QUERY_TIMESTAMP:
227       return is_gl3;
228 
229    /* The hardware requires element alignment for data conversion to work
230     * as expected. If data conversion is not required, this restriction is
231     * lifted on Midgard at a performance penalty. We conservatively
232     * require element alignment for vertex buffers, using u_vbuf to
233     * translate to match the hardware requirement.
234     *
235     * This is less heavy-handed than the 4BYTE_ALIGNED_ONLY caps, which
236     * would needlessly require alignment even for 8-bit formats.
237     */
238    case PIPE_CAP_VERTEX_ATTRIB_ELEMENT_ALIGNED_ONLY:
239       return 1;
240 
241    case PIPE_CAP_MAX_TEXTURE_2D_SIZE:
242       return 1 << (MAX_MIP_LEVELS - 1);
243 
244    case PIPE_CAP_MAX_TEXTURE_3D_LEVELS:
245    case PIPE_CAP_MAX_TEXTURE_CUBE_LEVELS:
246       return MAX_MIP_LEVELS;
247 
248    case PIPE_CAP_FS_COORD_ORIGIN_LOWER_LEFT:
249    case PIPE_CAP_FS_COORD_PIXEL_CENTER_INTEGER:
250       /* Hardware is upper left. Pixel center at (0.5, 0.5) */
251       return 0;
252 
253    case PIPE_CAP_FS_COORD_ORIGIN_UPPER_LEFT:
254    case PIPE_CAP_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
255    case PIPE_CAP_TGSI_TEXCOORD:
256       return 1;
257 
258    /* We would prefer varyings on Midgard, but proper sysvals on Bifrost */
259    case PIPE_CAP_FS_FACE_IS_INTEGER_SYSVAL:
260    case PIPE_CAP_FS_POSITION_IS_SYSVAL:
261    case PIPE_CAP_FS_POINT_IS_SYSVAL:
262       return dev->arch >= 6;
263 
264    case PIPE_CAP_SEAMLESS_CUBE_MAP:
265    case PIPE_CAP_SEAMLESS_CUBE_MAP_PER_TEXTURE:
266       return true;
267 
268    case PIPE_CAP_MAX_VERTEX_ELEMENT_SRC_OFFSET:
269       return 0xffff;
270 
271    case PIPE_CAP_TEXTURE_TRANSFER_MODES:
272       return 0;
273 
274    case PIPE_CAP_ENDIANNESS:
275       return PIPE_ENDIAN_NATIVE;
276 
277    case PIPE_CAP_MAX_TEXTURE_GATHER_COMPONENTS:
278       return 4;
279 
280    case PIPE_CAP_MIN_TEXTURE_GATHER_OFFSET:
281       return -8;
282 
283    case PIPE_CAP_MAX_TEXTURE_GATHER_OFFSET:
284       return 7;
285 
286    case PIPE_CAP_VIDEO_MEMORY: {
287       uint64_t system_memory;
288 
289       if (!os_get_total_physical_memory(&system_memory))
290          return 0;
291 
292       return (int)(system_memory >> 20);
293    }
294 
295    case PIPE_CAP_SHADER_STENCIL_EXPORT:
296    case PIPE_CAP_CONDITIONAL_RENDER:
297    case PIPE_CAP_CONDITIONAL_RENDER_INVERTED:
298       return true;
299 
300    case PIPE_CAP_SHADER_BUFFER_OFFSET_ALIGNMENT:
301       return 4;
302 
303    case PIPE_CAP_MAX_VARYINGS:
304       /* Return the GLSL maximum. The internal maximum
305        * PAN_MAX_VARYINGS accommodates internal varyings. */
306       return MAX_VARYING;
307 
308    /* Removed in v6 (Bifrost) */
309    case PIPE_CAP_GL_CLAMP:
310    case PIPE_CAP_TEXTURE_MIRROR_CLAMP:
311    case PIPE_CAP_ALPHA_TEST:
312       return dev->arch <= 5;
313 
314    /* Removed in v9 (Valhall). PRIMTIIVE_RESTART_FIXED_INDEX is of course
315     * still supported as it is core GLES3.0 functionality
316     */
317    case PIPE_CAP_EMULATE_NONFIXED_PRIMITIVE_RESTART:
318       return dev->arch >= 9;
319 
320    case PIPE_CAP_FLATSHADE:
321    case PIPE_CAP_TWO_SIDED_COLOR:
322    case PIPE_CAP_CLIP_PLANES:
323       return 0;
324 
325    case PIPE_CAP_PACKED_STREAM_OUTPUT:
326       return 0;
327 
328    case PIPE_CAP_VIEWPORT_TRANSFORM_LOWERED:
329    case PIPE_CAP_PSIZ_CLAMPED:
330       return 1;
331 
332    case PIPE_CAP_NIR_IMAGES_AS_DEREF:
333       return 0;
334 
335    case PIPE_CAP_DRAW_INDIRECT:
336       return has_heap;
337 
338    case PIPE_CAP_START_INSTANCE:
339    case PIPE_CAP_DRAW_PARAMETERS:
340       return pan_is_bifrost(dev);
341 
342    case PIPE_CAP_SUPPORTED_PRIM_MODES:
343    case PIPE_CAP_SUPPORTED_PRIM_MODES_WITH_RESTART: {
344       /* Mali supports GLES and QUADS. Midgard and v6 Bifrost
345        * support more */
346       uint32_t modes = BITFIELD_MASK(MESA_PRIM_QUADS + 1);
347 
348       if (dev->arch <= 6) {
349          modes |= BITFIELD_BIT(MESA_PRIM_QUAD_STRIP);
350          modes |= BITFIELD_BIT(MESA_PRIM_POLYGON);
351       }
352 
353       if (dev->arch >= 9) {
354          /* Although Valhall is supposed to support quads, they
355           * don't seem to work correctly. Disable to fix
356           * arb-provoking-vertex-render.
357           */
358          modes &= ~BITFIELD_BIT(MESA_PRIM_QUADS);
359       }
360 
361       return modes;
362    }
363 
364    case PIPE_CAP_IMAGE_STORE_FORMATTED:
365       return 1;
366 
367    case PIPE_CAP_NATIVE_FENCE_FD:
368       return 1;
369 
370    default:
371       return u_pipe_screen_get_param_defaults(screen, param);
372    }
373 }
374 
375 static int
panfrost_get_shader_param(struct pipe_screen * screen,enum pipe_shader_type shader,enum pipe_shader_cap param)376 panfrost_get_shader_param(struct pipe_screen *screen,
377                           enum pipe_shader_type shader,
378                           enum pipe_shader_cap param)
379 {
380    struct panfrost_device *dev = pan_device(screen);
381    bool is_nofp16 = dev->debug & PAN_DBG_NOFP16;
382 
383    switch (shader) {
384    case PIPE_SHADER_VERTEX:
385    case PIPE_SHADER_FRAGMENT:
386    case PIPE_SHADER_COMPUTE:
387       break;
388    default:
389       return 0;
390    }
391 
392    /* We only allow observable side effects (memory writes) in compute and
393     * fragment shaders. Side effects in the geometry pipeline cause
394     * trouble with IDVS and conflict with our transform feedback lowering.
395     */
396    bool allow_side_effects = (shader != PIPE_SHADER_VERTEX);
397 
398    switch (param) {
399    case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
400    case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
401    case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
402    case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
403       return 16384; /* arbitrary */
404 
405    case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
406       return 1024; /* arbitrary */
407 
408    case PIPE_SHADER_CAP_MAX_INPUTS:
409       /* Used as ABI on Midgard */
410       return 16;
411 
412    case PIPE_SHADER_CAP_MAX_OUTPUTS:
413       return shader == PIPE_SHADER_FRAGMENT ? 8 : PIPE_MAX_ATTRIBS;
414 
415    case PIPE_SHADER_CAP_MAX_TEMPS:
416       return 256; /* arbitrary */
417 
418    case PIPE_SHADER_CAP_MAX_CONST_BUFFER0_SIZE:
419       return 16 * 1024 * sizeof(float);
420 
421    case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
422       STATIC_ASSERT(PAN_MAX_CONST_BUFFERS < 0x100);
423       return PAN_MAX_CONST_BUFFERS;
424 
425    case PIPE_SHADER_CAP_CONT_SUPPORTED:
426       return 0;
427 
428    case PIPE_SHADER_CAP_INDIRECT_INPUT_ADDR:
429       return 1;
430    case PIPE_SHADER_CAP_INDIRECT_OUTPUT_ADDR:
431       return 0;
432 
433    case PIPE_SHADER_CAP_INDIRECT_TEMP_ADDR:
434       return dev->arch >= 6;
435 
436    case PIPE_SHADER_CAP_INDIRECT_CONST_ADDR:
437       return 1;
438 
439    case PIPE_SHADER_CAP_SUBROUTINES:
440       return 0;
441 
442    case PIPE_SHADER_CAP_TGSI_SQRT_SUPPORTED:
443       return 0;
444 
445    case PIPE_SHADER_CAP_INTEGERS:
446       return 1;
447 
448       /* The Bifrost compiler supports full 16-bit. Midgard could but int16
449        * support is untested, so restrict INT16 to Bifrost. Midgard
450        * architecturally cannot support fp16 derivatives. */
451 
452    case PIPE_SHADER_CAP_FP16:
453    case PIPE_SHADER_CAP_GLSL_16BIT_CONSTS:
454       return !is_nofp16;
455    case PIPE_SHADER_CAP_FP16_DERIVATIVES:
456    case PIPE_SHADER_CAP_FP16_CONST_BUFFERS:
457       return dev->arch >= 6 && !is_nofp16;
458    case PIPE_SHADER_CAP_INT16:
459       /* Blocked on https://gitlab.freedesktop.org/mesa/mesa/-/issues/6075 */
460       return false;
461 
462    case PIPE_SHADER_CAP_INT64_ATOMICS:
463    case PIPE_SHADER_CAP_TGSI_ANY_INOUT_DECL_RANGE:
464       return 0;
465 
466    case PIPE_SHADER_CAP_MAX_TEXTURE_SAMPLERS:
467       STATIC_ASSERT(PIPE_MAX_SAMPLERS < 0x10000);
468       return PIPE_MAX_SAMPLERS;
469 
470    case PIPE_SHADER_CAP_MAX_SAMPLER_VIEWS:
471       STATIC_ASSERT(PIPE_MAX_SHADER_SAMPLER_VIEWS < 0x10000);
472       return PIPE_MAX_SHADER_SAMPLER_VIEWS;
473 
474    case PIPE_SHADER_CAP_SUPPORTED_IRS:
475       return (1 << PIPE_SHADER_IR_NIR);
476 
477    case PIPE_SHADER_CAP_MAX_SHADER_BUFFERS:
478       return allow_side_effects ? 16 : 0;
479 
480    case PIPE_SHADER_CAP_MAX_SHADER_IMAGES:
481       return allow_side_effects ? PIPE_MAX_SHADER_IMAGES : 0;
482 
483    case PIPE_SHADER_CAP_MAX_HW_ATOMIC_COUNTERS:
484    case PIPE_SHADER_CAP_MAX_HW_ATOMIC_COUNTER_BUFFERS:
485       return 0;
486 
487    default:
488       return 0;
489    }
490 
491    return 0;
492 }
493 
494 static float
panfrost_get_paramf(struct pipe_screen * screen,enum pipe_capf param)495 panfrost_get_paramf(struct pipe_screen *screen, enum pipe_capf param)
496 {
497    switch (param) {
498    case PIPE_CAPF_MIN_LINE_WIDTH:
499    case PIPE_CAPF_MIN_LINE_WIDTH_AA:
500    case PIPE_CAPF_MIN_POINT_SIZE:
501    case PIPE_CAPF_MIN_POINT_SIZE_AA:
502       return 1;
503 
504    case PIPE_CAPF_POINT_SIZE_GRANULARITY:
505    case PIPE_CAPF_LINE_WIDTH_GRANULARITY:
506       return 0.0625;
507 
508    case PIPE_CAPF_MAX_LINE_WIDTH:
509    case PIPE_CAPF_MAX_LINE_WIDTH_AA:
510    case PIPE_CAPF_MAX_POINT_SIZE:
511    case PIPE_CAPF_MAX_POINT_SIZE_AA:
512       return 4095.9375;
513 
514    case PIPE_CAPF_MAX_TEXTURE_ANISOTROPY:
515       return 16.0;
516 
517    case PIPE_CAPF_MAX_TEXTURE_LOD_BIAS:
518       return 16.0; /* arbitrary */
519 
520    case PIPE_CAPF_MIN_CONSERVATIVE_RASTER_DILATE:
521    case PIPE_CAPF_MAX_CONSERVATIVE_RASTER_DILATE:
522    case PIPE_CAPF_CONSERVATIVE_RASTER_DILATE_GRANULARITY:
523       return 0.0f;
524 
525    default:
526       debug_printf("Unexpected PIPE_CAPF %d query\n", param);
527       return 0.0;
528    }
529 }
530 
531 static uint32_t
pipe_to_pan_bind_flags(uint32_t pipe_bind_flags)532 pipe_to_pan_bind_flags(uint32_t pipe_bind_flags)
533 {
534    static_assert(PIPE_BIND_DEPTH_STENCIL == PAN_BIND_DEPTH_STENCIL, "");
535    static_assert(PIPE_BIND_RENDER_TARGET == PAN_BIND_RENDER_TARGET, "");
536    static_assert(PIPE_BIND_SAMPLER_VIEW == PAN_BIND_SAMPLER_VIEW, "");
537    static_assert(PIPE_BIND_VERTEX_BUFFER == PAN_BIND_VERTEX_BUFFER, "");
538 
539    return pipe_bind_flags & (PAN_BIND_DEPTH_STENCIL | PAN_BIND_RENDER_TARGET |
540                              PAN_BIND_VERTEX_BUFFER | PAN_BIND_SAMPLER_VIEW);
541 }
542 
543 /**
544  * Query format support for creating a texture, drawing surface, etc.
545  * \param format  the format to test
546  * \param type  one of PIPE_TEXTURE, PIPE_SURFACE
547  */
548 static bool
panfrost_is_format_supported(struct pipe_screen * screen,enum pipe_format format,enum pipe_texture_target target,unsigned sample_count,unsigned storage_sample_count,unsigned bind)549 panfrost_is_format_supported(struct pipe_screen *screen,
550                              enum pipe_format format,
551                              enum pipe_texture_target target,
552                              unsigned sample_count,
553                              unsigned storage_sample_count, unsigned bind)
554 {
555    struct panfrost_device *dev = pan_device(screen);
556 
557    assert(target == PIPE_BUFFER || target == PIPE_TEXTURE_1D ||
558           target == PIPE_TEXTURE_1D_ARRAY || target == PIPE_TEXTURE_2D ||
559           target == PIPE_TEXTURE_2D_ARRAY || target == PIPE_TEXTURE_RECT ||
560           target == PIPE_TEXTURE_3D || target == PIPE_TEXTURE_CUBE ||
561           target == PIPE_TEXTURE_CUBE_ARRAY);
562 
563    /* MSAA 2x gets rounded up to 4x. MSAA 8x/16x only supported on v5+.
564     * TODO: debug MSAA 8x/16x */
565 
566    switch (sample_count) {
567    case 0:
568    case 1:
569    case 4:
570       break;
571    case 8:
572    case 16:
573       if (dev->debug & PAN_DBG_MSAA16)
574          break;
575       else
576          return false;
577    default:
578       return false;
579    }
580 
581    if (MAX2(sample_count, 1) != MAX2(storage_sample_count, 1))
582       return false;
583 
584    /* Z16 causes dEQP failures on t720 */
585    if (format == PIPE_FORMAT_Z16_UNORM && dev->arch <= 4)
586       return false;
587 
588    /* Check we support the format with the given bind */
589 
590    unsigned pan_bind_flags = pipe_to_pan_bind_flags(bind);
591 
592    struct panfrost_format fmt = dev->formats[format];
593 
594    /* Also check that compressed texture formats are supported on this
595     * particular chip. They may not be depending on system integration
596     * differences. */
597 
598    bool supported =
599       panfrost_supports_compressed_format(dev, MALI_EXTRACT_INDEX(fmt.hw));
600 
601    if (!supported)
602       return false;
603 
604    return MALI_EXTRACT_INDEX(fmt.hw) && ((pan_bind_flags & ~fmt.bind) == 0);
605 }
606 
607 /* We always support linear and tiled operations, both external and internal.
608  * We support AFBC for a subset of formats, and colourspace transform for a
609  * subset of those. */
610 
611 static void
panfrost_walk_dmabuf_modifiers(struct pipe_screen * screen,enum pipe_format format,int max,uint64_t * modifiers,unsigned int * external_only,int * out_count,uint64_t test_modifier)612 panfrost_walk_dmabuf_modifiers(struct pipe_screen *screen,
613                                enum pipe_format format, int max,
614                                uint64_t *modifiers, unsigned int *external_only,
615                                int *out_count, uint64_t test_modifier)
616 {
617    /* Query AFBC status */
618    struct panfrost_device *dev = pan_device(screen);
619    bool afbc =
620       dev->has_afbc && panfrost_format_supports_afbc(dev->arch, format);
621    bool ytr = panfrost_afbc_can_ytr(format);
622    bool tiled_afbc = panfrost_afbc_can_tile(dev->arch);
623 
624    unsigned count = 0;
625 
626    for (unsigned i = 0; i < PAN_MODIFIER_COUNT; ++i) {
627       if (drm_is_afbc(pan_best_modifiers[i]) && !afbc)
628          continue;
629 
630       if ((pan_best_modifiers[i] & AFBC_FORMAT_MOD_YTR) && !ytr)
631          continue;
632 
633       if ((pan_best_modifiers[i] & AFBC_FORMAT_MOD_TILED) && !tiled_afbc)
634          continue;
635 
636       if (test_modifier != DRM_FORMAT_MOD_INVALID &&
637           test_modifier != pan_best_modifiers[i])
638          continue;
639 
640       if (max > (int)count) {
641          modifiers[count] = pan_best_modifiers[i];
642 
643          if (external_only)
644             external_only[count] = false;
645       }
646       count++;
647    }
648 
649    *out_count = count;
650 }
651 
652 static void
panfrost_query_dmabuf_modifiers(struct pipe_screen * screen,enum pipe_format format,int max,uint64_t * modifiers,unsigned int * external_only,int * out_count)653 panfrost_query_dmabuf_modifiers(struct pipe_screen *screen,
654                                 enum pipe_format format, int max,
655                                 uint64_t *modifiers,
656                                 unsigned int *external_only, int *out_count)
657 {
658    panfrost_walk_dmabuf_modifiers(screen, format, max, modifiers, external_only,
659                                   out_count, DRM_FORMAT_MOD_INVALID);
660 }
661 
662 static bool
panfrost_is_dmabuf_modifier_supported(struct pipe_screen * screen,uint64_t modifier,enum pipe_format format,bool * external_only)663 panfrost_is_dmabuf_modifier_supported(struct pipe_screen *screen,
664                                       uint64_t modifier,
665                                       enum pipe_format format,
666                                       bool *external_only)
667 {
668    uint64_t unused;
669    unsigned int uint_extern_only = 0;
670    int count;
671 
672    panfrost_walk_dmabuf_modifiers(screen, format, 1, &unused, &uint_extern_only,
673                                   &count, modifier);
674 
675    if (external_only)
676       *external_only = uint_extern_only ? true : false;
677 
678    return count > 0;
679 }
680 
681 static int
panfrost_get_compute_param(struct pipe_screen * pscreen,enum pipe_shader_ir ir_type,enum pipe_compute_cap param,void * ret)682 panfrost_get_compute_param(struct pipe_screen *pscreen,
683                            enum pipe_shader_ir ir_type,
684                            enum pipe_compute_cap param, void *ret)
685 {
686    struct panfrost_device *dev = pan_device(pscreen);
687    const char *const ir = "panfrost";
688 
689 #define RET(x)                                                                 \
690    do {                                                                        \
691       if (ret)                                                                 \
692          memcpy(ret, x, sizeof(x));                                            \
693       return sizeof(x);                                                        \
694    } while (0)
695 
696    switch (param) {
697    case PIPE_COMPUTE_CAP_ADDRESS_BITS:
698       RET((uint32_t[]){64});
699 
700    case PIPE_COMPUTE_CAP_IR_TARGET:
701       if (ret)
702          sprintf(ret, "%s", ir);
703       return strlen(ir) * sizeof(char);
704 
705    case PIPE_COMPUTE_CAP_GRID_DIMENSION:
706       RET((uint64_t[]){3});
707 
708    case PIPE_COMPUTE_CAP_MAX_GRID_SIZE:
709       RET(((uint64_t[]){65535, 65535, 65535}));
710 
711    case PIPE_COMPUTE_CAP_MAX_BLOCK_SIZE:
712       /* Unpredictable behaviour at larger sizes. Mali-G52 advertises
713        * 384x384x384.
714        *
715        * On Midgard, we don't allow more than 128 threads in each
716        * direction to match PIPE_COMPUTE_CAP_MAX_THREADS_PER_BLOCK.
717        * That still exceeds the minimum-maximum.
718        */
719       if (dev->arch >= 6)
720          RET(((uint64_t[]){256, 256, 256}));
721       else
722          RET(((uint64_t[]){128, 128, 128}));
723 
724    case PIPE_COMPUTE_CAP_MAX_THREADS_PER_BLOCK:
725       /* On Bifrost and newer, all GPUs can support at least 256 threads
726        * regardless of register usage, so we report 256.
727        *
728        * On Midgard, with maximum register usage, the maximum
729        * thread count is only 64. We would like to report 64 here, but
730        * the GLES3.1 spec minimum is 128, so we report 128 and limit
731        * the register allocation of affected compute kernels.
732        */
733       RET((uint64_t[]){dev->arch >= 6 ? 256 : 128});
734 
735    case PIPE_COMPUTE_CAP_MAX_GLOBAL_SIZE:
736       RET((uint64_t[]){1024 * 1024 * 512 /* Maybe get memory */});
737 
738    case PIPE_COMPUTE_CAP_MAX_LOCAL_SIZE:
739       RET((uint64_t[]){32768});
740 
741    case PIPE_COMPUTE_CAP_MAX_PRIVATE_SIZE:
742    case PIPE_COMPUTE_CAP_MAX_INPUT_SIZE:
743       RET((uint64_t[]){4096});
744 
745    case PIPE_COMPUTE_CAP_MAX_MEM_ALLOC_SIZE:
746       RET((uint64_t[]){1024 * 1024 * 512 /* Maybe get memory */});
747 
748    case PIPE_COMPUTE_CAP_MAX_CLOCK_FREQUENCY:
749       RET((uint32_t[]){800 /* MHz -- TODO */});
750 
751    case PIPE_COMPUTE_CAP_MAX_COMPUTE_UNITS:
752       RET((uint32_t[]){dev->core_count});
753 
754    case PIPE_COMPUTE_CAP_IMAGES_SUPPORTED:
755       RET((uint32_t[]){1});
756 
757    case PIPE_COMPUTE_CAP_SUBGROUP_SIZES:
758       RET((uint32_t[]){pan_subgroup_size(dev->arch)});
759 
760    case PIPE_COMPUTE_CAP_MAX_SUBGROUPS:
761       RET((uint32_t[]){0 /* TODO */});
762 
763    case PIPE_COMPUTE_CAP_MAX_VARIABLE_THREADS_PER_BLOCK:
764       RET((uint64_t[]){1024}); // TODO
765    }
766 
767    return 0;
768 }
769 
770 static void
panfrost_destroy_screen(struct pipe_screen * pscreen)771 panfrost_destroy_screen(struct pipe_screen *pscreen)
772 {
773    struct panfrost_device *dev = pan_device(pscreen);
774    struct panfrost_screen *screen = pan_screen(pscreen);
775 
776    panfrost_resource_screen_destroy(pscreen);
777    panfrost_pool_cleanup(&screen->blitter.bin_pool);
778    panfrost_pool_cleanup(&screen->blitter.desc_pool);
779    pan_blend_shader_cache_cleanup(&dev->blend_shaders);
780 
781    if (screen->vtbl.screen_destroy)
782       screen->vtbl.screen_destroy(pscreen);
783 
784    if (dev->ro)
785       dev->ro->destroy(dev->ro);
786    panfrost_close_device(dev);
787 
788    disk_cache_destroy(screen->disk_cache);
789    ralloc_free(pscreen);
790 }
791 
792 static const void *
panfrost_screen_get_compiler_options(struct pipe_screen * pscreen,enum pipe_shader_ir ir,enum pipe_shader_type shader)793 panfrost_screen_get_compiler_options(struct pipe_screen *pscreen,
794                                      enum pipe_shader_ir ir,
795                                      enum pipe_shader_type shader)
796 {
797    return pan_screen(pscreen)->vtbl.get_compiler_options();
798 }
799 
800 static struct disk_cache *
panfrost_get_disk_shader_cache(struct pipe_screen * pscreen)801 panfrost_get_disk_shader_cache(struct pipe_screen *pscreen)
802 {
803    return pan_screen(pscreen)->disk_cache;
804 }
805 
806 static int
panfrost_get_screen_fd(struct pipe_screen * pscreen)807 panfrost_get_screen_fd(struct pipe_screen *pscreen)
808 {
809    return panfrost_device_fd(pan_device(pscreen));
810 }
811 
812 int
panfrost_get_driver_query_info(struct pipe_screen * pscreen,unsigned index,struct pipe_driver_query_info * info)813 panfrost_get_driver_query_info(struct pipe_screen *pscreen, unsigned index,
814                                struct pipe_driver_query_info *info)
815 {
816    int num_queries = ARRAY_SIZE(panfrost_driver_query_list);
817 
818    if (!info)
819       return num_queries;
820 
821    if (index >= num_queries)
822       return 0;
823 
824    *info = panfrost_driver_query_list[index];
825 
826    return 1;
827 }
828 
829 struct pipe_screen *
panfrost_create_screen(int fd,const struct pipe_screen_config * config,struct renderonly * ro)830 panfrost_create_screen(int fd, const struct pipe_screen_config *config,
831                        struct renderonly *ro)
832 {
833    /* Create the screen */
834    struct panfrost_screen *screen = rzalloc(NULL, struct panfrost_screen);
835 
836    if (!screen)
837       return NULL;
838 
839    struct panfrost_device *dev = pan_device(&screen->base);
840 
841    /* Debug must be set first for pandecode to work correctly */
842    dev->debug =
843       debug_get_flags_option("PAN_MESA_DEBUG", panfrost_debug_options, 0);
844    screen->max_afbc_packing_ratio = debug_get_num_option(
845       "PAN_MAX_AFBC_PACKING_RATIO", DEFAULT_MAX_AFBC_PACKING_RATIO);
846    panfrost_open_device(screen, fd, dev);
847 
848    if (dev->debug & PAN_DBG_NO_AFBC)
849       dev->has_afbc = false;
850 
851    /* Bail early on unsupported hardware */
852    if (dev->model == NULL) {
853       debug_printf("panfrost: Unsupported model %X",
854                    panfrost_device_gpu_id(dev));
855       panfrost_destroy_screen(&(screen->base));
856       return NULL;
857    }
858 
859    dev->ro = ro;
860 
861    screen->base.destroy = panfrost_destroy_screen;
862 
863    screen->base.get_screen_fd = panfrost_get_screen_fd;
864    screen->base.get_name = panfrost_get_name;
865    screen->base.get_vendor = panfrost_get_vendor;
866    screen->base.get_device_vendor = panfrost_get_device_vendor;
867    screen->base.get_driver_query_info = panfrost_get_driver_query_info;
868    screen->base.get_param = panfrost_get_param;
869    screen->base.get_shader_param = panfrost_get_shader_param;
870    screen->base.get_compute_param = panfrost_get_compute_param;
871    screen->base.get_paramf = panfrost_get_paramf;
872    screen->base.get_timestamp = u_default_get_timestamp;
873    screen->base.is_format_supported = panfrost_is_format_supported;
874    screen->base.query_dmabuf_modifiers = panfrost_query_dmabuf_modifiers;
875    screen->base.is_dmabuf_modifier_supported =
876       panfrost_is_dmabuf_modifier_supported;
877    screen->base.context_create = panfrost_create_context;
878    screen->base.get_compiler_options = panfrost_screen_get_compiler_options;
879    screen->base.get_disk_shader_cache = panfrost_get_disk_shader_cache;
880    screen->base.fence_reference = panfrost_fence_reference;
881    screen->base.fence_finish = panfrost_fence_finish;
882    screen->base.fence_get_fd = panfrost_fence_get_fd;
883    screen->base.set_damage_region = panfrost_resource_set_damage_region;
884 
885    panfrost_resource_screen_init(&screen->base);
886    pan_blend_shader_cache_init(&dev->blend_shaders,
887                                panfrost_device_gpu_id(dev));
888 
889    panfrost_disk_cache_init(screen);
890 
891    panfrost_pool_init(&screen->blitter.bin_pool, NULL, dev, PAN_BO_EXECUTE,
892                       4096, "Blitter shaders", false, true);
893    panfrost_pool_init(&screen->blitter.desc_pool, NULL, dev, 0, 65536,
894                       "Blitter RSDs", false, true);
895    if (dev->arch == 4)
896       panfrost_cmdstream_screen_init_v4(screen);
897    else if (dev->arch == 5)
898       panfrost_cmdstream_screen_init_v5(screen);
899    else if (dev->arch == 6)
900       panfrost_cmdstream_screen_init_v6(screen);
901    else if (dev->arch == 7)
902       panfrost_cmdstream_screen_init_v7(screen);
903    else if (dev->arch == 9)
904       panfrost_cmdstream_screen_init_v9(screen);
905    else
906       unreachable("Unhandled architecture major");
907 
908    return &screen->base;
909 }
910