Go to the source code of this file.
Defines | |
#define | ST_MAX_SHADER_TOKENS 4096 |
#define | TGSI_DEBUG 0 |
Functions | |
static void * | mem_dup (const void *src, uint size) |
XXX we should use the version of this from u_memory.h but including that header causes symbol collisions. | |
void | st_translate_vertex_program (struct st_context *st, struct st_vertex_program *stvp, const GLuint outputMapping[], const ubyte *outputSemanticName, const ubyte *outputSemanticIndex) |
Translate a Mesa vertex shader into a TGSI shader. | |
void | st_translate_fragment_program (struct st_context *st, struct st_fragment_program *stfp, const GLuint inputMapping[]) |
Translate a Mesa fragment shader into a TGSI shader. | |
void | st_print_shaders (GLcontext *ctx) |
Debug- print current shader text. |
#define ST_MAX_SHADER_TOKENS 4096 |
Definition at line 52 of file st_program.c.
#define TGSI_DEBUG 0 |
Definition at line 55 of file st_program.c.
static void* mem_dup | ( | const void * | src, | |
uint | size | |||
) | [static] |
XXX we should use the version of this from u_memory.h but including that header causes symbol collisions.
Definition at line 62 of file st_program.c.
References MALLOC.
00063 { 00064 void *dup = MALLOC(size); 00065 if (dup) 00066 memcpy(dup, src, size); 00067 return dup; 00068 }
void st_print_shaders | ( | GLcontext * | ctx | ) |
Debug- print current shader text.
Definition at line 544 of file st_program.c.
00545 { 00546 struct gl_shader_program *shProg = ctx->Shader.CurrentProgram; 00547 if (shProg) { 00548 GLuint i; 00549 for (i = 0; i < shProg->NumShaders; i++) { 00550 printf("GLSL shader %u of %u:\n", i, shProg->NumShaders); 00551 printf("%s\n", shProg->Shaders[i]->Source); 00552 } 00553 } 00554 }
void st_translate_fragment_program | ( | struct st_context * | st, | |
struct st_fragment_program * | stfp, | |||
const GLuint | inputMapping[] | |||
) |
Translate a Mesa fragment shader into a TGSI shader.
inputMapping | to map fragment program input registers to TGSI input slots | |
tokensOut | destination for TGSI tokens |
Definition at line 364 of file st_program.c.
References assert, st_fragment_program::Base, pipe_context::create_fs_state, st_fragment_program::driver_shader, st_fragment_program::input_map, st_fragment_program::input_semantic_index, st_fragment_program::input_semantic_name, mem_dup(), st_context::pipe, PIPE_MAX_SHADER_OUTPUTS, st_translate_mesa_program(), st_fragment_program::state, TGSI_DEBUG, tgsi_dump(), TGSI_INTERPOLATE_LINEAR, TGSI_INTERPOLATE_PERSPECTIVE, TGSI_PROCESSOR_FRAGMENT, TGSI_SEMANTIC_COLOR, TGSI_SEMANTIC_FOG, TGSI_SEMANTIC_GENERIC, TGSI_SEMANTIC_POSITION, and pipe_shader_state::tokens.
00367 { 00368 struct pipe_context *pipe = st->pipe; 00369 struct tgsi_token tokens[ST_MAX_SHADER_TOKENS]; 00370 GLuint outputMapping[FRAG_RESULT_MAX]; 00371 GLuint defaultInputMapping[FRAG_ATTRIB_MAX]; 00372 struct pipe_shader_state fs; 00373 GLuint interpMode[16]; /* XXX size? */ 00374 GLuint attr; 00375 const GLbitfield inputsRead = stfp->Base.Base.InputsRead; 00376 GLuint vslot = 0; 00377 GLuint num_generic = 0; 00378 GLuint num_tokens; 00379 00380 uint fs_num_inputs = 0; 00381 00382 ubyte fs_output_semantic_name[PIPE_MAX_SHADER_OUTPUTS]; 00383 ubyte fs_output_semantic_index[PIPE_MAX_SHADER_OUTPUTS]; 00384 uint fs_num_outputs = 0; 00385 00386 GLbitfield input_flags[MAX_PROGRAM_INPUTS]; 00387 GLbitfield output_flags[MAX_PROGRAM_OUTPUTS]; 00388 00389 memset(&fs, 0, sizeof(fs)); 00390 memset(input_flags, 0, sizeof(input_flags)); 00391 memset(output_flags, 0, sizeof(output_flags)); 00392 00393 /* which vertex output goes to the first fragment input: */ 00394 if (inputsRead & FRAG_BIT_WPOS) 00395 vslot = 0; 00396 else 00397 vslot = 1; 00398 00399 /* 00400 * Convert Mesa program inputs to TGSI input register semantics. 00401 */ 00402 for (attr = 0; attr < FRAG_ATTRIB_MAX; attr++) { 00403 if (inputsRead & (1 << attr)) { 00404 const GLuint slot = fs_num_inputs; 00405 00406 defaultInputMapping[attr] = slot; 00407 00408 stfp->input_map[slot] = vslot++; 00409 00410 fs_num_inputs++; 00411 00412 switch (attr) { 00413 case FRAG_ATTRIB_WPOS: 00414 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_POSITION; 00415 stfp->input_semantic_index[slot] = 0; 00416 interpMode[slot] = TGSI_INTERPOLATE_LINEAR; 00417 break; 00418 case FRAG_ATTRIB_COL0: 00419 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_COLOR; 00420 stfp->input_semantic_index[slot] = 0; 00421 interpMode[slot] = TGSI_INTERPOLATE_LINEAR; 00422 break; 00423 case FRAG_ATTRIB_COL1: 00424 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_COLOR; 00425 stfp->input_semantic_index[slot] = 1; 00426 interpMode[slot] = TGSI_INTERPOLATE_LINEAR; 00427 break; 00428 case FRAG_ATTRIB_FOGC: 00429 if (stfp->Base.UsesPointCoord) 00430 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00431 else 00432 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_FOG; 00433 stfp->input_semantic_index[slot] = 0; 00434 interpMode[slot] = TGSI_INTERPOLATE_PERSPECTIVE; 00435 break; 00436 case FRAG_ATTRIB_TEX0: 00437 case FRAG_ATTRIB_TEX1: 00438 case FRAG_ATTRIB_TEX2: 00439 case FRAG_ATTRIB_TEX3: 00440 case FRAG_ATTRIB_TEX4: 00441 case FRAG_ATTRIB_TEX5: 00442 case FRAG_ATTRIB_TEX6: 00443 case FRAG_ATTRIB_TEX7: 00444 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00445 stfp->input_semantic_index[slot] = num_generic++; 00446 interpMode[slot] = TGSI_INTERPOLATE_PERSPECTIVE; 00447 break; 00448 case FRAG_ATTRIB_VAR0: 00449 /* fall-through */ 00450 default: 00451 stfp->input_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00452 stfp->input_semantic_index[slot] = num_generic++; 00453 interpMode[slot] = TGSI_INTERPOLATE_PERSPECTIVE; 00454 } 00455 00456 input_flags[slot] = stfp->Base.Base.InputFlags[attr]; 00457 } 00458 } 00459 00460 /* 00461 * Semantics and mapping for outputs 00462 */ 00463 { 00464 uint numColors = 0; 00465 GLbitfield outputsWritten = stfp->Base.Base.OutputsWritten; 00466 00467 /* if z is written, emit that first */ 00468 if (outputsWritten & (1 << FRAG_RESULT_DEPR)) { 00469 fs_output_semantic_name[fs_num_outputs] = TGSI_SEMANTIC_POSITION; 00470 fs_output_semantic_index[fs_num_outputs] = 0; 00471 outputMapping[FRAG_RESULT_DEPR] = fs_num_outputs; 00472 fs_num_outputs++; 00473 outputsWritten &= ~(1 << FRAG_RESULT_DEPR); 00474 } 00475 00476 /* handle remaning outputs (color) */ 00477 for (attr = 0; attr < FRAG_RESULT_MAX; attr++) { 00478 if (outputsWritten & (1 << attr)) { 00479 switch (attr) { 00480 case FRAG_RESULT_DEPR: 00481 /* handled above */ 00482 assert(0); 00483 break; 00484 case FRAG_RESULT_COLR: 00485 fs_output_semantic_name[fs_num_outputs] = TGSI_SEMANTIC_COLOR; 00486 fs_output_semantic_index[fs_num_outputs] = numColors; 00487 outputMapping[attr] = fs_num_outputs; 00488 numColors++; 00489 break; 00490 default: 00491 assert(0); 00492 } 00493 00494 output_flags[fs_num_outputs] = stfp->Base.Base.OutputFlags[attr]; 00495 00496 fs_num_outputs++; 00497 } 00498 } 00499 } 00500 00501 if (!inputMapping) 00502 inputMapping = defaultInputMapping; 00503 00504 /* XXX: fix static allocation of tokens: 00505 */ 00506 num_tokens = st_translate_mesa_program(TGSI_PROCESSOR_FRAGMENT, 00507 &stfp->Base.Base, 00508 /* inputs */ 00509 fs_num_inputs, 00510 inputMapping, 00511 stfp->input_semantic_name, 00512 stfp->input_semantic_index, 00513 interpMode, 00514 input_flags, 00515 /* outputs */ 00516 fs_num_outputs, 00517 outputMapping, 00518 fs_output_semantic_name, 00519 fs_output_semantic_index, 00520 output_flags, 00521 /* tokenized result */ 00522 tokens, ST_MAX_SHADER_TOKENS); 00523 00524 assert(num_tokens < ST_MAX_SHADER_TOKENS); 00525 00526 fs.tokens = (struct tgsi_token *) 00527 mem_dup(tokens, num_tokens * sizeof(tokens[0])); 00528 00529 stfp->state = fs; /* struct copy */ 00530 stfp->driver_shader = pipe->create_fs_state(pipe, &fs); 00531 00532 if (0) 00533 _mesa_print_program(&stfp->Base.Base); 00534 00535 if (TGSI_DEBUG) 00536 tgsi_dump( fs.tokens, 0/*TGSI_DUMP_VERBOSE*/ ); 00537 }
void st_translate_vertex_program | ( | struct st_context * | st, | |
struct st_vertex_program * | stvp, | |||
const GLuint | outputMapping[], | |||
const ubyte * | outputSemanticName, | |||
const ubyte * | outputSemanticIndex | |||
) |
Translate a Mesa vertex shader into a TGSI shader.
outputMapping | to map vertex program output registers (VERT_RESULT_x) to TGSI output slots | |
tokensOut | destination for TGSI tokens |
Definition at line 80 of file st_program.c.
References assert, st_vertex_program::Base, pipe_context::create_vs_state, st_context::cso_context, cso_delete_vertex_shader(), st_context::ctx, st_vertex_program::driver_shader, FREE, st_vertex_program::index_to_input, st_vertex_program::input_to_index, mem_dup(), st_vertex_program::num_inputs, st_context::pipe, PIPE_MAX_SHADER_INPUTS, PIPE_MAX_SHADER_OUTPUTS, st_translate_mesa_program(), st_vertex_program::state, TGSI_DEBUG, tgsi_dump(), TGSI_PROCESSOR_VERTEX, TGSI_SEMANTIC_BCOLOR, TGSI_SEMANTIC_COLOR, TGSI_SEMANTIC_COUNT, TGSI_SEMANTIC_FOG, TGSI_SEMANTIC_GENERIC, TGSI_SEMANTIC_POSITION, TGSI_SEMANTIC_PSIZE, and pipe_shader_state::tokens.
00085 { 00086 struct pipe_context *pipe = st->pipe; 00087 struct tgsi_token tokens[ST_MAX_SHADER_TOKENS]; 00088 GLuint defaultOutputMapping[VERT_RESULT_MAX]; 00089 struct pipe_shader_state vs; 00090 GLuint attr, i; 00091 GLuint num_generic = 0; 00092 GLuint num_tokens; 00093 00094 ubyte vs_input_semantic_name[PIPE_MAX_SHADER_INPUTS]; 00095 ubyte vs_input_semantic_index[PIPE_MAX_SHADER_INPUTS]; 00096 uint vs_num_inputs = 0; 00097 00098 ubyte vs_output_semantic_name[PIPE_MAX_SHADER_OUTPUTS]; 00099 ubyte vs_output_semantic_index[PIPE_MAX_SHADER_OUTPUTS]; 00100 uint vs_num_outputs = 0; 00101 00102 GLbitfield input_flags[MAX_PROGRAM_INPUTS]; 00103 GLbitfield output_flags[MAX_PROGRAM_OUTPUTS]; 00104 00105 memset(&vs, 0, sizeof(vs)); 00106 memset(input_flags, 0, sizeof(input_flags)); 00107 memset(output_flags, 0, sizeof(output_flags)); 00108 00109 if (stvp->Base.IsPositionInvariant) 00110 _mesa_insert_mvp_code(st->ctx, &stvp->Base); 00111 00112 /* 00113 * Determine number of inputs, the mappings between VERT_ATTRIB_x 00114 * and TGSI generic input indexes, plus input attrib semantic info. 00115 */ 00116 for (attr = 0; attr < VERT_ATTRIB_MAX; attr++) { 00117 if (stvp->Base.Base.InputsRead & (1 << attr)) { 00118 const GLuint slot = vs_num_inputs; 00119 00120 vs_num_inputs++; 00121 00122 stvp->input_to_index[attr] = slot; 00123 stvp->index_to_input[slot] = attr; 00124 00125 switch (attr) { 00126 case VERT_ATTRIB_POS: 00127 vs_input_semantic_name[slot] = TGSI_SEMANTIC_POSITION; 00128 vs_input_semantic_index[slot] = 0; 00129 break; 00130 case VERT_ATTRIB_WEIGHT: 00131 /* fall-through */ 00132 case VERT_ATTRIB_NORMAL: 00133 /* just label as a generic */ 00134 vs_input_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00135 vs_input_semantic_index[slot] = 0; 00136 break; 00137 case VERT_ATTRIB_COLOR0: 00138 vs_input_semantic_name[slot] = TGSI_SEMANTIC_COLOR; 00139 vs_input_semantic_index[slot] = 0; 00140 break; 00141 case VERT_ATTRIB_COLOR1: 00142 vs_input_semantic_name[slot] = TGSI_SEMANTIC_COLOR; 00143 vs_input_semantic_index[slot] = 1; 00144 break; 00145 case VERT_ATTRIB_FOG: 00146 vs_input_semantic_name[slot] = TGSI_SEMANTIC_FOG; 00147 vs_input_semantic_index[slot] = 0; 00148 break; 00149 case VERT_ATTRIB_POINT_SIZE: 00150 vs_input_semantic_name[slot] = TGSI_SEMANTIC_PSIZE; 00151 vs_input_semantic_index[slot] = 0; 00152 break; 00153 case VERT_ATTRIB_TEX0: 00154 case VERT_ATTRIB_TEX1: 00155 case VERT_ATTRIB_TEX2: 00156 case VERT_ATTRIB_TEX3: 00157 case VERT_ATTRIB_TEX4: 00158 case VERT_ATTRIB_TEX5: 00159 case VERT_ATTRIB_TEX6: 00160 case VERT_ATTRIB_TEX7: 00161 vs_input_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00162 vs_input_semantic_index[slot] = num_generic++; 00163 break; 00164 case VERT_ATTRIB_GENERIC0: 00165 case VERT_ATTRIB_GENERIC1: 00166 case VERT_ATTRIB_GENERIC2: 00167 case VERT_ATTRIB_GENERIC3: 00168 case VERT_ATTRIB_GENERIC4: 00169 case VERT_ATTRIB_GENERIC5: 00170 case VERT_ATTRIB_GENERIC6: 00171 case VERT_ATTRIB_GENERIC7: 00172 assert(attr < VERT_ATTRIB_MAX); 00173 vs_input_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00174 vs_input_semantic_index[slot] = num_generic++; 00175 break; 00176 default: 00177 assert(0); 00178 } 00179 00180 input_flags[slot] = stvp->Base.Base.InputFlags[attr]; 00181 } 00182 } 00183 00184 #if 0 00185 if (outputMapping && outputSemanticName) { 00186 printf("VERT_RESULT written out_slot semantic_name semantic_index\n"); 00187 for (attr = 0; attr < VERT_RESULT_MAX; attr++) { 00188 printf(" %-2d %c %3d %2d %2d\n", 00189 attr, 00190 ((stvp->Base.Base.OutputsWritten & (1 << attr)) ? 'Y' : ' '), 00191 outputMapping[attr], 00192 outputSemanticName[attr], 00193 outputSemanticIndex[attr]); 00194 } 00195 } 00196 #endif 00197 00198 /* initialize output semantics to defaults */ 00199 for (i = 0; i < PIPE_MAX_SHADER_OUTPUTS; i++) { 00200 vs_output_semantic_name[i] = TGSI_SEMANTIC_GENERIC; 00201 vs_output_semantic_index[i] = 0; 00202 output_flags[i] = 0x0; 00203 } 00204 00205 num_generic = 0; 00206 /* 00207 * Determine number of outputs, the (default) output register 00208 * mapping and the semantic information for each output. 00209 */ 00210 for (attr = 0; attr < VERT_RESULT_MAX; attr++) { 00211 if (stvp->Base.Base.OutputsWritten & (1 << attr)) { 00212 GLuint slot; 00213 00214 /* XXX 00215 * Pass in the fragment program's input's semantic info. 00216 * Use the generic semantic indexes from there, instead of 00217 * guessing below. 00218 */ 00219 00220 if (outputMapping) { 00221 slot = outputMapping[attr]; 00222 assert(slot != ~0); 00223 } 00224 else { 00225 slot = vs_num_outputs; 00226 vs_num_outputs++; 00227 defaultOutputMapping[attr] = slot; 00228 } 00229 00230 switch (attr) { 00231 case VERT_RESULT_HPOS: 00232 assert(slot == 0); 00233 vs_output_semantic_name[slot] = TGSI_SEMANTIC_POSITION; 00234 vs_output_semantic_index[slot] = 0; 00235 break; 00236 case VERT_RESULT_COL0: 00237 vs_output_semantic_name[slot] = TGSI_SEMANTIC_COLOR; 00238 vs_output_semantic_index[slot] = 0; 00239 break; 00240 case VERT_RESULT_COL1: 00241 vs_output_semantic_name[slot] = TGSI_SEMANTIC_COLOR; 00242 vs_output_semantic_index[slot] = 1; 00243 break; 00244 case VERT_RESULT_BFC0: 00245 vs_output_semantic_name[slot] = TGSI_SEMANTIC_BCOLOR; 00246 vs_output_semantic_index[slot] = 0; 00247 break; 00248 case VERT_RESULT_BFC1: 00249 vs_output_semantic_name[slot] = TGSI_SEMANTIC_BCOLOR; 00250 vs_output_semantic_index[slot] = 1; 00251 break; 00252 case VERT_RESULT_FOGC: 00253 vs_output_semantic_name[slot] = TGSI_SEMANTIC_FOG; 00254 vs_output_semantic_index[slot] = 0; 00255 break; 00256 case VERT_RESULT_PSIZ: 00257 vs_output_semantic_name[slot] = TGSI_SEMANTIC_PSIZE; 00258 vs_output_semantic_index[slot] = 0; 00259 break; 00260 case VERT_RESULT_EDGE: 00261 assert(0); 00262 break; 00263 case VERT_RESULT_TEX0: 00264 case VERT_RESULT_TEX1: 00265 case VERT_RESULT_TEX2: 00266 case VERT_RESULT_TEX3: 00267 case VERT_RESULT_TEX4: 00268 case VERT_RESULT_TEX5: 00269 case VERT_RESULT_TEX6: 00270 case VERT_RESULT_TEX7: 00271 /* fall-through */ 00272 case VERT_RESULT_VAR0: 00273 /* fall-through */ 00274 default: 00275 if (outputSemanticName) { 00276 /* use provided semantic into */ 00277 assert(outputSemanticName[attr] != TGSI_SEMANTIC_COUNT); 00278 vs_output_semantic_name[slot] = outputSemanticName[attr]; 00279 vs_output_semantic_index[slot] = outputSemanticIndex[attr]; 00280 } 00281 else { 00282 /* use default semantic info */ 00283 vs_output_semantic_name[slot] = TGSI_SEMANTIC_GENERIC; 00284 vs_output_semantic_index[slot] = num_generic++; 00285 } 00286 } 00287 00288 output_flags[slot] = stvp->Base.Base.OutputFlags[attr]; 00289 } 00290 } 00291 00292 assert(vs_output_semantic_name[0] == TGSI_SEMANTIC_POSITION); 00293 00294 00295 if (outputMapping) { 00296 /* find max output slot referenced to compute vs_num_outputs */ 00297 GLuint maxSlot = 0; 00298 for (attr = 0; attr < VERT_RESULT_MAX; attr++) { 00299 if (outputMapping[attr] != ~0 && outputMapping[attr] > maxSlot) 00300 maxSlot = outputMapping[attr]; 00301 } 00302 vs_num_outputs = maxSlot + 1; 00303 } 00304 else { 00305 outputMapping = defaultOutputMapping; 00306 } 00307 00308 /* free old shader state, if any */ 00309 if (stvp->state.tokens) { 00310 FREE((void *) stvp->state.tokens); 00311 stvp->state.tokens = NULL; 00312 } 00313 if (stvp->driver_shader) { 00314 cso_delete_vertex_shader(st->cso_context, stvp->driver_shader); 00315 stvp->driver_shader = NULL; 00316 } 00317 00318 /* XXX: fix static allocation of tokens: 00319 */ 00320 num_tokens = st_translate_mesa_program(TGSI_PROCESSOR_VERTEX, 00321 &stvp->Base.Base, 00322 /* inputs */ 00323 vs_num_inputs, 00324 stvp->input_to_index, 00325 vs_input_semantic_name, 00326 vs_input_semantic_index, 00327 NULL, 00328 input_flags, 00329 /* outputs */ 00330 vs_num_outputs, 00331 outputMapping, 00332 vs_output_semantic_name, 00333 vs_output_semantic_index, 00334 output_flags, 00335 /* tokenized result */ 00336 tokens, ST_MAX_SHADER_TOKENS); 00337 00338 assert(num_tokens < ST_MAX_SHADER_TOKENS); 00339 00340 vs.tokens = (struct tgsi_token *) 00341 mem_dup(tokens, num_tokens * sizeof(tokens[0])); 00342 00343 stvp->num_inputs = vs_num_inputs; 00344 stvp->state = vs; /* struct copy */ 00345 stvp->driver_shader = pipe->create_vs_state(pipe, &vs); 00346 00347 if (0) 00348 _mesa_print_program(&stvp->Base.Base); 00349 00350 if (TGSI_DEBUG) 00351 tgsi_dump( vs.tokens, 0 ); 00352 }