diff options
author | Glenn Kennard <[email protected]> | 2014-07-23 11:57:55 +0200 |
---|---|---|
committer | Andreas Boll <[email protected]> | 2014-07-31 11:51:05 +0200 |
commit | b1eb00cd4008e9529f3cbdf0ce8a58aa68e75793 (patch) | |
tree | 8481d0e21d287faa8f529bd9a6ed193b6e6af5b9 | |
parent | 2768a56f5851c7c2f611ca2a9fb12ad010b608d7 (diff) |
r600g: gpu_shader5 gl_SampleMaskIn support
Map TGSI_SEMANTIC_SAMPLEMASK to register/component.
Enable face register when sample mask is needed by shader.
Requires Evergreen/Cayman
Reviewed-by: Alex Deucher <[email protected]>
-rw-r--r-- | docs/GL3.txt | 2 | ||||
-rw-r--r-- | src/gallium/drivers/r600/evergreen_state.c | 10 | ||||
-rw-r--r-- | src/gallium/drivers/r600/r600_shader.c | 37 |
3 files changed, 41 insertions, 8 deletions
diff --git a/docs/GL3.txt b/docs/GL3.txt index 89a4ea31613..59b20dc2e42 100644 --- a/docs/GL3.txt +++ b/docs/GL3.txt @@ -109,7 +109,7 @@ GL 4.0: - Enhanced textureGather DONE (i965, nvc0, radeonsi) - Geometry shader instancing DONE (i965, nvc0) - Geometry shader multiple streams DONE (i965, nvc0) - - Enhanced per-sample shading DONE (i965) + - Enhanced per-sample shading DONE (i965, r600) - Interpolation functions DONE (i965) - New overload resolution rules DONE GL_ARB_gpu_shader_fp64 started (Dave) diff --git a/src/gallium/drivers/r600/evergreen_state.c b/src/gallium/drivers/r600/evergreen_state.c index 45c611e5cc2..608b05b332f 100644 --- a/src/gallium/drivers/r600/evergreen_state.c +++ b/src/gallium/drivers/r600/evergreen_state.c @@ -2841,8 +2841,14 @@ void evergreen_update_ps_state(struct pipe_context *ctx, struct r600_pipe_shader POSITION goes via GPRs from the SC so isn't counted */ if (rshader->input[i].name == TGSI_SEMANTIC_POSITION) pos_index = i; - else if (rshader->input[i].name == TGSI_SEMANTIC_FACE) - face_index = i; + else if (rshader->input[i].name == TGSI_SEMANTIC_FACE) { + if (face_index == -1) + face_index = i; + } + else if (rshader->input[i].name == TGSI_SEMANTIC_SAMPLEMASK) { + if (face_index == -1) + face_index = i; /* lives in same register, same enable bit */ + } else { ninterp++; if (rshader->input[i].interpolate == TGSI_INTERPOLATE_LINEAR) diff --git a/src/gallium/drivers/r600/r600_shader.c b/src/gallium/drivers/r600/r600_shader.c index 175c09b9501..00b2f4aeaed 100644 --- a/src/gallium/drivers/r600/r600_shader.c +++ b/src/gallium/drivers/r600/r600_shader.c @@ -287,7 +287,9 @@ struct r600_shader_ctx { boolean input_linear; boolean input_perspective; int num_interp_gpr; + /* evergreen/cayman also store sample mask in face register */ int face_gpr; + boolean has_samplemask; int colors_used; boolean clip_vertex_write; unsigned cv_output; @@ -498,7 +500,8 @@ static int r600_spi_sid(struct r600_shader_io * io) if (name == TGSI_SEMANTIC_POSITION || name == TGSI_SEMANTIC_PSIZE || name == TGSI_SEMANTIC_EDGEFLAG || - name == TGSI_SEMANTIC_FACE) + name == TGSI_SEMANTIC_FACE || + name == TGSI_SEMANTIC_SAMPLEMASK) index = 0; else { if (name == TGSI_SEMANTIC_GENERIC) { @@ -585,7 +588,8 @@ static int tgsi_declaration(struct r600_shader_ctx *ctx) ctx->shader->input[i].spi_sid = r600_spi_sid(&ctx->shader->input[i]); switch (ctx->shader->input[i].name) { case TGSI_SEMANTIC_FACE: - ctx->face_gpr = ctx->shader->input[i].gpr; + if (ctx->face_gpr == -1) + ctx->face_gpr = ctx->shader->input[i].gpr; break; case TGSI_SEMANTIC_COLOR: ctx->colors_used++; @@ -675,7 +679,14 @@ static int tgsi_declaration(struct r600_shader_ctx *ctx) break; case TGSI_FILE_SYSTEM_VALUE: - if (d->Semantic.Name == TGSI_SEMANTIC_INSTANCEID) { + if (d->Semantic.Name == TGSI_SEMANTIC_SAMPLEMASK) { + ctx->has_samplemask = true; + /* lives in Front Face GPR */ + if (ctx->face_gpr == -1) + ctx->face_gpr = ctx->file_offset[TGSI_FILE_SYSTEM_VALUE] + d->Range.First; + break; + } + else if (d->Semantic.Name == TGSI_SEMANTIC_INSTANCEID) { if (!ctx->native_integers) { struct r600_bytecode_alu alu; memset(&alu, 0, sizeof(struct r600_bytecode_alu)); @@ -729,7 +740,8 @@ static int evergreen_gpr_count(struct r600_shader_ctx *ctx) for (i = 0; i < ctx->info.num_inputs; i++) { /* skip position/face */ if (ctx->info.input_semantic_name[i] == TGSI_SEMANTIC_POSITION || - ctx->info.input_semantic_name[i] == TGSI_SEMANTIC_FACE) + ctx->info.input_semantic_name[i] == TGSI_SEMANTIC_FACE || + ctx->info.input_semantic_name[i] == TGSI_SEMANTIC_SAMPLEMASK) continue; if (ctx->info.input_interpolate[i] == TGSI_INTERPOLATE_LINEAR) ctx->input_linear = TRUE; @@ -781,7 +793,13 @@ static void tgsi_src(struct r600_shader_ctx *ctx, r600_src->sel = V_SQ_ALU_SRC_LITERAL; memcpy(r600_src->value, ctx->literals + index * 4, sizeof(r600_src->value)); } else if (tgsi_src->Register.File == TGSI_FILE_SYSTEM_VALUE) { - if (ctx->info.system_value_semantic_name[tgsi_src->Register.Index] == TGSI_SEMANTIC_INSTANCEID) { + if (ctx->info.system_value_semantic_name[tgsi_src->Register.Index] == TGSI_SEMANTIC_SAMPLEMASK) { + r600_src->swizzle[0] = 2; // Z value + r600_src->swizzle[0] = 2; + r600_src->swizzle[0] = 2; + r600_src->swizzle[0] = 2; + r600_src->sel = ctx->face_gpr; + } else if (ctx->info.system_value_semantic_name[tgsi_src->Register.Index] == TGSI_SEMANTIC_INSTANCEID) { r600_src->swizzle[0] = 3; r600_src->swizzle[1] = 3; r600_src->swizzle[2] = 3; @@ -1585,6 +1603,7 @@ static int r600_shader_from_tgsi(struct r600_context *rctx, ctx.gs_next_vertex = 0; ctx.face_gpr = -1; + ctx.has_samplemask = false; ctx.fragcoord_input = -1; ctx.colors_used = 0; ctx.clip_vertex_write = 0; @@ -1744,6 +1763,14 @@ static int r600_shader_from_tgsi(struct r600_context *rctx, shader->ring_item_size = ctx.next_ring_offset; + /* Need to tell setup to program FACE register */ + if (ctx.has_samplemask && ctx.face_gpr != -1) { + i = ctx.shader->ninput++; + ctx.shader->input[i].name = TGSI_SEMANTIC_SAMPLEMASK; + ctx.shader->input[i].spi_sid = 0; + ctx.shader->input[i].gpr = ctx.face_gpr; + } + /* Process two side if needed */ if (shader->two_side && ctx.colors_used) { int i, count = ctx.shader->ninput; |