#include "shader/prog_print.h"
#include "slang_compile.h"
#include "slang_compile_variable.h"
+#include "slang_emit.h"
#include "slang_mem.h"
#include "slang_vartable.h"
#include "slang_ir.h"
/**
- * Create new table, put at head, return ptr to it.
- * XXX we should take a maxTemps parameter to indicate how many temporaries
- * are available for the current shader/program target.
+ * Create new table on top of vartable stack.
+ * Used when we enter a {} block.
*/
void
_slang_push_var_table(slang_var_table *vt)
/**
- * Destroy given table, return ptr to Parent
+ * Pop top entry from variable table.
+ * Used when we leave a {} block.
*/
void
_slang_pop_var_table(slang_var_table *vt)
/* free the storage allocated for each variable */
for (i = 0; i < t->NumVars; i++) {
- slang_ir_storage *store = (slang_ir_storage *) t->Vars[i]->aux;
+ slang_ir_storage *store = t->Vars[i]->store;
GLint j;
GLuint comp;
if (dbg) printf(" Free var %s, size %d at %d.%s\n",
store->Index,
_mesa_swizzle_string(store->Swizzle, 0, 0));
+ if (store->File == PROGRAM_SAMPLER) {
+ /* samplers have no storage */
+ continue;
+ }
+
if (store->Size == 1)
comp = GET_SWZ(store->Swizzle, 0);
else
comp = 0;
- assert(store->Index >= 0);
- for (j = 0; j < store->Size; j++) {
- assert(t->Temps[store->Index * 4 + j + comp] == VAR);
- t->Temps[store->Index * 4 + j + comp] = FREE;
+ /* store->Index may be -1 if we run out of registers */
+ if (store->Index >= 0) {
+ for (j = 0; j < store->Size; j++) {
+ assert(t->Temps[store->Index * 4 + j + comp] == VAR);
+ t->Temps[store->Index * 4 + j + comp] = FREE;
+ }
}
store->Index = -1;
}
/**
- * Add a new variable to the given symbol table.
+ * Add a new variable to the given var/symbol table.
*/
void
_slang_add_variable(slang_var_table *vt, slang_variable *v)
assert(vt);
t = vt->Top;
assert(t);
- if (dbg) printf("Adding var %s, store %p\n", (char *) v->a_name, v->aux);
+ if (dbg) printf("Adding var %s, store %p\n", (char *) v->a_name, (void *) v->store);
t->Vars = (slang_variable **)
_slang_realloc(t->Vars,
t->NumVars * sizeof(slang_variable *),
for (i = 0; i <= vt->MaxRegisters * 4 - size; i += step) {
GLuint found = 0;
for (j = 0; j < (GLuint) size; j++) {
+ assert(i + j < 4 * MAX_PROGRAM_TEMPS);
if (i + j < vt->MaxRegisters * 4 && t->Temps[i + j] == FREE) {
found++;
}
/* found block of size free regs */
if (size > 1)
assert(i % 4 == 0);
- for (j = 0; j < (GLuint) size; j++)
+ for (j = 0; j < (GLuint) size; j++) {
+ assert(i + j < 4 * MAX_PROGRAM_TEMPS);
t->Temps[i + j] = isTemp ? TEMP : VAR;
+ }
assert(i < MAX_PROGRAM_TEMPS * 4);
t->ValSize[i] = size;
return i;
}
}
+
+ /* if we get here, we ran out of registers */
return -1;
}
_slang_alloc_var(slang_var_table *vt, slang_ir_storage *store)
{
struct table *t = vt->Top;
- const int i = alloc_reg(vt, store->Size, GL_FALSE);
+ int i;
+
+ if (store->File == PROGRAM_SAMPLER) {
+ /* don't really allocate storage */
+ store->Index = 0;
+ return GL_TRUE;
+ }
+
+ i = alloc_reg(vt, store->Size, GL_FALSE);
if (i < 0)
return GL_FALSE;
store->Index = i / 4;
- if (store->Size == 1) {
- const GLuint comp = i % 4;
- store->Swizzle = MAKE_SWIZZLE4(comp, comp, comp, comp);
- }
- else if (store->Size == 2) {
- store->Swizzle = MAKE_SWIZZLE4(SWIZZLE_X, SWIZZLE_Y,
- SWIZZLE_NIL, SWIZZLE_NIL);
- }
- else if (store->Size == 3) {
- store->Swizzle = MAKE_SWIZZLE4(SWIZZLE_X, SWIZZLE_Y,
- SWIZZLE_Z, SWIZZLE_NIL);
- }
- else {
- store->Swizzle = SWIZZLE_NOOP;
- }
+ store->Swizzle = _slang_var_swizzle(store->Size, i % 4);
if (dbg)
printf("Alloc var storage sz %d at %d.%s (level %d) store %p\n",
assert(store->Index < 0);
store->Index = i / 4;
- if (store->Size == 1) {
- const GLuint comp = i % 4;
- store->Swizzle = MAKE_SWIZZLE4(comp, comp, comp, comp);
- }
- else {
- /* XXX improve swizzled for size=2/3, use for writemask... */
-#if 1
- if (store->Size == 2) {
- store->Swizzle = MAKE_SWIZZLE4(SWIZZLE_X, SWIZZLE_Y,
- SWIZZLE_NIL, SWIZZLE_NIL);
- }
-#endif
- store->Swizzle = SWIZZLE_NOOP;
- }
+ store->Swizzle = _slang_var_swizzle(store->Size, i % 4);
if (dbg) printf("Alloc temp sz %d at %d.%s (level %d) store %p\n",
store->Size, store->Index,