From: Marek Olšák Date: Tue, 24 Dec 2019 03:16:42 +0000 (-0500) Subject: radeonsi: separate code computing info for small primitive culling X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=8070402a3043edb34000b1d410f9b73ab45ae686;p=mesa.git radeonsi: separate code computing info for small primitive culling Reviewed-by: Pierre-Eric Pelloux-Prayer --- diff --git a/src/gallium/drivers/radeonsi/si_compute_prim_discard.c b/src/gallium/drivers/radeonsi/si_compute_prim_discard.c index 2092510e53d..4e691d088c2 100644 --- a/src/gallium/drivers/radeonsi/si_compute_prim_discard.c +++ b/src/gallium/drivers/radeonsi/si_compute_prim_discard.c @@ -1315,50 +1315,18 @@ void si_dispatch_prim_discard_cs_and_draw(struct si_context *sctx, S_008F0C_NUM_FORMAT(V_008F0C_BUF_NUM_FORMAT_UINT) | S_008F0C_DATA_FORMAT(output_indexbuf_format); - /* Viewport state. - * This is needed by the small primitive culling, because it's done - * in screen space. - */ - float scale[2], translate[2]; - - scale[0] = sctx->viewports.states[0].scale[0]; - scale[1] = sctx->viewports.states[0].scale[1]; - translate[0] = sctx->viewports.states[0].translate[0]; - translate[1] = sctx->viewports.states[0].translate[1]; - - /* The viewport shouldn't flip the X axis for the small prim culling to work. */ - assert(-scale[0] + translate[0] <= scale[0] + translate[0]); - - /* If the Y axis is inverted (OpenGL default framebuffer), reverse it. - * This is because the viewport transformation inverts the clip space - * bounding box, so min becomes max, which breaks small primitive - * culling. - */ - if (sctx->viewports.y_inverted) { - scale[1] = -scale[1]; - translate[1] = -translate[1]; - } + /* Viewport state. */ + struct si_small_prim_cull_info cull_info; + si_get_small_prim_cull_info(sctx, &cull_info); - /* Scale the framebuffer up, so that samples become pixels and small - * primitive culling is the same for all sample counts. - * This only works with the standard DX sample positions, because - * the samples are evenly spaced on both X and Y axes. - */ - unsigned num_samples = sctx->framebuffer.nr_samples; - assert(num_samples >= 1); - - for (unsigned i = 0; i < 2; i++) { - scale[i] *= num_samples; - translate[i] *= num_samples; - } - - desc[8] = fui(scale[0]); - desc[9] = fui(scale[1]); - desc[10] = fui(translate[0]); - desc[11] = fui(translate[1]); + desc[8] = fui(cull_info.scale[0]); + desc[9] = fui(cull_info.scale[1]); + desc[10] = fui(cull_info.translate[0]); + desc[11] = fui(cull_info.translate[1]); /* Better subpixel precision increases the efficiency of small * primitive culling. */ + unsigned num_samples = sctx->framebuffer.nr_samples; unsigned quant_mode = sctx->viewports.as_scissor[0].quant_mode; float small_prim_cull_precision; diff --git a/src/gallium/drivers/radeonsi/si_pipe.h b/src/gallium/drivers/radeonsi/si_pipe.h index d42f0ff4616..c75b131f8c6 100644 --- a/src/gallium/drivers/radeonsi/si_pipe.h +++ b/src/gallium/drivers/radeonsi/si_pipe.h @@ -862,6 +862,10 @@ struct si_sdma_upload { unsigned size; }; +struct si_small_prim_cull_info { + float scale[2], translate[2]; +}; + struct si_context { struct pipe_context b; /* base class */ @@ -1491,6 +1495,8 @@ struct pipe_video_buffer *si_video_buffer_create(struct pipe_context *pipe, const struct pipe_video_buffer *tmpl); /* si_viewport.c */ +void si_get_small_prim_cull_info(struct si_context *sctx, + struct si_small_prim_cull_info *out); void si_update_vs_viewport_state(struct si_context *ctx); void si_init_viewport_functions(struct si_context *ctx); diff --git a/src/gallium/drivers/radeonsi/si_state_viewport.c b/src/gallium/drivers/radeonsi/si_state_viewport.c index 1c59321f9fe..e0d81078139 100644 --- a/src/gallium/drivers/radeonsi/si_state_viewport.c +++ b/src/gallium/drivers/radeonsi/si_state_viewport.c @@ -27,6 +27,46 @@ #define SI_MAX_SCISSOR 16384 +void si_get_small_prim_cull_info(struct si_context *sctx, + struct si_small_prim_cull_info *out) +{ + /* This is needed by the small primitive culling, because it's done + * in screen space. + */ + struct si_small_prim_cull_info info; + unsigned num_samples = sctx->framebuffer.nr_samples; + assert(num_samples >= 1); + + info.scale[0] = sctx->viewports.states[0].scale[0]; + info.scale[1] = sctx->viewports.states[0].scale[1]; + info.translate[0] = sctx->viewports.states[0].translate[0]; + info.translate[1] = sctx->viewports.states[0].translate[1]; + + /* The viewport shouldn't flip the X axis for the small prim culling to work. */ + assert(-info.scale[0] + info.translate[0] <= info.scale[0] + info.translate[0]); + + /* If the Y axis is inverted (OpenGL default framebuffer), reverse it. + * This is because the viewport transformation inverts the clip space + * bounding box, so min becomes max, which breaks small primitive + * culling. + */ + if (sctx->viewports.y_inverted) { + info.scale[1] = -info.scale[1]; + info.translate[1] = -info.translate[1]; + } + + /* Scale the framebuffer up, so that samples become pixels and small + * primitive culling is the same for all sample counts. + * This only works with the standard DX sample positions, because + * the samples are evenly spaced on both X and Y axes. + */ + for (unsigned i = 0; i < 2; i++) { + info.scale[i] *= num_samples; + info.translate[i] *= num_samples; + } + *out = info; +} + static void si_set_scissor_states(struct pipe_context *pctx, unsigned start_slot, unsigned num_scissors,