Mesa (glsl2): glsl2: Make the clone() method take a talloc context.

Eric Anholt anholt at kemper.freedesktop.org
Wed Aug 4 19:55:41 UTC 2010


Module: Mesa
Branch: glsl2
Commit: 8273bd46877e2ea2b8a02b87a11c68102d07e1f2
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=8273bd46877e2ea2b8a02b87a11c68102d07e1f2

Author: Eric Anholt <eric at anholt.net>
Date:   Wed Aug  4 12:34:56 2010 -0700

glsl2: Make the clone() method take a talloc context.

In most cases, we needed to be reparenting the cloned IR to a
different context (for example, to the linked shader instead of the
unlinked shader), or optimization before the reparent would cause
memory usage of the original object to grow and grow.

---

 src/glsl/ast_to_hir.cpp                  |   10 +-
 src/glsl/ir.h                            |   47 +++++----
 src/glsl/ir_clone.cpp                    |  150 +++++++++++++----------------
 src/glsl/ir_constant_expression.cpp      |    7 +-
 src/glsl/ir_function_inlining.cpp        |    6 +-
 src/glsl/ir_import_prototypes.cpp        |    2 +-
 src/glsl/ir_vec_index_to_cond_assign.cpp |    8 +-
 src/glsl/link_functions.cpp              |    6 +-
 src/glsl/linker.cpp                      |   25 +++--
 9 files changed, 130 insertions(+), 131 deletions(-)

diff --git a/src/glsl/ast_to_hir.cpp b/src/glsl/ast_to_hir.cpp
index 3522f55..b65a323 100644
--- a/src/glsl/ast_to_hir.cpp
+++ b/src/glsl/ast_to_hir.cpp
@@ -966,7 +966,7 @@ ast_expression::hir(exec_list *instructions,
 						   op[0], op[1]);
 
       result = do_assignment(instructions, state,
-			     op[0]->clone(NULL), temp_rhs,
+			     op[0]->clone(ctx, NULL), temp_rhs,
 			     this->subexpressions[0]->get_location());
       type = result->type;
       error_emitted = (op[0]->type->is_error());
@@ -992,7 +992,7 @@ ast_expression::hir(exec_list *instructions,
 					op[0], op[1]);
 
       result = do_assignment(instructions, state,
-			     op[0]->clone(NULL), temp_rhs,
+			     op[0]->clone(ctx, NULL), temp_rhs,
 			     this->subexpressions[0]->get_location());
       type = result->type;
       error_emitted = type->is_error();
@@ -1113,7 +1113,7 @@ ast_expression::hir(exec_list *instructions,
 					op[0], op[1]);
 
       result = do_assignment(instructions, state,
-			     op[0]->clone(NULL), temp_rhs,
+			     op[0]->clone(ctx, NULL), temp_rhs,
 			     this->subexpressions[0]->get_location());
       type = result->type;
       error_emitted = op[0]->type->is_error();
@@ -1139,10 +1139,10 @@ ast_expression::hir(exec_list *instructions,
       /* Get a temporary of a copy of the lvalue before it's modified.
        * This may get thrown away later.
        */
-      result = get_lvalue_copy(instructions, op[0]->clone(NULL));
+      result = get_lvalue_copy(instructions, op[0]->clone(ctx, NULL));
 
       (void)do_assignment(instructions, state,
-			  op[0]->clone(NULL), temp_rhs,
+			  op[0]->clone(ctx, NULL), temp_rhs,
 			  this->subexpressions[0]->get_location());
 
       type = result->type;
diff --git a/src/glsl/ir.h b/src/glsl/ir.h
index f88a243..f964b36 100644
--- a/src/glsl/ir.h
+++ b/src/glsl/ir.h
@@ -76,7 +76,8 @@ public:
 
    virtual void accept(ir_visitor *) = 0;
    virtual ir_visitor_status accept(ir_hierarchical_visitor *) = 0;
-   virtual ir_instruction *clone(struct hash_table *ht) const = 0;
+   virtual ir_instruction *clone(void *mem_ctx,
+				 struct hash_table *ht) const = 0;
 
    /**
     * \name IR instruction downcast functions
@@ -113,7 +114,7 @@ protected:
 
 class ir_rvalue : public ir_instruction {
 public:
-   virtual ir_rvalue *clone(struct hash_table *) const = 0;
+   virtual ir_rvalue *clone(void *mem_ctx, struct hash_table *) const = 0;
 
    virtual ir_constant *constant_expression_value() = 0;
 
@@ -175,7 +176,7 @@ class ir_variable : public ir_instruction {
 public:
    ir_variable(const struct glsl_type *, const char *, ir_variable_mode);
 
-   virtual ir_variable *clone(struct hash_table *ht) const;
+   virtual ir_variable *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual ir_variable *as_variable()
    {
@@ -283,7 +284,8 @@ class ir_function_signature : public ir_instruction {
 public:
    ir_function_signature(const glsl_type *return_type);
 
-   virtual ir_function_signature *clone(struct hash_table *ht) const;
+   virtual ir_function_signature *clone(void *mem_ctx,
+					struct hash_table *ht) const;
 
    virtual void accept(ir_visitor *v)
    {
@@ -369,7 +371,7 @@ class ir_function : public ir_instruction {
 public:
    ir_function(const char *name);
 
-   virtual ir_function *clone(struct hash_table *ht) const;
+   virtual ir_function *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual ir_function *as_function()
    {
@@ -439,7 +441,7 @@ public:
       ir_type = ir_type_if;
    }
 
-   virtual ir_if *clone(struct hash_table *ht) const;
+   virtual ir_if *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual ir_if *as_if()
    {
@@ -471,7 +473,7 @@ public:
       ir_type = ir_type_loop;
    }
 
-   virtual ir_loop *clone(struct hash_table *ht) const;
+   virtual ir_loop *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual void accept(ir_visitor *v)
    {
@@ -512,7 +514,7 @@ class ir_assignment : public ir_instruction {
 public:
    ir_assignment(ir_rvalue *lhs, ir_rvalue *rhs, ir_rvalue *condition);
 
-   virtual ir_assignment *clone(struct hash_table *ht) const;
+   virtual ir_assignment *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -662,7 +664,7 @@ public:
       return this;
    }
 
-   virtual ir_expression *clone(struct hash_table *ht) const;
+   virtual ir_expression *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -708,7 +710,7 @@ public:
       actual_parameters->move_nodes_to(& this->actual_parameters);
    }
 
-   virtual ir_call *clone(struct hash_table *ht) const;
+   virtual ir_call *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -805,7 +807,7 @@ public:
       this->ir_type = ir_type_return;
    }
 
-   virtual ir_return *clone(struct hash_table *) const;
+   virtual ir_return *clone(void *mem_ctx, struct hash_table *) const;
 
    virtual ir_return *as_return()
    {
@@ -850,7 +852,7 @@ public:
       this->loop = loop;
    }
 
-   virtual ir_loop_jump *clone(struct hash_table *) const;
+   virtual ir_loop_jump *clone(void *mem_ctx, struct hash_table *) const;
 
    virtual void accept(ir_visitor *v)
    {
@@ -893,7 +895,7 @@ public:
       this->condition = cond;
    }
 
-   virtual ir_discard *clone(struct hash_table *ht) const;
+   virtual ir_discard *clone(void *mem_ctx, struct hash_table *ht) const;
 
    virtual void accept(ir_visitor *v)
    {
@@ -945,7 +947,7 @@ public:
       this->ir_type = ir_type_texture;
    }
 
-   virtual ir_texture *clone(struct hash_table *) const;
+   virtual ir_texture *clone(void *mem_ctx, struct hash_table *) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -1037,7 +1039,7 @@ public:
 
    ir_swizzle(ir_rvalue *val, ir_swizzle_mask mask);
 
-   virtual ir_swizzle *clone(struct hash_table *) const;
+   virtual ir_swizzle *clone(void *mem_ctx, struct hash_table *) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -1083,7 +1085,7 @@ private:
 
 class ir_dereference : public ir_rvalue {
 public:
-   virtual ir_dereference *clone(struct hash_table *) const = 0;
+   virtual ir_dereference *clone(void *mem_ctx, struct hash_table *) const = 0;
 
    virtual ir_dereference *as_dereference()
    {
@@ -1103,7 +1105,8 @@ class ir_dereference_variable : public ir_dereference {
 public:
    ir_dereference_variable(ir_variable *var);
 
-   virtual ir_dereference_variable *clone(struct hash_table *) const;
+   virtual ir_dereference_variable *clone(void *mem_ctx,
+					  struct hash_table *) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -1151,7 +1154,8 @@ public:
 
    ir_dereference_array(ir_variable *var, ir_rvalue *array_index);
 
-   virtual ir_dereference_array *clone(struct hash_table *) const;
+   virtual ir_dereference_array *clone(void *mem_ctx,
+				       struct hash_table *) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -1189,7 +1193,8 @@ public:
 
    ir_dereference_record(ir_variable *var, const char *field);
 
-   virtual ir_dereference_record *clone(struct hash_table *) const;
+   virtual ir_dereference_record *clone(void *mem_ctx,
+					struct hash_table *) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -1254,7 +1259,7 @@ public:
     */
    static ir_constant *zero(void *mem_ctx, const glsl_type *type);
 
-   virtual ir_constant *clone(struct hash_table *) const;
+   virtual ir_constant *clone(void *mem_ctx, struct hash_table *) const;
 
    virtual ir_constant *constant_expression_value();
 
@@ -1327,7 +1332,7 @@ void validate_ir_tree(exec_list *instructions);
  * \param out  List to hold the cloned instructions
  */
 void
-clone_ir_list(exec_list *out, const exec_list *in);
+clone_ir_list(void *mem_ctx, exec_list *out, const exec_list *in);
 
 extern void
 _mesa_glsl_initialize_variables(exec_list *instructions,
diff --git a/src/glsl/ir_clone.cpp b/src/glsl/ir_clone.cpp
index 5ea3a79..5983183 100644
--- a/src/glsl/ir_clone.cpp
+++ b/src/glsl/ir_clone.cpp
@@ -36,11 +36,10 @@ extern "C" {
  * eventually.
  */
 ir_variable *
-ir_variable::clone(struct hash_table *ht) const
+ir_variable::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   ir_variable *var = new(ctx) ir_variable(this->type, this->name,
-					   (ir_variable_mode) this->mode);
+   ir_variable *var = new(mem_ctx) ir_variable(this->type, this->name,
+					       (ir_variable_mode) this->mode);
 
    var->max_array_access = this->max_array_access;
    var->read_only = this->read_only;
@@ -56,7 +55,7 @@ ir_variable::clone(struct hash_table *ht) const
    var->pixel_center_integer = this->pixel_center_integer;
 
    if (this->constant_value)
-      var->constant_value = this->constant_value->clone(ht);
+      var->constant_value = this->constant_value->clone(mem_ctx, ht);
 
    if (ht) {
       hash_table_insert(ht, var, (void *)const_cast<ir_variable *>(this));
@@ -66,118 +65,109 @@ ir_variable::clone(struct hash_table *ht) const
 }
 
 ir_swizzle *
-ir_swizzle::clone(struct hash_table *ht) const
+ir_swizzle::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   return new(ctx) ir_swizzle(this->val->clone(ht), this->mask);
+   return new(mem_ctx) ir_swizzle(this->val->clone(mem_ctx, ht), this->mask);
 }
 
 ir_return *
-ir_return::clone(struct hash_table *ht) const
+ir_return::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    ir_rvalue *new_value = NULL;
 
    if (this->value)
-      new_value = this->value->clone(ht);
+      new_value = this->value->clone(mem_ctx, ht);
 
-   return new(ctx) ir_return(new_value);
+   return new(mem_ctx) ir_return(new_value);
 }
 
 ir_discard *
-ir_discard::clone(struct hash_table *ht) const
+ir_discard::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    ir_rvalue *new_condition = NULL;
 
    if (this->condition != NULL)
-      new_condition = this->condition->clone(ht);
+      new_condition = this->condition->clone(mem_ctx, ht);
 
-   return new(ctx) ir_discard(new_condition);
+   return new(mem_ctx) ir_discard(new_condition);
 }
 
 ir_loop_jump *
-ir_loop_jump::clone(struct hash_table *ht) const
+ir_loop_jump::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    (void)ht;
 
-   return new(ctx) ir_loop_jump(this->mode);
+   return new(mem_ctx) ir_loop_jump(this->mode);
 }
 
 ir_if *
-ir_if::clone(struct hash_table *ht) const
+ir_if::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   ir_if *new_if = new(ctx) ir_if(this->condition->clone(ht));
+   ir_if *new_if = new(mem_ctx) ir_if(this->condition->clone(mem_ctx, ht));
 
    foreach_iter(exec_list_iterator, iter, this->then_instructions) {
       ir_instruction *ir = (ir_instruction *)iter.get();
-      new_if->then_instructions.push_tail(ir->clone(ht));
+      new_if->then_instructions.push_tail(ir->clone(mem_ctx, ht));
    }
 
    foreach_iter(exec_list_iterator, iter, this->else_instructions) {
       ir_instruction *ir = (ir_instruction *)iter.get();
-      new_if->else_instructions.push_tail(ir->clone(ht));
+      new_if->else_instructions.push_tail(ir->clone(mem_ctx, ht));
    }
 
    return new_if;
 }
 
 ir_loop *
-ir_loop::clone(struct hash_table *ht) const
+ir_loop::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   ir_loop *new_loop = new(ctx) ir_loop();
+   ir_loop *new_loop = new(mem_ctx) ir_loop();
 
    if (this->from)
-      new_loop->from = this->from->clone(ht);
+      new_loop->from = this->from->clone(mem_ctx, ht);
    if (this->to)
-      new_loop->to = this->to->clone(ht);
+      new_loop->to = this->to->clone(mem_ctx, ht);
    if (this->increment)
-      new_loop->increment = this->increment->clone(ht);
+      new_loop->increment = this->increment->clone(mem_ctx, ht);
    new_loop->counter = counter;
 
    foreach_iter(exec_list_iterator, iter, this->body_instructions) {
       ir_instruction *ir = (ir_instruction *)iter.get();
-      new_loop->body_instructions.push_tail(ir->clone(ht));
+      new_loop->body_instructions.push_tail(ir->clone(mem_ctx, ht));
    }
 
    return new_loop;
 }
 
 ir_call *
-ir_call::clone(struct hash_table *ht) const
+ir_call::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    exec_list new_parameters;
 
    foreach_iter(exec_list_iterator, iter, this->actual_parameters) {
       ir_instruction *ir = (ir_instruction *)iter.get();
-      new_parameters.push_tail(ir->clone(ht));
+      new_parameters.push_tail(ir->clone(mem_ctx, ht));
    }
 
-   return new(ctx) ir_call(this->callee, &new_parameters);
+   return new(mem_ctx) ir_call(this->callee, &new_parameters);
 }
 
 ir_expression *
-ir_expression::clone(struct hash_table *ht) const
+ir_expression::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    ir_rvalue *op[2] = {NULL, NULL};
    unsigned int i;
 
    for (i = 0; i < get_num_operands(); i++) {
-      op[i] = this->operands[i]->clone(ht);
+      op[i] = this->operands[i]->clone(mem_ctx, ht);
    }
 
-   return new(ctx) ir_expression(this->operation, this->type, op[0], op[1]);
+   return new(mem_ctx) ir_expression(this->operation, this->type, op[0], op[1]);
 }
 
 ir_dereference_variable *
-ir_dereference_variable::clone(struct hash_table *ht) const
+ir_dereference_variable::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    ir_variable *new_var;
 
    if (ht) {
@@ -188,38 +178,36 @@ ir_dereference_variable::clone(struct hash_table *ht) const
       new_var = this->var;
    }
 
-   return new(ctx) ir_dereference_variable(new_var);
+   return new(mem_ctx) ir_dereference_variable(new_var);
 }
 
 ir_dereference_array *
-ir_dereference_array::clone(struct hash_table *ht) const
+ir_dereference_array::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   return new(ctx) ir_dereference_array(this->array->clone(ht),
-					this->array_index->clone(ht));
+   return new(mem_ctx) ir_dereference_array(this->array->clone(mem_ctx, ht),
+					    this->array_index->clone(mem_ctx,
+								     ht));
 }
 
 ir_dereference_record *
-ir_dereference_record::clone(struct hash_table *ht) const
+ir_dereference_record::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   return new(ctx) ir_dereference_record(this->record->clone(ht),
-					 this->field);
+   return new(mem_ctx) ir_dereference_record(this->record->clone(mem_ctx, ht),
+					     this->field);
 }
 
 ir_texture *
-ir_texture::clone(struct hash_table *ht) const
+ir_texture::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
-   ir_texture *new_tex = new(ctx) ir_texture(this->op);
+   ir_texture *new_tex = new(mem_ctx) ir_texture(this->op);
    new_tex->type = this->type;
 
-   new_tex->sampler = this->sampler->clone(ht);
-   new_tex->coordinate = this->coordinate->clone(ht);
+   new_tex->sampler = this->sampler->clone(mem_ctx, ht);
+   new_tex->coordinate = this->coordinate->clone(mem_ctx, ht);
    if (this->projector)
-      new_tex->projector = this->projector->clone(ht);
+      new_tex->projector = this->projector->clone(mem_ctx, ht);
    if (this->shadow_comparitor) {
-      new_tex->shadow_comparitor = this->shadow_comparitor->clone(ht);
+      new_tex->shadow_comparitor = this->shadow_comparitor->clone(mem_ctx, ht);
    }
 
    for (int i = 0; i < 3; i++)
@@ -229,15 +217,15 @@ ir_texture::clone(struct hash_table *ht) const
    case ir_tex:
       break;
    case ir_txb:
-      new_tex->lod_info.bias = this->lod_info.bias->clone(ht);
+      new_tex->lod_info.bias = this->lod_info.bias->clone(mem_ctx, ht);
       break;
    case ir_txl:
    case ir_txf:
-      new_tex->lod_info.lod = this->lod_info.lod->clone(ht);
+      new_tex->lod_info.lod = this->lod_info.lod->clone(mem_ctx, ht);
       break;
    case ir_txd:
-      new_tex->lod_info.grad.dPdx = this->lod_info.grad.dPdx->clone(ht);
-      new_tex->lod_info.grad.dPdy = this->lod_info.grad.dPdy->clone(ht);
+      new_tex->lod_info.grad.dPdx = this->lod_info.grad.dPdx->clone(mem_ctx, ht);
+      new_tex->lod_info.grad.dPdy = this->lod_info.grad.dPdy->clone(mem_ctx, ht);
       break;
    }
 
@@ -245,30 +233,28 @@ ir_texture::clone(struct hash_table *ht) const
 }
 
 ir_assignment *
-ir_assignment::clone(struct hash_table *ht) const
+ir_assignment::clone(void *mem_ctx, struct hash_table *ht) const
 {
    ir_rvalue *new_condition = NULL;
 
    if (this->condition)
-      new_condition = this->condition->clone(ht);
+      new_condition = this->condition->clone(mem_ctx, ht);
 
-   void *ctx = talloc_parent(this);
-   return new(ctx) ir_assignment(this->lhs->clone(ht),
-				 this->rhs->clone(ht),
-				 new_condition);
+   return new(mem_ctx) ir_assignment(this->lhs->clone(mem_ctx, ht),
+				     this->rhs->clone(mem_ctx, ht),
+				     new_condition);
 }
 
 ir_function *
-ir_function::clone(struct hash_table *ht) const
+ir_function::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *mem_ctx = talloc_parent(this);
    ir_function *copy = new(mem_ctx) ir_function(this->name);
 
    foreach_list_const(node, &this->signatures) {
       const ir_function_signature *const sig =
 	 (const ir_function_signature *const) node;
 
-      ir_function_signature *sig_copy = sig->clone(ht);
+      ir_function_signature *sig_copy = sig->clone(mem_ctx, ht);
       copy->add_signature(sig_copy);
 
       if (ht != NULL)
@@ -280,9 +266,8 @@ ir_function::clone(struct hash_table *ht) const
 }
 
 ir_function_signature *
-ir_function_signature::clone(struct hash_table *ht) const
+ir_function_signature::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *mem_ctx = talloc_parent(this);
    ir_function_signature *copy =
       new(mem_ctx) ir_function_signature(this->return_type);
 
@@ -296,7 +281,7 @@ ir_function_signature::clone(struct hash_table *ht) const
 
       assert(const_cast<ir_variable *>(param)->as_variable() != NULL);
 
-      ir_variable *const param_copy = param->clone(ht);
+      ir_variable *const param_copy = param->clone(mem_ctx, ht);
       copy->parameters.push_tail(param_copy);
    }
 
@@ -305,7 +290,7 @@ ir_function_signature::clone(struct hash_table *ht) const
    foreach_list_const(node, &this->body) {
       const ir_instruction *const inst = (const ir_instruction *) node;
 
-      ir_instruction *const inst_copy = inst->clone(ht);
+      ir_instruction *const inst_copy = inst->clone(mem_ctx, ht);
       copy->body.push_tail(inst_copy);
    }
 
@@ -313,9 +298,8 @@ ir_function_signature::clone(struct hash_table *ht) const
 }
 
 ir_constant *
-ir_constant::clone(struct hash_table *ht) const
+ir_constant::clone(void *mem_ctx, struct hash_table *ht) const
 {
-   void *ctx = talloc_parent(this);
    (void)ht;
 
    switch (this->type->base_type) {
@@ -323,10 +307,10 @@ ir_constant::clone(struct hash_table *ht) const
    case GLSL_TYPE_INT:
    case GLSL_TYPE_FLOAT:
    case GLSL_TYPE_BOOL:
-      return new(ctx) ir_constant(this->type, &this->value);
+      return new(mem_ctx) ir_constant(this->type, &this->value);
 
    case GLSL_TYPE_STRUCT: {
-      ir_constant *c = new(ctx) ir_constant;
+      ir_constant *c = new(mem_ctx) ir_constant;
 
       c->type = this->type;
       for (exec_node *node = this->components.head
@@ -334,19 +318,19 @@ ir_constant::clone(struct hash_table *ht) const
 	      ; node = node->next) {
 	 ir_constant *const orig = (ir_constant *) node;
 
-	 c->components.push_tail(orig->clone(NULL));
+	 c->components.push_tail(orig->clone(mem_ctx, NULL));
       }
 
       return c;
    }
 
    case GLSL_TYPE_ARRAY: {
-      ir_constant *c = new(ctx) ir_constant;
+      ir_constant *c = new(mem_ctx) ir_constant;
 
       c->type = this->type;
       c->array_elements = talloc_array(c, ir_constant *, this->type->length);
       for (unsigned i = 0; i < this->type->length; i++) {
-	 c->array_elements[i] = this->array_elements[i]->clone(NULL);
+	 c->array_elements[i] = this->array_elements[i]->clone(mem_ctx, NULL);
       }
       return c;
    }
@@ -395,14 +379,14 @@ fixup_function_calls(struct hash_table *ht, exec_list *instructions)
 
 
 void
-clone_ir_list(exec_list *out, const exec_list *in)
+clone_ir_list(void *mem_ctx, exec_list *out, const exec_list *in)
 {
    struct hash_table *ht =
       hash_table_ctor(0, hash_table_pointer_hash, hash_table_pointer_compare);
 
    foreach_list_const(node, in) {
       const ir_instruction *const original = (ir_instruction *) node;
-      ir_instruction *copy = original->clone(ht);
+      ir_instruction *copy = original->clone(mem_ctx, ht);
 
       out->push_tail(copy);
    }
diff --git a/src/glsl/ir_constant_expression.cpp b/src/glsl/ir_constant_expression.cpp
index 06bea2b..677353e 100644
--- a/src/glsl/ir_constant_expression.cpp
+++ b/src/glsl/ir_constant_expression.cpp
@@ -680,7 +680,10 @@ ir_dereference_variable::constant_expression_value()
    if (var->mode == ir_var_uniform)
       return NULL;
 
-   return var->constant_value ? var->constant_value->clone(NULL) : NULL;
+   if (!var->constant_value)
+      return NULL;
+
+   return var->constant_value->clone(talloc_parent(var), NULL);
 }
 
 
@@ -732,7 +735,7 @@ ir_dereference_array::constant_expression_value()
 	 return new(ctx) ir_constant(array, component);
       } else {
 	 const unsigned index = idx->value.u[0];
-	 return array->get_array_element(index)->clone(NULL);
+	 return array->get_array_element(index)->clone(ctx, NULL);
       }
    }
    return NULL;
diff --git a/src/glsl/ir_function_inlining.cpp b/src/glsl/ir_function_inlining.cpp
index 9599306..9738137 100644
--- a/src/glsl/ir_function_inlining.cpp
+++ b/src/glsl/ir_function_inlining.cpp
@@ -147,7 +147,7 @@ ir_call::generate_inline(ir_instruction *next_ir)
 	 parameters[i] = NULL;
 	 hash_table_insert(ht, param->variable_referenced(), sig_param);
       } else {
-	 parameters[i] = sig_param->clone(ht);
+	 parameters[i] = sig_param->clone(ctx, ht);
 	 parameters[i]->mode = ir_var_auto;
 	 next_ir->insert_before(parameters[i]);
       }
@@ -169,7 +169,7 @@ ir_call::generate_inline(ir_instruction *next_ir)
    /* Generate the inlined body of the function. */
    foreach_iter(exec_list_iterator, iter, callee->body) {
       ir_instruction *ir = (ir_instruction *)iter.get();
-      ir_instruction *new_ir = ir->clone(ht);
+      ir_instruction *new_ir = ir->clone(ctx, ht);
 
       next_ir->insert_before(new_ir);
       visit_tree(new_ir, replace_return_with_assignment, retval);
@@ -190,7 +190,7 @@ ir_call::generate_inline(ir_instruction *next_ir)
 			    sig_param->mode == ir_var_inout)) {
 	 ir_assignment *assign;
 
-	 assign = new(ctx) ir_assignment(param->clone(NULL)->as_rvalue(),
+	 assign = new(ctx) ir_assignment(param->clone(ctx, NULL)->as_rvalue(),
 					 new(ctx) ir_dereference_variable(parameters[i]),
 					 NULL);
 	 next_ir->insert_before(assign);
diff --git a/src/glsl/ir_import_prototypes.cpp b/src/glsl/ir_import_prototypes.cpp
index 5c5dc00..e553e12 100644
--- a/src/glsl/ir_import_prototypes.cpp
+++ b/src/glsl/ir_import_prototypes.cpp
@@ -95,7 +95,7 @@ public:
 
 	 assert(const_cast<ir_variable *>(param)->as_variable() != NULL);
 
-	 ir_variable *const param_copy = param->clone(NULL);
+	 ir_variable *const param_copy = param->clone(mem_ctx, NULL);
 	 copy->parameters.push_tail(param_copy);
       }
 
diff --git a/src/glsl/ir_vec_index_to_cond_assign.cpp b/src/glsl/ir_vec_index_to_cond_assign.cpp
index dbc6f9a..cd8dedf 100644
--- a/src/glsl/ir_vec_index_to_cond_assign.cpp
+++ b/src/glsl/ir_vec_index_to_cond_assign.cpp
@@ -82,6 +82,8 @@ ir_vec_index_to_cond_assign_visitor::convert_vec_index_to_cond_assign(ir_rvalue
        orig_deref->array->type->is_array())
       return ir;
 
+   void *mem_ctx = talloc_parent(ir);
+
    assert(orig_deref->array_index->type->base_type == GLSL_TYPE_INT);
 
    /* Store the index to a temporary to avoid reusing its tree. */
@@ -109,7 +111,7 @@ ir_vec_index_to_cond_assign_visitor::convert_vec_index_to_cond_assign(ir_rvalue
       /* Just clone the rest of the deref chain when trying to get at the
        * underlying variable.
        */
-      swizzle = new(base_ir) ir_swizzle(orig_deref->array->clone(NULL),
+      swizzle = new(base_ir) ir_swizzle(orig_deref->array->clone(mem_ctx, NULL),
 					i, 0, 0, 0, 1);
 
       deref = new(base_ir) ir_dereference_variable(var);
@@ -165,6 +167,8 @@ ir_vec_index_to_cond_assign_visitor::visit_leave(ir_assignment *ir)
        orig_deref->array->type->is_array())
       return visit_continue;
 
+   void *mem_ctx = talloc_parent(ir);
+
    assert(orig_deref->array_index->type->base_type == GLSL_TYPE_INT);
 
    /* Store the index to a temporary to avoid reusing its tree. */
@@ -196,7 +200,7 @@ ir_vec_index_to_cond_assign_visitor::visit_leave(ir_assignment *ir)
       /* Just clone the rest of the deref chain when trying to get at the
        * underlying variable.
        */
-      swizzle = new(ir) ir_swizzle(orig_deref->array->clone(NULL),
+      swizzle = new(ir) ir_swizzle(orig_deref->array->clone(mem_ctx, NULL),
 				   i, 0, 0, 0, 1);
 
       deref = new(ir) ir_dereference_variable(var);
diff --git a/src/glsl/link_functions.cpp b/src/glsl/link_functions.cpp
index fdf886f..dfda05f 100644
--- a/src/glsl/link_functions.cpp
+++ b/src/glsl/link_functions.cpp
@@ -143,7 +143,7 @@ public:
 	 const ir_instruction *const original = (ir_instruction *) node;
 	 assert(const_cast<ir_instruction *>(original)->as_variable());
 
-	 ir_instruction *copy = original->clone(ht);
+	 ir_instruction *copy = original->clone(linked, ht);
 	 formal_parameters.push_tail(copy);
       }
 
@@ -152,7 +152,7 @@ public:
       foreach_list_const(node, &sig->body) {
 	 const ir_instruction *const original = (ir_instruction *) node;
 
-	 ir_instruction *copy = original->clone(ht);
+	 ir_instruction *copy = original->clone(linked, ht);
 	 linked_sig->body.push_tail(copy);
       }
 
@@ -182,7 +182,7 @@ public:
 	    /* Clone the ir_variable that the dereference already has and add
 	     * it to the linked shader.
 	     */
-	    var = ir->var->clone(NULL);
+	    var = ir->var->clone(linked, NULL);
 	    linked->symbols->add_variable(var->name, var);
 	    linked->ir->push_head(var);
 	 }
diff --git a/src/glsl/linker.cpp b/src/glsl/linker.cpp
index a5faff2..65f3697 100644
--- a/src/glsl/linker.cpp
+++ b/src/glsl/linker.cpp
@@ -323,7 +323,8 @@ cross_validate_globals(struct gl_shader_program *prog,
 		   * FINISHME: modify the shader, and linking with the second
 		   * FINISHME: will fail.
 		   */
-		  existing->constant_value = var->constant_value->clone(NULL);
+		  existing->constant_value =
+		     var->constant_value->clone(talloc_parent(existing), NULL);
 	    }
 	 } else
 	    variables.add_variable(var->name, var);
@@ -488,16 +489,17 @@ populate_symbol_table(gl_shader *sh)
  *                     should be added.
  */
 void
-remap_variables(ir_instruction *inst, glsl_symbol_table *symbols,
-		exec_list *instructions, hash_table *temps)
+remap_variables(ir_instruction *inst, struct gl_shader *target,
+		hash_table *temps)
 {
    class remap_visitor : public ir_hierarchical_visitor {
    public:
-      remap_visitor(glsl_symbol_table *symbols, exec_list *instructions,
+	 remap_visitor(struct gl_shader *target,
 		    hash_table *temps)
       {
-	 this->symbols = symbols;
-	 this->instructions = instructions;
+	 this->target = target;
+	 this->symbols = target->symbols;
+	 this->instructions = target->ir;
 	 this->temps = temps;
       }
 
@@ -516,7 +518,7 @@ remap_variables(ir_instruction *inst, glsl_symbol_table *symbols,
 	 if (existing != NULL)
 	    ir->var = existing;
 	 else {
-	    ir_variable *copy = ir->var->clone(NULL);
+	    ir_variable *copy = ir->var->clone(this->target, NULL);
 
 	    this->symbols->add_variable(copy->name, copy);
 	    this->instructions->push_head(copy);
@@ -527,12 +529,13 @@ remap_variables(ir_instruction *inst, glsl_symbol_table *symbols,
       }
 
    private:
+      struct gl_shader *target;
       glsl_symbol_table *symbols;
       exec_list *instructions;
       hash_table *temps;
    };
 
-   remap_visitor v(symbols, instructions, temps);
+   remap_visitor v(target, temps);
 
    inst->accept(&v);
 }
@@ -583,12 +586,12 @@ move_non_declarations(exec_list *instructions, exec_node *last,
 	     || ((var != NULL) && (var->mode == ir_var_temporary)));
 
       if (make_copies) {
-	 inst = inst->clone(NULL);
+	 inst = inst->clone(target, NULL);
 
 	 if (var != NULL)
 	    hash_table_insert(temps, inst, var);
 	 else
-	    remap_variables(inst, target->symbols, target->ir, temps);
+	    remap_variables(inst, target, temps);
       } else {
 	 inst->remove();
       }
@@ -713,7 +716,7 @@ link_intrastage_shaders(struct gl_shader_program *prog,
 
    gl_shader *const linked = _mesa_new_shader(NULL, 0, main->Type);
    linked->ir = new(linked) exec_list;
-   clone_ir_list(linked->ir, main->ir);
+   clone_ir_list(linked, linked->ir, main->ir);
 
    populate_symbol_table(linked);
 




More information about the mesa-commit mailing list