diff options
Diffstat (limited to 'mesalib/src/mesa/shader')
-rw-r--r-- | mesalib/src/mesa/shader/program.c | 4 | ||||
-rw-r--r-- | mesalib/src/mesa/shader/shader_api.c | 79 | ||||
-rw-r--r-- | mesalib/src/mesa/shader/slang/slang_codegen.c | 3 | ||||
-rw-r--r-- | mesalib/src/mesa/shader/slang/slang_compile_variable.h | 2 | ||||
-rw-r--r-- | mesalib/src/mesa/shader/slang/slang_link.c | 5 |
5 files changed, 62 insertions, 31 deletions
diff --git a/mesalib/src/mesa/shader/program.c b/mesalib/src/mesa/shader/program.c index f4f701b54..f77a77375 100644 --- a/mesalib/src/mesa/shader/program.c +++ b/mesalib/src/mesa/shader/program.c @@ -625,7 +625,7 @@ replace_registers(struct prog_instruction *inst, GLuint numInst, GLuint i, j; for (i = 0; i < numInst; i++) { /* src regs */ - for (j = 0; j < _mesa_num_inst_src_regs(inst->Opcode); j++) { + for (j = 0; j < _mesa_num_inst_src_regs(inst[i].Opcode); j++) { if (inst[i].SrcReg[j].File == oldFile && inst[i].SrcReg[j].Index == oldIndex) { inst[i].SrcReg[j].File = newFile; @@ -652,7 +652,7 @@ adjust_param_indexes(struct prog_instruction *inst, GLuint numInst, { GLuint i, j; for (i = 0; i < numInst; i++) { - for (j = 0; j < _mesa_num_inst_src_regs(inst->Opcode); j++) { + for (j = 0; j < _mesa_num_inst_src_regs(inst[i].Opcode); j++) { GLuint f = inst[i].SrcReg[j].File; if (f == PROGRAM_CONSTANT || f == PROGRAM_UNIFORM || diff --git a/mesalib/src/mesa/shader/shader_api.c b/mesalib/src/mesa/shader/shader_api.c index 940fe2d03..5e87bb405 100644 --- a/mesalib/src/mesa/shader/shader_api.c +++ b/mesalib/src/mesa/shader/shader_api.c @@ -1260,6 +1260,54 @@ lookup_uniform_parameter(GLcontext *ctx, GLuint program, GLint location, /** + * GLGL uniform arrays and structs require special handling. + * + * The GL_ARB_shader_objects spec says that if you use + * glGetUniformLocation to get the location of an array, you CANNOT + * access other elements of the array by adding an offset to the + * returned location. For example, you must call + * glGetUniformLocation("foo[16]") if you want to set the 16th element + * of the array with glUniform(). + * + * HOWEVER, some other OpenGL drivers allow accessing array elements + * by adding an offset to the returned array location. And some apps + * seem to depend on that behaviour. + * + * Mesa's gl_uniform_list doesn't directly support this since each + * entry in the list describes one uniform variable, not one uniform + * element. We could insert dummy entries in the list for each array + * element after [0] but that causes complications elsewhere. + * + * We solve this problem by encoding two values in the location that's + * returned by glGetUniformLocation(): + * a) index into gl_uniform_list::Uniforms[] for the uniform + * b) an array/field offset (0 for simple types) + * + * These two values are encoded in the high and low halves of a GLint. + * By putting the uniform number in the high part and the offset in the + * low part, we can support the unofficial ability to index into arrays + * by adding offsets to the location value. + */ +static void +merge_location_offset(GLint *location, GLint offset) +{ + *location = (*location << 16) | offset; +} + + +/** + * Seperate the uniform location and parameter offset. See above. + */ +static void +split_location_offset(GLint *location, GLint *offset) +{ + *offset = *location & 0xffff; + *location = *location >> 16; +} + + + +/** * Called via ctx->Driver.GetUniformfv(). */ static void @@ -1268,6 +1316,9 @@ _mesa_get_uniformfv(GLcontext *ctx, GLuint program, GLint location, { struct gl_program *prog; GLint paramPos; + GLint offset; + + split_location_offset(&location, &offset); lookup_uniform_parameter(ctx, program, location, &prog, ¶mPos); @@ -1298,7 +1349,10 @@ _mesa_get_uniformiv(GLcontext *ctx, GLuint program, GLint location, { struct gl_program *prog; GLint paramPos; + GLint offset; + split_location_offset(&location, &offset); + lookup_uniform_parameter(ctx, program, location, &prog, ¶mPos); if (prog) { @@ -1319,31 +1373,6 @@ _mesa_get_uniformiv(GLcontext *ctx, GLuint program, GLint location, /** - * The value returned by GetUniformLocation actually encodes two things: - * 1. the index into the prog->Uniforms[] array for the uniform - * 2. an offset in the prog->ParameterValues[] array for specifying array - * elements or structure fields. - * This function merges those two values. - */ -static void -merge_location_offset(GLint *location, GLint offset) -{ - *location = *location | (offset << 16); -} - - -/** - * Seperate the uniform location and parameter offset. See above. - */ -static void -split_location_offset(GLint *location, GLint *offset) -{ - *offset = (*location >> 16); - *location = *location & 0xffff; -} - - -/** * Called via ctx->Driver.GetUniformLocation(). * * The return value will encode two values, the uniform location and an diff --git a/mesalib/src/mesa/shader/slang/slang_codegen.c b/mesalib/src/mesa/shader/slang/slang_codegen.c index ecb2f6d5c..7d5e5eb29 100644 --- a/mesalib/src/mesa/shader/slang/slang_codegen.c +++ b/mesalib/src/mesa/shader/slang/slang_codegen.c @@ -4187,11 +4187,10 @@ _slang_gen_variable(slang_assemble_ctx * A, slang_operation *oper) slang_atom name = oper->var ? oper->var->a_name : oper->a_id; slang_variable *var = _slang_variable_locate(oper->locals, name, GL_TRUE); slang_ir_node *n; - if (!var) { + if (!var || !var->declared) { slang_info_log_error(A->log, "undefined variable '%s'", (char *) name); return NULL; } - assert(var->declared); n = new_var(A, var); return n; } diff --git a/mesalib/src/mesa/shader/slang/slang_compile_variable.h b/mesalib/src/mesa/shader/slang/slang_compile_variable.h index b4585599f..5c9d248b3 100644 --- a/mesalib/src/mesa/shader/slang/slang_compile_variable.h +++ b/mesalib/src/mesa/shader/slang/slang_compile_variable.h @@ -41,7 +41,7 @@ typedef struct slang_variable_ GLuint size; /**< Variable's size in bytes */ GLboolean is_global; GLboolean isTemp; /**< a named temporary (__resultTmp) */ - GLboolean declared; /**< for debug */ + GLboolean declared; /**< has the var been declared? */ struct slang_ir_storage_ *store; /**< Storage for this var */ } slang_variable; diff --git a/mesalib/src/mesa/shader/slang/slang_link.c b/mesalib/src/mesa/shader/slang/slang_link.c index 7c7bfbdbc..e8dca0142 100644 --- a/mesalib/src/mesa/shader/slang/slang_link.c +++ b/mesalib/src/mesa/shader/slang/slang_link.c @@ -921,7 +921,10 @@ _slang_link(GLcontext *ctx, if (!vertNotify || !fragNotify) { /* driver rejected one/both of the vertex/fragment programs */ - link_error(shProg, "Vertex and/or fragment program rejected by driver\n"); + if (!shProg->InfoLog) { + link_error(shProg, + "Vertex and/or fragment program rejected by driver\n"); + } } else { shProg->LinkStatus = (shProg->VertexProgram || shProg->FragmentProgram); |