summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gallium/drivers/svga/svga_tgsi_decl_sm30.c88
-rw-r--r--src/gallium/drivers/svga/svga_tgsi_emit.h7
-rw-r--r--src/gallium/drivers/svga/svga_tgsi_insn.c4
3 files changed, 86 insertions, 13 deletions
diff --git a/src/gallium/drivers/svga/svga_tgsi_decl_sm30.c b/src/gallium/drivers/svga/svga_tgsi_decl_sm30.c
index 3b70a3a7635..ed4b000e4f3 100644
--- a/src/gallium/drivers/svga/svga_tgsi_decl_sm30.c
+++ b/src/gallium/drivers/svga/svga_tgsi_decl_sm30.c
@@ -58,8 +58,7 @@ static boolean translate_vs_ps_semantic( struct tgsi_declaration_semantic semant
*usage = SVGA3D_DECLUSAGE_PSIZE;
break;
case TGSI_SEMANTIC_GENERIC:
- *idx = semantic.Index + 2; /* texcoord[0] is reserved for fog,
- texcoord[1] is reserved for position */
+ *idx = semantic.Index + 1; /* texcoord[0] is reserved for fog & position */
*usage = SVGA3D_DECLUSAGE_TEXCOORD;
break;
case TGSI_SEMANTIC_NORMAL:
@@ -113,6 +112,28 @@ static boolean emit_vface_decl( struct svga_shader_emitter *emit )
return TRUE;
}
+static boolean
+ps30_input_emit_depth_fog( struct svga_shader_emitter *emit,
+ struct src_register *out )
+{
+ struct src_register reg;
+
+
+ if (emit->emitted_depth_fog) {
+ *out = emit->ps_depth_fog;
+ return TRUE;
+ }
+
+ reg = src_register( SVGA3DREG_INPUT,
+ emit->ps30_input_count++ );
+
+ *out = emit->ps_depth_fog = reg;
+
+ emit->emitted_depth_fog = TRUE;
+
+ return emit_decl( emit, dst( reg ), SVGA3D_DECLUSAGE_TEXCOORD, 0 );
+}
+
static boolean ps30_input( struct svga_shader_emitter *emit,
struct tgsi_declaration_semantic semantic,
unsigned idx )
@@ -135,16 +156,18 @@ static boolean ps30_input( struct svga_shader_emitter *emit,
if (emit->info.reads_z) {
emit->ps_temp_pos = dst_register( SVGA3DREG_TEMP,
emit->nr_hw_temp );
- emit->ps_depth_pos = src_register( SVGA3DREG_INPUT,
- emit->ps30_input_count++ );
emit->input_map[idx] = src_register( SVGA3DREG_TEMP,
emit->nr_hw_temp );
emit->nr_hw_temp++;
- if (!emit_decl( emit, dst( emit->ps_depth_pos ),
- SVGA3D_DECLUSAGE_TEXCOORD, 1 ))
+ if (!ps30_input_emit_depth_fog( emit, &emit->ps_depth_pos ))
return FALSE;
+
+ emit->ps_depth_pos.base.swizzle = TRANSLATE_SWIZZLE( TGSI_SWIZZLE_Z,
+ TGSI_SWIZZLE_Z,
+ TGSI_SWIZZLE_Z,
+ TGSI_SWIZZLE_W );
}
else {
emit->input_map[idx] = emit->ps_true_pos;
@@ -189,6 +212,20 @@ static boolean ps30_input( struct svga_shader_emitter *emit,
emit->internal_frontface_idx = idx;
return TRUE;
}
+ else if (semantic.Name == TGSI_SEMANTIC_FOG) {
+
+ assert(semantic.Index == 0);
+
+ if (!ps30_input_emit_depth_fog( emit, &emit->input_map[idx] ))
+ return FALSE;
+
+ emit->input_map[idx].base.swizzle = TRANSLATE_SWIZZLE( TGSI_SWIZZLE_X,
+ TGSI_SWIZZLE_X,
+ TGSI_SWIZZLE_X,
+ TGSI_SWIZZLE_X );
+
+ return TRUE;
+ }
else {
if (!translate_vs_ps_semantic( semantic, &usage, &index ))
@@ -289,6 +326,25 @@ static boolean vs30_input( struct svga_shader_emitter *emit,
return TRUE;
}
+static boolean vs30_output_emit_depth_fog( struct svga_shader_emitter *emit,
+ SVGA3dShaderDestToken *out )
+{
+ SVGA3dShaderDestToken reg;
+
+ if (emit->emitted_depth_fog) {
+ *out = emit->vs_depth_fog;
+ return TRUE;
+ }
+
+ reg = dst_register( SVGA3DREG_OUTPUT, emit->vs30_output_count++ );
+
+ *out = emit->vs_depth_fog = reg;
+
+ emit->emitted_depth_fog = TRUE;
+
+ return emit_decl( emit, reg, SVGA3D_DECLUSAGE_TEXCOORD, 0 );
+}
+
/* VS3.0 outputs have proper declarations and semantic info for
* matching against PS inputs.
*/
@@ -318,13 +374,11 @@ static boolean vs30_output( struct svga_shader_emitter *emit,
emit->nr_hw_temp++ );
emit->temp_pos = emit->output_map[idx];
emit->true_pos = dcl.dst;
+
/* Grab an extra output for the depth output */
- emit->depth_pos = dst_register( SVGA3DREG_OUTPUT,
- emit->vs30_output_count++ );
- emit->info.num_outputs++;
+ if (!vs30_output_emit_depth_fog( emit, &emit->depth_pos ))
+ return FALSE;
- emit_decl( emit, emit->depth_pos,
- SVGA3D_DECLUSAGE_TEXCOORD, 1 );
}
else if (semantic.Name == TGSI_SEMANTIC_PSIZE) {
emit->output_map[idx] = dst_register( SVGA3DREG_TEMP,
@@ -339,6 +393,18 @@ static boolean vs30_output( struct svga_shader_emitter *emit,
emit->true_psiz = dcl.dst;
}
+ else if (semantic.Name == TGSI_SEMANTIC_FOG) {
+ /*
+ * Fog is shared with depth.
+ * So we need to decrement out_count since emit_depth_fog will increment it.
+ */
+ emit->vs30_output_count--;
+
+ if (!vs30_output_emit_depth_fog( emit, &emit->output_map[idx] ))
+ return FALSE;
+
+ return TRUE;
+ }
else {
emit->output_map[idx] = dcl.dst;
}
diff --git a/src/gallium/drivers/svga/svga_tgsi_emit.h b/src/gallium/drivers/svga/svga_tgsi_emit.h
index 21bb8da44f8..b1300dc8ecd 100644
--- a/src/gallium/drivers/svga/svga_tgsi_emit.h
+++ b/src/gallium/drivers/svga/svga_tgsi_emit.h
@@ -101,15 +101,22 @@ struct svga_shader_emitter
SVGA3dShaderDestToken output_map[PIPE_MAX_ATTRIBS];
boolean ps_reads_pos;
+ boolean emitted_depth_fog;
struct src_register ps_true_pos;
struct src_register ps_depth_pos;
SVGA3dShaderDestToken ps_temp_pos;
+ /* shared input for depth and fog */
+ struct src_register ps_depth_fog;
+
struct src_register imm_0055;
SVGA3dShaderDestToken temp_pos;
SVGA3dShaderDestToken true_pos;
SVGA3dShaderDestToken depth_pos;
+ /* shared output for depth and fog */
+ SVGA3dShaderDestToken vs_depth_fog;
+
SVGA3dShaderDestToken temp_col[PIPE_MAX_COLOR_BUFS];
SVGA3dShaderDestToken true_col[PIPE_MAX_COLOR_BUFS];
diff --git a/src/gallium/drivers/svga/svga_tgsi_insn.c b/src/gallium/drivers/svga/svga_tgsi_insn.c
index e6ec5966eaa..10688accdaa 100644
--- a/src/gallium/drivers/svga/svga_tgsi_insn.c
+++ b/src/gallium/drivers/svga/svga_tgsi_insn.c
@@ -2692,7 +2692,7 @@ static boolean emit_vs_postamble( struct svga_shader_emitter *emit )
/* Also write to depth value */
if (!submit_op3( emit,
inst_token(SVGA3DOP_MAD),
- writemask(depth, TGSI_WRITEMASK_XYZ),
+ writemask(depth, TGSI_WRITEMASK_Z),
swizzle(src(temp_pos), 3, 3, 3, 3),
prescale_trans,
src(temp_pos) ))
@@ -2725,7 +2725,7 @@ static boolean emit_vs_postamble( struct svga_shader_emitter *emit )
/* Move the manipulated depth into the extra texcoord reg */
if (!submit_op1( emit,
inst_token(SVGA3DOP_MOV),
- depth,
+ writemask(depth, TGSI_WRITEMASK_ZW),
src(temp_pos) ))
return FALSE;
}