xref: /aosp_15_r20/external/mesa3d/src/intel/blorp/blorp_priv.h (revision 6104692788411f58d303aa86923a9ff6ecaded22)
1 /*
2  * Copyright © 2012 Intel Corporation
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a
5  * copy of this software and associated documentation files (the "Software"),
6  * to deal in the Software without restriction, including without limitation
7  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8  * and/or sell copies of the Software, and to permit persons to whom the
9  * Software is furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice (including the next
12  * paragraph) shall be included in all copies or substantial portions of the
13  * Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21  * IN THE SOFTWARE.
22  */
23 
24 #ifndef BLORP_PRIV_H
25 #define BLORP_PRIV_H
26 
27 #include <stdint.h>
28 
29 #include "common/intel_measure.h"
30 #include "compiler/nir/nir.h"
31 
32 #include "blorp.h"
33 
34 #ifdef __cplusplus
35 extern "C" {
36 #endif
37 
38 void blorp_init(struct blorp_context *blorp, void *driver_ctx,
39                 struct isl_device *isl_dev, const struct blorp_config *config);
40 
41 struct blorp_compiler {
42    const struct brw_compiler *brw;
43    const struct elk_compiler *elk;
44 
45    const nir_shader_compiler_options *(*nir_options)(struct blorp_context *blorp,
46                                                      gl_shader_stage stage);
47 
48    struct blorp_program (*compile_fs)(struct blorp_context *blorp, void *mem_ctx,
49                                       struct nir_shader *nir,
50                                       bool multisample_fbo,
51                                       bool use_repclear);
52    struct blorp_program (*compile_vs)(struct blorp_context *blorp, void *mem_ctx,
53                                       struct nir_shader *nir);
54 
55    struct blorp_program (*compile_cs)(struct blorp_context *blorp, void *mem_ctx,
56                                       struct nir_shader *nir);
57 
58    bool (*ensure_sf_program)(struct blorp_batch *batch,
59                              struct blorp_params *params);
60 
61    bool (*params_get_layer_offset_vs)(struct blorp_batch *batch,
62                                       struct blorp_params *params);
63 };
64 
65 /**
66  * Binding table indices used by BLORP.
67  */
68 enum {
69    BLORP_RENDERBUFFER_BT_INDEX,
70    BLORP_TEXTURE_BT_INDEX,
71    BLORP_NUM_BT_ENTRIES
72 };
73 
74 #define BLORP_SAMPLER_INDEX 0
75 
76 struct blorp_surface_info
77 {
78    bool enabled;
79 
80    struct isl_surf surf;
81    struct blorp_address addr;
82 
83    struct isl_surf aux_surf;
84    struct blorp_address aux_addr;
85    enum isl_aux_usage aux_usage;
86 
87    union isl_color_value clear_color;
88    struct blorp_address clear_color_addr;
89 
90    struct isl_view view;
91 
92    /* Z offset into a 3-D texture or slice of a 2-D array texture. */
93    float z_offset;
94 
95    uint32_t tile_x_sa, tile_y_sa;
96 };
97 
98 void
99 blorp_surface_info_init(struct blorp_batch *batch,
100                             struct blorp_surface_info *info,
101                             const struct blorp_surf *surf,
102                             unsigned int level, float layer,
103                             enum isl_format format, bool is_dest);
104 void
105 blorp_surf_convert_to_single_slice(const struct isl_device *isl_dev,
106                                    struct blorp_surface_info *info);
107 void
108 surf_fake_rgb_with_red(const struct isl_device *isl_dev,
109                        struct blorp_surface_info *info);
110 void
111 blorp_surf_convert_to_uncompressed(const struct isl_device *isl_dev,
112                                    struct blorp_surface_info *info,
113                                    uint32_t *x, uint32_t *y,
114                                    uint32_t *width, uint32_t *height);
115 void
116 blorp_surf_fake_interleaved_msaa(const struct isl_device *isl_dev,
117                                  struct blorp_surface_info *info);
118 void
119 blorp_surf_retile_w_to_y(const struct isl_device *isl_dev,
120                          struct blorp_surface_info *info);
121 
122 
123 struct blorp_coord_transform
124 {
125    float multiplier;
126    float offset;
127 };
128 
129 /**
130  * Bounding rectangle telling pixel discard which pixels are to be touched.
131  * This is needed in when surfaces are configured as something else what they
132  * really are:
133  *
134  *    - writing W-tiled stencil as Y-tiled
135  *    - writing interleaved multisampled as single sampled.
136  *
137  * See blorp_check_in_bounds().
138  */
139 struct blorp_bounds_rect
140 {
141    uint32_t x0;
142    uint32_t x1;
143    uint32_t y0;
144    uint32_t y1;
145 };
146 
147 /**
148  * Grid needed for blended and scaled blits of integer formats, see
149  * blorp_nir_manual_blend_bilinear().
150  */
151 struct blorp_rect_grid
152 {
153    float x1;
154    float y1;
155    float pad[2];
156 };
157 
158 struct blorp_surf_offset {
159    uint32_t x;
160    uint32_t y;
161 };
162 
163 struct blorp_wm_inputs
164 {
165    uint32_t clear_color[4];
166 
167    struct blorp_bounds_rect bounds_rect;
168    struct blorp_rect_grid rect_grid;
169    struct blorp_coord_transform coord_transform[2];
170 
171    struct blorp_surf_offset src_offset;
172    struct blorp_surf_offset dst_offset;
173 
174    /* (1/width, 1/height) for the source surface */
175    float src_inv_size[2];
176 
177    /* Minimum layer setting works for all the textures types but texture_3d
178     * for which the setting has no effect. Use the z-coordinate instead.
179     */
180    float src_z;
181 
182    /* Note: Pad out to an integral number of registers when extending, but
183     * make sure subgroup_id is the last 32-bit item.
184     */
185    /* uint32_t pad[?]; */
186    uint32_t subgroup_id;
187 };
188 
189 static inline nir_variable *
blorp_create_nir_input(struct nir_shader * nir,const char * name,const struct glsl_type * type,unsigned int offset)190 blorp_create_nir_input(struct nir_shader *nir,
191                        const char *name,
192                        const struct glsl_type *type,
193                        unsigned int offset)
194 {
195    nir_variable *input;
196    if (nir->info.stage == MESA_SHADER_COMPUTE) {
197       input = nir_variable_create(nir, nir_var_uniform, type, name);
198       input->data.driver_location = offset;
199       input->data.location = offset;
200    } else {
201       input = nir_variable_create(nir, nir_var_shader_in, type, name);
202       input->data.location = VARYING_SLOT_VAR0 + offset / (4 * sizeof(float));
203       input->data.location_frac = (offset / sizeof(float)) % 4;
204    }
205    if (nir->info.stage == MESA_SHADER_FRAGMENT)
206       input->data.interpolation = INTERP_MODE_FLAT;
207    return input;
208 }
209 
210 #define BLORP_CREATE_NIR_INPUT(shader, name, type) \
211    blorp_create_nir_input((shader), #name, (type), \
212                           offsetof(struct blorp_wm_inputs, name))
213 
214 struct blorp_vs_inputs {
215    uint32_t base_layer;
216    uint32_t _instance_id; /* Set in hardware by SGVS */
217    uint32_t pad[2];
218 };
219 
220 enum blorp_shader_type {
221    BLORP_SHADER_TYPE_COPY,
222    BLORP_SHADER_TYPE_BLIT,
223    BLORP_SHADER_TYPE_CLEAR,
224    BLORP_SHADER_TYPE_MCS_PARTIAL_RESOLVE,
225    BLORP_SHADER_TYPE_LAYER_OFFSET_VS,
226    BLORP_SHADER_TYPE_GFX4_SF,
227 };
228 
229 enum blorp_shader_pipeline {
230    BLORP_SHADER_PIPELINE_RENDER,
231    BLORP_SHADER_PIPELINE_COMPUTE,
232 };
233 
234 struct blorp_params
235 {
236    enum blorp_op op;
237    uint32_t x0;
238    uint32_t y0;
239    uint32_t x1;
240    uint32_t y1;
241    float z;
242    uint8_t stencil_mask;
243    uint8_t stencil_ref;
244    struct blorp_surface_info depth;
245    struct blorp_surface_info stencil;
246    uint32_t depth_format;
247    struct blorp_surface_info src;
248    struct blorp_surface_info dst;
249    enum isl_aux_op hiz_op;
250    bool full_surface_hiz_op;
251    enum isl_aux_op fast_clear_op;
252    uint8_t color_write_disable;
253    struct blorp_wm_inputs wm_inputs;
254    struct blorp_vs_inputs vs_inputs;
255    bool dst_clear_color_as_input;
256    unsigned num_samples;
257    unsigned num_draw_buffers;
258    unsigned num_layers;
259    uint32_t vs_prog_kernel;
260    void *vs_prog_data;
261    uint32_t sf_prog_kernel;
262    void *sf_prog_data;
263    uint32_t wm_prog_kernel;
264    void *wm_prog_data;
265    uint32_t cs_prog_kernel;
266    void *cs_prog_data;
267 
268    bool use_pre_baked_binding_table;
269    uint32_t pre_baked_binding_table_offset;
270    enum blorp_shader_type shader_type;
271    enum blorp_shader_pipeline shader_pipeline;
272 };
273 
274 enum intel_measure_snapshot_type
275 blorp_op_to_intel_measure_snapshot(enum blorp_op op);
276 
277 const char *blorp_op_to_name(enum blorp_op op);
278 
279 void blorp_params_init(struct blorp_params *params);
280 
281 struct blorp_base_key
282 {
283    char name[8];
284    enum blorp_shader_type shader_type;
285    enum blorp_shader_pipeline shader_pipeline;
286 };
287 
288 #define BLORP_BASE_KEY_INIT(_type)                      \
289    (struct blorp_base_key) {                            \
290       .name = "blorp",                                  \
291       .shader_type = _type,                             \
292       .shader_pipeline = BLORP_SHADER_PIPELINE_RENDER,  \
293    }
294 
295 struct blorp_blit_prog_key
296 {
297    struct blorp_base_key base;
298 
299    /* Number of samples per pixel that have been configured in the surface
300     * state for texturing from.
301     */
302    unsigned tex_samples;
303 
304    /* MSAA layout that has been configured in the surface state for texturing
305     * from.
306     */
307    enum isl_msaa_layout tex_layout;
308 
309    enum isl_aux_usage tex_aux_usage;
310 
311    /* Actual number of samples per pixel in the source image. */
312    unsigned src_samples;
313 
314    /* Actual MSAA layout used by the source image. */
315    enum isl_msaa_layout src_layout;
316 
317    /* The swizzle to apply to the source in the shader */
318    struct isl_swizzle src_swizzle;
319 
320    /* The format of the source if format-specific workarounds are needed
321     * and 0 (ISL_FORMAT_R32G32B32A32_FLOAT) if the destination is natively
322     * renderable.
323     */
324    enum isl_format src_format;
325 
326    /* True if the source requires normalized coordinates */
327    bool src_coords_normalized;
328 
329    /* Number of samples per pixel that have been configured in the render
330     * target.
331     */
332    unsigned rt_samples;
333 
334    /* MSAA layout that has been configured in the render target. */
335    enum isl_msaa_layout rt_layout;
336 
337    /* Actual number of samples per pixel in the destination image. */
338    unsigned dst_samples;
339 
340    /* Actual MSAA layout used by the destination image. */
341    enum isl_msaa_layout dst_layout;
342 
343    /* The swizzle to apply to the destination in the shader */
344    struct isl_swizzle dst_swizzle;
345 
346    /* The format of the destination if format-specific workarounds are needed
347     * and 0 (ISL_FORMAT_R32G32B32A32_FLOAT) if the destination is natively
348     * renderable.
349     */
350    enum isl_format dst_format;
351 
352    /* Whether or not the format workarounds are a bitcast operation */
353    bool format_bit_cast;
354 
355    /** True if we need to perform SINT -> UINT clamping. */
356    bool sint32_to_uint;
357 
358    /** True if we need to perform UINT -> SINT clamping. */
359    bool uint32_to_sint;
360 
361    /* Type of the data to be read from the texture (one of
362     * nir_type_(int|uint|float)).
363     */
364    nir_alu_type texture_data_type;
365 
366    /* True if the source image is W tiled.  If true, the surface state for the
367     * source image must be configured as Y tiled, and tex_samples must be 0.
368     */
369    bool src_tiled_w;
370 
371    /* True if the destination image is W tiled.  If true, the surface state
372     * for the render target must be configured as Y tiled, and rt_samples must
373     * be 0.
374     */
375    bool dst_tiled_w;
376 
377    /* True if the destination is an RGB format.  If true, the surface state
378     * for the render target must be configured as red with three times the
379     * normal width.  We need to do this because you cannot render to
380     * non-power-of-two formats.
381     */
382    bool dst_rgb;
383 
384    isl_surf_usage_flags_t dst_usage;
385 
386    enum blorp_filter filter;
387 
388    /* True if the rectangle being sent through the rendering pipeline might be
389     * larger than the destination rectangle, so the WM program should kill any
390     * pixels that are outside the destination rectangle.
391     */
392    bool use_kill;
393 
394    /**
395     * True if the WM program should be run in MSDISPMODE_PERSAMPLE with more
396     * than one sample per pixel.
397     */
398    bool persample_msaa_dispatch;
399 
400    /* True if this blit operation may involve intratile offsets on the source.
401     * In this case, we need to add the offset before texturing.
402     */
403    bool need_src_offset;
404 
405    /* True if this blit operation may involve intratile offsets on the
406     * destination.  In this case, we need to add the offset to gl_FragCoord.
407     */
408    bool need_dst_offset;
409 
410    /* Scale factors between the pixel grid and the grid of samples. We're
411     * using grid of samples for bilinear filetring in multisample scaled blits.
412     */
413    float x_scale;
414    float y_scale;
415 
416    /* If a compute shader is used, this is the local size y dimension.
417     */
418    uint8_t local_y;
419 };
420 
421 /**
422  * \name BLORP internals
423  * \{
424  *
425  * Used internally by gfx6_blorp_exec() and gfx7_blorp_exec().
426  */
427 
428 bool blorp_blitter_supports_aux(const struct intel_device_info *devinfo,
429                                 enum isl_aux_usage aux_usage);
430 
431 const char *blorp_shader_type_to_name(enum blorp_shader_type type);
432 const char *blorp_shader_pipeline_to_name(enum blorp_shader_pipeline pipe);
433 
434 struct blorp_program {
435    const void *kernel;
436    uint32_t    kernel_size;
437 
438    const void *prog_data;
439    uint32_t    prog_data_size;
440 };
441 
442 static inline struct blorp_program
blorp_compile_fs(struct blorp_context * blorp,void * mem_ctx,struct nir_shader * nir,bool multisample_fbo,bool use_repclear)443 blorp_compile_fs(struct blorp_context *blorp, void *mem_ctx,
444                  struct nir_shader *nir,
445                  bool multisample_fbo,
446                  bool use_repclear)
447 {
448    return blorp->compiler->compile_fs(blorp, mem_ctx, nir, multisample_fbo, use_repclear);
449 }
450 
451 static inline struct blorp_program
blorp_compile_vs(struct blorp_context * blorp,void * mem_ctx,struct nir_shader * nir)452 blorp_compile_vs(struct blorp_context *blorp, void *mem_ctx,
453                  struct nir_shader *nir)
454 {
455    return blorp->compiler->compile_vs(blorp, mem_ctx, nir);
456 }
457 
458 static inline bool
blorp_ensure_sf_program(struct blorp_batch * batch,struct blorp_params * params)459 blorp_ensure_sf_program(struct blorp_batch *batch,
460                         struct blorp_params *params)
461 {
462    struct blorp_compiler *c = batch->blorp->compiler;
463    /* Absence of callback indicates it is not needed.  This is the case for
464     * brw, which is Gfx9+.
465     */
466    return !c->ensure_sf_program || c->ensure_sf_program(batch, params);
467 }
468 
469 static inline uint8_t
blorp_get_cs_local_y(struct blorp_params * params)470 blorp_get_cs_local_y(struct blorp_params *params)
471 {
472    uint32_t height = params->y1 - params->y0;
473    uint32_t or_ys = params->y0 | params->y1;
474    if (height > 32 || (or_ys & 3) == 0) {
475       return 4;
476    } else if ((or_ys & 1) == 0) {
477       return 2;
478    } else {
479       return 1;
480    }
481 }
482 
483 static inline void
blorp_set_cs_dims(struct nir_shader * nir,uint8_t local_y)484 blorp_set_cs_dims(struct nir_shader *nir, uint8_t local_y)
485 {
486    assert(local_y != 0 && (16 % local_y == 0));
487    nir->info.workgroup_size[0] = 16 / local_y;
488    nir->info.workgroup_size[1] = local_y;
489    nir->info.workgroup_size[2] = 1;
490 }
491 
492 static inline struct blorp_program
blorp_compile_cs(struct blorp_context * blorp,void * mem_ctx,struct nir_shader * nir)493 blorp_compile_cs(struct blorp_context *blorp, void *mem_ctx,
494                  struct nir_shader *nir)
495 {
496    return blorp->compiler->compile_cs(blorp, mem_ctx, nir);
497 }
498 
499 static inline bool
blorp_params_get_layer_offset_vs(struct blorp_batch * batch,struct blorp_params * params)500 blorp_params_get_layer_offset_vs(struct blorp_batch *batch,
501                                  struct blorp_params *params)
502 {
503    return batch->blorp->compiler->params_get_layer_offset_vs(batch, params);
504 }
505 
506 /** \} */
507 
508 #ifdef __cplusplus
509 } /* end extern "C" */
510 #endif /* __cplusplus */
511 
512 #endif /* BLORP_PRIV_H */
513