From bfc02dd30f625c134638b20a903065dc78e9ccd3 Mon Sep 17 00:00:00 2001 From: Brian Date: Fri, 15 Dec 2006 15:35:57 -0700 Subject: [PATCH] Lots of assorted changes. Implement assignment/move for types larger than 4 floats. Fix codegen bug for "return expr" in inlined functions. More clean-up of storage allocation code (slang_resolve_storage). --- src/mesa/shader/slang/slang_assemble.h | 7 + src/mesa/shader/slang/slang_codegen.c | 163 +++++++++++------------ src/mesa/shader/slang/slang_compile_operation.c | 11 ++ src/mesa/shader/slang/slang_compile_operation.h | 3 + src/mesa/shader/slang/slang_emit.c | 168 ++++++++++++++++-------- src/mesa/shader/slang/slang_emit.h | 16 ++- src/mesa/shader/slang/slang_link2.c | 28 ++-- 7 files changed, 242 insertions(+), 154 deletions(-) diff --git a/src/mesa/shader/slang/slang_assemble.h b/src/mesa/shader/slang/slang_assemble.h index d507fc0..1225ee4 100644 --- a/src/mesa/shader/slang/slang_assemble.h +++ b/src/mesa/shader/slang/slang_assemble.h @@ -242,6 +242,12 @@ typedef struct slang_assembly_name_space_ struct slang_variable_scope_ *vars; } slang_assembly_name_space; + +typedef struct { + GLboolean TempUsed[MAX_PROGRAM_TEMPS]; +} slang_gen_context; + + typedef struct slang_assemble_ctx_ { slang_assembly_file *file; @@ -253,6 +259,7 @@ typedef struct slang_assemble_ctx_ slang_ref_type ref; slang_swizzle swz; struct gl_program *program; + slang_gen_context *codegen; } slang_assemble_ctx; extern struct slang_function_ * diff --git a/src/mesa/shader/slang/slang_codegen.c b/src/mesa/shader/slang/slang_codegen.c index af543ad..acca05d 100644 --- a/src/mesa/shader/slang/slang_codegen.c +++ b/src/mesa/shader/slang/slang_codegen.c @@ -53,37 +53,6 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper); -/** - * Allocate storage for given variable, attach it to 'ir'. - */ -static GLboolean -slang_alloc_var_storage(slang_variable *variable, slang_ir_node *ir) -{ - slang_ir_storage *store; - - assert(variable); - - /*assert(!variable->aux);*/ - - if (variable->aux) { - store = (slang_ir_storage *) variable->aux; - ir->Store = store; - if (store) - store->Size = -12; - } - else { - /* alloc storage */ - store = (slang_ir_storage *) _mesa_calloc(sizeof(*store)); - store->File = PROGRAM_TEMPORARY; - store->Index = -1; - store->Size = -10; - variable->aux = store; - ir->Store = store; - } - return GL_TRUE; -} - - static slang_ir_node * new_node(slang_ir_opcode op, slang_ir_node *left, slang_ir_node *right) { @@ -180,7 +149,7 @@ new_var(slang_assemble_ctx *A, slang_operation *oper, oper->var = v; n->Swizzle = swizzle; n->Var = v; - slang_resolve_storage(NULL, n, A->program); + slang_resolve_storage(A->codegen/**NULL**/, n, A->program); return n; } @@ -221,15 +190,30 @@ slang_is_writemask(const char *field, GLuint *mask) } +/** + * Assemble a "return" statement. + */ static slang_ir_node * slang_assemble_return(slang_assemble_ctx * A, slang_operation *oper) { - if (oper->num_children == 0) { - /* Convert to: + if (oper->num_children == 0 || + (oper->num_children == 1 && + oper->children[0].type == slang_oper_void)) { + /* Convert from: + * return; + * To: * goto __endOfFunction; */ - oper->type = slang_oper_goto; - oper->a_id = slang_atom_pool_atom(A->atoms, CurFunction->end_label); + slang_ir_node *n; + slang_operation gotoOp; + slang_operation_construct(&gotoOp); + gotoOp.type = slang_oper_goto; + gotoOp.a_id = slang_atom_pool_atom(A->atoms, CurFunction->end_label); + /* assemble the new code */ + n = slang_assemble_operation(A, &gotoOp); + /* destroy temp code */ + slang_operation_destruct(&gotoOp); + return n; } else { /* @@ -241,11 +225,12 @@ slang_assemble_return(slang_assemble_ctx * A, slang_operation *oper) */ slang_operation *block, *assign, *jump; slang_atom a_retVal; + slang_ir_node *n; a_retVal = slang_atom_pool_atom(A->atoms, "__retVal"); assert(a_retVal); -#if 1 +#if 1 /* DEBUG */ { slang_variable *v = _slang_locate_variable(oper->locals, a_retVal, GL_TRUE); @@ -266,17 +251,13 @@ slang_assemble_return(slang_assemble_ctx * A, slang_operation *oper) assign->locals->outer_scope = block->locals; assign->num_children = 2; assign->children = slang_operation_new(2); - /* lhs */ + /* lhs (__retVal) */ assign->children[0].type = slang_oper_identifier; assign->children[0].a_id = a_retVal; assign->children[0].locals->outer_scope = assign->locals; - /* rhs */ -#if 0 - assign->children[1] = oper->children[0]; /* XXX copy */ -#else + /* rhs (expr) */ + /* XXX we might be able to avoid this copy someday */ slang_operation_copy(&assign->children[1], &oper->children[0]); -#endif - /* child[1]: goto __endOfFunction */ jump = &block->children[1]; @@ -284,17 +265,16 @@ slang_assemble_return(slang_assemble_ctx * A, slang_operation *oper) assert(CurFunction->end_label); jump->a_id = slang_atom_pool_atom(A->atoms, CurFunction->end_label); -#if 00 +#if 0 /* debug */ printf("NEW RETURN:\n"); slang_print_tree(block, 0); #endif - slang_operation_copy(oper, block); - /* XXX destruct block */ + /* assemble the new code */ + n = slang_assemble_operation(A, block); + slang_operation_delete(block); + return n; } - - /* assemble the new code */ - return slang_assemble_operation(A, oper); } @@ -426,28 +406,37 @@ slang_substitute(slang_assemble_ctx *A, slang_operation *oper, } } break; +#if 0 /* XXX rely on default case below */ case slang_oper_return: /* do return replacement here too */ - slang_assemble_return(A, oper); - slang_substitute(A, oper, substCount, substOld, substNew, GL_FALSE); + assert(oper->num_children == 0 || oper->num_children == 1); + if (oper->num_children == 1) { + slang_substitute(A, &oper->children[0], + substCount, substOld, substNew, GL_FALSE); + } break; +#endif case slang_oper_assign: case slang_oper_subscript: /* special case: * child[0] can't have substitutions but child[1] can. */ - slang_substitute(A, &oper->children[0], substCount, substOld, substNew, GL_TRUE); - slang_substitute(A, &oper->children[1], substCount, substOld, substNew, GL_FALSE); + slang_substitute(A, &oper->children[0], + substCount, substOld, substNew, GL_TRUE); + slang_substitute(A, &oper->children[1], + substCount, substOld, substNew, GL_FALSE); break; case slang_oper_field: /* XXX NEW - test */ - slang_substitute(A, &oper->children[0], substCount, substOld, substNew, GL_TRUE); + slang_substitute(A, &oper->children[0], + substCount, substOld, substNew, GL_TRUE); break; default: { GLuint i; for (i = 0; i < oper->num_children; i++) - slang_substitute(A, &oper->children[i], substCount, substOld, substNew, GL_FALSE); + slang_substitute(A, &oper->children[i], + substCount, substOld, substNew, GL_FALSE); } } } @@ -1015,11 +1004,10 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper) assert(oper->num_children == 0 || oper->num_children == 1); - v = _slang_locate_variable(oper->locals, - oper->a_id, GL_TRUE); + v = _slang_locate_variable(oper->locals, oper->a_id, GL_TRUE); assert(v); varDecl = new_var_decl(A, v); - slang_alloc_var_storage(v, varDecl); + slang_resolve_storage(A->codegen, varDecl, A->program); if (oper->num_children > 0) { /* child is initializer */ @@ -1027,18 +1015,26 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper) assert(oper->num_children == 1); var = new_var(A, oper, oper->a_id, SWIZZLE_NOOP); /* XXX make copy of this initializer? */ + /* printf("\n*** ASSEMBLE INITIALIZER %p\n", (void*) v->initializer); + */ rhs = slang_assemble_operation(A, &oper->children[0]); init = new_node(IR_MOVE, var, rhs); + /*assert(rhs->Opcode != IR_SEQ);*/ n = new_seq(varDecl, init); } else if (v->initializer) { slang_ir_node *var, *init, *rhs; var = new_var(A, oper, oper->a_id, SWIZZLE_NOOP); /* XXX make copy of this initializer? */ + /* printf("\n*** ASSEMBLE INITIALIZER %p\n", (void*) v->initializer); + */ rhs = slang_assemble_operation(A, v->initializer); init = new_node(IR_MOVE, var, rhs); + /* + assert(rhs->Opcode != IR_SEQ); + */ n = new_seq(varDecl, init); } else { @@ -1056,10 +1052,9 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper) oper->children[1].type == slang_oper_call) { /* special case */ slang_ir_node *n; - printf(">>>>>>>>>>>>>> Assign function call\n"); n = slang_assemble_function_call_name(A, - (const char *) oper->children[1].a_id, - &oper->children[1], &oper->children[0]); + (const char *) oper->children[1].a_id, + &oper->children[1], &oper->children[0]); return n; } else @@ -1077,6 +1072,9 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper) c1 = slang_assemble_operation(A, &oper->children[1]); n = new_node(IR_MOVE, c0, c1); + /* + assert(c1->Opcode != IR_SEQ); + */ n->Writemask = mask; return n; } @@ -1148,33 +1146,29 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper) /* array dereference */ if (oper->children[1].type == slang_oper_literal_int) { /* compile-time constant index - OK */ - slang_assembly_typeinfo ti; + slang_assembly_typeinfo elem_ti; slang_ir_node *base; - slang_ir_storage *store2; GLint index; - slang_assembly_typeinfo_construct(&ti); - _slang_typeof_operation(A, &oper->children[0], &ti); + + /* get type of array element */ + slang_assembly_typeinfo_construct(&elem_ti); + _slang_typeof_operation(A, oper, &elem_ti); base = slang_assemble_operation(A, &oper->children[0]); assert(base->Opcode == IR_VAR); + assert(base->Store); index = (GLint) oper->children[1].literal[0]; - /* - printf("element[%d]\n", index); - */ -#if 1 - store2 = (slang_ir_storage *) _mesa_calloc(sizeof(*store2)); - *store2 = *base->Store; - base->Store = store2; - base->Store->Size = -15; -#endif - assert(base->Store); + /*printf("element[%d]\n", index);*/ + /* new storage info since we don't want to change the original */ + base->Store = _slang_clone_ir_storage(base->Store); + /* bias Index by array subscript, update storage size */ base->Store->Index += index; - base->Store->Size = 1; + base->Store->Size = _slang_sizeof_type_specifier(&elem_ti.spec); return base; } else { - /* run-time index - TBD */ + /* run-time index - not supported yet - TBD */ abort(); } return NULL; @@ -1192,6 +1186,7 @@ slang_assemble_operation(slang_assemble_ctx * A, slang_operation *oper) slang_ir_node *one = new_float_literal(1.0, 1.0, 1.0, 1.0); slang_ir_node *sum = new_node(IR_ADD, var, one); slang_ir_node *assign = new_node(IR_MOVE, var, sum); + assert(sum->Opcode != IR_SEQ); return assign; } break; @@ -1233,12 +1228,13 @@ _slang_codegen_function(slang_assemble_ctx * A, slang_function * fun) return 0; printf("\n*********** Assemble function2(%s)\n", (char*)fun->header.a_name); -#if 0 +#if 1 slang_print_function(fun, 1); #endif A->program->Parameters = _mesa_new_parameter_list(); A->program->Varying = _mesa_new_parameter_list(); + A->codegen = _slang_new_codegen_context(); /*printf("** Begin Simplify\n");*/ slang_simplify(fun->body, &A->space, A->atoms); @@ -1246,11 +1242,11 @@ _slang_codegen_function(slang_assemble_ctx * A, slang_function * fun) CurFunction = fun; - n = slang_assemble_operation(A, fun->body); - if (!CurFunction->end_label) CurFunction->end_label = slang_atom_pool_gen(A->atoms, "__endOfFunction_Main"); + n = slang_assemble_operation(A, fun->body); + endLabel = new_label(fun->end_label); n = new_seq(n, endLabel); @@ -1263,14 +1259,13 @@ _slang_codegen_function(slang_assemble_ctx * A, slang_function * fun) printf("************* IR for %s *******\n", (char*)fun->header.a_name); slang_print_ir(n, 0); + printf("************* End assemble function2 ************\n\n"); #endif if (_mesa_strcmp((char*) fun->header.a_name, "main") == 0) { - _slang_emit_code(n, A->program); + _slang_emit_code(n, A->codegen, A->program); } - printf("************* End assemble function2 ************\n\n"); - return n; } diff --git a/src/mesa/shader/slang/slang_compile_operation.c b/src/mesa/shader/slang/slang_compile_operation.c index 192f2b0..28d9fdf 100644 --- a/src/mesa/shader/slang/slang_compile_operation.c +++ b/src/mesa/shader/slang/slang_compile_operation.c @@ -135,6 +135,17 @@ slang_operation_new(GLuint count) } +/** + * Delete operation and all children + */ +void +slang_operation_delete(slang_operation *oper) +{ + slang_operation_destruct(oper); + _mesa_free(oper); +} + + slang_operation * slang_operation_grow(GLuint *numChildren, slang_operation **children) { diff --git a/src/mesa/shader/slang/slang_compile_operation.h b/src/mesa/shader/slang/slang_compile_operation.h index f6d0ba8..ad52b66 100644 --- a/src/mesa/shader/slang/slang_compile_operation.h +++ b/src/mesa/shader/slang/slang_compile_operation.h @@ -138,6 +138,9 @@ slang_operation_copy(slang_operation *, const slang_operation *); extern slang_operation * slang_operation_new(GLuint count); +extern void +slang_operation_delete(slang_operation *oper); + extern slang_operation * slang_operation_grow(GLuint *numChildren, slang_operation **children); diff --git a/src/mesa/shader/slang/slang_emit.c b/src/mesa/shader/slang/slang_emit.c index 104064f..4f7a9dd 100644 --- a/src/mesa/shader/slang/slang_emit.c +++ b/src/mesa/shader/slang/slang_emit.c @@ -130,6 +130,15 @@ _slang_new_ir_storage(enum register_file file, GLint index, GLint size) } +slang_ir_storage * +_slang_clone_ir_storage(slang_ir_storage *store) +{ + slang_ir_storage *clone + = _slang_new_ir_storage(store->File, store->Index, store->Size); + return clone; +} + + static const char * swizzle_string(GLuint swizzle) { @@ -194,10 +203,10 @@ sizeof_struct(const slang_struct *s) } -static GLuint -sizeof_type(const slang_fully_specified_type *t) +GLuint +_slang_sizeof_type_specifier(const slang_type_specifier *spec) { - switch (t->specifier.type) { + switch (spec->type) { case slang_spec_void: abort(); return 0; @@ -240,7 +249,7 @@ sizeof_type(const slang_fully_specified_type *t) abort(); return 0; case slang_spec_struct: - return sizeof_struct(t->specifier._struct); + return sizeof_struct(spec->_struct); case slang_spec_array: return 1; /* XXX */ default: @@ -251,6 +260,14 @@ sizeof_type(const slang_fully_specified_type *t) } + +static GLuint +sizeof_type(const slang_fully_specified_type *t) +{ + return _slang_sizeof_type_specifier(&t->specifier); +} + + #define IND 0 void slang_print_ir(const slang_ir_node *n, int indent) @@ -269,7 +286,7 @@ slang_print_ir(const slang_ir_node *n, int indent) switch (n->Opcode) { case IR_SEQ: #if IND - printf("SEQ store %p\n", (void*) n->Store); + printf("SEQ at %p\n", (void*) n); #endif assert(n->Children[0]); assert(n->Children[1]); @@ -325,12 +342,22 @@ slang_print_ir(const slang_ir_node *n, int indent) static GLint -alloc_temporary(slang_gen_context *gc) +alloc_temporary(slang_gen_context *gc, GLint size) { - GLuint i; + const GLuint sz4 = (size + 3) / 4; + GLuint i, j; + ASSERT(size > 0); /* number of floats */ for (i = 0; i < MAX_PROGRAM_TEMPS; i++) { - if (!gc->TempUsed[i]) { - gc->TempUsed[i] = GL_TRUE; + GLuint found = 0; + for (j = 0; j < sz4; j++) { + if (!gc->TempUsed[i + j]) { + found++; + } + } + if (found == sz4) { + /* found block of size/4 free regs */ + for (j = 0; j < sz4; j++) + gc->TempUsed[i + j] = GL_TRUE; return i; } } @@ -349,10 +376,14 @@ is_temporary(const slang_gen_context *gc, const slang_ir_storage *st) static void -free_temporary(slang_gen_context *gc, GLuint r) +free_temporary(slang_gen_context *gc, GLuint r, GLint size) { - if (gc->TempUsed[r]) - gc->TempUsed[r] = GL_FALSE; + const GLuint sz4 = (size + 3) / 4; + GLuint i; + for (i = 0; i < sz4; i++) { + if (gc->TempUsed[r + i]) + gc->TempUsed[r + i] = GL_FALSE; + } } @@ -589,7 +620,7 @@ slang_alloc_temp_storage(slang_gen_context *gc, slang_ir_node *n, GLint size) assert(!n->Var); assert(!n->Store); assert(size > 0); - indx = alloc_temporary(gc); + indx = alloc_temporary(gc, size); n->Store = _slang_new_ir_storage(PROGRAM_TEMPORARY, indx, size); } @@ -609,9 +640,12 @@ void slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, struct gl_program *prog) { - int k = 0; + assert(gc); + assert(n); + assert(prog); + if (!n->Store) { - /**assert(n->Var);**/ + /* allocate storage info for this node */ if (n->Var && n->Var->aux) { /* node storage info = var storage info */ n->Store = (slang_ir_storage *) n->Var->aux; @@ -619,21 +653,19 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, else { /* alloc new storage info */ n->Store = _slang_new_ir_storage(PROGRAM_UNDEFINED, -1, -5); - k = 1; - /*XXX n->Store->Size = sizeof(var's type) */ if (n->Var) n->Var->aux = n->Store; } } if (n->Opcode == IR_VAR_DECL) { - /* allocate storage for a user's variable */ + /* storage declaration */ assert(n->Var); - if (n->Store->Index < 0) { + if (n->Store->Index < 0) { /* XXX assert this? */ assert(gc); n->Store->File = PROGRAM_TEMPORARY; - n->Store->Index = alloc_temporary(gc); n->Store->Size = sizeof_type(&n->Var->type); + n->Store->Index = alloc_temporary(gc, n->Store->Size); printf("alloc var %s storage at %d (size %d)\n", (char *) n->Var->a_name, n->Store->Index, @@ -641,6 +673,7 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, assert(n->Store->Size > 0); n->Var->declared = GL_TRUE; } + assert(n->Store->Size > 0); return; } @@ -649,7 +682,12 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, GLint i; assert(n->Var); - assert(prog); + + if (n->Store->Size < 0) { + /* determine var/storage size now */ + n->Store->Size = sizeof_type(&n->Var->type); + assert(n->Store->Size > 0); + } #if 0 assert(n->Var->declared || @@ -665,7 +703,6 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, if (i >= 0) { n->Store->File = PROGRAM_INPUT; n->Store->Index = i; - n->Store->Size = sizeof_type(&n->Var->type); assert(n->Store->Size > 0); prog->InputsRead |= (1 << i); return; @@ -675,7 +712,6 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, if (i >= 0) { n->Store->File = PROGRAM_OUTPUT; n->Store->Index = i; - n->Store->Size = sizeof_type(&n->Var->type); prog->OutputsWritten |= (1 << i); return; } @@ -684,7 +720,6 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, if (i >= 0) { n->Store->File = PROGRAM_STATE_VAR; n->Store->Index = i; - n->Store->Size = sizeof_type(&n->Var->type); return; } @@ -692,7 +727,6 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, if (i >= 0) { n->Store->File = PROGRAM_CONSTANT; n->Store->Index = i; - n->Store->Size = sizeof_type(&n->Var->type); return; } @@ -702,7 +736,6 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, if (i >= 0) { n->Store->File = PROGRAM_UNIFORM; n->Store->Index = i; - n->Store->Size = sizeof_type(&n->Var->type); return; } } @@ -717,27 +750,17 @@ slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, #else n->Store->File = PROGRAM_VARYING; #endif - n->Store->Size = sizeof_type(&n->Var->type); n->Store->Index = i; return; } } - /* what is this?!? */ - /* - abort(); - */ - } - - if (n->Store->File == PROGRAM_TEMPORARY && n->Store->Index < 0) { - /* unnamed intermediate temporary */ - if (gc) - n->Store->Index = alloc_temporary(gc); - return; - } - - if (gc && n->Store->File == PROGRAM_UNDEFINED && n->Store->Size < 0) { - abort(); + if (n->Store->File == PROGRAM_UNDEFINED && n->Store->Index < 0) { + /* ordinary local var */ + assert(n->Store->Size > 0); + n->Store->File = PROGRAM_TEMPORARY; + n->Store->Index = alloc_temporary(gc, n->Store->Size); + } } } @@ -755,6 +778,7 @@ alloc_constant(const GLfloat v[], GLuint size, struct gl_program *prog) /** * Swizzle a swizzle. */ +#if 0 static GLuint swizzle_compose(GLuint swz1, GLuint swz2) { @@ -766,6 +790,7 @@ swizzle_compose(GLuint swz1, GLuint swz2) swz = MAKE_SWIZZLE4(s[0], s[1], s[2], s[3]); return swz; } +#endif /** @@ -783,6 +808,7 @@ storage_to_dst_reg(struct prog_dst_register *dst, const slang_ir_storage *st, }; dst->File = st->File; dst->Index = st->Index; + assert(st->File != PROGRAM_UNDEFINED); assert(st->Size >= 1); assert(st->Size <= 4); dst->WriteMask = defaultWritemask[st->Size - 1] & writemask; @@ -805,6 +831,7 @@ storage_to_src_reg(struct prog_src_register *src, const slang_ir_storage *st, src->File = st->File; src->Index = st->Index; + assert(st->File != PROGRAM_UNDEFINED); assert(st->Size >= 1); assert(st->Size <= 4); /* XXX swizzling logic here may need some work */ @@ -945,7 +972,8 @@ gen(slang_gen_context *gc, slang_ir_node *n, struct gl_program *prog) * Just modify the RHS to put its result into the dest of this * MOVE operation. Then, this MOVE is a no-op. */ - free_temporary(gc, n->Children[1]->Store->Index); + free_temporary(gc, n->Children[1]->Store->Index, + n->Children[1]->Store->Size); *n->Children[1]->Store = *n->Children[0]->Store; /* fixup the prev (RHS) instruction */ storage_to_dst_reg(&inst->DstReg, n->Children[0]->Store, n->Writemask); @@ -954,14 +982,40 @@ gen(slang_gen_context *gc, slang_ir_node *n, struct gl_program *prog) else #endif { - inst = new_instruction(prog, OPCODE_MOV); - storage_to_dst_reg(&inst->DstReg, n->Children[0]->Store, n->Writemask); - storage_to_src_reg(&inst->SrcReg[0], n->Children[1]->Store, - n->Children[1]->Swizzle); +#if 1 + if (n->Children[0]->Store->Size > 4) { + /* move matrix/struct etc */ + slang_ir_storage dstStore = *n->Children[0]->Store; + slang_ir_storage srcStore = *n->Children[1]->Store; + GLint size = srcStore.Size; + ASSERT(n->Children[0]->Writemask == WRITEMASK_XYZW); + ASSERT(n->Children[1]->Swizzle == SWIZZLE_NOOP); + dstStore.Size = 4; + srcStore.Size = 4; + while (size >= 4) { + inst = new_instruction(prog, OPCODE_MOV); + inst->Comment = _mesa_strdup("IR_MOVE block"); + storage_to_dst_reg(&inst->DstReg, &dstStore, n->Writemask); + storage_to_src_reg(&inst->SrcReg[0], &srcStore, + n->Children[1]->Swizzle); + srcStore.Index++; + dstStore.Index++; + size -= 4; + } + } + else +#endif + { + inst = new_instruction(prog, OPCODE_MOV); + storage_to_dst_reg(&inst->DstReg, n->Children[0]->Store, n->Writemask); + storage_to_src_reg(&inst->SrcReg[0], n->Children[1]->Store, + n->Children[1]->Swizzle); + } if (n->Children[1]->Store->File == PROGRAM_TEMPORARY) { - free_temporary(gc, n->Children[1]->Store->Index); + free_temporary(gc, n->Children[1]->Store->Index, + n->Children[1]->Store->Size); } - inst->Comment = n->Comment; + /*inst->Comment = _mesa_strdup("IR_MOVE");*/ n->Store = n->Children[0]->Store; /*XXX new */ return inst; } @@ -1012,14 +1066,24 @@ gen(slang_gen_context *gc, slang_ir_node *n, struct gl_program *prog) } +slang_gen_context * +_slang_new_codegen_context(void) +{ + slang_gen_context *gc = (slang_gen_context *) _mesa_calloc(sizeof(*gc)); + return gc; +} + + GLboolean -_slang_emit_code(slang_ir_node *n, struct gl_program *prog) +_slang_emit_code(slang_ir_node *n, slang_gen_context *gc, + struct gl_program *prog) { - slang_gen_context *gc; /*GET_CURRENT_CONTEXT(ctx);*/ - gc = (slang_gen_context *) _mesa_calloc(sizeof(*gc)); + /* + gc = _slang_new_codegen_context(); + */ printf("************ Begin generate code\n"); diff --git a/src/mesa/shader/slang/slang_emit.h b/src/mesa/shader/slang/slang_emit.h index 1683542..8ac17e6 100644 --- a/src/mesa/shader/slang/slang_emit.h +++ b/src/mesa/shader/slang/slang_emit.h @@ -32,9 +32,8 @@ #include "mtypes.h" -typedef struct { - GLboolean TempUsed[MAX_PROGRAM_TEMPS]; -} slang_gen_context; +extern slang_gen_context * +_slang_new_codegen_context(void); extern void @@ -45,12 +44,21 @@ extern slang_ir_storage * _slang_new_ir_storage(enum register_file file, GLint index, GLint size); +extern slang_ir_storage * +_slang_clone_ir_storage(slang_ir_storage *store); + + +extern GLuint +_slang_sizeof_type_specifier(const slang_type_specifier *spec); + + extern void slang_resolve_storage(slang_gen_context *gc, slang_ir_node *n, struct gl_program *prog); extern GLboolean -_slang_emit_code(slang_ir_node *n, struct gl_program *prog); +_slang_emit_code(slang_ir_node *n, slang_gen_context *gc, + struct gl_program *prog); #endif /* SLANG_EMIT_H */ diff --git a/src/mesa/shader/slang/slang_link2.c b/src/mesa/shader/slang/slang_link2.c index 9fa5399..50e62d8 100644 --- a/src/mesa/shader/slang/slang_link2.c +++ b/src/mesa/shader/slang/slang_link2.c @@ -320,18 +320,6 @@ _slang_link2(GLcontext *ctx, linked->FragmentProgram = (struct gl_fragment_program *) _mesa_clone_program(ctx, &fragProg->Base); -#if 1 - printf("************** orig fragment program\n"); - _mesa_print_program(&fragProg->Base); - _mesa_print_program_parameters(ctx, &fragProg->Base); -#endif - -#if 1 - printf("************** orig vertex program\n"); - _mesa_print_program(&vertProg->Base); - _mesa_print_program_parameters(ctx, &fragProg->Base); -#endif - link_varying_vars(linked, &linked->VertexProgram->Base); link_varying_vars(linked, &linked->FragmentProgram->Base); @@ -345,10 +333,22 @@ _slang_link2(GLcontext *ctx, linked->FragmentProgram->Base.Parameters = linked->Uniforms; #if 1 - printf("************** linked/cloned frag prog\n"); + printf("************** original fragment program\n"); + _mesa_print_program(&fragProg->Base); + _mesa_print_program_parameters(ctx, &fragProg->Base); +#endif +#if 1 + printf("************** linked fragment prog\n"); _mesa_print_program(&linked->FragmentProgram->Base); _mesa_print_program_parameters(ctx, &linked->FragmentProgram->Base); - printf("************** linked/cloned vert prog\n"); +#endif +#if 1 + printf("************** original vertex program\n"); + _mesa_print_program(&vertProg->Base); + _mesa_print_program_parameters(ctx, &fragProg->Base); +#endif +#if 1 + printf("************** linked vertex prog\n"); _mesa_print_program(&linked->VertexProgram->Base); _mesa_print_program_parameters(ctx, &linked->VertexProgram->Base); #endif -- 2.7.4