summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/r600
diff options
context:
space:
mode:
authorDave Airlie <[email protected]>2016-05-13 14:35:33 +1000
committerDave Airlie <[email protected]>2017-11-21 09:00:52 +1000
commit464c2d80834e4ccf7f28fb62b82a2fa13e6445fb (patch)
tree1c6f03a46fbadfe95eed07e399f661e64d4b73cb /src/gallium/drivers/r600
parent971b3c019b7309c32048b68f61af03d1ae2b7d10 (diff)
r600: add cull distance support
This passes all the tests in piglit. Signed-off-by: Dave Airlie <[email protected]>
Diffstat (limited to 'src/gallium/drivers/r600')
-rw-r--r--src/gallium/drivers/r600/evergreen_state.c4
-rw-r--r--src/gallium/drivers/r600/r600_pipe.c3
-rw-r--r--src/gallium/drivers/r600/r600_pipe.h2
-rw-r--r--src/gallium/drivers/r600/r600_shader.c14
-rw-r--r--src/gallium/drivers/r600/r600_shader.h2
-rw-r--r--src/gallium/drivers/r600/r600_state_common.c5
6 files changed, 24 insertions, 6 deletions
diff --git a/src/gallium/drivers/r600/evergreen_state.c b/src/gallium/drivers/r600/evergreen_state.c
index 5a3a8514abb..dcbc6862832 100644
--- a/src/gallium/drivers/r600/evergreen_state.c
+++ b/src/gallium/drivers/r600/evergreen_state.c
@@ -3495,8 +3495,8 @@ void evergreen_update_vs_state(struct pipe_context *ctx, struct r600_pipe_shader
/* After that, the NOP relocation packet must be emitted (shader->bo, RADEON_USAGE_READ). */
shader->pa_cl_vs_out_cntl =
- S_02881C_VS_OUT_CCDIST0_VEC_ENA((rshader->clip_dist_write & 0x0F) != 0) |
- S_02881C_VS_OUT_CCDIST1_VEC_ENA((rshader->clip_dist_write & 0xF0) != 0) |
+ S_02881C_VS_OUT_CCDIST0_VEC_ENA((rshader->cc_dist_mask & 0x0F) != 0) |
+ S_02881C_VS_OUT_CCDIST1_VEC_ENA((rshader->cc_dist_mask & 0xF0) != 0) |
S_02881C_VS_OUT_MISC_VEC_ENA(rshader->vs_out_misc_write) |
S_02881C_USE_VTX_POINT_SIZE(rshader->vs_out_point_size) |
S_02881C_USE_VTX_EDGE_FLAG(rshader->vs_out_edgeflag) |
diff --git a/src/gallium/drivers/r600/r600_pipe.c b/src/gallium/drivers/r600/r600_pipe.c
index a232ee46a86..9cdef10e480 100644
--- a/src/gallium/drivers/r600/r600_pipe.c
+++ b/src/gallium/drivers/r600/r600_pipe.c
@@ -387,7 +387,6 @@ static int r600_get_param(struct pipe_screen* pscreen, enum pipe_cap param)
case PIPE_CAP_STRING_MARKER:
case PIPE_CAP_QUERY_BUFFER_OBJECT:
case PIPE_CAP_ROBUST_BUFFER_ACCESS_BEHAVIOR:
- case PIPE_CAP_CULL_DISTANCE:
case PIPE_CAP_PRIMITIVE_RESTART_FOR_PATCHES:
case PIPE_CAP_TGSI_VOTE:
case PIPE_CAP_MAX_WINDOW_RECTANGLES:
@@ -422,6 +421,8 @@ static int r600_get_param(struct pipe_screen* pscreen, enum pipe_cap param)
rscreen->b.family == CHIP_HEMLOCK)
return 1;
return 0;
+ case PIPE_CAP_CULL_DISTANCE:
+ return 1;
case PIPE_CAP_MAX_SHADER_PATCH_VARYINGS:
if (family >= CHIP_CEDAR)
diff --git a/src/gallium/drivers/r600/r600_pipe.h b/src/gallium/drivers/r600/r600_pipe.h
index ad7e499be21..f651d66e070 100644
--- a/src/gallium/drivers/r600/r600_pipe.h
+++ b/src/gallium/drivers/r600/r600_pipe.h
@@ -154,7 +154,9 @@ struct r600_clip_misc_state {
unsigned pa_cl_clip_cntl; /* from rasterizer */
unsigned pa_cl_vs_out_cntl; /* from vertex shader */
unsigned clip_plane_enable; /* from rasterizer */
+ unsigned cc_dist_mask; /* from vertex shader */
unsigned clip_dist_write; /* from vertex shader */
+ unsigned cull_dist_write; /* from vertex shader */
boolean clip_disable; /* from vertex shader */
boolean vs_out_viewport; /* from vertex shader */
};
diff --git a/src/gallium/drivers/r600/r600_shader.c b/src/gallium/drivers/r600/r600_shader.c
index 9d0e6252957..1422abf6fa9 100644
--- a/src/gallium/drivers/r600/r600_shader.c
+++ b/src/gallium/drivers/r600/r600_shader.c
@@ -917,8 +917,6 @@ static int tgsi_declaration(struct r600_shader_ctx *ctx)
ctx->shader->output[i].spi_sid = r600_spi_sid(&ctx->shader->output[i]);
switch (d->Semantic.Name) {
case TGSI_SEMANTIC_CLIPDIST:
- ctx->shader->clip_dist_write |= d->Declaration.UsageMask <<
- ((d->Semantic.Index + j) << 2);
break;
case TGSI_SEMANTIC_PSIZE:
ctx->shader->vs_out_misc_write = 1;
@@ -2372,6 +2370,8 @@ static int generate_gs_copy_shader(struct r600_context *rctx,
/* spi_sid is 0 for clipdistance outputs that were generated
* for clipvertex - we don't need to pass them to PS */
ctx.shader->clip_dist_write = gs->shader.clip_dist_write;
+ ctx.shader->cull_dist_write = gs->shader.cull_dist_write;
+ ctx.shader->cc_dist_mask = gs->shader.cc_dist_mask;
if (out->spi_sid) {
/* duplicate it as PARAM to pass to the pixel shader */
output.array_base = next_param++;
@@ -3238,6 +3238,15 @@ static int r600_shader_from_tgsi(struct r600_context *rctx,
shader->vs_position_window_space = ctx.info.properties[TGSI_PROPERTY_VS_WINDOW_SPACE_POSITION];
shader->ps_conservative_z = (uint8_t)ctx.info.properties[TGSI_PROPERTY_FS_DEPTH_LAYOUT];
+ if (ctx.type == PIPE_SHADER_VERTEX ||
+ ctx.type == PIPE_SHADER_GEOMETRY ||
+ ctx.type == PIPE_SHADER_TESS_EVAL) {
+ shader->cc_dist_mask = (1 << (ctx.info.properties[TGSI_PROPERTY_NUM_CULLDIST_ENABLED] +
+ ctx.info.properties[TGSI_PROPERTY_NUM_CLIPDIST_ENABLED])) - 1;
+ shader->clip_dist_write = (1 << ctx.info.properties[TGSI_PROPERTY_NUM_CLIPDIST_ENABLED]) - 1;
+ shader->cull_dist_write = ((1 << ctx.info.properties[TGSI_PROPERTY_NUM_CULLDIST_ENABLED]) - 1) << ctx.info.properties[TGSI_PROPERTY_NUM_CLIPDIST_ENABLED];
+ }
+
if (shader->vs_as_gs_a)
vs_add_primid_output(&ctx, key.vs.prim_id_out);
@@ -3490,6 +3499,7 @@ static int r600_shader_from_tgsi(struct r600_context *rctx,
shader->output[ctx.cv_output].spi_sid = 0;
shader->clip_dist_write = 0xFF;
+ shader->cc_dist_mask = 0xFF;
for (i = 0; i < 8; i++) {
int oreg = i >> 2;
diff --git a/src/gallium/drivers/r600/r600_shader.h b/src/gallium/drivers/r600/r600_shader.h
index 5d6501c8d38..84449078839 100644
--- a/src/gallium/drivers/r600/r600_shader.h
+++ b/src/gallium/drivers/r600/r600_shader.h
@@ -85,7 +85,9 @@ struct r600_shader {
/* Real number of ps color exports compiled in the bytecode */
unsigned nr_ps_color_exports;
/* bit n is set if the shader writes gl_ClipDistance[n] */
+ unsigned cc_dist_mask;
unsigned clip_dist_write;
+ unsigned cull_dist_write;
boolean vs_position_window_space;
/* flag is set if the shader writes VS_OUT_MISC_VEC (e.g. for PSIZE) */
boolean vs_out_misc_write;
diff --git a/src/gallium/drivers/r600/r600_state_common.c b/src/gallium/drivers/r600/r600_state_common.c
index b8d4b8f70fa..a977cdc30d2 100644
--- a/src/gallium/drivers/r600/r600_state_common.c
+++ b/src/gallium/drivers/r600/r600_state_common.c
@@ -1465,10 +1465,12 @@ static void r600_update_clip_state(struct r600_context *rctx,
{
if (current->pa_cl_vs_out_cntl != rctx->clip_misc_state.pa_cl_vs_out_cntl ||
current->shader.clip_dist_write != rctx->clip_misc_state.clip_dist_write ||
+ current->shader.cull_dist_write != rctx->clip_misc_state.cull_dist_write ||
current->shader.vs_position_window_space != rctx->clip_misc_state.clip_disable ||
current->shader.vs_out_viewport != rctx->clip_misc_state.vs_out_viewport) {
rctx->clip_misc_state.pa_cl_vs_out_cntl = current->pa_cl_vs_out_cntl;
rctx->clip_misc_state.clip_dist_write = current->shader.clip_dist_write;
+ rctx->clip_misc_state.cull_dist_write = current->shader.cull_dist_write;
rctx->clip_misc_state.clip_disable = current->shader.vs_position_window_space;
rctx->clip_misc_state.vs_out_viewport = current->shader.vs_out_viewport;
r600_mark_atom_dirty(rctx, &rctx->clip_misc_state.atom);
@@ -1769,7 +1771,8 @@ void r600_emit_clip_misc_state(struct r600_context *rctx, struct r600_atom *atom
S_028810_CLIP_DISABLE(state->clip_disable));
radeon_set_context_reg(cs, R_02881C_PA_CL_VS_OUT_CNTL,
state->pa_cl_vs_out_cntl |
- (state->clip_plane_enable & state->clip_dist_write));
+ (state->clip_plane_enable & state->clip_dist_write) |
+ (state->cull_dist_write << 8));
/* reuse needs to be set off if we write oViewport */
if (rctx->b.chip_class >= EVERGREEN)
radeon_set_context_reg(cs, R_028AB4_VGT_REUSE_OFF,