exec_node: Add new talloc-based new()
authorCarl Worth <cworth@cworth.org>
Thu, 24 Jun 2010 01:11:51 +0000 (18:11 -0700)
committerCarl Worth <cworth@cworth.org>
Thu, 24 Jun 2010 01:59:35 +0000 (18:59 -0700)
And fix all callers to use the tallbac-based new for exec_node
construction. We make ready use of talloc_parent in order to get
valid, (and appropriate) talloc owners for everything we construct
without having to add new 'ctx' parameters up and down all the call
trees.

This closes the majority of the memory leaks in the
glsl-orangebook-ch06-bump.frag test:

total heap usage: 55,623 allocs, 42,672 frees
(was 14,533 frees)

Now 76.7% leak-free. Woo-hoo!

18 files changed:
ast_function.cpp
ast_to_hir.cpp
glsl_types.cpp
hir_field_selection.cpp
ir.cpp
ir_clone.cpp
ir_constant_expression.cpp
ir_copy_propagation.cpp
ir_dead_code.cpp
ir_dead_code_local.cpp
ir_expression_flattening.cpp
ir_function_inlining.cpp
ir_reader.cpp
ir_variable.cpp
ir_vec_index_to_swizzle.cpp
list.h
s_expression.cpp
s_expression.h

index ff2dfa502f3c6044d3337fe577cf70a9b4c2927b..866cbc4ecdf6a5a8b0f88183825bcba5ce2e1508 100644 (file)
@@ -54,6 +54,8 @@ process_call(exec_list *instructions, ir_function *f,
             YYLTYPE *loc, exec_list *actual_parameters,
             struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
+
    const ir_function_signature *sig =
       f->matching_signature(actual_parameters);
 
@@ -93,7 +95,7 @@ process_call(exec_list *instructions, ir_function *f,
       /* FINISHME: The list of actual parameters needs to be modified to
        * FINISHME: include any necessary conversions.
        */
-      return new ir_call(sig, actual_parameters);
+      return new(ctx) ir_call(sig, actual_parameters);
    } else {
       /* FINISHME: Log a better error message here.  G++ will show the types
        * FINISHME: of the actual parameters and the set of candidate
@@ -132,6 +134,7 @@ match_function_by_name(exec_list *instructions, const char *name,
 static ir_rvalue *
 convert_component(ir_rvalue *src, const glsl_type *desired_type)
 {
+   void *ctx = talloc_parent(src);
    const unsigned a = desired_type->base_type;
    const unsigned b = src->type->base_type;
    ir_expression *result = NULL;
@@ -149,22 +152,22 @@ convert_component(ir_rvalue *src, const glsl_type *desired_type)
    case GLSL_TYPE_UINT:
    case GLSL_TYPE_INT:
       if (b == GLSL_TYPE_FLOAT)
-        result = new ir_expression(ir_unop_f2i, desired_type, src, NULL);
+        result = new(ctx) ir_expression(ir_unop_f2i, desired_type, src, NULL);
       else {
         assert(b == GLSL_TYPE_BOOL);
-        result = new ir_expression(ir_unop_b2i, desired_type, src, NULL);
+        result = new(ctx) ir_expression(ir_unop_b2i, desired_type, src, NULL);
       }
       break;
    case GLSL_TYPE_FLOAT:
       switch (b) {
       case GLSL_TYPE_UINT:
-        result = new ir_expression(ir_unop_u2f, desired_type, src, NULL);
+        result = new(ctx) ir_expression(ir_unop_u2f, desired_type, src, NULL);
         break;
       case GLSL_TYPE_INT:
-        result = new ir_expression(ir_unop_i2f, desired_type, src, NULL);
+        result = new(ctx) ir_expression(ir_unop_i2f, desired_type, src, NULL);
         break;
       case GLSL_TYPE_BOOL:
-        result = new ir_expression(ir_unop_b2f, desired_type, src, NULL);
+        result = new(ctx) ir_expression(ir_unop_b2f, desired_type, src, NULL);
         break;
       }
       break;
@@ -172,12 +175,12 @@ convert_component(ir_rvalue *src, const glsl_type *desired_type)
       ir_constant *zero = NULL;
 
       switch (b) {
-      case GLSL_TYPE_UINT:  zero = new ir_constant(unsigned(0)); break;
-      case GLSL_TYPE_INT:   zero = new ir_constant(int(0));      break;
-      case GLSL_TYPE_FLOAT: zero = new ir_constant(0.0f);        break;
+      case GLSL_TYPE_UINT:  zero = new(ctx) ir_constant(unsigned(0)); break;
+      case GLSL_TYPE_INT:   zero = new(ctx) ir_constant(int(0));      break;
+      case GLSL_TYPE_FLOAT: zero = new(ctx) ir_constant(0.0f);        break;
       }
 
-      result = new ir_expression(ir_binop_nequal, desired_type, src, zero);
+      result = new(ctx) ir_expression(ir_binop_nequal, desired_type, src, zero);
    }
    }
 
@@ -194,6 +197,7 @@ convert_component(ir_rvalue *src, const glsl_type *desired_type)
 static ir_rvalue *
 dereference_component(ir_rvalue *src, unsigned component)
 {
+   void *ctx = talloc_parent(src);
    assert(component < src->type->components());
 
    /* If the source is a constant, just create a new constant instead of a
@@ -201,12 +205,12 @@ dereference_component(ir_rvalue *src, unsigned component)
     */
    ir_constant *constant = src->as_constant();
    if (constant)
-      return new ir_constant(constant, component);
+      return new(ctx) ir_constant(constant, component);
 
    if (src->type->is_scalar()) {
       return src;
    } else if (src->type->is_vector()) {
-      return new ir_swizzle(src, component, 0, 0, 0, 1);
+      return new(ctx) ir_swizzle(src, component, 0, 0, 0, 1);
    } else {
       assert(src->type->is_matrix());
 
@@ -215,8 +219,8 @@ dereference_component(ir_rvalue *src, unsigned component)
        */
       const int c = component / src->type->column_type()->vector_elements;
       const int r = component % src->type->column_type()->vector_elements;
-      ir_constant *const col_index = new ir_constant(c);
-      ir_dereference *const col = new ir_dereference_array(src, col_index);
+      ir_constant *const col_index = new(ctx) ir_constant(c);
+      ir_dereference *const col = new(ctx) ir_dereference_array(src, col_index);
 
       col->type = src->type->column_type();
 
@@ -306,6 +310,7 @@ constant_record_constructor(const glsl_type *constructor_type,
                            YYLTYPE *loc, exec_list *parameters,
                            struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    bool all_parameters_are_constant = true;
 
    exec_node *node = parameters->head;
@@ -338,7 +343,7 @@ constant_record_constructor(const glsl_type *constructor_type,
    if (!all_parameters_are_constant)
       return NULL;
 
-   return new ir_constant(constructor_type, parameters);
+   return new(ctx) ir_constant(constructor_type, parameters);
 }
 
 
@@ -440,6 +445,7 @@ ir_rvalue *
 ast_function_expression::hir(exec_list *instructions,
                             struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    /* There are three sorts of function calls.
     *
     * 1. contstructors - The first subexpression is an ast_type_specifier.
@@ -574,11 +580,13 @@ ast_function_expression::hir(exec_list *instructions,
             * glsl-vs-constructor-call.shader_test.
             */
            if (result->type->components() >= 1 && !result->as_constant()) {
-              result_var = new ir_variable(result->type, "constructor_tmp");
+              result_var = new(ctx) ir_variable(result->type,
+                                                "constructor_tmp");
               ir_dereference_variable *lhs;
 
-              lhs = new ir_dereference_variable(result_var);
-              instructions->push_tail(new ir_assignment(lhs, result, NULL));
+              lhs = new(ctx) ir_dereference_variable(result_var);
+              instructions->push_tail(new(ctx) ir_assignment(lhs,
+                                                             result, NULL));
            }
 
            /* Process each of the components of the parameter.  Dereference
@@ -592,7 +600,7 @@ ast_function_expression::hir(exec_list *instructions,
               ir_rvalue *component;
 
               if (result_var) {
-                 ir_dereference *d = new ir_dereference_variable(result_var);
+                 ir_dereference *d = new(ctx) ir_dereference_variable(result_var);
                  component = dereference_component(d, i);
               } else {
                  component = dereference_component(result, i);
@@ -674,7 +682,8 @@ ast_function_expression::hir(exec_list *instructions,
             */
            if (all_parameters_are_constant) {
               if (components_used >= type_components)
-                 return new ir_constant(sig->return_type, & actual_parameters);
+                 return new(ctx) ir_constant(sig->return_type,
+                                             & actual_parameters);
 
               assert(sig->return_type->is_vector()
                      || sig->return_type->is_matrix());
@@ -695,9 +704,9 @@ ast_function_expression::hir(exec_list *instructions,
                  generate_constructor_vector(sig->return_type, initializer,
                                              &data);
 
-              return new ir_constant(sig->return_type, &data);
+              return new(ctx) ir_constant(sig->return_type, &data);
            } else
-              return new ir_call(sig, & actual_parameters);
+              return new(ctx) ir_call(sig, & actual_parameters);
         } else {
            /* FINISHME: Log a better error message here.  G++ will show the
             * FINSIHME: types of the actual parameters and the set of
index c70f0f9de9fdacab0544cbb7377b8d4023ca8584..eafc9e81145317f3df6a2964465fde7cf8bd463e 100644 (file)
@@ -87,6 +87,7 @@ static bool
 apply_implicit_conversion(const glsl_type *to, ir_rvalue * &from,
                          struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    if (to->base_type == from->type->base_type)
       return true;
 
@@ -111,13 +112,13 @@ apply_implicit_conversion(const glsl_type *to, ir_rvalue * &from,
 
    switch (from->type->base_type) {
    case GLSL_TYPE_INT:
-      from = new ir_expression(ir_unop_i2f, to, from, NULL);
+      from = new(ctx) ir_expression(ir_unop_i2f, to, from, NULL);
       break;
    case GLSL_TYPE_UINT:
-      from = new ir_expression(ir_unop_u2f, to, from, NULL);
+      from = new(ctx) ir_expression(ir_unop_u2f, to, from, NULL);
       break;
    case GLSL_TYPE_BOOL:
-      from = new ir_expression(ir_unop_b2f, to, from, NULL);
+      from = new(ctx) ir_expression(ir_unop_b2f, to, from, NULL);
       break;
    default:
       assert(0);
@@ -467,6 +468,7 @@ do_assignment(exec_list *instructions, struct _mesa_glsl_parse_state *state,
              ir_rvalue *lhs, ir_rvalue *rhs,
              YYLTYPE lhs_loc)
 {
+   void *ctx = talloc_parent(state);
    bool error_emitted = (lhs->type->is_error() || rhs->type->is_error());
 
    if (!error_emitted) {
@@ -519,16 +521,16 @@ do_assignment(exec_list *instructions, struct _mesa_glsl_parse_state *state,
     * temporary and return a deref of that temporary.  If the rvalue
     * ends up not being used, the temp will get copy-propagated out.
     */
-   ir_variable *var = new ir_variable(rhs->type, "assignment_tmp");
-   instructions->push_tail(new ir_assignment(new ir_dereference_variable(var),
-                                            rhs,
-                                            NULL));
+   ir_variable *var = new(ctx) ir_variable(rhs->type, "assignment_tmp");
+   instructions->push_tail(new(ctx) ir_assignment(new(ctx) ir_dereference_variable(var),
+                                                 rhs,
+                                                 NULL));
 
-   instructions->push_tail(new ir_assignment(lhs,
-                                            new ir_dereference_variable(var),
-                                            NULL));
+   instructions->push_tail(new(ctx) ir_assignment(lhs,
+                                                 new(ctx) ir_dereference_variable(var),
+                                                 NULL));
 
-   return new ir_dereference_variable(var);
+   return new(ctx) ir_dereference_variable(var);
 }
 
 
@@ -539,12 +541,13 @@ static ir_variable *
 generate_temporary(const glsl_type *type, exec_list *instructions,
                   struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    char *name = (char *) malloc(sizeof(char) * 13);
 
    snprintf(name, 13, "tmp_%08X", state->temp_index);
    state->temp_index++;
 
-   ir_variable *const var = new ir_variable(type, name);
+   ir_variable *const var = new(ctx) ir_variable(type, name);
    instructions->push_tail(var);
 
    return var;
@@ -554,21 +557,22 @@ generate_temporary(const glsl_type *type, exec_list *instructions,
 static ir_rvalue *
 get_lvalue_copy(exec_list *instructions, ir_rvalue *lvalue)
 {
+   void *ctx = talloc_parent(lvalue);
    ir_variable *var;
 
    /* FINISHME: Give unique names to the temporaries. */
-   var = new ir_variable(lvalue->type, "_post_incdec_tmp");
+   var = new(ctx) ir_variable(lvalue->type, "_post_incdec_tmp");
    var->mode = ir_var_auto;
 
-   instructions->push_tail(new ir_assignment(new ir_dereference_variable(var),
-                                            lvalue, NULL));
+   instructions->push_tail(new(ctx) ir_assignment(new(ctx) ir_dereference_variable(var),
+                                                 lvalue, NULL));
 
    /* Once we've created this temporary, mark it read only so it's no
     * longer considered an lvalue.
     */
    var->read_only = true;
 
-   return new ir_dereference_variable(var);
+   return new(ctx) ir_dereference_variable(var);
 }
 
 
@@ -587,6 +591,7 @@ ir_rvalue *
 ast_expression::hir(exec_list *instructions,
                    struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    static const int operations[AST_NUM_OPERATORS] = {
       -1,               /* ast_assign doesn't convert to ir_expression. */
       -1,               /* ast_plus doesn't convert to ir_expression. */
@@ -679,8 +684,8 @@ ast_expression::hir(exec_list *instructions,
 
       error_emitted = type->is_error();
 
-      result = new ir_expression(operations[this->oper], type,
-                                op[0], NULL);
+      result = new(ctx) ir_expression(operations[this->oper], type,
+                                     op[0], NULL);
       break;
 
    case ast_add:
@@ -695,8 +700,8 @@ ast_expression::hir(exec_list *instructions,
                                    state, & loc);
       error_emitted = type->is_error();
 
-      result = new ir_expression(operations[this->oper], type,
-                                op[0], op[1]);
+      result = new(ctx) ir_expression(operations[this->oper], type,
+                                     op[0], op[1]);
       break;
 
    case ast_mod:
@@ -707,8 +712,8 @@ ast_expression::hir(exec_list *instructions,
 
       assert(operations[this->oper] == ir_binop_mod);
 
-      result = new ir_expression(operations[this->oper], type,
-                                op[0], op[1]);
+      result = new(ctx) ir_expression(operations[this->oper], type,
+                                     op[0], op[1]);
       error_emitted = type->is_error();
       break;
 
@@ -734,8 +739,8 @@ ast_expression::hir(exec_list *instructions,
             || ((type->base_type == GLSL_TYPE_BOOL)
                 && type->is_scalar()));
 
-      result = new ir_expression(operations[this->oper], type,
-                                op[0], op[1]);
+      result = new(ctx) ir_expression(operations[this->oper], type,
+                                     op[0], op[1]);
       error_emitted = type->is_error();
       break;
 
@@ -766,8 +771,8 @@ ast_expression::hir(exec_list *instructions,
         error_emitted = true;
       }
 
-      result = new ir_expression(operations[this->oper], glsl_type::bool_type,
-                                op[0], op[1]);
+      result = new(ctx) ir_expression(operations[this->oper], glsl_type::bool_type,
+                                     op[0], op[1]);
       type = glsl_type::bool_type;
 
       assert(result->type == glsl_type::bool_type);
@@ -811,7 +816,7 @@ ast_expression::hir(exec_list *instructions,
         }
         type = glsl_type::bool_type;
       } else {
-        ir_if *const stmt = new ir_if(op[0]);
+        ir_if *const stmt = new(ctx) ir_if(op[0]);
         instructions->push_tail(stmt);
 
         op[1] = this->subexpressions[1]->hir(&stmt->then_instructions, state);
@@ -828,17 +833,17 @@ ast_expression::hir(exec_list *instructions,
         ir_variable *const tmp = generate_temporary(glsl_type::bool_type,
                                                     instructions, state);
 
-        ir_dereference *const then_deref = new ir_dereference_variable(tmp);
+        ir_dereference *const then_deref = new(ctx) ir_dereference_variable(tmp);
         ir_assignment *const then_assign =
-           new ir_assignment(then_deref, op[1], NULL);
+           new(ctx) ir_assignment(then_deref, op[1], NULL);
         stmt->then_instructions.push_tail(then_assign);
 
-        ir_dereference *const else_deref = new ir_dereference_variable(tmp);
+        ir_dereference *const else_deref = new(ctx) ir_dereference_variable(tmp);
         ir_assignment *const else_assign =
-           new ir_assignment(else_deref, new ir_constant(false), NULL);
+           new(ctx) ir_assignment(else_deref, new(ctx) ir_constant(false), NULL);
         stmt->else_instructions.push_tail(else_assign);
 
-        result = new ir_dereference_variable(tmp);
+        result = new(ctx) ir_dereference_variable(tmp);
         type = tmp->type;
       }
       break;
@@ -874,7 +879,7 @@ ast_expression::hir(exec_list *instructions,
         }
         type = glsl_type::bool_type;
       } else {
-        ir_if *const stmt = new ir_if(op[0]);
+        ir_if *const stmt = new(ctx) ir_if(op[0]);
         instructions->push_tail(stmt);
 
         ir_variable *const tmp = generate_temporary(glsl_type::bool_type,
@@ -890,17 +895,17 @@ ast_expression::hir(exec_list *instructions,
            error_emitted = true;
         }
 
-        ir_dereference *const then_deref = new ir_dereference_variable(tmp);
+        ir_dereference *const then_deref = new(ctx) ir_dereference_variable(tmp);
         ir_assignment *const then_assign =
-           new ir_assignment(then_deref, new ir_constant(true), NULL);
+           new(ctx) ir_assignment(then_deref, new(ctx) ir_constant(true), NULL);
         stmt->then_instructions.push_tail(then_assign);
 
-        ir_dereference *const else_deref = new ir_dereference_variable(tmp);
+        ir_dereference *const else_deref = new(ctx) ir_dereference_variable(tmp);
         ir_assignment *const else_assign =
-           new ir_assignment(else_deref, op[1], NULL);
+           new(ctx) ir_assignment(else_deref, op[1], NULL);
         stmt->else_instructions.push_tail(else_assign);
 
-        result = new ir_dereference_variable(tmp);
+        result = new(ctx) ir_dereference_variable(tmp);
         type = tmp->type;
       }
       break;
@@ -911,8 +916,8 @@ ast_expression::hir(exec_list *instructions,
       op[1] = this->subexpressions[1]->hir(instructions, state);
 
 
-      result = new ir_expression(operations[this->oper], glsl_type::bool_type,
-                                op[0], op[1]);
+      result = new(ctx) ir_expression(operations[this->oper], glsl_type::bool_type,
+                                     op[0], op[1]);
       type = glsl_type::bool_type;
       break;
 
@@ -927,8 +932,8 @@ ast_expression::hir(exec_list *instructions,
         error_emitted = true;
       }
 
-      result = new ir_expression(operations[this->oper], glsl_type::bool_type,
-                                op[0], NULL);
+      result = new(ctx) ir_expression(operations[this->oper], glsl_type::bool_type,
+                                     op[0], NULL);
       type = glsl_type::bool_type;
       break;
 
@@ -943,8 +948,8 @@ ast_expression::hir(exec_list *instructions,
                                    (this->oper == ast_mul_assign),
                                    state, & loc);
 
-      ir_rvalue *temp_rhs = new ir_expression(operations[this->oper], type,
-                                             op[0], op[1]);
+      ir_rvalue *temp_rhs = new(ctx) ir_expression(operations[this->oper], type,
+                                                  op[0], op[1]);
 
       result = do_assignment(instructions, state,
                             (ir_rvalue *)op[0]->clone(NULL), temp_rhs,
@@ -969,8 +974,8 @@ ast_expression::hir(exec_list *instructions,
       assert(operations[this->oper] == ir_binop_mod);
 
       struct ir_rvalue *temp_rhs;
-      temp_rhs = new ir_expression(operations[this->oper], type,
-                                  op[0], op[1]);
+      temp_rhs = new(ctx) ir_expression(operations[this->oper], type,
+                                       op[0], op[1]);
 
       result = do_assignment(instructions, state,
                             (ir_rvalue *)op[0]->clone(NULL), temp_rhs,
@@ -1056,22 +1061,24 @@ ast_expression::hir(exec_list *instructions,
         ir_variable *const tmp = generate_temporary(type,
                                                     instructions, state);
 
-        ir_if *const stmt = new ir_if(op[0]);
+        ir_if *const stmt = new(ctx) ir_if(op[0]);
         instructions->push_tail(stmt);
 
         then_instructions.move_nodes_to(& stmt->then_instructions);
-        ir_dereference *const then_deref = new ir_dereference_variable(tmp);
+        ir_dereference *const then_deref =
+           new(ctx) ir_dereference_variable(tmp);
         ir_assignment *const then_assign =
-           new ir_assignment(then_deref, op[1], NULL);
+           new(ctx) ir_assignment(then_deref, op[1], NULL);
         stmt->then_instructions.push_tail(then_assign);
 
         else_instructions.move_nodes_to(& stmt->else_instructions);
-        ir_dereference *const else_deref = new ir_dereference_variable(tmp);
+        ir_dereference *const else_deref =
+           new(ctx) ir_dereference_variable(tmp);
         ir_assignment *const else_assign =
-           new ir_assignment(else_deref, op[2], NULL);
+           new(ctx) ir_assignment(else_deref, op[2], NULL);
         stmt->else_instructions.push_tail(else_assign);
 
-        result = new ir_dereference_variable(tmp);
+        result = new(ctx) ir_dereference_variable(tmp);
       }
       break;
    }
@@ -1080,15 +1087,15 @@ ast_expression::hir(exec_list *instructions,
    case ast_pre_dec: {
       op[0] = this->subexpressions[0]->hir(instructions, state);
       if (op[0]->type->base_type == GLSL_TYPE_FLOAT)
-        op[1] = new ir_constant(1.0f);
+        op[1] = new(ctx) ir_constant(1.0f);
       else
-        op[1] = new ir_constant(1);
+        op[1] = new(ctx) ir_constant(1);
 
       type = arithmetic_result_type(op[0], op[1], false, state, & loc);
 
       struct ir_rvalue *temp_rhs;
-      temp_rhs = new ir_expression(operations[this->oper], type,
-                                  op[0], op[1]);
+      temp_rhs = new(ctx) ir_expression(operations[this->oper], type,
+                                       op[0], op[1]);
 
       result = do_assignment(instructions, state,
                             (ir_rvalue *)op[0]->clone(NULL), temp_rhs,
@@ -1102,17 +1109,17 @@ ast_expression::hir(exec_list *instructions,
    case ast_post_dec: {
       op[0] = this->subexpressions[0]->hir(instructions, state);
       if (op[0]->type->base_type == GLSL_TYPE_FLOAT)
-        op[1] = new ir_constant(1.0f);
+        op[1] = new(ctx) ir_constant(1.0f);
       else
-        op[1] = new ir_constant(1);
+        op[1] = new(ctx) ir_constant(1);
 
       error_emitted = op[0]->type->is_error() || op[1]->type->is_error();
 
       type = arithmetic_result_type(op[0], op[1], false, state, & loc);
 
       struct ir_rvalue *temp_rhs;
-      temp_rhs = new ir_expression(operations[this->oper], type,
-                                  op[0], op[1]);
+      temp_rhs = new(ctx) ir_expression(operations[this->oper], type,
+                                       op[0], op[1]);
 
       /* Get a temporary of a copy of the lvalue before it's modified.
        * This may get thrown away later.
@@ -1143,7 +1150,7 @@ ast_expression::hir(exec_list *instructions,
 
       ir_rvalue *const array = op[0];
 
-      result = new ir_dereference_array(op[0], op[1]);
+      result = new(ctx) ir_dereference_array(op[0], op[1]);
 
       /* Do not use op[0] after this point.  Use array.
        */
@@ -1259,7 +1266,7 @@ ast_expression::hir(exec_list *instructions,
       ir_variable *var = 
         state->symbols->get_variable(this->primary_expression.identifier);
 
-      result = new ir_dereference_variable(var);
+      result = new(ctx) ir_dereference_variable(var);
 
       if (var != NULL) {
         type = result->type;
@@ -1274,22 +1281,22 @@ ast_expression::hir(exec_list *instructions,
 
    case ast_int_constant:
       type = glsl_type::int_type;
-      result = new ir_constant(this->primary_expression.int_constant);
+      result = new(ctx) ir_constant(this->primary_expression.int_constant);
       break;
 
    case ast_uint_constant:
       type = glsl_type::uint_type;
-      result = new ir_constant(this->primary_expression.uint_constant);
+      result = new(ctx) ir_constant(this->primary_expression.uint_constant);
       break;
 
    case ast_float_constant:
       type = glsl_type::float_type;
-      result = new ir_constant(this->primary_expression.float_constant);
+      result = new(ctx) ir_constant(this->primary_expression.float_constant);
       break;
 
    case ast_bool_constant:
       type = glsl_type::bool_type;
-      result = new ir_constant(bool(this->primary_expression.bool_constant));
+      result = new(ctx) ir_constant(bool(this->primary_expression.bool_constant));
       break;
 
    case ast_sequence: {
@@ -1528,6 +1535,7 @@ ir_rvalue *
 ast_declarator_list::hir(exec_list *instructions,
                         struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    const struct glsl_type *decl_type;
    const char *type_name = NULL;
    ir_rvalue *result = NULL;
@@ -1588,7 +1596,7 @@ ast_declarator_list::hir(exec_list *instructions,
         var_type = decl_type;
       }
 
-      var = new ir_variable(var_type, decl->identifier);
+      var = new(ctx) ir_variable(var_type, decl->identifier);
 
       /* From page 22 (page 28 of the PDF) of the GLSL 1.10 specification;
        *
@@ -1788,7 +1796,7 @@ ast_declarator_list::hir(exec_list *instructions,
                             ? "attribute" : "varying");
         }
 
-        ir_dereference *const lhs = new ir_dereference_variable(var);
+        ir_dereference *const lhs = new(ctx) ir_dereference_variable(var);
         ir_rvalue *rhs = decl->initializer->hir(instructions, state);
 
         /* Calculate the constant value if this is a const or uniform
@@ -1866,6 +1874,7 @@ ir_rvalue *
 ast_parameter_declarator::hir(exec_list *instructions,
                              struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    const struct glsl_type *type;
    const char *name = NULL;
    YYLTYPE loc = this->get_location();
@@ -1913,7 +1922,7 @@ ast_parameter_declarator::hir(exec_list *instructions,
    }
 
    is_void = false;
-   ir_variable *var = new ir_variable(type, this->identifier);
+   ir_variable *var = new(ctx) ir_variable(type, this->identifier);
 
    /* FINISHME: Handle array declarations.  Note that this requires
     * FINISHME: complete handling of constant expressions.
@@ -1966,6 +1975,7 @@ ir_rvalue *
 ast_function::hir(exec_list *instructions,
                  struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    ir_function *f = NULL;
    ir_function_signature *sig = NULL;
    exec_list hir_parameters;
@@ -2025,7 +2035,7 @@ ast_function::hir(exec_list *instructions,
                       "non-function", name);
       sig = NULL;
    } else {
-      f = new ir_function(name);
+      f = new(ctx) ir_function(name);
       state->symbols->add_function(f->name, f);
 
       /* Emit the new function header */
@@ -2050,7 +2060,7 @@ ast_function::hir(exec_list *instructions,
    /* Finish storing the information about this new function in its signature.
     */
    if (sig == NULL) {
-      sig = new ir_function_signature(return_type);
+      sig = new(ctx) ir_function_signature(return_type);
       f->add_signature(sig);
    }
 
@@ -2115,6 +2125,7 @@ ir_rvalue *
 ast_jump_statement::hir(exec_list *instructions,
                        struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
 
    switch (mode) {
    case ast_return: {
@@ -2140,7 +2151,7 @@ ast_jump_statement::hir(exec_list *instructions,
          * FINISHME: type of the enclosing function.
          */
 
-        inst = new ir_return(ret);
+        inst = new(ctx) ir_return(ret);
       } else {
         if (state->current_function->return_type->base_type !=
             GLSL_TYPE_VOID) {
@@ -2151,7 +2162,7 @@ ast_jump_statement::hir(exec_list *instructions,
                             "non-void",
                             state->current_function->function_name());
         }
-        inst = new ir_return;
+        inst = new(ctx) ir_return;
       }
 
       instructions->push_tail(inst);
@@ -2188,9 +2199,9 @@ ast_jump_statement::hir(exec_list *instructions,
 
         if (loop != NULL) {
            ir_loop_jump *const jump =
-              new ir_loop_jump((mode == ast_break)
-                               ? ir_loop_jump::jump_break
-                               : ir_loop_jump::jump_continue);
+              new(ctx) ir_loop_jump((mode == ast_break)
+                                    ? ir_loop_jump::jump_break
+                                    : ir_loop_jump::jump_continue);
            instructions->push_tail(jump);
         }
       }
@@ -2208,6 +2219,8 @@ ir_rvalue *
 ast_selection_statement::hir(exec_list *instructions,
                             struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
+
    ir_rvalue *const condition = this->condition->hir(instructions, state);
 
    /* From page 66 (page 72 of the PDF) of the GLSL 1.50 spec:
@@ -2226,7 +2239,7 @@ ast_selection_statement::hir(exec_list *instructions,
                       "boolean");
    }
 
-   ir_if *const stmt = new ir_if(condition);
+   ir_if *const stmt = new(ctx) ir_if(condition);
 
    if (then_statement != NULL)
       then_statement->hir(& stmt->then_instructions, state);
@@ -2246,6 +2259,8 @@ void
 ast_iteration_statement::condition_to_hir(ir_loop *stmt,
                                          struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
+
    if (condition != NULL) {
       ir_rvalue *const cond =
         condition->hir(& stmt->body_instructions, state);
@@ -2261,13 +2276,13 @@ ast_iteration_statement::condition_to_hir(ir_loop *stmt,
          * like 'if (!condition) break;' as the loop termination condition.
          */
         ir_rvalue *const not_cond =
-           new ir_expression(ir_unop_logic_not, glsl_type::bool_type, cond,
-                             NULL);
+           new(ctx) ir_expression(ir_unop_logic_not, glsl_type::bool_type, cond,
+                                  NULL);
 
-        ir_if *const if_stmt = new ir_if(not_cond);
+        ir_if *const if_stmt = new(ctx) ir_if(not_cond);
 
         ir_jump *const break_stmt =
-           new ir_loop_jump(ir_loop_jump::jump_break);
+           new(ctx) ir_loop_jump(ir_loop_jump::jump_break);
 
         if_stmt->then_instructions.push_tail(break_stmt);
         stmt->body_instructions.push_tail(if_stmt);
@@ -2280,6 +2295,8 @@ ir_rvalue *
 ast_iteration_statement::hir(exec_list *instructions,
                             struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
+
    /* For-loops and while-loops start a new scope, but do-while loops do not.
     */
    if (mode != ast_do_while)
@@ -2288,7 +2305,7 @@ ast_iteration_statement::hir(exec_list *instructions,
    if (init_statement != NULL)
       init_statement->hir(instructions, state);
 
-   ir_loop *const stmt = new ir_loop();
+   ir_loop *const stmt = new(ctx) ir_loop();
    instructions->push_tail(stmt);
 
    /* Track the current loop and / or switch-statement nesting.
index ca19de6bec3f3150662d01e865afde24a944c47c..fcc77458b28c830e09e26a321519ee521dff77ce 100644 (file)
@@ -150,14 +150,16 @@ const glsl_type *glsl_type::get_base_type() const
 ir_function *
 glsl_type::generate_constructor(glsl_symbol_table *symtab) const
 {
+   void *ctx = symtab;
+
    /* Generate the function name and add it to the symbol table.
     */
-   ir_function *const f = new ir_function(name);
+   ir_function *const f = new(ctx) ir_function(name);
 
    bool added = symtab->add_function(name, f);
    assert(added);
 
-   ir_function_signature *const sig = new ir_function_signature(this);
+   ir_function_signature *const sig = new(ctx) ir_function_signature(this);
    f->add_signature(sig);
 
    ir_variable **declarations =
@@ -168,8 +170,8 @@ glsl_type::generate_constructor(glsl_symbol_table *symtab) const
       snprintf(param_name, 10, "p%08X", i);
 
       ir_variable *var = (this->base_type == GLSL_TYPE_ARRAY)
-        ? new ir_variable(fields.array, param_name)
-        : new ir_variable(fields.structure[i].type, param_name);
+        ? new(ctx) ir_variable(fields.array, param_name)
+        : new(ctx) ir_variable(fields.structure[i].type, param_name);
 
       var->mode = ir_var_in;
       declarations[i] = var;
@@ -181,24 +183,26 @@ glsl_type::generate_constructor(glsl_symbol_table *symtab) const
     * the same type as the constructor.  After initializing __retval,
     * __retval is returned.
     */
-   ir_variable *retval = new ir_variable(this, "__retval");
+   ir_variable *retval = new(ctx) ir_variable(this, "__retval");
    sig->body.push_tail(retval);
 
    for (unsigned i = 0; i < length; i++) {
       ir_dereference *const lhs = (this->base_type == GLSL_TYPE_ARRAY)
-        ? (ir_dereference *) new ir_dereference_array(retval, new ir_constant(i))
-        : (ir_dereference *) new ir_dereference_record(retval, fields.structure[i].name);
+        ? (ir_dereference *) new(ctx) ir_dereference_array(retval,
+                                                           new(ctx) ir_constant(i))
+        : (ir_dereference *) new(ctx) ir_dereference_record(retval,
+                                                            fields.structure[i].name);
 
-      ir_dereference *const rhs = new ir_dereference_variable(declarations[i]);
-      ir_instruction *const assign = new ir_assignment(lhs, rhs, NULL);
+      ir_dereference *const rhs = new(ctx) ir_dereference_variable(declarations[i]);
+      ir_instruction *const assign = new(ctx) ir_assignment(lhs, rhs, NULL);
 
       sig->body.push_tail(assign);
    }
 
    free(declarations);
 
-   ir_dereference *const retref = new ir_dereference_variable(retval);
-   ir_instruction *const inst = new ir_return(retref);
+   ir_dereference *const retref = new(ctx) ir_dereference_variable(retval);
+   ir_instruction *const inst = new(ctx) ir_return(retref);
    sig->body.push_tail(inst);
 
    return f;
@@ -223,6 +227,8 @@ static ir_function_signature *
 generate_constructor_intro(const glsl_type *type, unsigned parameter_count,
                           ir_variable **declarations)
 {
+   /* NULL is wrong here and leaks. */
+   void *ctx = NULL;
    /* Names of parameters used in vector and matrix constructors
     */
    static const char *const names[] = {
@@ -234,10 +240,10 @@ generate_constructor_intro(const glsl_type *type, unsigned parameter_count,
 
    const glsl_type *const parameter_type = type->get_base_type();
 
-   ir_function_signature *const signature = new ir_function_signature(type);
+   ir_function_signature *const signature = new(ctx) ir_function_signature(type);
 
    for (unsigned i = 0; i < parameter_count; i++) {
-      ir_variable *var = new ir_variable(parameter_type, names[i]);
+      ir_variable *var = new(ctx) ir_variable(parameter_type, names[i]);
 
       var->mode = ir_var_in;
       signature->parameters.push_tail(var);
@@ -245,7 +251,7 @@ generate_constructor_intro(const glsl_type *type, unsigned parameter_count,
       declarations[i] = var;
    }
 
-   ir_variable *retval = new ir_variable(type, "__retval");
+   ir_variable *retval = new(ctx) ir_variable(type, "__retval");
    signature->body.push_tail(retval);
 
    declarations[16] = retval;
@@ -260,26 +266,28 @@ static void
 generate_vec_body_from_scalar(exec_list *instructions,
                              ir_variable **declarations)
 {
+   /* NULL is wrong here and leaks. */
+   void *ctx = NULL;
    ir_instruction *inst;
 
    /* Generate a single assignment of the parameter to __retval.x and return
     * __retval.xxxx for however many vector components there are.
     */
    ir_dereference *const lhs_ref =
-      new ir_dereference_variable(declarations[16]);
-   ir_dereference *const rhs = new ir_dereference_variable(declarations[0]);
+      new(ctx) ir_dereference_variable(declarations[16]);
+   ir_dereference *const rhs = new(ctx) ir_dereference_variable(declarations[0]);
 
-   ir_swizzle *lhs = new ir_swizzle(lhs_ref, 0, 0, 0, 0, 1);
+   ir_swizzle *lhs = new(ctx) ir_swizzle(lhs_ref, 0, 0, 0, 0, 1);
 
-   inst = new ir_assignment(lhs, rhs, NULL);
+   inst = new(ctx) ir_assignment(lhs, rhs, NULL);
    instructions->push_tail(inst);
 
-   ir_dereference *const retref = new ir_dereference_variable(declarations[16]);
+   ir_dereference *const retref = new(ctx) ir_dereference_variable(declarations[16]);
 
-   ir_swizzle *retval = new ir_swizzle(retref, 0, 0, 0, 0,
-                                       declarations[16]->type->vector_elements);
+   ir_swizzle *retval = new(ctx) ir_swizzle(retref, 0, 0, 0, 0,
+                                           declarations[16]->type->vector_elements);
 
-   inst = new ir_return(retval);
+   inst = new(ctx) ir_return(retval);
    instructions->push_tail(inst);
 }
 
@@ -291,27 +299,28 @@ static void
 generate_vec_body_from_N_scalars(exec_list *instructions,
                                 ir_variable **declarations)
 {
+   /* NULL is wrong here and leaks. */
+   void *ctx = NULL;
    ir_instruction *inst;
    const glsl_type *const vec_type = declarations[16]->type;
 
-
    /* Generate an assignment of each parameter to a single component of
     * __retval.x and return __retval.
     */
    for (unsigned i = 0; i < vec_type->vector_elements; i++) {
       ir_dereference *const lhs_ref =
-        new ir_dereference_variable(declarations[16]);
-      ir_dereference *const rhs = new ir_dereference_variable(declarations[i]);
+        new(ctx) ir_dereference_variable(declarations[16]);
+      ir_dereference *const rhs = new(ctx) ir_dereference_variable(declarations[i]);
 
-      ir_swizzle *lhs = new ir_swizzle(lhs_ref, i, 0, 0, 0, 1);
+      ir_swizzle *lhs = new(ctx) ir_swizzle(lhs_ref, i, 0, 0, 0, 1);
 
-      inst = new ir_assignment(lhs, rhs, NULL);
+      inst = new(ctx) ir_assignment(lhs, rhs, NULL);
       instructions->push_tail(inst);
    }
 
-   ir_dereference *retval = new ir_dereference_variable(declarations[16]);
+   ir_dereference *retval = new(ctx) ir_dereference_variable(declarations[16]);
 
-   inst = new ir_return(retval);
+   inst = new(ctx) ir_return(retval);
    instructions->push_tail(inst);
 }
 
@@ -323,6 +332,8 @@ static void
 generate_mat_body_from_scalar(exec_list *instructions,
                              ir_variable **declarations)
 {
+   /* NULL is wrong here and leaks. */
+   void *ctx = NULL;
    ir_instruction *inst;
 
    /* Generate an assignment of the parameter to the X component of a
@@ -347,49 +358,50 @@ generate_mat_body_from_scalar(exec_list *instructions,
     */
    const glsl_type *const column_type = declarations[16]->type->column_type();
    const glsl_type *const row_type = declarations[16]->type->row_type();
-   ir_variable *const column = new ir_variable(column_type, "v");
+
+   ir_variable *const column = new(ctx) ir_variable(column_type, "v");
 
    instructions->push_tail(column);
 
-   ir_dereference *const lhs_ref = new ir_dereference_variable(column);
-   ir_dereference *const rhs = new ir_dereference_variable(declarations[0]);
+   ir_dereference *const lhs_ref = new(ctx) ir_dereference_variable(column);
+   ir_dereference *const rhs = new(ctx) ir_dereference_variable(declarations[0]);
 
-   ir_swizzle *lhs = new ir_swizzle(lhs_ref, 0, 0, 0, 0, 1);
+   ir_swizzle *lhs = new(ctx) ir_swizzle(lhs_ref, 0, 0, 0, 0, 1);
 
-   inst = new ir_assignment(lhs, rhs, NULL);
+   inst = new(ctx) ir_assignment(lhs, rhs, NULL);
    instructions->push_tail(inst);
 
    for (unsigned i = 1; i < column_type->vector_elements; i++) {
-      ir_dereference *const lhs_ref = new ir_dereference_variable(column);
-      ir_constant *const zero = new ir_constant(0.0f);
+      ir_dereference *const lhs_ref = new(ctx) ir_dereference_variable(column);
+      ir_constant *const zero = new(ctx) ir_constant(0.0f);
 
-      ir_swizzle *lhs = new ir_swizzle(lhs_ref, i, 0, 0, 0, 1);
+      ir_swizzle *lhs = new(ctx) ir_swizzle(lhs_ref, i, 0, 0, 0, 1);
 
-      inst = new ir_assignment(lhs, zero, NULL);
+      inst = new(ctx) ir_assignment(lhs, zero, NULL);
       instructions->push_tail(inst);
    }
 
 
    for (unsigned i = 0; i < row_type->vector_elements; i++) {
       static const unsigned swiz[] = { 1, 1, 1, 0, 1, 1, 1 };
-      ir_dereference *const rhs_ref = new ir_dereference_variable(column);
+      ir_dereference *const rhs_ref = new(ctx) ir_dereference_variable(column);
 
       /* This will be .xyyy when i=0, .yxyy when i=1, etc.
        */
-      ir_swizzle *rhs = new ir_swizzle(rhs_ref, swiz[3 - i], swiz[4 - i],
-                                       swiz[5 - i], swiz[6 - i],
-                                      column_type->vector_elements);
+      ir_swizzle *rhs = new(ctx) ir_swizzle(rhs_ref, swiz[3 - i], swiz[4 - i],
+                                           swiz[5 - i], swiz[6 - i],
+                                           column_type->vector_elements);
 
-      ir_constant *const idx = new ir_constant(int(i));
+      ir_constant *const idx = new(ctx) ir_constant(int(i));
       ir_dereference *const lhs =
-        new ir_dereference_array(declarations[16], idx);
+        new(ctx) ir_dereference_array(declarations[16], idx);
 
-      inst = new ir_assignment(lhs, rhs, NULL);
+      inst = new(ctx) ir_assignment(lhs, rhs, NULL);
       instructions->push_tail(inst);
    }
 
-   ir_dereference *const retval = new ir_dereference_variable(declarations[16]);
-   inst = new ir_return(retval);
+   ir_dereference *const retval = new(ctx) ir_dereference_variable(declarations[16]);
+   inst = new(ctx) ir_return(retval);
    instructions->push_tail(inst);
 }
 
@@ -401,35 +413,36 @@ static void
 generate_mat_body_from_N_scalars(exec_list *instructions,
                                 ir_variable **declarations)
 {
+   /* NULL is wrong here and leaks. */
+   void *ctx = NULL;
    ir_instruction *inst;
    const glsl_type *const row_type = declarations[16]->type->row_type();
    const glsl_type *const column_type = declarations[16]->type->column_type();
 
-
    /* Generate an assignment of each parameter to a single component of
     * of a particular column of __retval and return __retval.
     */
    for (unsigned i = 0; i < column_type->vector_elements; i++) {
       for (unsigned j = 0; j < row_type->vector_elements; j++) {
-        ir_constant *row_index = new ir_constant(int(i));
+        ir_constant *row_index = new(ctx) ir_constant(int(i));
         ir_dereference *const row_access =
-           new ir_dereference_array(declarations[16], row_index);
+           new(ctx) ir_dereference_array(declarations[16], row_index);
 
-        ir_swizzle *component_access = new ir_swizzle(row_access,
-                                                      j, 0, 0, 0, 1);
+        ir_swizzle *component_access = new(ctx) ir_swizzle(row_access,
+                                                           j, 0, 0, 0, 1);
 
         const unsigned param = (i * row_type->vector_elements) + j;
         ir_dereference *const rhs =
-           new ir_dereference_variable(declarations[param]);
+           new(ctx) ir_dereference_variable(declarations[param]);
 
-        inst = new ir_assignment(component_access, rhs, NULL);
+        inst = new(ctx) ir_assignment(component_access, rhs, NULL);
         instructions->push_tail(inst);
       }
    }
 
-   ir_dereference *retval = new ir_dereference_variable(declarations[16]);
+   ir_dereference *retval = new(ctx) ir_dereference_variable(declarations[16]);
 
-   inst = new ir_return(retval);
+   inst = new(ctx) ir_return(retval);
    instructions->push_tail(inst);
 }
 
@@ -444,6 +457,7 @@ static void
 generate_constructor(glsl_symbol_table *symtab, const struct glsl_type *types,
                     unsigned num_types, exec_list *instructions)
 {
+   void *ctx = symtab;
    ir_variable *declarations[17];
 
    for (unsigned i = 0; i < num_types; i++) {
@@ -459,7 +473,7 @@ generate_constructor(glsl_symbol_table *symtab, const struct glsl_type *types,
 
       /* Generate the function block, add it to the symbol table, and emit it.
        */
-      ir_function *const f = new ir_function(types[i].name);
+      ir_function *const f = new(ctx) ir_function(types[i].name);
 
       bool added = symtab->add_function(types[i].name, f);
       assert(added);
index e60ea30d7ff37026aea19745302fcaa57321b6e2..6da14925b98ca6b4c48ed4ff33f6c4e653cbce97 100644 (file)
@@ -33,6 +33,7 @@ _mesa_ast_field_selection_to_hir(const ast_expression *expr,
                                 exec_list *instructions,
                                 struct _mesa_glsl_parse_state *state)
 {
+   void *ctx = talloc_parent(state);
    ir_rvalue *result = NULL;
    ir_rvalue *op;
 
@@ -62,8 +63,8 @@ _mesa_ast_field_selection_to_hir(const ast_expression *expr,
                          expr->primary_expression.identifier);
       }
    } else if (op->type->base_type == GLSL_TYPE_STRUCT) {
-      result = new ir_dereference_record(op,
-                                        expr->primary_expression.identifier);
+      result = new(ctx) ir_dereference_record(op,
+                                             expr->primary_expression.identifier);
 
       if (result->type->is_error()) {
         _mesa_glsl_error(& loc, state, "Cannot access field `%s' of "
diff --git a/ir.cpp b/ir.cpp
index 98b085e91bfc1543f078002ef554065e524753f3..26cd4755520da808c924e790ee18140640c93a13 100644 (file)
--- a/ir.cpp
+++ b/ir.cpp
@@ -300,15 +300,17 @@ ir_constant::ir_constant(const struct glsl_type *type, exec_list *value_list)
 ir_instruction *
 ir_constant::clone(struct hash_table *ht) const
 {
+   void *ctx = talloc_parent(this);
+
    switch (this->type->base_type) {
    case GLSL_TYPE_UINT:
    case GLSL_TYPE_INT:
    case GLSL_TYPE_FLOAT:
    case GLSL_TYPE_BOOL:
-      return new ir_constant(this->type, &this->value);
+      return new(ctx) ir_constant(this->type, &this->value);
 
    case GLSL_TYPE_STRUCT: {
-      ir_constant *c = new ir_constant;
+      ir_constant *c = new(ctx)ir_constant;
 
       c->type = this->type;
       for (exec_node *node = this->components.head
@@ -497,8 +499,10 @@ ir_dereference_array::ir_dereference_array(ir_rvalue *value,
 ir_dereference_array::ir_dereference_array(ir_variable *var,
                                           ir_rvalue *array_index)
 {
+   void *ctx = talloc_parent(var);
+
    this->array_index = array_index;
-   this->set_array(new ir_dereference_variable(var));
+   this->set_array(new(ctx) ir_dereference_variable(var));
 }
 
 
@@ -535,7 +539,9 @@ ir_dereference_record::ir_dereference_record(ir_rvalue *value,
 ir_dereference_record::ir_dereference_record(ir_variable *var,
                                             const char *field)
 {
-   this->record = new ir_dereference_variable(var);
+   void *ctx = talloc_parent(var);
+
+   this->record = new(ctx) ir_dereference_variable(var);
    this->field = field;
    this->type = (this->record != NULL)
       ? this->record->type->field_type(field) : glsl_type::error_type;
@@ -646,6 +652,8 @@ ir_swizzle::ir_swizzle(ir_rvalue *val, ir_swizzle_mask mask)
 ir_swizzle *
 ir_swizzle::create(ir_rvalue *val, const char *str, unsigned vector_length)
 {
+   void *ctx = talloc_parent(val);
+
    /* For each possible swizzle character, this table encodes the value in
     * \c idx_map that represents the 0th element of the vector.  For invalid
     * swizzle characters (e.g., 'k'), a special value is used that will allow
@@ -710,8 +718,8 @@ ir_swizzle::create(ir_rvalue *val, const char *str, unsigned vector_length)
    if (str[i] != '\0')
         return NULL;
 
-   return new ir_swizzle(val, swiz_idx[0], swiz_idx[1], swiz_idx[2],
-                         swiz_idx[3], i);
+   return new(ctx) ir_swizzle(val, swiz_idx[0], swiz_idx[1], swiz_idx[2],
+                             swiz_idx[3], i);
 }
 
 #undef X
@@ -811,7 +819,6 @@ ir_function_signature::replace_parameters(exec_list *new_params)
       assert(((ir_instruction *) iter.get())->as_variable() != NULL);
 
       iter.remove();
-      delete (ir_instruction*) iter.get();
    }
 
    new_params->move_nodes_to(&parameters);
@@ -828,7 +835,9 @@ ir_function::ir_function(const char *name)
 ir_call *
 ir_call::get_error_instruction()
 {
-   ir_call *call = new ir_call;
+   /* NULL is wrong and leaks */
+   void *ctx = NULL;
+   ir_call *call = new(ctx) ir_call;
 
    call->type = glsl_type::error_type;
    return call;
index c810fe86164e75eb9e3f7cf7a01895009ef90858..5ffd3fc00b2ccbc0bb528023e8207dbdeb589e24 100644 (file)
@@ -36,7 +36,8 @@
 ir_instruction *
 ir_variable::clone(struct hash_table *ht) const
 {
-   ir_variable *var = new ir_variable(type, name);
+   void *ctx = talloc_parent(this);
+   ir_variable *var = new(ctx) ir_variable(type, name);
 
    var->max_array_access = this->max_array_access;
    var->read_only = this->read_only;
@@ -55,32 +56,36 @@ ir_variable::clone(struct hash_table *ht) const
 ir_instruction *
 ir_swizzle::clone(struct hash_table *ht) const
 {
-   return new ir_swizzle((ir_rvalue *)this->val->clone(ht), this->mask);
+   void *ctx = talloc_parent(this);
+   return new(ctx) ir_swizzle((ir_rvalue *)this->val->clone(ht), this->mask);
 }
 
 ir_instruction *
 ir_return::clone(struct hash_table *ht) const
 {
+   void *ctx = talloc_parent(this);
    ir_rvalue *new_value = NULL;
 
    if (this->value)
       new_value = (ir_rvalue *)this->value->clone(ht);
 
-   return new ir_return(new_value);
+   return new(ctx) ir_return(new_value);
 }
 
 ir_instruction *
 ir_loop_jump::clone(struct hash_table *ht) const
 {
+   void *ctx = talloc_parent(this);
    (void)ht;
 
-   return new ir_loop_jump(this->mode);
+   return new(ctx) ir_loop_jump(this->mode);
 }
 
 ir_instruction *
 ir_if::clone(struct hash_table *ht) const
 {
-   ir_if *new_if = new ir_if((ir_rvalue *)this->condition->clone(ht));
+   void *ctx = talloc_parent(this);
+   ir_if *new_if = new(ctx) ir_if((ir_rvalue *)this->condition->clone(ht));
 
    foreach_iter(exec_list_iterator, iter, this->then_instructions) {
       ir_instruction *ir = (ir_instruction *)iter.get();
@@ -98,7 +103,8 @@ ir_if::clone(struct hash_table *ht) const
 ir_instruction *
 ir_loop::clone(struct hash_table *ht) const
 {
-   ir_loop *new_loop = new ir_loop();
+   void *ctx = talloc_parent(this);
+   ir_loop *new_loop = new(ctx) ir_loop();
 
    if (this->from)
       new_loop->from = (ir_rvalue *)this->from->clone(ht);
@@ -119,6 +125,7 @@ ir_loop::clone(struct hash_table *ht) const
 ir_instruction *
 ir_call::clone(struct hash_table *ht) const
 {
+   void *ctx = talloc_parent(this);
    exec_list new_parameters;
 
    foreach_iter(exec_list_iterator, iter, this->actual_parameters) {
@@ -126,12 +133,13 @@ ir_call::clone(struct hash_table *ht) const
       new_parameters.push_tail(ir->clone(ht));
    }
 
-   return new ir_call(this->callee, &new_parameters);
+   return new(ctx) ir_call(this->callee, &new_parameters);
 }
 
 ir_instruction *
 ir_expression::clone(struct hash_table *ht) const
 {
+   void *ctx = talloc_parent(this);
    ir_rvalue *op[2] = {NULL, NULL};
    unsigned int i;
 
@@ -139,12 +147,13 @@ ir_expression::clone(struct hash_table *ht) const
       op[i] = (ir_rvalue *)this->operands[i]->clone(ht);
    }
 
-   return new ir_expression(this->operation, this->type, op[0], op[1]);
+   return new(ctx) ir_expression(this->operation, this->type, op[0], op[1]);
 }
 
 ir_instruction *
 ir_dereference_variable::clone(struct hash_table *ht) const
 {
+   void *ctx = talloc_parent(this);
    ir_variable *new_var;
 
    if (ht) {
@@ -155,27 +164,30 @@ ir_dereference_variable::clone(struct hash_table *ht) const
       new_var = this->var;
    }
 
-   return new ir_dereference_variable(new_var);
+   return new(ctx) ir_dereference_variable(new_var);
 }
 
 ir_instruction *
 ir_dereference_array::clone(struct hash_table *ht) const
 {
-   return new ir_dereference_array((ir_rvalue *)this->array->clone(ht),
-                                  (ir_rvalue *)this->array_index->clone(ht));
+   void *ctx = talloc_parent(this);
+   return new(ctx) ir_dereference_array((ir_rvalue *)this->array->clone(ht),
+                                       (ir_rvalue *)this->array_index->clone(ht));
 }
 
 ir_instruction *
 ir_dereference_record::clone(struct hash_table *ht) const
 {
-   return new ir_dereference_record((ir_rvalue *)this->record->clone(ht),
-                                   this->field);
+   void *ctx = talloc_parent(this);
+   return new(ctx) ir_dereference_record((ir_rvalue *)this->record->clone(ht),
+                                        this->field);
 }
 
 ir_instruction *
 ir_texture::clone(struct hash_table *ht) const
 {
-   ir_texture *new_tex = new ir_texture(this->op);
+   void *ctx = talloc_parent(this);
+   ir_texture *new_tex = new(ctx) ir_texture(this->op);
 
    new_tex->sampler = (ir_dereference *)this->sampler->clone(ht);
    new_tex->coordinate = (ir_rvalue *)this->coordinate->clone(ht);
@@ -218,9 +230,10 @@ ir_assignment::clone(struct hash_table *ht) const
    if (this->condition)
       new_condition = (ir_rvalue *)this->condition->clone(ht);
 
-   return new ir_assignment((ir_rvalue *)this->lhs->clone(ht),
-                           (ir_rvalue *)this->rhs->clone(ht),
-                           new_condition);
+   void *ctx = talloc_parent(this);
+   return new(ctx) ir_assignment((ir_rvalue *)this->lhs->clone(ht),
+                                (ir_rvalue *)this->rhs->clone(ht),
+                                new_condition);
 }
 
 ir_instruction *
index effb88844ee8b59e87bc5dad327858b33b4ea903..4010e4626745665a05040c93272072ed3201a7f6 100644 (file)
@@ -127,6 +127,7 @@ ir_constant_visitor::visit(ir_function *ir)
 void
 ir_constant_visitor::visit(ir_expression *ir)
 {
+   void *ctx = talloc_parent(ir);
    value = NULL;
    ir_constant *op[2];
    unsigned int operand, c;
@@ -497,7 +498,7 @@ ir_constant_visitor::visit(ir_expression *ir)
       return;
    }
 
-   this->value = new ir_constant(ir->type, &data);
+   this->value = new(ctx) ir_constant(ir->type, &data);
 }
 
 
@@ -513,6 +514,7 @@ ir_constant_visitor::visit(ir_texture *ir)
 void
 ir_constant_visitor::visit(ir_swizzle *ir)
 {
+   void *ctx = talloc_parent(ir);
    ir_constant *v = ir->val->constant_expression_value();
 
    this->value = NULL;
@@ -534,7 +536,7 @@ ir_constant_visitor::visit(ir_swizzle *ir)
         }
       }
 
-      this->value = new ir_constant(ir->type, &data);
+      this->value = new(ctx) ir_constant(ir->type, &data);
    }
 }
 
@@ -553,6 +555,7 @@ ir_constant_visitor::visit(ir_dereference_variable *ir)
 void
 ir_constant_visitor::visit(ir_dereference_array *ir)
 {
+   void *ctx = talloc_parent(ir);
    ir_constant *array = ir->array->constant_expression_value();
    ir_constant *idx = ir->array_index->constant_expression_value();
 
@@ -592,11 +595,11 @@ ir_constant_visitor::visit(ir_dereference_array *ir)
            break;
         }
 
-        this->value = new ir_constant(column_type, &data);
+        this->value = new(ctx) ir_constant(column_type, &data);
       } else if (array->type->is_vector()) {
         const unsigned component = idx->value.u[0];
 
-        this->value = new ir_constant(array, component);
+        this->value = new(ctx) ir_constant(array, component);
       } else {
         /* FINISHME: Handle access of constant arrays. */
       }
index 16a2ba79bf6f562774663ce8fe21bee0cdb4bf51..46ef6679d9f68517c529826f61eb0a15f482887f 100644 (file)
@@ -197,6 +197,7 @@ kill_invalidated_copies(ir_assignment *ir, exec_list *acp)
 static void
 add_copy(ir_assignment *ir, exec_list *acp)
 {
+   void *ctx = talloc_parent(ir);
    acp_entry *entry;
 
    if (ir->condition) {
@@ -209,7 +210,7 @@ add_copy(ir_assignment *ir, exec_list *acp)
    ir_variable *rhs_var = ir->rhs->whole_variable_referenced();
 
    if ((lhs_var != NULL) && (rhs_var != NULL)) {
-      entry = new acp_entry(lhs_var, rhs_var);
+      entry = new(ctx) acp_entry(lhs_var, rhs_var);
       acp->push_tail(entry);
    }
 }
index 8465d863aa394d15a5774743ae8873fb3741ffa4..01b7d2d832a5b17a7cb0e206334e6f71f0e374a8 100644 (file)
@@ -77,6 +77,7 @@ public:
 variable_entry *
 ir_dead_code_visitor::get_variable_entry(ir_variable *var)
 {
+   void *ctx = talloc_parent(var);
    assert(var);
    foreach_iter(exec_list_iterator, iter, this->variable_list) {
       variable_entry *entry = (variable_entry *)iter.get();
@@ -84,7 +85,7 @@ ir_dead_code_visitor::get_variable_entry(ir_variable *var)
         return entry;
    }
 
-   variable_entry *entry = new variable_entry(var);
+   variable_entry *entry = new(ctx) variable_entry(var);
    this->variable_list.push_tail(entry);
    return entry;
 }
index d3b3858617d611e7105d47447951af4bc311ccaa..e01877077c9b9b282364359e1d2852169c8d7b04 100644 (file)
@@ -113,6 +113,7 @@ public:
 static bool
 process_assignment(ir_assignment *ir, exec_list *assignments)
 {
+   void *ctx = talloc_parent(ir);
    ir_variable *var = NULL;
    bool progress = false;
    kill_for_derefs_visitor v(assignments);
@@ -157,7 +158,7 @@ process_assignment(ir_assignment *ir, exec_list *assignments)
    }
 
    /* Add this instruction to the assignment list. */
-   assignment_entry *entry = new assignment_entry(var, ir);
+   assignment_entry *entry = new(ctx) assignment_entry(var, ir);
    assignments->push_tail(entry);
 
    if (debug) {
index 3089f17ae1498c13021ada929084a39aa1230016..5ba24e390b4554db698370e3d0e096bc375e5149 100644 (file)
@@ -80,18 +80,19 @@ do_expression_flattening(exec_list *instructions,
 static ir_rvalue *
 operand_to_temp(ir_instruction *base_ir, ir_rvalue *ir)
 {
+   void *ctx = talloc_parent(base_ir);
    ir_variable *var;
    ir_assignment *assign;
 
-   var = new ir_variable(ir->type, "flattening_tmp");
+   var = new(ctx) ir_variable(ir->type, "flattening_tmp");
    base_ir->insert_before(var);
 
-   assign = new ir_assignment(new ir_dereference_variable(var),
-                             ir,
-                             NULL);
+   assign = new(ctx) ir_assignment(new(ctx) ir_dereference_variable(var),
+                                  ir,
+                                  NULL);
    base_ir->insert_before(assign);
 
-   return new ir_dereference_variable(var);
+   return new(ctx) ir_dereference_variable(var);
 }
 
 ir_visitor_status
index effb01c8f68dbdf53ecdbb3684f27eb5fd9ae66e..8a1cf4f1d24384c753ef041aaddd514677b9d115 100644 (file)
@@ -94,6 +94,7 @@ do_function_inlining(exec_list *instructions)
 ir_rvalue *
 ir_call::generate_inline(ir_instruction *next_ir)
 {
+   void *ctx = talloc_parent(this);
    ir_variable **parameters;
    int num_parameters;
    int i;
@@ -110,7 +111,7 @@ ir_call::generate_inline(ir_instruction *next_ir)
 
    /* Generate storage for the return value. */
    if (this->callee->return_type) {
-      retval = new ir_variable(this->callee->return_type, "__retval");
+      retval = new(ctx) ir_variable(this->callee->return_type, "__retval");
       next_ir->insert_before(retval);
    }
 
@@ -133,8 +134,8 @@ ir_call::generate_inline(ir_instruction *next_ir)
          parameters[i]->mode == ir_var_inout) {
         ir_assignment *assign;
 
-        assign = new ir_assignment(new ir_dereference_variable(parameters[i]),
-                                   param, NULL);
+        assign = new(ctx) ir_assignment(new(ctx) ir_dereference_variable(parameters[i]),
+                                        param, NULL);
         next_ir->insert_before(assign);
       }
 
@@ -162,9 +163,9 @@ ir_call::generate_inline(ir_instruction *next_ir)
          parameters[i]->mode == ir_var_inout) {
         ir_assignment *assign;
 
-        assign = new ir_assignment(param->as_rvalue(),
-                                   new ir_dereference_variable(parameters[i]),
-                                   NULL);
+        assign = new(ctx) ir_assignment(param->as_rvalue(),
+                                        new(ctx) ir_dereference_variable(parameters[i]),
+                                        NULL);
         next_ir->insert_before(assign);
       }
 
@@ -176,7 +177,7 @@ ir_call::generate_inline(ir_instruction *next_ir)
    hash_table_dtor(ht);
 
    if (retval)
-      return new ir_dereference_variable(retval);
+      return new(ctx) ir_dereference_variable(retval);
    else
       return NULL;
 }
index ee320ddac28bbbbcc6866b43c63971b5ea19e834..d6985c4981cda78fb056a7db7bcc7fad30cffe01 100644 (file)
@@ -70,7 +70,8 @@ void
 _mesa_glsl_read_ir(_mesa_glsl_parse_state *state, exec_list *instructions,
                   const char *src)
 {
-   s_expression *expr = s_expression::read_expression(src);
+   void *ctx = talloc_parent(state);
+   s_expression *expr = s_expression::read_expression(ctx, src);
    if (expr == NULL) {
       ir_read_error(state, NULL, "couldn't parse S-Expression.");
       return;
@@ -190,6 +191,7 @@ scan_for_prototypes(_mesa_glsl_parse_state *st, exec_list *instructions,
 static ir_function *
 read_function(_mesa_glsl_parse_state *st, s_list *list, bool skip_body)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() < 3) {
       ir_read_error(st, list, "Expected (function <name> (signature ...) ...)");
       return NULL;
@@ -203,7 +205,7 @@ read_function(_mesa_glsl_parse_state *st, s_list *list, bool skip_body)
 
    ir_function *f = st->symbols->get_function(name->value());
    if (f == NULL) {
-      f = new ir_function(name->value());
+      f = new(ctx) ir_function(name->value());
       bool added = st->symbols->add_function(name->value(), f);
       assert(added);
    }
@@ -233,6 +235,7 @@ static void
 read_function_sig(_mesa_glsl_parse_state *st, ir_function *f, s_list *list,
                  bool skip_body)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 4) {
       ir_read_error(st, list, "Expected (signature <type> (parameters ...) "
                              "(<instruction> ...))");
@@ -286,7 +289,7 @@ read_function_sig(_mesa_glsl_parse_state *st, ir_function *f, s_list *list,
         return;
       }
    } else {
-      sig = new ir_function_signature(return_type);
+      sig = new(ctx) ir_function_signature(return_type);
       f->add_signature(sig);
    }
 
@@ -331,12 +334,13 @@ static ir_instruction *
 read_instruction(_mesa_glsl_parse_state *st, s_expression *expr,
                 ir_loop *loop_ctx)
 {
+   void *ctx = talloc_parent(st);
    s_symbol *symbol = SX_AS_SYMBOL(expr);
    if (symbol != NULL) {
       if (strcmp(symbol->value(), "break") == 0 && loop_ctx != NULL)
-        return new ir_loop_jump(ir_loop_jump::jump_break);
+        return new(ctx) ir_loop_jump(ir_loop_jump::jump_break);
       if (strcmp(symbol->value(), "continue") == 0 && loop_ctx != NULL)
-        return new ir_loop_jump(ir_loop_jump::jump_continue);
+        return new(ctx) ir_loop_jump(ir_loop_jump::jump_continue);
    }
 
    s_list *list = SX_AS_LIST(expr);
@@ -372,6 +376,7 @@ read_instruction(_mesa_glsl_parse_state *st, s_expression *expr,
 static ir_variable *
 read_declaration(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 4) {
       ir_read_error(st, list, "expected (declare (<qualifiers>) <type> "
                              "<name>)");
@@ -395,7 +400,7 @@ read_declaration(_mesa_glsl_parse_state *st, s_list *list)
       return NULL;
    }
 
-   ir_variable *var = new ir_variable(type, var_name->value());
+   ir_variable *var = new(ctx) ir_variable(type, var_name->value());
 
    foreach_iter(exec_list_iterator, it, quals->subexpressions) {
       s_symbol *qualifier = SX_AS_SYMBOL(it.get());
@@ -443,6 +448,7 @@ read_declaration(_mesa_glsl_parse_state *st, s_list *list)
 static ir_if *
 read_if(_mesa_glsl_parse_state *st, s_list *list, ir_loop *loop_ctx)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 4) {
       ir_read_error(st, list, "expected (if <condition> (<then> ...) "
                           "(<else> ...))");
@@ -459,7 +465,7 @@ read_if(_mesa_glsl_parse_state *st, s_list *list, ir_loop *loop_ctx)
    s_expression *then_expr = (s_expression*) cond_expr->next;
    s_expression *else_expr = (s_expression*) then_expr->next;
 
-   ir_if *iff = new ir_if(condition);
+   ir_if *iff = new(ctx) ir_if(condition);
 
    read_instructions(st, &iff->then_instructions, then_expr, loop_ctx);
    read_instructions(st, &iff->else_instructions, else_expr, loop_ctx);
@@ -474,6 +480,7 @@ read_if(_mesa_glsl_parse_state *st, s_list *list, ir_loop *loop_ctx)
 static ir_loop *
 read_loop(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 6) {
       ir_read_error(st, list, "expected (loop <counter> <from> <to> "
                              "<increment> <body>)");
@@ -488,7 +495,7 @@ read_loop(_mesa_glsl_parse_state *st, s_list *list)
 
    // FINISHME: actually read the count/from/to fields.
 
-   ir_loop *loop = new ir_loop;
+   ir_loop *loop = new(ctx) ir_loop;
    read_instructions(st, &loop->body_instructions, body_expr, loop);
    if (st->error) {
       delete loop;
@@ -501,6 +508,7 @@ read_loop(_mesa_glsl_parse_state *st, s_list *list)
 static ir_return *
 read_return(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 2) {
       ir_read_error(st, list, "expected (return <rvalue>)");
       return NULL;
@@ -514,7 +522,7 @@ read_return(_mesa_glsl_parse_state *st, s_list *list)
       return NULL;
    }
 
-   return new ir_return(retval);
+   return new(ctx) ir_return(retval);
 }
 
 
@@ -556,6 +564,7 @@ read_rvalue(_mesa_glsl_parse_state *st, s_expression *expr)
 static ir_assignment *
 read_assignment(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 4) {
       ir_read_error(st, list, "expected (assign <condition> <lhs> <rhs>)");
       return NULL;
@@ -584,12 +593,13 @@ read_assignment(_mesa_glsl_parse_state *st, s_list *list)
       return NULL;
    }
 
-   return new ir_assignment(lhs, rhs, condition);
+   return new(ctx) ir_assignment(lhs, rhs, condition);
 }
 
 static ir_call *
 read_call(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 3) {
       ir_read_error(st, list, "expected (call <name> (<param> ...))");
       return NULL;
@@ -628,12 +638,13 @@ read_call(_mesa_glsl_parse_state *st, s_list *list)
       return NULL;
    }
 
-   return new ir_call(callee, &parameters);
+   return new(ctx) ir_call(callee, &parameters);
 }
 
 static ir_expression *
 read_expression(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    const unsigned list_length = list->length();
    if (list_length < 4) {
       ir_read_error(st, list, "expected (expression <type> <operator> "
@@ -693,7 +704,7 @@ read_expression(_mesa_glsl_parse_state *st, s_list *list)
       }
    }
 
-   return new ir_expression(op, type, arg1, arg2);
+   return new(ctx) ir_expression(op, type, arg1, arg2);
 }
 
 static ir_swizzle *
@@ -738,6 +749,7 @@ read_swizzle(_mesa_glsl_parse_state *st, s_list *list)
 static ir_constant *
 read_constant(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 3) {
       ir_read_error(st, list, "expected (constant <type> (<num> ... <num>))");
       return NULL;
@@ -803,7 +815,7 @@ read_constant(_mesa_glsl_parse_state *st, s_list *list)
       ++k;
    }
 
-   return new ir_constant(type, &data);
+   return new(ctx) ir_constant(type, &data);
 }
 
 static ir_dereference *
@@ -828,6 +840,7 @@ read_dereference(_mesa_glsl_parse_state *st, s_expression *expr)
 static ir_dereference *
 read_var_ref(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 2) {
       ir_read_error(st, list, "expected (var_ref <variable name>)");
       return NULL;
@@ -844,12 +857,13 @@ read_var_ref(_mesa_glsl_parse_state *st, s_list *list)
       return NULL;
    }
 
-   return new ir_dereference_variable(var);
+   return new(ctx) ir_dereference_variable(var);
 }
 
 static ir_dereference *
 read_array_ref(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 3) {
       ir_read_error(st, list, "expected (array_ref <rvalue> <index>)");
       return NULL;
@@ -864,12 +878,13 @@ read_array_ref(_mesa_glsl_parse_state *st, s_list *list)
 
    s_expression *idx_expr = (s_expression*) subj_expr->next;
    ir_rvalue *idx = read_rvalue(st, idx_expr);
-   return new ir_dereference_array(subject, idx);
+   return new(ctx) ir_dereference_array(subject, idx);
 }
 
 static ir_dereference *
 read_record_ref(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    if (list->length() != 3) {
       ir_read_error(st, list, "expected (record_ref <rvalue> <field>)");
       return NULL;
@@ -887,7 +902,7 @@ read_record_ref(_mesa_glsl_parse_state *st, s_list *list)
       ir_read_error(st, list, "expected (record_ref ... <field name>)");
       return NULL;
    }
-   return new ir_dereference_record(subject, field->value());
+   return new(ctx) ir_dereference_record(subject, field->value());
 }
 
 static bool
@@ -905,6 +920,7 @@ valid_texture_list_length(ir_texture_opcode op, s_list *list)
 static ir_texture *
 read_texture(_mesa_glsl_parse_state *st, s_list *list)
 {
+   void *ctx = talloc_parent(st);
    s_symbol *tag = SX_AS_SYMBOL(list->subexpressions.head);
    assert(tag != NULL);
 
@@ -917,7 +933,7 @@ read_texture(_mesa_glsl_parse_state *st, s_list *list)
       return NULL;
    }
 
-   ir_texture *tex = new ir_texture(op);
+   ir_texture *tex = new(ctx) ir_texture(op);
 
    // Read sampler (must be a deref)
    s_expression *sampler_expr = (s_expression *) tag->next;
index efebe9199fad9cddb8aaf7decfd4195af384f4ed..fabd856591a5c0e00577511ed8f3d74a8faf81de 100644 (file)
@@ -35,7 +35,7 @@ add_variable(const char *name, enum ir_variable_mode mode, int slot,
             const glsl_type *type, exec_list *instructions,
                     glsl_symbol_table *symtab)
 {
-   ir_variable *var = new ir_variable(type, name);
+   ir_variable *var = new(symtab) ir_variable(type, name);
 
    var->mode = mode;
    switch (var->mode) {
index eb0e556c9dba0576ddb293b53418806ba75d4aab..bbd873791a17bed898d56c42e68e5f688fc8e9a3 100644 (file)
@@ -60,6 +60,7 @@ public:
 ir_rvalue *
 ir_vec_index_to_swizzle_visitor::convert_vec_index_to_swizzle(ir_rvalue *ir)
 {
+   void *ctx = talloc_parent(ir);
    ir_dereference_array *deref = ir->as_dereference_array();
    ir_constant *ir_constant;
 
@@ -75,7 +76,8 @@ ir_vec_index_to_swizzle_visitor::convert_vec_index_to_swizzle(ir_rvalue *ir)
       return ir;
 
    this->progress = true;
-   return new ir_swizzle(deref->array, ir_constant->value.i[0], 0, 0, 0, 1);
+   return new(ctx) ir_swizzle(deref->array,
+                             ir_constant->value.i[0], 0, 0, 0, 1);
 }
 
 ir_visitor_status
diff --git a/list.h b/list.h
index 0b91647be4f69c240da55169c8ba5b7bf4eb214a..7732d66d7a69607e751dadc1a8c7bf821265d83b 100644 (file)
--- a/list.h
+++ b/list.h
 
 #ifndef __cplusplus
 #include <stddef.h>
+#include <talloc.h>
+#else
+extern "C" {
+#include <talloc.h>
+}
 #endif
+
 #include <assert.h>
 
 struct exec_node {
@@ -74,6 +80,25 @@ struct exec_node {
    struct exec_node *prev;
 
 #ifdef __cplusplus
+   /* Callers of this talloc-based new need not call delete. It's
+    * easier to just talloc_free 'ctx' (or any of its ancestors). */
+   static void* operator new(size_t size, void *ctx)
+   {
+      void *node;
+
+      node = talloc_size(ctx, size);
+      assert(node != NULL);
+
+      return node;
+   }
+
+   /* If the user *does* call delete, that's OK, we will just
+    * talloc_free in that case. */
+   static void operator delete(void *node)
+   {
+      talloc_free(node);
+   }
+
    exec_node() : next(NULL), prev(NULL)
    {
       /* empty */
index 0fb296ef6716f42b67acff11f63ab0028b6e5ce9..875d739d84223cb16b55e9deb530130ecc6b8ce2 100644 (file)
@@ -49,7 +49,7 @@ s_list::length() const
 }
 
 static s_expression *
-read_atom(const char *& src)
+read_atom(void *ctx, const char *& src)
 {
    char buf[101];
    int n;
@@ -65,20 +65,20 @@ read_atom(const char *& src)
       int i = strtol(buf, &int_end, 10);
       // If strtod matched more characters, it must have a decimal part
       if (float_end > int_end)
-        return new s_float(f);
+        return new(ctx) s_float(f);
 
-      return new s_int(i);
+      return new(ctx) s_int(i);
    }
    // Not a number; return a symbol.
-   return new s_symbol(buf);
+   return new(ctx) s_symbol(buf);
 }
 
 s_expression *
-s_expression::read_expression(const char *&src)
+s_expression::read_expression(void *ctx, const char *&src)
 {
    assert(src != NULL);
 
-   s_expression *atom = read_atom(src);
+   s_expression *atom = read_atom(ctx, src);
    if (atom != NULL)
       return atom;
 
@@ -87,10 +87,10 @@ s_expression::read_expression(const char *&src)
    if (sscanf(src, " %c%n", &c, &n) == 1 && c == '(') {
       src += n;
 
-      s_list *list = new s_list;
+      s_list *list = new(ctx) s_list;
       s_expression *expr;
 
-      while ((expr = read_expression(src)) != NULL) {
+      while ((expr = read_expression(ctx, src)) != NULL) {
         list->subexpressions.push_tail(expr);
       }
       if (sscanf(src, " %c%n", &c, &n) != 1 || c != ')') {
index 8a4eda28dae40974ab2dedac3cc1843de5e70794..1a0c03c2189537e9da4719d19d5057313f43cfb0 100644 (file)
@@ -49,8 +49,10 @@ public:
    /**
     * Read an S-Expression from the given string.
     * Advances the supplied pointer to just after the expression read.
+    *
+    * Any allocation will be performed with 'ctx' as the talloc owner.
     */
-   static s_expression *read_expression(const char *&src);
+   static s_expression *read_expression(void *ctx, const char *&src);
 
    /**
     * Print out an S-Expression.  Useful for debugging.