summaryrefslogtreecommitdiffstats
path: root/src/mesa/shader
diff options
context:
space:
mode:
Diffstat (limited to 'src/mesa/shader')
-rw-r--r--src/mesa/shader/arbprogparse.c2
-rw-r--r--src/mesa/shader/prog_execute.c3
-rw-r--r--src/mesa/shader/prog_parameter.c24
-rw-r--r--src/mesa/shader/prog_print.c17
-rw-r--r--src/mesa/shader/programopt.c12
-rw-r--r--src/mesa/shader/programopt.h2
-rw-r--r--src/mesa/shader/slang/slang_compile.c31
-rw-r--r--src/mesa/shader/slang/slang_emit.c16
-rw-r--r--src/mesa/shader/slang/slang_ir.h1
-rw-r--r--src/mesa/shader/slang/slang_link.c3
10 files changed, 88 insertions, 23 deletions
diff --git a/src/mesa/shader/arbprogparse.c b/src/mesa/shader/arbprogparse.c
index 60aaabe679f..97bda9c6b38 100644
--- a/src/mesa/shader/arbprogparse.c
+++ b/src/mesa/shader/arbprogparse.c
@@ -3869,7 +3869,7 @@ _mesa_parse_arb_fragment_program(GLcontext* ctx, GLenum target,
program->Base.Parameters = ap.Base.Parameters;
#if DEBUG_FP
- _mesa_printf("____________Fragment program %u ________\n", program->Base.ID);
+ _mesa_printf("____________Fragment program %u ________\n", program->Base.Id);
_mesa_print_program(&program->Base);
#endif
}
diff --git a/src/mesa/shader/prog_execute.c b/src/mesa/shader/prog_execute.c
index 8ce2ca39641..4575a069ea5 100644
--- a/src/mesa/shader/prog_execute.c
+++ b/src/mesa/shader/prog_execute.c
@@ -90,7 +90,8 @@ get_register_pointer(const struct prog_src_register *source,
const struct gl_program_parameter_list *params;
ASSERT(source->File == PROGRAM_LOCAL_PARAM ||
source->File == PROGRAM_CONSTANT ||
- source->File == PROGRAM_STATE_VAR);
+ source->File == PROGRAM_STATE_VAR ||
+ source->File == PROGRAM_UNIFORM);
params = machine->CurProgram->Parameters;
if (reg < 0 || reg >= params->NumParameters)
return ZeroVec;
diff --git a/src/mesa/shader/prog_parameter.c b/src/mesa/shader/prog_parameter.c
index 152bd79f695..afdd7e5489c 100644
--- a/src/mesa/shader/prog_parameter.c
+++ b/src/mesa/shader/prog_parameter.c
@@ -62,6 +62,28 @@ _mesa_free_parameter_list(struct gl_program_parameter_list *paramList)
}
+static GLint
+_mesa_fit_type_in_vec4(GLenum type)
+{
+ switch (type) {
+ case GL_FLOAT:
+ case GL_INT:
+ return 4;
+ break;
+ case GL_FLOAT_VEC2:
+ case GL_INT_VEC2:
+ return 2;
+ break;
+ case GL_FLOAT_VEC3:
+ case GL_INT_VEC3:
+ return 1;
+ break;
+ case GL_FLOAT_VEC4:
+ case GL_INT_VEC4:
+ default:
+ return 1;
+ }
+}
/**
* Add a new parameter to a parameter list.
@@ -272,7 +294,7 @@ _mesa_add_uniform(struct gl_program_parameter_list *paramList,
}
else {
i = _mesa_add_parameter(paramList, PROGRAM_UNIFORM, name,
- size, datatype, NULL, NULL);
+ size * _mesa_fit_type_in_vec4(datatype), datatype, NULL, NULL);
return i;
}
}
diff --git a/src/mesa/shader/prog_print.c b/src/mesa/shader/prog_print.c
index 1c35ce3fecf..2c5e03acc25 100644
--- a/src/mesa/shader/prog_print.c
+++ b/src/mesa/shader/prog_print.c
@@ -206,7 +206,7 @@ arb_output_attrib_string(GLint index, GLenum progType)
*/
static const char *
reg_string(enum register_file f, GLint index, gl_prog_print_mode mode,
- const struct gl_program *prog)
+ GLboolean relAddr, const struct gl_program *prog)
{
static char str[100];
@@ -214,7 +214,10 @@ reg_string(enum register_file f, GLint index, gl_prog_print_mode mode,
switch (mode) {
case PROG_PRINT_DEBUG:
- sprintf(str, "%s[%d]", file_string(f, mode), index);
+ if (relAddr)
+ sprintf(str, "%s[ADDR%s%d]", file_string(f, mode), (index > 0) ? "+" : "", index);
+ else
+ sprintf(str, "%s[%d]", file_string(f, mode), index);
break;
case PROG_PRINT_ARB:
@@ -401,7 +404,7 @@ print_dst_reg(const struct prog_dst_register *dstReg, gl_prog_print_mode mode,
{
_mesa_printf("%s%s",
reg_string((enum register_file) dstReg->File,
- dstReg->Index, mode, prog),
+ dstReg->Index, mode, GL_FALSE, prog),
writemask_string(dstReg->WriteMask));
if (dstReg->CondMask != COND_TR) {
@@ -424,9 +427,9 @@ print_src_reg(const struct prog_src_register *srcReg, gl_prog_print_mode mode,
{
_mesa_printf("%s%s",
reg_string((enum register_file) srcReg->File,
- srcReg->Index, mode, prog),
+ srcReg->Index, mode, srcReg->RelAddr, prog),
_mesa_swizzle_string(srcReg->Swizzle,
- srcReg->NegateBase, GL_FALSE));
+ srcReg->NegateBase, GL_FALSE));
#if 0
_mesa_printf("%s[%d]%s",
file_string((enum register_file) srcReg->File, mode),
@@ -590,7 +593,9 @@ _mesa_print_instruction_opt(const struct prog_instruction *inst, GLint indent,
break;
case OPCODE_ARL:
- _mesa_printf("ARL addr.x, ");
+ _mesa_printf("ARL ");
+ print_dst_reg(&inst->DstReg, mode, prog);
+ _mesa_printf(", ");
print_src_reg(&inst->SrcReg[0], mode, prog);
print_comment(inst);
break;
diff --git a/src/mesa/shader/programopt.c b/src/mesa/shader/programopt.c
index 7d560c74a54..f3511ba00ec 100644
--- a/src/mesa/shader/programopt.c
+++ b/src/mesa/shader/programopt.c
@@ -367,20 +367,22 @@ _mesa_count_texture_instructions(struct gl_program *prog)
/**
- * Scan/rewrite program to remove reads of varying (output) registers.
+ * Scan/rewrite program to remove reads of custom (output) registers.
+ * The passed type has to be either PROGRAM_VARYING or PROGRAM_OUTPUT.
* In GLSL vertex shaders, varying vars can be read and written.
* Normally, vertex varying vars are implemented as output registers.
* On some hardware, trying to read an output register causes trouble.
* So, rewrite the program to use a temporary register in this case.
*/
void
-_mesa_remove_varying_reads(struct gl_program *prog)
+_mesa_remove_output_reads(struct gl_program *prog, enum register_file type)
{
GLuint i;
GLint outputMap[VERT_RESULT_MAX];
GLuint numVaryingReads = 0;
assert(prog->Target == GL_VERTEX_PROGRAM_ARB);
+ assert(type == PROGRAM_VARYING || type == PROGRAM_OUTPUT);
for (i = 0; i < VERT_RESULT_MAX; i++)
outputMap[i] = -1;
@@ -391,7 +393,7 @@ _mesa_remove_varying_reads(struct gl_program *prog)
const GLuint numSrc = _mesa_num_inst_src_regs(inst->Opcode);
GLuint j;
for (j = 0; j < numSrc; j++) {
- if (inst->SrcReg[j].File == PROGRAM_VARYING) {
+ if (inst->SrcReg[j].File == type) {
/* replace the read with a temp reg */
const GLuint var = inst->SrcReg[j].Index;
if (outputMap[var] == -1) {
@@ -414,7 +416,7 @@ _mesa_remove_varying_reads(struct gl_program *prog)
const GLuint numSrc = _mesa_num_inst_src_regs(inst->Opcode);
GLuint j;
for (j = 0; j < numSrc; j++) {
- if (inst->DstReg.File == PROGRAM_VARYING &&
+ if (inst->DstReg.File == type &&
outputMap[inst->DstReg.Index] >= 0) {
/* change inst to write to the temp reg, instead of the varying */
inst->DstReg.File = PROGRAM_TEMPORARY;
@@ -447,7 +449,7 @@ _mesa_remove_varying_reads(struct gl_program *prog)
if (outputMap[var] >= 0) {
/* MOV VAR[var], TEMP[tmp]; */
inst->Opcode = OPCODE_MOV;
- inst->DstReg.File = PROGRAM_VARYING;
+ inst->DstReg.File = type;
inst->DstReg.Index = var;
inst->SrcReg[0].File = PROGRAM_TEMPORARY;
inst->SrcReg[0].Index = outputMap[var];
diff --git a/src/mesa/shader/programopt.h b/src/mesa/shader/programopt.h
index 47ff2f0c7be..11572e64f5a 100644
--- a/src/mesa/shader/programopt.h
+++ b/src/mesa/shader/programopt.h
@@ -40,6 +40,6 @@ extern void
_mesa_count_texture_instructions(struct gl_program *prog);
extern void
-_mesa_remove_varying_reads(struct gl_program *prog);
+_mesa_remove_output_reads(struct gl_program *prog, enum register_file type);
#endif /* PROGRAMOPT_H */
diff --git a/src/mesa/shader/slang/slang_compile.c b/src/mesa/shader/slang/slang_compile.c
index 46b5c54bbeb..cdea1c51287 100644
--- a/src/mesa/shader/slang/slang_compile.c
+++ b/src/mesa/shader/slang/slang_compile.c
@@ -258,9 +258,33 @@ parse_array_len(slang_parse_ctx * C, slang_output_ctx * O, GLuint * len)
/* evaluate compile-time expression which is array size */
_slang_simplify(&array_size, &space, C->atoms);
- result = (array_size.type == SLANG_OPER_LITERAL_INT);
- *len = (GLint) array_size.literal[0];
+ if (array_size.type == SLANG_OPER_LITERAL_INT) {
+ result = GL_TRUE;
+ *len = (GLint) array_size.literal[0];
+ } else if (array_size.type == SLANG_OPER_IDENTIFIER) {
+ slang_variable *var = _slang_locate_variable(array_size.locals, array_size.a_id, GL_TRUE);
+ if (!var) {
+ slang_info_log_error(C->L, "undefined variable '%s'",
+ (char *) array_size.a_id);
+ result = GL_FALSE;
+ } else if (var->type.qualifier == SLANG_QUAL_CONST &&
+ var->type.specifier.type == SLANG_SPEC_INT) {
+ if (var->initializer &&
+ var->initializer->type == SLANG_OPER_LITERAL_INT) {
+ *len = (GLint) var->initializer->literal[0];
+ result = GL_TRUE;
+ } else {
+ slang_info_log_error(C->L, "unable to parse array size declaration");
+ result = GL_FALSE;
+ }
+ } else {
+ slang_info_log_error(C->L, "unable to parse array size declaration");
+ result = GL_FALSE;
+ }
+ } else {
+ result = GL_FALSE;
+ }
slang_operation_destruct(&array_size);
return result;
@@ -2188,7 +2212,8 @@ _slang_compile(GLcontext *ctx, struct gl_shader *shader)
printf("Pre-remove output reads:\n");
_mesa_print_program(shader->Programs[0]);
#endif
- _mesa_remove_varying_reads(shader->Programs[0]);
+ _mesa_remove_output_reads(shader->Programs[0], PROGRAM_VARYING);
+ _mesa_remove_output_reads(shader->Programs[0], PROGRAM_OUTPUT);
#if 0
printf("Post-remove output reads:\n");
_mesa_print_program(shader->Programs[0]);
diff --git a/src/mesa/shader/slang/slang_emit.c b/src/mesa/shader/slang/slang_emit.c
index ff63e05dd20..93256f8647c 100644
--- a/src/mesa/shader/slang/slang_emit.c
+++ b/src/mesa/shader/slang/slang_emit.c
@@ -223,6 +223,7 @@ storage_to_src_reg(struct prog_src_register *src, const slang_ir_storage *st)
assert(st->Size <= 4);
src->File = st->File;
src->Index = st->Index;
+ src->RelAddr = st->RelAddr;
if (st->Swizzle != SWIZZLE_NOOP)
src->Swizzle = st->Swizzle;
else
@@ -1488,11 +1489,16 @@ emit_array_element(slang_emit_info *emitInfo, slang_ir_node *n)
n->Store->Index = arrayAddr + index;
}
else {
- /* Variable index - PROBLEM */
- const GLint arrayAddr = n->Children[0]->Store->Index;
- const GLint index = 0;
- _mesa_problem(NULL, "variable array indexes not supported yet!");
- n->Store->Index = arrayAddr + index;
+ /* Variable index*/
+ struct prog_instruction *inst;
+ inst = new_instruction(emitInfo, OPCODE_ARL);
+ storage_to_dst_reg(&inst->DstReg, n->Store, n->Writemask);
+ storage_to_src_reg(&inst->SrcReg[0], n->Children[1]->Store);
+ inst->DstReg.File = PROGRAM_ADDRESS;
+ inst->Comment = _mesa_strdup("ARL ADDR");
+ n->Store->RelAddr = GL_TRUE;
+ n->Store->Index = inst->DstReg.Index;/*index of the array*/
+ inst->DstReg.Index = 0; /*addr index is always 0*/
}
return NULL; /* no instruction */
}
diff --git a/src/mesa/shader/slang/slang_ir.h b/src/mesa/shader/slang/slang_ir.h
index c7c0ddbf9a6..ba0735d64dd 100644
--- a/src/mesa/shader/slang/slang_ir.h
+++ b/src/mesa/shader/slang/slang_ir.h
@@ -146,6 +146,7 @@ struct _slang_ir_storage
GLint Size; /**< number of floats */
GLuint Swizzle;
GLint RefCount; /**< Used during IR tree delete */
+ GLboolean RelAddr;
};
typedef struct _slang_ir_storage slang_ir_storage;
diff --git a/src/mesa/shader/slang/slang_link.c b/src/mesa/shader/slang/slang_link.c
index 80cd4b6df62..dd4990ba023 100644
--- a/src/mesa/shader/slang/slang_link.c
+++ b/src/mesa/shader/slang/slang_link.c
@@ -262,6 +262,9 @@ _slang_resolve_attributes(struct gl_shader_program *shProg,
return GL_FALSE;
}
_mesa_add_attribute(shProg->Attributes, name, size, attr);
+
+ /* set the attribute as used */
+ usedAttributes |= 1<<attr;
}
inst->SrcReg[j].Index = VERT_ATTRIB_GENERIC0 + attr;