xref: /aosp_15_r20/external/mesa3d/src/gallium/drivers/panfrost/pan_screen.c (revision 6104692788411f58d303aa86923a9ff6ecaded22)
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 <[email protected]>
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 #include "util/xmlconfig.h"
41 
42 #include <fcntl.h>
43 
44 #include "drm-uapi/drm_fourcc.h"
45 #include "drm-uapi/panfrost_drm.h"
46 
47 #include "decode.h"
48 #include "pan_bo.h"
49 #include "pan_fence.h"
50 #include "pan_public.h"
51 #include "pan_resource.h"
52 #include "pan_screen.h"
53 #include "pan_shader.h"
54 #include "pan_util.h"
55 
56 #include "pan_context.h"
57 
58 #define DEFAULT_MAX_AFBC_PACKING_RATIO 90
59 
60 /* clang-format off */
61 static const struct debug_named_value panfrost_debug_options[] = {
62    {"perf",       PAN_DBG_PERF,     "Enable performance warnings"},
63    {"trace",      PAN_DBG_TRACE,    "Trace the command stream"},
64    {"dirty",      PAN_DBG_DIRTY,    "Always re-emit all state"},
65    {"sync",       PAN_DBG_SYNC,     "Wait for each job's completion and abort on GPU faults"},
66    {"nofp16",     PAN_DBG_NOFP16,    "Disable 16-bit support"},
67    {"gl3",        PAN_DBG_GL3,      "Enable experimental GL 3.x implementation, up to 3.3"},
68    {"noafbc",     PAN_DBG_NO_AFBC,  "Disable AFBC support"},
69    {"crc",        PAN_DBG_CRC,      "Enable transaction elimination"},
70    {"msaa16",     PAN_DBG_MSAA16,   "Enable MSAA 8x and 16x support"},
71    {"linear",     PAN_DBG_LINEAR,   "Force linear textures"},
72    {"nocache",    PAN_DBG_NO_CACHE, "Disable BO cache"},
73    {"dump",       PAN_DBG_DUMP,     "Dump all graphics memory"},
74 #ifdef PAN_DBG_OVERFLOW
75    {"overflow",   PAN_DBG_OVERFLOW, "Check for buffer overflows in pool uploads"},
76 #endif
77    {"yuv",        PAN_DBG_YUV,      "Tint YUV textures with blue for 1-plane and green for 2-plane"},
78    {"forcepack",  PAN_DBG_FORCE_PACK,  "Force packing of AFBC textures on upload"},
79    DEBUG_NAMED_VALUE_END
80 };
81 /* clang-format on */
82 
83 static const char *
panfrost_get_name(struct pipe_screen * screen)84 panfrost_get_name(struct pipe_screen *screen)
85 {
86    return pan_device(screen)->model->name;
87 }
88 
89 static const char *
panfrost_get_vendor(struct pipe_screen * screen)90 panfrost_get_vendor(struct pipe_screen *screen)
91 {
92    return "Mesa";
93 }
94 
95 static const char *
panfrost_get_device_vendor(struct pipe_screen * screen)96 panfrost_get_device_vendor(struct pipe_screen *screen)
97 {
98    return "Arm";
99 }
100 
101 static int
panfrost_get_param(struct pipe_screen * screen,enum pipe_cap param)102 panfrost_get_param(struct pipe_screen *screen, enum pipe_cap param)
103 {
104    struct panfrost_device *dev = pan_device(screen);
105 
106    /* Our GL 3.x implementation is WIP */
107    bool is_gl3 = dev->debug & PAN_DBG_GL3;
108 
109    /* Native MRT is introduced with v5 */
110    bool has_mrt = (dev->arch >= 5);
111 
112    switch (param) {
113    case PIPE_CAP_NPOT_TEXTURES:
114    case PIPE_CAP_MIXED_COLOR_DEPTH_BITS:
115    case PIPE_CAP_FRAGMENT_SHADER_TEXTURE_LOD:
116    case PIPE_CAP_VERTEX_COLOR_UNCLAMPED:
117    case PIPE_CAP_DEPTH_CLIP_DISABLE:
118    case PIPE_CAP_MIXED_FRAMEBUFFER_SIZES:
119    case PIPE_CAP_FRONTEND_NOOP:
120    case PIPE_CAP_SAMPLE_SHADING:
121    case PIPE_CAP_FRAGMENT_SHADER_DERIVATIVES:
122    case PIPE_CAP_FRAMEBUFFER_NO_ATTACHMENT:
123    case PIPE_CAP_QUADS_FOLLOW_PROVOKING_VERTEX_CONVENTION:
124    case PIPE_CAP_SHADER_PACK_HALF_FLOAT:
125    case PIPE_CAP_HAS_CONST_BW:
126       return 1;
127 
128    /* Removed in v9 (Valhall) */
129    case PIPE_CAP_DEPTH_CLIP_DISABLE_SEPARATE:
130       return dev->arch < 9;
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 || dev->arch >= 10)
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 PAN_MAX_TEXEL_BUFFER_ELEMENTS;
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_TIME_ELAPSED:
227    case PIPE_CAP_QUERY_TIMESTAMP:
228       return dev->kmod.props.gpu_can_query_timestamp &&
229              dev->kmod.props.timestamp_frequency != 0;
230 
231    case PIPE_CAP_TIMER_RESOLUTION:
232       return pan_gpu_time_to_ns(dev, 1);
233 
234    /* The hardware requires element alignment for data conversion to work
235     * as expected. If data conversion is not required, this restriction is
236     * lifted on Midgard at a performance penalty. We conservatively
237     * require element alignment for vertex buffers, using u_vbuf to
238     * translate to match the hardware requirement.
239     *
240     * This is less heavy-handed than the 4BYTE_ALIGNED_ONLY caps, which
241     * would needlessly require alignment even for 8-bit formats.
242     */
243    case PIPE_CAP_VERTEX_ATTRIB_ELEMENT_ALIGNED_ONLY:
244       return 1;
245 
246    case PIPE_CAP_MAX_TEXTURE_2D_SIZE:
247       return 1 << (PAN_MAX_MIP_LEVELS - 1);
248 
249    case PIPE_CAP_MAX_TEXTURE_3D_LEVELS:
250    case PIPE_CAP_MAX_TEXTURE_CUBE_LEVELS:
251       return PAN_MAX_MIP_LEVELS;
252 
253    /* pixel coord is in integer sysval on bifrost. */
254    case PIPE_CAP_FS_COORD_PIXEL_CENTER_INTEGER:
255       return dev->arch >= 6;
256    case PIPE_CAP_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
257       return dev->arch < 6;
258 
259    case PIPE_CAP_FS_COORD_ORIGIN_LOWER_LEFT:
260       /* Hardware is upper left */
261       return 0;
262 
263    case PIPE_CAP_FS_COORD_ORIGIN_UPPER_LEFT:
264    case PIPE_CAP_TGSI_TEXCOORD:
265       return 1;
266 
267    /* We would prefer varyings on Midgard, but proper sysvals on Bifrost */
268    case PIPE_CAP_FS_FACE_IS_INTEGER_SYSVAL:
269    case PIPE_CAP_FS_POSITION_IS_SYSVAL:
270    case PIPE_CAP_FS_POINT_IS_SYSVAL:
271       return dev->arch >= 6;
272 
273    case PIPE_CAP_SEAMLESS_CUBE_MAP:
274    case PIPE_CAP_SEAMLESS_CUBE_MAP_PER_TEXTURE:
275       return true;
276 
277    case PIPE_CAP_MAX_VERTEX_ELEMENT_SRC_OFFSET:
278       return 0xffff;
279 
280    case PIPE_CAP_TEXTURE_TRANSFER_MODES:
281       return 0;
282 
283    case PIPE_CAP_ENDIANNESS:
284       return PIPE_ENDIAN_NATIVE;
285 
286    case PIPE_CAP_MAX_TEXTURE_GATHER_COMPONENTS:
287       return 4;
288 
289    case PIPE_CAP_MIN_TEXTURE_GATHER_OFFSET:
290       return -8;
291 
292    case PIPE_CAP_MAX_TEXTURE_GATHER_OFFSET:
293       return 7;
294 
295    case PIPE_CAP_VIDEO_MEMORY: {
296       uint64_t system_memory;
297 
298       if (!os_get_total_physical_memory(&system_memory))
299          return 0;
300 
301       return (int)(system_memory >> 20);
302    }
303 
304    case PIPE_CAP_SHADER_STENCIL_EXPORT:
305    case PIPE_CAP_CONDITIONAL_RENDER:
306    case PIPE_CAP_CONDITIONAL_RENDER_INVERTED:
307       return true;
308 
309    case PIPE_CAP_SHADER_BUFFER_OFFSET_ALIGNMENT:
310       return 4;
311 
312    case PIPE_CAP_MAX_VARYINGS:
313       return dev->arch >= 9 ? 16 : 32;
314 
315    /* Removed in v6 (Bifrost) */
316    case PIPE_CAP_GL_CLAMP:
317    case PIPE_CAP_TEXTURE_MIRROR_CLAMP:
318    case PIPE_CAP_ALPHA_TEST:
319       return dev->arch <= 5;
320 
321    /* Removed in v9 (Valhall). PRIMTIIVE_RESTART_FIXED_INDEX is of course
322     * still supported as it is core GLES3.0 functionality
323     */
324    case PIPE_CAP_EMULATE_NONFIXED_PRIMITIVE_RESTART:
325       return dev->arch >= 9;
326 
327    case PIPE_CAP_FLATSHADE:
328    case PIPE_CAP_TWO_SIDED_COLOR:
329    case PIPE_CAP_CLIP_PLANES:
330       return 0;
331 
332    case PIPE_CAP_PACKED_STREAM_OUTPUT:
333       return 0;
334 
335    case PIPE_CAP_VIEWPORT_TRANSFORM_LOWERED:
336    case PIPE_CAP_PSIZ_CLAMPED:
337       return 1;
338 
339    case PIPE_CAP_NIR_IMAGES_AS_DEREF:
340       return 0;
341 
342    case PIPE_CAP_DRAW_INDIRECT:
343       return 1;
344 
345    case PIPE_CAP_MULTI_DRAW_INDIRECT:
346       return dev->arch >= 10;
347 
348    case PIPE_CAP_START_INSTANCE:
349    case PIPE_CAP_DRAW_PARAMETERS:
350       return pan_is_bifrost(dev);
351 
352    case PIPE_CAP_SUPPORTED_PRIM_MODES:
353    case PIPE_CAP_SUPPORTED_PRIM_MODES_WITH_RESTART: {
354       /* Mali supports GLES and QUADS. Midgard and v6 Bifrost
355        * support more */
356       uint32_t modes = BITFIELD_MASK(MESA_PRIM_QUADS + 1);
357 
358       if (dev->arch <= 6) {
359          modes |= BITFIELD_BIT(MESA_PRIM_QUAD_STRIP);
360          modes |= BITFIELD_BIT(MESA_PRIM_POLYGON);
361       }
362 
363       if (dev->arch >= 9) {
364          /* Although Valhall is supposed to support quads, they
365           * don't seem to work correctly. Disable to fix
366           * arb-provoking-vertex-render.
367           */
368          modes &= ~BITFIELD_BIT(MESA_PRIM_QUADS);
369       }
370 
371       return modes;
372    }
373 
374    case PIPE_CAP_IMAGE_STORE_FORMATTED:
375       return 1;
376 
377    case PIPE_CAP_NATIVE_FENCE_FD:
378       return 1;
379 
380    case PIPE_CAP_ASTC_DECODE_MODE:
381       return dev->arch >= 9 && (dev->compressed_formats & (1 << 30));
382 
383    default:
384       return u_pipe_screen_get_param_defaults(screen, param);
385    }
386 }
387 
388 static int
panfrost_get_shader_param(struct pipe_screen * screen,enum pipe_shader_type shader,enum pipe_shader_cap param)389 panfrost_get_shader_param(struct pipe_screen *screen,
390                           enum pipe_shader_type shader,
391                           enum pipe_shader_cap param)
392 {
393    struct panfrost_device *dev = pan_device(screen);
394    bool is_nofp16 = dev->debug & PAN_DBG_NOFP16;
395 
396    switch (shader) {
397    case PIPE_SHADER_VERTEX:
398    case PIPE_SHADER_FRAGMENT:
399    case PIPE_SHADER_COMPUTE:
400       break;
401    default:
402       return 0;
403    }
404 
405    /* We only allow observable side effects (memory writes) in compute and
406     * fragment shaders. Side effects in the geometry pipeline cause
407     * trouble with IDVS and conflict with our transform feedback lowering.
408     */
409    bool allow_side_effects = (shader != PIPE_SHADER_VERTEX);
410 
411    switch (param) {
412    case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
413    case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
414    case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
415    case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
416       return 16384; /* arbitrary */
417 
418    case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
419       return 1024; /* arbitrary */
420 
421    case PIPE_SHADER_CAP_MAX_INPUTS:
422       /* Used as ABI on Midgard */
423       return 16;
424 
425    case PIPE_SHADER_CAP_MAX_OUTPUTS:
426       return shader == PIPE_SHADER_FRAGMENT ? 8 : PIPE_MAX_ATTRIBS;
427 
428    case PIPE_SHADER_CAP_MAX_TEMPS:
429       return 256; /* arbitrary */
430 
431    case PIPE_SHADER_CAP_MAX_CONST_BUFFER0_SIZE:
432       return 16 * 1024 * sizeof(float);
433 
434    case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
435       STATIC_ASSERT(PAN_MAX_CONST_BUFFERS < 0x100);
436       return PAN_MAX_CONST_BUFFERS;
437 
438    case PIPE_SHADER_CAP_CONT_SUPPORTED:
439       return 0;
440 
441    case PIPE_SHADER_CAP_INDIRECT_INPUT_ADDR:
442       return 1;
443    case PIPE_SHADER_CAP_INDIRECT_OUTPUT_ADDR:
444       return 0;
445 
446    case PIPE_SHADER_CAP_INDIRECT_TEMP_ADDR:
447       return dev->arch >= 6;
448 
449    case PIPE_SHADER_CAP_INDIRECT_CONST_ADDR:
450       return 1;
451 
452    case PIPE_SHADER_CAP_SUBROUTINES:
453       return 0;
454 
455    case PIPE_SHADER_CAP_TGSI_SQRT_SUPPORTED:
456       return 0;
457 
458    case PIPE_SHADER_CAP_INTEGERS:
459       return 1;
460 
461       /* The Bifrost compiler supports full 16-bit. Midgard could but int16
462        * support is untested, so restrict INT16 to Bifrost. Midgard
463        * architecturally cannot support fp16 derivatives. */
464 
465    case PIPE_SHADER_CAP_FP16:
466    case PIPE_SHADER_CAP_GLSL_16BIT_CONSTS:
467       return !is_nofp16;
468    case PIPE_SHADER_CAP_FP16_DERIVATIVES:
469    case PIPE_SHADER_CAP_FP16_CONST_BUFFERS:
470       return dev->arch >= 6 && !is_nofp16;
471    case PIPE_SHADER_CAP_INT16:
472       /* Blocked on https://gitlab.freedesktop.org/mesa/mesa/-/issues/6075 */
473       return false;
474 
475    case PIPE_SHADER_CAP_INT64_ATOMICS:
476    case PIPE_SHADER_CAP_TGSI_ANY_INOUT_DECL_RANGE:
477       return 0;
478 
479    case PIPE_SHADER_CAP_MAX_TEXTURE_SAMPLERS:
480       STATIC_ASSERT(PIPE_MAX_SAMPLERS < 0x10000);
481       return PIPE_MAX_SAMPLERS;
482 
483    case PIPE_SHADER_CAP_MAX_SAMPLER_VIEWS:
484       STATIC_ASSERT(PIPE_MAX_SHADER_SAMPLER_VIEWS < 0x10000);
485       return PIPE_MAX_SHADER_SAMPLER_VIEWS;
486 
487    case PIPE_SHADER_CAP_SUPPORTED_IRS:
488       return (1 << PIPE_SHADER_IR_NIR);
489 
490    case PIPE_SHADER_CAP_MAX_SHADER_BUFFERS:
491       return allow_side_effects ? 16 : 0;
492 
493    case PIPE_SHADER_CAP_MAX_SHADER_IMAGES:
494       return allow_side_effects ? PIPE_MAX_SHADER_IMAGES : 0;
495 
496    case PIPE_SHADER_CAP_MAX_HW_ATOMIC_COUNTERS:
497    case PIPE_SHADER_CAP_MAX_HW_ATOMIC_COUNTER_BUFFERS:
498       return 0;
499 
500    default:
501       return 0;
502    }
503 
504    return 0;
505 }
506 
507 static float
panfrost_get_paramf(struct pipe_screen * screen,enum pipe_capf param)508 panfrost_get_paramf(struct pipe_screen *screen, enum pipe_capf param)
509 {
510    switch (param) {
511    case PIPE_CAPF_MIN_LINE_WIDTH:
512    case PIPE_CAPF_MIN_LINE_WIDTH_AA:
513    case PIPE_CAPF_MIN_POINT_SIZE:
514    case PIPE_CAPF_MIN_POINT_SIZE_AA:
515       return 1;
516 
517    case PIPE_CAPF_POINT_SIZE_GRANULARITY:
518    case PIPE_CAPF_LINE_WIDTH_GRANULARITY:
519       return 0.0625;
520 
521    case PIPE_CAPF_MAX_LINE_WIDTH:
522    case PIPE_CAPF_MAX_LINE_WIDTH_AA:
523    case PIPE_CAPF_MAX_POINT_SIZE:
524    case PIPE_CAPF_MAX_POINT_SIZE_AA:
525       return 4095.9375;
526 
527    case PIPE_CAPF_MAX_TEXTURE_ANISOTROPY:
528       return 16.0;
529 
530    case PIPE_CAPF_MAX_TEXTURE_LOD_BIAS:
531       return 16.0; /* arbitrary */
532 
533    case PIPE_CAPF_MIN_CONSERVATIVE_RASTER_DILATE:
534    case PIPE_CAPF_MAX_CONSERVATIVE_RASTER_DILATE:
535    case PIPE_CAPF_CONSERVATIVE_RASTER_DILATE_GRANULARITY:
536       return 0.0f;
537 
538    default:
539       debug_printf("Unexpected PIPE_CAPF %d query\n", param);
540       return 0.0;
541    }
542 }
543 
544 static uint32_t
pipe_to_pan_bind_flags(uint32_t pipe_bind_flags)545 pipe_to_pan_bind_flags(uint32_t pipe_bind_flags)
546 {
547    static_assert(PIPE_BIND_DEPTH_STENCIL == PAN_BIND_DEPTH_STENCIL, "");
548    static_assert(PIPE_BIND_RENDER_TARGET == PAN_BIND_RENDER_TARGET, "");
549    static_assert(PIPE_BIND_SAMPLER_VIEW == PAN_BIND_SAMPLER_VIEW, "");
550    static_assert(PIPE_BIND_VERTEX_BUFFER == PAN_BIND_VERTEX_BUFFER, "");
551 
552    return pipe_bind_flags & (PAN_BIND_DEPTH_STENCIL | PAN_BIND_RENDER_TARGET |
553                              PAN_BIND_VERTEX_BUFFER | PAN_BIND_SAMPLER_VIEW);
554 }
555 
556 /**
557  * Query format support for creating a texture, drawing surface, etc.
558  * \param format  the format to test
559  * \param type  one of PIPE_TEXTURE, PIPE_SURFACE
560  */
561 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)562 panfrost_is_format_supported(struct pipe_screen *screen,
563                              enum pipe_format format,
564                              enum pipe_texture_target target,
565                              unsigned sample_count,
566                              unsigned storage_sample_count, unsigned bind)
567 {
568    struct panfrost_device *dev = pan_device(screen);
569 
570    /* MSAA 2x gets rounded up to 4x. MSAA 8x/16x only supported on v5+.
571     * TODO: debug MSAA 8x/16x */
572 
573    switch (sample_count) {
574    case 0:
575    case 1:
576    case 4:
577       break;
578    case 8:
579    case 16:
580       if (dev->debug & PAN_DBG_MSAA16)
581          break;
582       else
583          return false;
584    default:
585       return false;
586    }
587 
588    if (MAX2(sample_count, 1) != MAX2(storage_sample_count, 1))
589       return false;
590 
591    /* Z16 causes dEQP failures on t720 */
592    if (format == PIPE_FORMAT_Z16_UNORM && dev->arch <= 4)
593       return false;
594 
595    /* Check we support the format with the given bind */
596 
597    unsigned pan_bind_flags = pipe_to_pan_bind_flags(bind);
598 
599    struct panfrost_format fmt = dev->formats[format];
600 
601    /* Also check that compressed texture formats are supported on this
602     * particular chip. They may not be depending on system integration
603     * differences. */
604 
605    bool supported =
606       panfrost_supports_compressed_format(dev, MALI_EXTRACT_INDEX(fmt.hw));
607 
608    if (!supported)
609       return false;
610 
611    return MALI_EXTRACT_INDEX(fmt.hw) && ((pan_bind_flags & ~fmt.bind) == 0);
612 }
613 
614 static void
panfrost_query_compression_rates(struct pipe_screen * screen,enum pipe_format format,int max,uint32_t * rates,int * count)615 panfrost_query_compression_rates(struct pipe_screen *screen,
616                                  enum pipe_format format, int max,
617                                  uint32_t *rates, int *count)
618 {
619    struct panfrost_device *dev = pan_device(screen);
620 
621    if (!dev->has_afrc) {
622       *count = 0;
623       return;
624    }
625 
626    *count = panfrost_afrc_query_rates(format, max, rates);
627 }
628 
629 static void
panfrost_query_compression_modifiers(struct pipe_screen * screen,enum pipe_format format,uint32_t rate,int max,uint64_t * modifiers,int * count)630 panfrost_query_compression_modifiers(struct pipe_screen *screen,
631                                      enum pipe_format format, uint32_t rate,
632                                      int max, uint64_t *modifiers, int *count)
633 {
634    struct panfrost_device *dev = pan_device(screen);
635 
636    if (!dev->has_afrc || rate == PIPE_COMPRESSION_FIXED_RATE_NONE) {
637       int mod_count = 0;
638       for (unsigned i = 0; i < PAN_MODIFIER_COUNT; ++i) {
639          if (drm_is_afrc(pan_best_modifiers[i]))
640             continue;
641          if (mod_count < max)
642             modifiers[mod_count] = pan_best_modifiers[i];
643          mod_count++;
644          if (max > 0 && mod_count >= max)
645             break;
646       }
647       *count = mod_count;
648       return;
649    }
650 
651    *count = panfrost_afrc_get_modifiers(format, rate, max, modifiers);
652 }
653 
654 static bool
panfrost_is_compression_modifier(struct pipe_screen * screen,enum pipe_format format,uint64_t modifier,uint32_t * rate)655 panfrost_is_compression_modifier(struct pipe_screen *screen,
656                                  enum pipe_format format, uint64_t modifier,
657                                  uint32_t *rate)
658 {
659    struct panfrost_device *dev = pan_device(screen);
660    uint32_t compression_rate = panfrost_afrc_get_rate(format, modifier);
661 
662    if (!dev->has_afrc)
663       return false;
664 
665    if (rate)
666       *rate = compression_rate;
667 
668    return (compression_rate != 0);
669 }
670 
671 /* We always support linear and tiled operations, both external and internal.
672  * We support AFBC for a subset of formats, and colourspace transform for a
673  * subset of those. */
674 
675 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)676 panfrost_walk_dmabuf_modifiers(struct pipe_screen *screen,
677                                enum pipe_format format, int max,
678                                uint64_t *modifiers, unsigned int *external_only,
679                                int *out_count, uint64_t test_modifier)
680 {
681    /* Query AFBC status */
682    struct panfrost_device *dev = pan_device(screen);
683    bool afbc =
684       dev->has_afbc && panfrost_format_supports_afbc(dev->arch, format);
685    bool ytr = panfrost_afbc_can_ytr(format);
686    bool tiled_afbc = panfrost_afbc_can_tile(dev->arch);
687    bool afrc = dev->has_afrc && panfrost_format_supports_afrc(format);
688 
689    unsigned count = 0;
690 
691    for (unsigned i = 0; i < PAN_MODIFIER_COUNT; ++i) {
692       if (drm_is_afbc(pan_best_modifiers[i]) && !afbc)
693          continue;
694 
695       if ((pan_best_modifiers[i] & AFBC_FORMAT_MOD_YTR) && !ytr)
696          continue;
697 
698       if ((pan_best_modifiers[i] & AFBC_FORMAT_MOD_TILED) && !tiled_afbc)
699          continue;
700 
701       if (drm_is_afrc(pan_best_modifiers[i]) && !afrc)
702          continue;
703 
704       if (test_modifier != DRM_FORMAT_MOD_INVALID &&
705           test_modifier != pan_best_modifiers[i])
706          continue;
707 
708       if (max > (int)count) {
709          modifiers[count] = pan_best_modifiers[i];
710 
711          if (external_only)
712             external_only[count] = false;
713       }
714       count++;
715    }
716 
717    *out_count = count;
718 }
719 
720 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)721 panfrost_query_dmabuf_modifiers(struct pipe_screen *screen,
722                                 enum pipe_format format, int max,
723                                 uint64_t *modifiers,
724                                 unsigned int *external_only, int *out_count)
725 {
726    panfrost_walk_dmabuf_modifiers(screen, format, max, modifiers, external_only,
727                                   out_count, DRM_FORMAT_MOD_INVALID);
728 }
729 
730 static bool
panfrost_is_dmabuf_modifier_supported(struct pipe_screen * screen,uint64_t modifier,enum pipe_format format,bool * external_only)731 panfrost_is_dmabuf_modifier_supported(struct pipe_screen *screen,
732                                       uint64_t modifier,
733                                       enum pipe_format format,
734                                       bool *external_only)
735 {
736    uint64_t unused;
737    unsigned int uint_extern_only = 0;
738    int count;
739 
740    panfrost_walk_dmabuf_modifiers(screen, format, 1, &unused, &uint_extern_only,
741                                   &count, modifier);
742 
743    if (external_only)
744       *external_only = uint_extern_only ? true : false;
745 
746    return count > 0;
747 }
748 
749 static int
panfrost_get_compute_param(struct pipe_screen * pscreen,enum pipe_shader_ir ir_type,enum pipe_compute_cap param,void * ret)750 panfrost_get_compute_param(struct pipe_screen *pscreen,
751                            enum pipe_shader_ir ir_type,
752                            enum pipe_compute_cap param, void *ret)
753 {
754    struct panfrost_device *dev = pan_device(pscreen);
755    const char *const ir = "panfrost";
756 
757 #define RET(x)                                                                 \
758    do {                                                                        \
759       if (ret)                                                                 \
760          memcpy(ret, x, sizeof(x));                                            \
761       return sizeof(x);                                                        \
762    } while (0)
763 
764    switch (param) {
765    case PIPE_COMPUTE_CAP_ADDRESS_BITS:
766       RET((uint32_t[]){64});
767 
768    case PIPE_COMPUTE_CAP_IR_TARGET:
769       if (ret)
770          sprintf(ret, "%s", ir);
771       return strlen(ir) * sizeof(char);
772 
773    case PIPE_COMPUTE_CAP_GRID_DIMENSION:
774       RET((uint64_t[]){3});
775 
776    case PIPE_COMPUTE_CAP_MAX_GRID_SIZE:
777       RET(((uint64_t[]){65535, 65535, 65535}));
778 
779    case PIPE_COMPUTE_CAP_MAX_BLOCK_SIZE:
780       /* Unpredictable behaviour at larger sizes. Mali-G52 advertises
781        * 384x384x384.
782        *
783        * On Midgard, we don't allow more than 128 threads in each
784        * direction to match PIPE_COMPUTE_CAP_MAX_THREADS_PER_BLOCK.
785        * That still exceeds the minimum-maximum.
786        */
787       if (dev->arch >= 6)
788          RET(((uint64_t[]){256, 256, 256}));
789       else
790          RET(((uint64_t[]){128, 128, 128}));
791 
792    case PIPE_COMPUTE_CAP_MAX_THREADS_PER_BLOCK:
793       /* On Bifrost and newer, all GPUs can support at least 256 threads
794        * regardless of register usage, so we report 256.
795        *
796        * On Midgard, with maximum register usage, the maximum
797        * thread count is only 64. We would like to report 64 here, but
798        * the GLES3.1 spec minimum is 128, so we report 128 and limit
799        * the register allocation of affected compute kernels.
800        */
801       RET((uint64_t[]){dev->arch >= 6 ? 256 : 128});
802 
803    case PIPE_COMPUTE_CAP_MAX_GLOBAL_SIZE:
804    case PIPE_COMPUTE_CAP_MAX_MEM_ALLOC_SIZE: {
805       uint64_t total_ram;
806 
807       if (!os_get_total_physical_memory(&total_ram))
808          return 0;
809 
810       /* We don't want to burn too much ram with the GPU. If the user has 4GiB
811        * or less, we use at most half. If they have more than 4GiB, we use 3/4.
812        */
813       uint64_t available_ram;
814       if (total_ram <= 4ull * 1024 * 1024 * 1024)
815          available_ram = total_ram / 2;
816       else
817          available_ram = total_ram * 3 / 4;
818 
819       /* 48bit address space max, with the lower 32MB reserved. We clamp
820        * things so it matches kmod VA range limitations.
821        */
822       uint64_t user_va_start =
823          panfrost_clamp_to_usable_va_range(dev->kmod.dev, PAN_VA_USER_START);
824       uint64_t user_va_end =
825          panfrost_clamp_to_usable_va_range(dev->kmod.dev, PAN_VA_USER_END);
826 
827       /* We cannot support more than the VA limit */
828       RET((uint64_t[]){MIN2(available_ram, user_va_end - user_va_start)});
829    }
830 
831    case PIPE_COMPUTE_CAP_MAX_LOCAL_SIZE:
832       RET((uint64_t[]){32768});
833 
834    case PIPE_COMPUTE_CAP_MAX_PRIVATE_SIZE:
835    case PIPE_COMPUTE_CAP_MAX_INPUT_SIZE:
836       RET((uint64_t[]){4096});
837 
838    case PIPE_COMPUTE_CAP_MAX_CLOCK_FREQUENCY:
839       RET((uint32_t[]){800 /* MHz -- TODO */});
840 
841    case PIPE_COMPUTE_CAP_MAX_COMPUTE_UNITS:
842       RET((uint32_t[]){dev->core_count});
843 
844    case PIPE_COMPUTE_CAP_IMAGES_SUPPORTED:
845       RET((uint32_t[]){1});
846 
847    case PIPE_COMPUTE_CAP_SUBGROUP_SIZES:
848       RET((uint32_t[]){pan_subgroup_size(dev->arch)});
849 
850    case PIPE_COMPUTE_CAP_MAX_SUBGROUPS:
851       RET((uint32_t[]){0 /* TODO */});
852 
853    case PIPE_COMPUTE_CAP_MAX_VARIABLE_THREADS_PER_BLOCK:
854       RET((uint64_t[]){1024}); // TODO
855    }
856 
857    return 0;
858 }
859 
860 static void
panfrost_destroy_screen(struct pipe_screen * pscreen)861 panfrost_destroy_screen(struct pipe_screen *pscreen)
862 {
863    struct panfrost_device *dev = pan_device(pscreen);
864    struct panfrost_screen *screen = pan_screen(pscreen);
865 
866    panfrost_resource_screen_destroy(pscreen);
867    panfrost_pool_cleanup(&screen->blitter.bin_pool);
868    panfrost_pool_cleanup(&screen->blitter.desc_pool);
869    pan_blend_shader_cache_cleanup(&dev->blend_shaders);
870 
871    if (screen->vtbl.screen_destroy)
872       screen->vtbl.screen_destroy(pscreen);
873 
874    if (dev->ro)
875       dev->ro->destroy(dev->ro);
876    panfrost_close_device(dev);
877 
878    disk_cache_destroy(screen->disk_cache);
879    ralloc_free(pscreen);
880 }
881 
882 static const void *
panfrost_screen_get_compiler_options(struct pipe_screen * pscreen,enum pipe_shader_ir ir,enum pipe_shader_type shader)883 panfrost_screen_get_compiler_options(struct pipe_screen *pscreen,
884                                      enum pipe_shader_ir ir,
885                                      enum pipe_shader_type shader)
886 {
887    return pan_screen(pscreen)->vtbl.get_compiler_options();
888 }
889 
890 static struct disk_cache *
panfrost_get_disk_shader_cache(struct pipe_screen * pscreen)891 panfrost_get_disk_shader_cache(struct pipe_screen *pscreen)
892 {
893    return pan_screen(pscreen)->disk_cache;
894 }
895 
896 static int
panfrost_get_screen_fd(struct pipe_screen * pscreen)897 panfrost_get_screen_fd(struct pipe_screen *pscreen)
898 {
899    return panfrost_device_fd(pan_device(pscreen));
900 }
901 
902 int
panfrost_get_driver_query_info(struct pipe_screen * pscreen,unsigned index,struct pipe_driver_query_info * info)903 panfrost_get_driver_query_info(struct pipe_screen *pscreen, unsigned index,
904                                struct pipe_driver_query_info *info)
905 {
906    int num_queries = ARRAY_SIZE(panfrost_driver_query_list);
907 
908    if (!info)
909       return num_queries;
910 
911    if (index >= num_queries)
912       return 0;
913 
914    *info = panfrost_driver_query_list[index];
915 
916    return 1;
917 }
918 
919 static uint64_t
panfrost_get_timestamp(struct pipe_screen * pscreen)920 panfrost_get_timestamp(struct pipe_screen *pscreen)
921 {
922    struct panfrost_device *dev = pan_device(pscreen);
923 
924    return pan_gpu_time_to_ns(dev, pan_kmod_query_timestamp(dev->kmod.dev));
925 }
926 
927 struct pipe_screen *
panfrost_create_screen(int fd,const struct pipe_screen_config * config,struct renderonly * ro)928 panfrost_create_screen(int fd, const struct pipe_screen_config *config,
929                        struct renderonly *ro)
930 {
931    /* Create the screen */
932    struct panfrost_screen *screen = rzalloc(NULL, struct panfrost_screen);
933 
934    if (!screen)
935       return NULL;
936 
937    struct panfrost_device *dev = pan_device(&screen->base);
938 
939    driParseConfigFiles(config->options, config->options_info, 0,
940                        "panfrost", NULL, NULL, NULL, 0, NULL, 0);
941 
942    /* Debug must be set first for pandecode to work correctly */
943    dev->debug =
944       debug_get_flags_option("PAN_MESA_DEBUG", panfrost_debug_options, 0);
945    screen->max_afbc_packing_ratio = debug_get_num_option(
946       "PAN_MAX_AFBC_PACKING_RATIO", DEFAULT_MAX_AFBC_PACKING_RATIO);
947    panfrost_open_device(screen, fd, dev);
948 
949    if (dev->debug & PAN_DBG_NO_AFBC)
950       dev->has_afbc = false;
951 
952    /* Bail early on unsupported hardware */
953    if (dev->model == NULL) {
954       debug_printf("panfrost: Unsupported model %X",
955                    panfrost_device_gpu_id(dev));
956       panfrost_destroy_screen(&(screen->base));
957       return NULL;
958    }
959 
960    screen->force_afbc_packing = dev->debug & PAN_DBG_FORCE_PACK;
961    if (!screen->force_afbc_packing)
962       screen->force_afbc_packing = driQueryOptionb(config->options,
963                                                    "pan_force_afbc_packing");
964 
965    const char *option = debug_get_option("PAN_AFRC_RATE", NULL);
966    if (!option) {
967       screen->force_afrc_rate = -1;
968    } else if (strcmp(option, "default") == 0) {
969       screen->force_afrc_rate = PIPE_COMPRESSION_FIXED_RATE_DEFAULT;
970    } else {
971       int64_t rate =
972          debug_parse_num_option(option, PIPE_COMPRESSION_FIXED_RATE_NONE);
973       screen->force_afrc_rate = rate;
974    }
975 
976    screen->csf_tiler_heap.chunk_size = driQueryOptioni(config->options,
977                                                        "pan_csf_chunk_size");
978    screen->csf_tiler_heap.initial_chunks = driQueryOptioni(config->options,
979                                                            "pan_csf_initial_chunks");
980    screen->csf_tiler_heap.max_chunks = driQueryOptioni(config->options,
981                                                        "pan_csf_max_chunks");
982 
983    dev->ro = ro;
984 
985    screen->base.destroy = panfrost_destroy_screen;
986 
987    screen->base.get_screen_fd = panfrost_get_screen_fd;
988    screen->base.get_name = panfrost_get_name;
989    screen->base.get_vendor = panfrost_get_vendor;
990    screen->base.get_device_vendor = panfrost_get_device_vendor;
991    screen->base.get_driver_query_info = panfrost_get_driver_query_info;
992    screen->base.get_param = panfrost_get_param;
993    screen->base.get_shader_param = panfrost_get_shader_param;
994    screen->base.get_compute_param = panfrost_get_compute_param;
995    screen->base.get_paramf = panfrost_get_paramf;
996    screen->base.get_timestamp = panfrost_get_timestamp;
997    screen->base.is_format_supported = panfrost_is_format_supported;
998    screen->base.query_dmabuf_modifiers = panfrost_query_dmabuf_modifiers;
999    screen->base.is_dmabuf_modifier_supported =
1000       panfrost_is_dmabuf_modifier_supported;
1001    screen->base.context_create = panfrost_create_context;
1002    screen->base.get_compiler_options = panfrost_screen_get_compiler_options;
1003    screen->base.get_disk_shader_cache = panfrost_get_disk_shader_cache;
1004    screen->base.fence_reference = panfrost_fence_reference;
1005    screen->base.fence_finish = panfrost_fence_finish;
1006    screen->base.fence_get_fd = panfrost_fence_get_fd;
1007    screen->base.set_damage_region = panfrost_resource_set_damage_region;
1008    screen->base.query_compression_rates = panfrost_query_compression_rates;
1009    screen->base.query_compression_modifiers =
1010       panfrost_query_compression_modifiers;
1011    screen->base.is_compression_modifier = panfrost_is_compression_modifier;
1012 
1013    panfrost_resource_screen_init(&screen->base);
1014    pan_blend_shader_cache_init(&dev->blend_shaders,
1015                                panfrost_device_gpu_id(dev));
1016 
1017    panfrost_disk_cache_init(screen);
1018 
1019    panfrost_pool_init(&screen->blitter.bin_pool, NULL, dev, PAN_BO_EXECUTE,
1020                       4096, "Blitter shaders", false, true);
1021    panfrost_pool_init(&screen->blitter.desc_pool, NULL, dev, 0, 65536,
1022                       "Blitter RSDs", false, true);
1023    if (dev->arch == 4)
1024       panfrost_cmdstream_screen_init_v4(screen);
1025    else if (dev->arch == 5)
1026       panfrost_cmdstream_screen_init_v5(screen);
1027    else if (dev->arch == 6)
1028       panfrost_cmdstream_screen_init_v6(screen);
1029    else if (dev->arch == 7)
1030       panfrost_cmdstream_screen_init_v7(screen);
1031    else if (dev->arch == 9)
1032       panfrost_cmdstream_screen_init_v9(screen);
1033    else if (dev->arch == 10)
1034       panfrost_cmdstream_screen_init_v10(screen);
1035    else
1036       unreachable("Unhandled architecture major");
1037 
1038    return &screen->base;
1039 }
1040