X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=src%2Fmesa%2Fstate_tracker%2Fst_mesa_to_tgsi.c;h=e788008dfe1d337c3e0bfbb7e02a21afde99c3c2;hb=e32487b8a13a9efabb0359a9dde33e074e905e82;hp=b0a1b529f1e430b1966d5a7c3d4a33c7721884f8;hpb=8fda97afb8b7a03415dbca6d83691d2d6461126c;p=mesa.git diff --git a/src/mesa/state_tracker/st_mesa_to_tgsi.c b/src/mesa/state_tracker/st_mesa_to_tgsi.c index b0a1b529f1e..e788008dfe1 100644 --- a/src/mesa/state_tracker/st_mesa_to_tgsi.c +++ b/src/mesa/state_tracker/st_mesa_to_tgsi.c @@ -151,7 +151,7 @@ dst_register( struct st_translate *t, return t->address[index]; default: - assert( 0 ); + debug_assert( 0 ); return ureg_dst_undef(); } } @@ -160,22 +160,30 @@ dst_register( struct st_translate *t, static struct ureg_src src_register( struct st_translate *t, gl_register_file file, - GLuint index ) + GLint index ) { switch( file ) { case PROGRAM_UNDEFINED: return ureg_src_undef(); case PROGRAM_TEMPORARY: + ASSERT(index >= 0); if (ureg_dst_is_undef(t->temps[index])) t->temps[index] = ureg_DECL_temporary( t->ureg ); return ureg_src(t->temps[index]); case PROGRAM_STATE_VAR: case PROGRAM_NAMED_PARAM: + case PROGRAM_ENV_PARAM: + case PROGRAM_LOCAL_PARAM: case PROGRAM_UNIFORM: - case PROGRAM_CONSTANT: + ASSERT(index >= 0); return t->constants[index]; + case PROGRAM_CONSTANT: /* ie, immediate */ + if (index < 0) + return ureg_DECL_constant( t->ureg, 0 ); + else + return t->constants[index]; case PROGRAM_INPUT: return t->inputs[t->inputMapping[index]]; @@ -187,7 +195,7 @@ src_register( struct st_translate *t, return ureg_src(t->address[index]); default: - assert( 0 ); + debug_assert( 0 ); return ureg_src_undef(); } } @@ -216,7 +224,7 @@ translate_texture_target( GLuint textarget, case TEXTURE_CUBE_INDEX: return TGSI_TEXTURE_CUBE; case TEXTURE_RECT_INDEX: return TGSI_TEXTURE_RECT; default: - assert( 0 ); + debug_assert( 0 ); return TGSI_TEXTURE_1D; } } @@ -262,9 +270,14 @@ translate_src( struct st_translate *t, if (SrcReg->Abs) src = ureg_abs(src); - if (SrcReg->RelAddr) + if (SrcReg->RelAddr) { src = ureg_src_indirect( src, ureg_src(t->address[0])); - + /* If SrcReg->Index was negative, it was set to zero in + * src_register(). Reassign it now. + */ + src.Index = SrcReg->Index; + } + return src; } @@ -277,7 +290,7 @@ static struct ureg_src swizzle_4v( struct ureg_src src, /** - * Translate SWZ instructions into a single MAD. EG: + * Translate a SWZ instruction into a MOV, MUL or MAD instruction. EG: * * SWZ dst, src.x-y10 * @@ -386,7 +399,7 @@ static void emit_swz( struct st_translate *t, swizzle_4v( imm, add_swizzle ) ); } else { - assert(0); + debug_assert(0); } #undef IMM_ZERO @@ -395,6 +408,23 @@ static void emit_swz( struct st_translate *t, } +/** + * Negate the value of DDY to match GL semantics where (0,0) is the + * lower-left corner of the window. + * Note that the GL_ARB_fragment_coord_conventions extension will + * effect this someday. + */ +static void emit_ddy( struct st_translate *t, + struct ureg_dst dst, + const struct prog_src_register *SrcReg ) +{ + struct ureg_program *ureg = t->ureg; + struct ureg_src src = translate_src( t, SrcReg ); + src = ureg_negate( src ); + ureg_DDY( ureg, dst, src ); +} + + static unsigned translate_opcode( unsigned op ) @@ -480,14 +510,6 @@ translate_opcode( unsigned op ) return TGSI_OPCODE_MOV; case OPCODE_MUL: return TGSI_OPCODE_MUL; - case OPCODE_NOISE1: - return TGSI_OPCODE_NOISE1; - case OPCODE_NOISE2: - return TGSI_OPCODE_NOISE2; - case OPCODE_NOISE3: - return TGSI_OPCODE_NOISE3; - case OPCODE_NOISE4: - return TGSI_OPCODE_NOISE4; case OPCODE_NOP: return TGSI_OPCODE_NOP; case OPCODE_NRM3: @@ -522,8 +544,6 @@ translate_opcode( unsigned op ) return TGSI_OPCODE_SSG; case OPCODE_SUB: return TGSI_OPCODE_SUB; - case OPCODE_SWZ: - return TGSI_OPCODE_SWZ; case OPCODE_TEX: return TGSI_OPCODE_TEX; case OPCODE_TXB: @@ -539,7 +559,7 @@ translate_opcode( unsigned op ) case OPCODE_END: return TGSI_OPCODE_END; default: - assert( 0 ); + debug_assert( 0 ); return TGSI_OPCODE_NOP; } } @@ -578,7 +598,7 @@ compile_instruction( case OPCODE_ELSE: case OPCODE_ENDLOOP: case OPCODE_IF: - assert(num_dst == 0); + debug_assert(num_dst == 0); ureg_label_insn( ureg, translate_opcode( inst->Opcode ), src, num_src, @@ -615,6 +635,23 @@ compile_instruction( src, num_src ); break; + case OPCODE_NOISE1: + case OPCODE_NOISE2: + case OPCODE_NOISE3: + case OPCODE_NOISE4: + /* At some point, a motivated person could add a better + * implementation of noise. Currently not even the nvidia + * binary drivers do anything more than this. In any case, the + * place to do this is in the GL state tracker, not the poor + * driver. + */ + ureg_MOV( ureg, dst[0], ureg_imm1f(ureg, 0.5) ); + break; + + case OPCODE_DDY: + emit_ddy( t, dst[0], &inst->SrcReg[0] ); + break; + default: ureg_insn( ureg, translate_opcode( inst->Opcode ), @@ -669,6 +706,41 @@ emit_inverted_wpos( struct st_translate *t, } +/** + * OpenGL's fragment gl_FrontFace input is 1 for front-facing, 0 for back. + * TGSI uses +1 for front, -1 for back. + * This function converts the TGSI value to the GL value. Simply clamping/ + * saturating the value to [0,1] does the job. + */ +static void +emit_face_var( struct st_translate *t, + const struct gl_program *program ) +{ + struct ureg_program *ureg = t->ureg; + struct ureg_dst face_temp = ureg_DECL_temporary( ureg ); + struct ureg_src face_input = t->inputs[t->inputMapping[FRAG_ATTRIB_FACE]]; + + /* MOV_SAT face_temp, input[face] + */ + face_temp = ureg_saturate( face_temp ); + ureg_MOV( ureg, face_temp, face_input ); + + /* Use face_temp as face input from here on: + */ + t->inputs[t->inputMapping[FRAG_ATTRIB_FACE]] = ureg_src(face_temp); +} + +static void +emit_edgeflags( struct st_translate *t, + const struct gl_program *program ) +{ + struct ureg_program *ureg = t->ureg; + struct ureg_dst edge_dst = t->outputs[t->outputMapping[VERT_RESULT_EDGE]]; + struct ureg_src edge_src = t->inputs[t->inputMapping[VERT_ATTRIB_EDGEFLAG]]; + + ureg_MOV( ureg, edge_dst, edge_src ); +} + /** * Translate Mesa program to TGSI format. * \param program the program to translate @@ -688,26 +760,24 @@ emit_inverted_wpos( struct st_translate *t, * * \return array of translated tokens, caller's responsibility to free */ -const struct tgsi_token * +enum pipe_error st_translate_mesa_program( GLcontext *ctx, uint procType, + struct ureg_program *ureg, const struct gl_program *program, GLuint numInputs, const GLuint inputMapping[], const ubyte inputSemanticName[], const ubyte inputSemanticIndex[], const GLuint interpMode[], - const GLbitfield inputFlags[], GLuint numOutputs, const GLuint outputMapping[], const ubyte outputSemanticName[], const ubyte outputSemanticIndex[], - const GLbitfield outputFlags[] ) + boolean passthrough_edgeflags ) { struct st_translate translate, *t; - struct ureg_program *ureg; - const struct tgsi_token *tokens = NULL; unsigned i; t = &translate; @@ -716,11 +786,7 @@ st_translate_mesa_program( t->procType = procType; t->inputMapping = inputMapping; t->outputMapping = outputMapping; - t->ureg = ureg_create( procType ); - if (t->ureg == NULL) - return NULL; - - ureg = t->ureg; + t->ureg = ureg; /*_mesa_print_program(program);*/ @@ -742,6 +808,10 @@ st_translate_mesa_program( emit_inverted_wpos( t, program ); } + if (program->InputsRead & FRAG_BIT_FACE) { + emit_face_var( t, program ); + } + /* * Declare output attributes. */ @@ -761,7 +831,7 @@ st_translate_mesa_program( outputSemanticIndex[i] ); break; default: - assert(0); + debug_assert(0); return 0; } } @@ -776,12 +846,14 @@ st_translate_mesa_program( outputSemanticName[i], outputSemanticIndex[i] ); } + if (passthrough_edgeflags) + emit_edgeflags( t, program ); } /* Declare address register. */ if (program->NumAddressRegs > 0) { - assert( program->NumAddressRegs == 1 ); + debug_assert( program->NumAddressRegs == 1 ); t->address[0] = ureg_DECL_address( ureg ); } @@ -799,6 +871,7 @@ st_translate_mesa_program( for (i = 0; i < program->Parameters->NumParameters; i++) { switch (program->Parameters->Parameters[i].Type) { case PROGRAM_ENV_PARAM: + case PROGRAM_LOCAL_PARAM: case PROGRAM_STATE_VAR: case PROGRAM_NAMED_PARAM: case PROGRAM_UNIFORM: @@ -847,8 +920,7 @@ st_translate_mesa_program( t->insn[t->labels[i].branch_target] ); } - tokens = ureg_get_tokens( ureg, NULL ); - ureg_destroy( ureg ); + return PIPE_OK; out: FREE(t->insn); @@ -857,17 +929,9 @@ out: if (t->error) { debug_printf("%s: translate error flag set\n", __FUNCTION__); - FREE((void *)tokens); - tokens = NULL; - } - - if (!tokens) { - debug_printf("%s: failed to translate Mesa program:\n", __FUNCTION__); - _mesa_print_program(program); - assert(0); } - return tokens; + return PIPE_ERROR_OUT_OF_MEMORY; }