1 /* 2 * Mesa 3-D graphics library 3 * 4 * Copyright (C) 1999-2007 Brian Paul All Rights Reserved. 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a 7 * copy of this software and associated documentation files (the "Software"), 8 * to deal in the Software without restriction, including without limitation 9 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 10 * and/or sell copies of the Software, and to permit persons to whom the 11 * Software is furnished to do so, subject to the following conditions: 12 * 13 * The above copyright notice and this permission notice shall be included 14 * in all copies or substantial portions of the Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR 20 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 21 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 22 * OTHER DEALINGS IN THE SOFTWARE. 23 */ 24 25 /** 26 * \file program.c 27 * Vertex and fragment program support functions. 28 * \author Brian Paul 29 */ 30 31 32 #include "main/glheader.h" 33 #include "main/context.h" 34 #include "main/framebuffer.h" 35 #include "main/hash.h" 36 #include "main/macros.h" 37 #include "main/shaderobj.h" 38 #include "program.h" 39 #include "prog_cache.h" 40 #include "prog_parameter.h" 41 #include "prog_instruction.h" 42 #include "util/bitscan.h" 43 #include "util/ralloc.h" 44 #include "util/u_atomic.h" 45 46 47 /** 48 * A pointer to this dummy program is put into the hash table when 49 * glGenPrograms is called. 50 */ 51 struct gl_program _mesa_DummyProgram; 52 53 54 /** 55 * Init context's vertex/fragment program state 56 */ 57 void 58 _mesa_init_program(struct gl_context *ctx) 59 { 60 /* 61 * If this assertion fails, we need to increase the field 62 * size for register indexes (see INST_INDEX_BITS). 63 */ 64 assert(ctx->Const.Program[MESA_SHADER_VERTEX].MaxUniformComponents / 4 65 <= (1 << INST_INDEX_BITS)); 66 assert(ctx->Const.Program[MESA_SHADER_FRAGMENT].MaxUniformComponents / 4 67 <= (1 << INST_INDEX_BITS)); 68 69 assert(ctx->Const.Program[MESA_SHADER_VERTEX].MaxTemps <= (1 << INST_INDEX_BITS)); 70 assert(ctx->Const.Program[MESA_SHADER_VERTEX].MaxLocalParams <= (1 << INST_INDEX_BITS)); 71 assert(ctx->Const.Program[MESA_SHADER_FRAGMENT].MaxTemps <= (1 << INST_INDEX_BITS)); 72 assert(ctx->Const.Program[MESA_SHADER_FRAGMENT].MaxLocalParams <= (1 << INST_INDEX_BITS)); 73 74 assert(ctx->Const.Program[MESA_SHADER_VERTEX].MaxUniformComponents <= 4 * MAX_UNIFORMS); 75 assert(ctx->Const.Program[MESA_SHADER_FRAGMENT].MaxUniformComponents <= 4 * MAX_UNIFORMS); 76 77 assert(ctx->Const.Program[MESA_SHADER_VERTEX].MaxAddressOffset <= (1 << INST_INDEX_BITS)); 78 assert(ctx->Const.Program[MESA_SHADER_FRAGMENT].MaxAddressOffset <= (1 << INST_INDEX_BITS)); 79 80 /* If this fails, increase prog_instruction::TexSrcUnit size */ 81 STATIC_ASSERT(MAX_TEXTURE_UNITS <= (1 << 5)); 82 83 /* If this fails, increase prog_instruction::TexSrcTarget size */ 84 STATIC_ASSERT(NUM_TEXTURE_TARGETS <= (1 << 4)); 85 86 ctx->Program.ErrorPos = -1; 87 ctx->Program.ErrorString = strdup(""); 88 89 ctx->VertexProgram.Enabled = GL_FALSE; 90 ctx->VertexProgram.PointSizeEnabled = 91 (ctx->API == API_OPENGLES2) ? GL_TRUE : GL_FALSE; 92 ctx->VertexProgram.TwoSideEnabled = GL_FALSE; 93 _mesa_reference_program(ctx, &ctx->VertexProgram.Current, 94 ctx->Shared->DefaultVertexProgram); 95 assert(ctx->VertexProgram.Current); 96 ctx->VertexProgram.Cache = _mesa_new_program_cache(); 97 98 ctx->FragmentProgram.Enabled = GL_FALSE; 99 _mesa_reference_program(ctx, &ctx->FragmentProgram.Current, 100 ctx->Shared->DefaultFragmentProgram); 101 assert(ctx->FragmentProgram.Current); 102 ctx->FragmentProgram.Cache = _mesa_new_program_cache(); 103 104 /* XXX probably move this stuff */ 105 ctx->ATIFragmentShader.Enabled = GL_FALSE; 106 ctx->ATIFragmentShader.Current = ctx->Shared->DefaultFragmentShader; 107 assert(ctx->ATIFragmentShader.Current); 108 ctx->ATIFragmentShader.Current->RefCount++; 109 } 110 111 112 /** 113 * Free a context's vertex/fragment program state 114 */ 115 void 116 _mesa_free_program_data(struct gl_context *ctx) 117 { 118 _mesa_reference_program(ctx, &ctx->VertexProgram.Current, NULL); 119 _mesa_delete_program_cache(ctx, ctx->VertexProgram.Cache); 120 _mesa_reference_program(ctx, &ctx->FragmentProgram.Current, NULL); 121 _mesa_delete_shader_cache(ctx, ctx->FragmentProgram.Cache); 122 123 /* XXX probably move this stuff */ 124 if (ctx->ATIFragmentShader.Current) { 125 ctx->ATIFragmentShader.Current->RefCount--; 126 if (ctx->ATIFragmentShader.Current->RefCount <= 0) { 127 free(ctx->ATIFragmentShader.Current); 128 } 129 } 130 131 free((void *) ctx->Program.ErrorString); 132 } 133 134 135 /** 136 * Update the default program objects in the given context to reference those 137 * specified in the shared state and release those referencing the old 138 * shared state. 139 */ 140 void 141 _mesa_update_default_objects_program(struct gl_context *ctx) 142 { 143 _mesa_reference_program(ctx, &ctx->VertexProgram.Current, 144 ctx->Shared->DefaultVertexProgram); 145 assert(ctx->VertexProgram.Current); 146 147 _mesa_reference_program(ctx, &ctx->FragmentProgram.Current, 148 ctx->Shared->DefaultFragmentProgram); 149 assert(ctx->FragmentProgram.Current); 150 151 /* XXX probably move this stuff */ 152 if (ctx->ATIFragmentShader.Current) { 153 ctx->ATIFragmentShader.Current->RefCount--; 154 if (ctx->ATIFragmentShader.Current->RefCount <= 0) { 155 free(ctx->ATIFragmentShader.Current); 156 } 157 } 158 ctx->ATIFragmentShader.Current = (struct ati_fragment_shader *) ctx->Shared->DefaultFragmentShader; 159 assert(ctx->ATIFragmentShader.Current); 160 ctx->ATIFragmentShader.Current->RefCount++; 161 } 162 163 164 /** 165 * Set the vertex/fragment program error state (position and error string). 166 * This is generally called from within the parsers. 167 */ 168 void 169 _mesa_set_program_error(struct gl_context *ctx, GLint pos, const char *string) 170 { 171 ctx->Program.ErrorPos = pos; 172 free((void *) ctx->Program.ErrorString); 173 if (!string) 174 string = ""; 175 ctx->Program.ErrorString = strdup(string); 176 } 177 178 179 /** 180 * Initialize a new gl_program object. 181 */ 182 struct gl_program * 183 _mesa_init_gl_program(struct gl_program *prog, GLenum target, GLuint id, 184 bool is_arb_asm) 185 { 186 if (!prog) 187 return NULL; 188 189 memset(prog, 0, sizeof(*prog)); 190 prog->Id = id; 191 prog->Target = target; 192 prog->RefCount = 1; 193 prog->Format = GL_PROGRAM_FORMAT_ASCII_ARB; 194 prog->info.stage = _mesa_program_enum_to_shader_stage(target); 195 prog->is_arb_asm = is_arb_asm; 196 197 /* Uniforms that lack an initializer in the shader code have an initial 198 * value of zero. This includes sampler uniforms. 199 * 200 * Page 24 (page 30 of the PDF) of the GLSL 1.20 spec says: 201 * 202 * "The link time initial value is either the value of the variable's 203 * initializer, if present, or 0 if no initializer is present. Sampler 204 * types cannot have initializers." 205 * 206 * So we only initialise ARB assembly style programs. 207 */ 208 if (is_arb_asm) { 209 /* default mapping from samplers to texture units */ 210 for (unsigned i = 0; i < MAX_SAMPLERS; i++) 211 prog->SamplerUnits[i] = i; 212 } 213 214 return prog; 215 } 216 217 218 /** 219 * Allocate and initialize a new fragment/vertex program object but 220 * don't put it into the program hash table. Called via 221 * ctx->Driver.NewProgram. May be overridden (ie. replaced) by a 222 * device driver function to implement OO deriviation with additional 223 * types not understood by this function. 224 * 225 * \param ctx context 226 * \param id program id/number 227 * \param target program target/type 228 * \return pointer to new program object 229 */ 230 struct gl_program * 231 _mesa_new_program(struct gl_context *ctx, GLenum target, GLuint id, 232 bool is_arb_asm) 233 { 234 switch (target) { 235 case GL_VERTEX_PROGRAM_ARB: /* == GL_VERTEX_PROGRAM_NV */ 236 case GL_GEOMETRY_PROGRAM_NV: 237 case GL_TESS_CONTROL_PROGRAM_NV: 238 case GL_TESS_EVALUATION_PROGRAM_NV: 239 case GL_FRAGMENT_PROGRAM_ARB: 240 case GL_COMPUTE_PROGRAM_NV: { 241 struct gl_program *prog = rzalloc(NULL, struct gl_program); 242 return _mesa_init_gl_program(prog, target, id, is_arb_asm); 243 } 244 default: 245 _mesa_problem(ctx, "bad target in _mesa_new_program"); 246 return NULL; 247 } 248 } 249 250 251 /** 252 * Delete a program and remove it from the hash table, ignoring the 253 * reference count. 254 * Called via ctx->Driver.DeleteProgram. May be wrapped (OO deriviation) 255 * by a device driver function. 256 */ 257 void 258 _mesa_delete_program(struct gl_context *ctx, struct gl_program *prog) 259 { 260 (void) ctx; 261 assert(prog); 262 assert(prog->RefCount==0); 263 264 if (prog == &_mesa_DummyProgram) 265 return; 266 267 if (prog->Parameters) { 268 _mesa_free_parameter_list(prog->Parameters); 269 } 270 271 if (prog->nir) { 272 ralloc_free(prog->nir); 273 } 274 275 if (prog->sh.BindlessSamplers) { 276 ralloc_free(prog->sh.BindlessSamplers); 277 } 278 279 if (prog->sh.BindlessImages) { 280 ralloc_free(prog->sh.BindlessImages); 281 } 282 283 if (prog->driver_cache_blob) { 284 ralloc_free(prog->driver_cache_blob); 285 } 286 287 ralloc_free(prog); 288 } 289 290 291 /** 292 * Return the gl_program object for a given ID. 293 * Basically just a wrapper for _mesa_HashLookup() to avoid a lot of 294 * casts elsewhere. 295 */ 296 struct gl_program * 297 _mesa_lookup_program(struct gl_context *ctx, GLuint id) 298 { 299 if (id) 300 return (struct gl_program *) _mesa_HashLookup(ctx->Shared->Programs, id); 301 else 302 return NULL; 303 } 304 305 306 /** 307 * Reference counting for vertex/fragment programs 308 * This is normally only called from the _mesa_reference_program() macro 309 * when there's a real pointer change. 310 */ 311 void 312 _mesa_reference_program_(struct gl_context *ctx, 313 struct gl_program **ptr, 314 struct gl_program *prog) 315 { 316 #ifndef NDEBUG 317 assert(ptr); 318 if (*ptr && prog) { 319 /* sanity check */ 320 if ((*ptr)->Target == GL_VERTEX_PROGRAM_ARB) 321 assert(prog->Target == GL_VERTEX_PROGRAM_ARB); 322 else if ((*ptr)->Target == GL_FRAGMENT_PROGRAM_ARB) 323 assert(prog->Target == GL_FRAGMENT_PROGRAM_ARB || 324 prog->Target == GL_FRAGMENT_PROGRAM_NV); 325 else if ((*ptr)->Target == GL_GEOMETRY_PROGRAM_NV) 326 assert(prog->Target == GL_GEOMETRY_PROGRAM_NV); 327 } 328 #endif 329 330 if (*ptr) { 331 struct gl_program *oldProg = *ptr; 332 333 assert(oldProg->RefCount > 0); 334 335 if (p_atomic_dec_zero(&oldProg->RefCount)) { 336 assert(ctx); 337 _mesa_reference_shader_program_data(ctx, &oldProg->sh.data, NULL); 338 ctx->Driver.DeleteProgram(ctx, oldProg); 339 } 340 341 *ptr = NULL; 342 } 343 344 assert(!*ptr); 345 if (prog) { 346 p_atomic_inc(&prog->RefCount); 347 } 348 349 *ptr = prog; 350 } 351 352 353 /** 354 * Insert 'count' NOP instructions at 'start' in the given program. 355 * Adjust branch targets accordingly. 356 */ 357 GLboolean 358 _mesa_insert_instructions(struct gl_program *prog, GLuint start, GLuint count) 359 { 360 const GLuint origLen = prog->arb.NumInstructions; 361 const GLuint newLen = origLen + count; 362 struct prog_instruction *newInst; 363 GLuint i; 364 365 /* adjust branches */ 366 for (i = 0; i < prog->arb.NumInstructions; i++) { 367 struct prog_instruction *inst = prog->arb.Instructions + i; 368 if (inst->BranchTarget > 0) { 369 if ((GLuint)inst->BranchTarget >= start) { 370 inst->BranchTarget += count; 371 } 372 } 373 } 374 375 /* Alloc storage for new instructions */ 376 newInst = rzalloc_array(prog, struct prog_instruction, newLen); 377 if (!newInst) { 378 return GL_FALSE; 379 } 380 381 /* Copy 'start' instructions into new instruction buffer */ 382 _mesa_copy_instructions(newInst, prog->arb.Instructions, start); 383 384 /* init the new instructions */ 385 _mesa_init_instructions(newInst + start, count); 386 387 /* Copy the remaining/tail instructions to new inst buffer */ 388 _mesa_copy_instructions(newInst + start + count, 389 prog->arb.Instructions + start, 390 origLen - start); 391 392 /* free old instructions */ 393 ralloc_free(prog->arb.Instructions); 394 395 /* install new instructions */ 396 prog->arb.Instructions = newInst; 397 prog->arb.NumInstructions = newLen; 398 399 return GL_TRUE; 400 } 401 402 /** 403 * Delete 'count' instructions at 'start' in the given program. 404 * Adjust branch targets accordingly. 405 */ 406 GLboolean 407 _mesa_delete_instructions(struct gl_program *prog, GLuint start, GLuint count, 408 void *mem_ctx) 409 { 410 const GLuint origLen = prog->arb.NumInstructions; 411 const GLuint newLen = origLen - count; 412 struct prog_instruction *newInst; 413 GLuint i; 414 415 /* adjust branches */ 416 for (i = 0; i < prog->arb.NumInstructions; i++) { 417 struct prog_instruction *inst = prog->arb.Instructions + i; 418 if (inst->BranchTarget > 0) { 419 if (inst->BranchTarget > (GLint) start) { 420 inst->BranchTarget -= count; 421 } 422 } 423 } 424 425 /* Alloc storage for new instructions */ 426 newInst = rzalloc_array(mem_ctx, struct prog_instruction, newLen); 427 if (!newInst) { 428 return GL_FALSE; 429 } 430 431 /* Copy 'start' instructions into new instruction buffer */ 432 _mesa_copy_instructions(newInst, prog->arb.Instructions, start); 433 434 /* Copy the remaining/tail instructions to new inst buffer */ 435 _mesa_copy_instructions(newInst + start, 436 prog->arb.Instructions + start + count, 437 newLen - start); 438 439 /* free old instructions */ 440 ralloc_free(prog->arb.Instructions); 441 442 /* install new instructions */ 443 prog->arb.Instructions = newInst; 444 prog->arb.NumInstructions = newLen; 445 446 return GL_TRUE; 447 } 448 449 450 /** 451 * Populate the 'used' array with flags indicating which registers (TEMPs, 452 * INPUTs, OUTPUTs, etc, are used by the given program. 453 * \param file type of register to scan for 454 * \param used returns true/false flags for in use / free 455 * \param usedSize size of the 'used' array 456 */ 457 void 458 _mesa_find_used_registers(const struct gl_program *prog, 459 gl_register_file file, 460 GLboolean used[], GLuint usedSize) 461 { 462 GLuint i, j; 463 464 memset(used, 0, usedSize); 465 466 for (i = 0; i < prog->arb.NumInstructions; i++) { 467 const struct prog_instruction *inst = prog->arb.Instructions + i; 468 const GLuint n = _mesa_num_inst_src_regs(inst->Opcode); 469 470 if (inst->DstReg.File == file) { 471 assert(inst->DstReg.Index < usedSize); 472 if(inst->DstReg.Index < usedSize) 473 used[inst->DstReg.Index] = GL_TRUE; 474 } 475 476 for (j = 0; j < n; j++) { 477 if (inst->SrcReg[j].File == file) { 478 assert(inst->SrcReg[j].Index < (GLint) usedSize); 479 if (inst->SrcReg[j].Index < (GLint) usedSize) 480 used[inst->SrcReg[j].Index] = GL_TRUE; 481 } 482 } 483 } 484 } 485 486 487 /** 488 * Scan the given 'used' register flag array for the first entry 489 * that's >= firstReg. 490 * \param used vector of flags indicating registers in use (as returned 491 * by _mesa_find_used_registers()) 492 * \param usedSize size of the 'used' array 493 * \param firstReg first register to start searching at 494 * \return index of unused register, or -1 if none. 495 */ 496 GLint 497 _mesa_find_free_register(const GLboolean used[], 498 GLuint usedSize, GLuint firstReg) 499 { 500 GLuint i; 501 502 assert(firstReg < usedSize); 503 504 for (i = firstReg; i < usedSize; i++) 505 if (!used[i]) 506 return i; 507 508 return -1; 509 } 510 511 512 /* Gets the minimum number of shader invocations per fragment. 513 * This function is useful to determine if we need to do per 514 * sample shading or per fragment shading. 515 */ 516 GLint 517 _mesa_get_min_invocations_per_fragment(struct gl_context *ctx, 518 const struct gl_program *prog, 519 bool ignore_sample_qualifier) 520 { 521 /* From ARB_sample_shading specification: 522 * "Using gl_SampleID in a fragment shader causes the entire shader 523 * to be evaluated per-sample." 524 * 525 * "Using gl_SamplePosition in a fragment shader causes the entire 526 * shader to be evaluated per-sample." 527 * 528 * "If MULTISAMPLE or SAMPLE_SHADING_ARB is disabled, sample shading 529 * has no effect." 530 */ 531 if (ctx->Multisample.Enabled) { 532 /* The ARB_gpu_shader5 specification says: 533 * 534 * "Use of the "sample" qualifier on a fragment shader input 535 * forces per-sample shading" 536 */ 537 if (prog->info.fs.uses_sample_qualifier && !ignore_sample_qualifier) 538 return MAX2(_mesa_geometric_samples(ctx->DrawBuffer), 1); 539 540 if (prog->info.system_values_read & (SYSTEM_BIT_SAMPLE_ID | 541 SYSTEM_BIT_SAMPLE_POS)) 542 return MAX2(_mesa_geometric_samples(ctx->DrawBuffer), 1); 543 else if (ctx->Multisample.SampleShading) 544 return MAX2(ceil(ctx->Multisample.MinSampleShadingValue * 545 _mesa_geometric_samples(ctx->DrawBuffer)), 1); 546 else 547 return 1; 548 } 549 return 1; 550 } 551 552 553 GLbitfield 554 gl_external_samplers(const struct gl_program *prog) 555 { 556 GLbitfield external_samplers = 0; 557 GLbitfield mask = prog->SamplersUsed; 558 559 while (mask) { 560 int idx = u_bit_scan(&mask); 561 if (prog->sh.SamplerTargets[idx] == TEXTURE_EXTERNAL_INDEX) 562 external_samplers |= (1 << idx); 563 } 564 565 return external_samplers; 566 } 567