summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ast_function.cpp53
-rw-r--r--ast_to_hir.cpp181
-rw-r--r--glsl_types.cpp128
-rw-r--r--hir_field_selection.cpp5
-rw-r--r--ir.cpp25
-rw-r--r--ir_clone.cpp47
-rw-r--r--ir_constant_expression.cpp11
-rw-r--r--ir_copy_propagation.cpp3
-rw-r--r--ir_dead_code.cpp3
-rw-r--r--ir_dead_code_local.cpp3
-rw-r--r--ir_expression_flattening.cpp11
-rw-r--r--ir_function_inlining.cpp15
-rw-r--r--ir_reader.cpp50
-rw-r--r--ir_variable.cpp2
-rw-r--r--ir_vec_index_to_swizzle.cpp4
-rw-r--r--list.h25
-rw-r--r--s_expression.cpp16
-rw-r--r--s_expression.h4
18 files changed, 351 insertions, 235 deletions
diff --git a/ast_function.cpp b/ast_function.cpp
index ff2dfa502f3..866cbc4ecdf 100644
--- a/ast_function.cpp
+++ b/ast_function.cpp
@@ -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
diff --git a/ast_to_hir.cpp b/ast_to_hir.cpp
index c70f0f9de9f..eafc9e81145 100644
--- a/ast_to_hir.cpp
+++ b/ast_to_hir.cpp
@@ -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.
diff --git a/glsl_types.cpp b/glsl_types.cpp
index ca19de6bec3..fcc77458b28 100644
--- a/glsl_types.cpp
+++ b/glsl_types.cpp
@@ -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);
diff --git a/hir_field_selection.cpp b/hir_field_selection.cpp
index e60ea30d7ff..6da14925b98 100644
--- a/hir_field_selection.cpp
+++ b/hir_field_selection.cpp
@@ -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 98b085e91bf..26cd4755520 100644
--- 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;
diff --git a/ir_clone.cpp b/ir_clone.cpp
index c810fe86164..5ffd3fc00b2 100644
--- a/ir_clone.cpp
+++ b/ir_clone.cpp
@@ -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 *
diff --git a/ir_constant_expression.cpp b/ir_constant_expression.cpp
index effb88844ee..4010e462674 100644
--- a/ir_constant_expression.cpp
+++ b/ir_constant_expression.cpp
@@ -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. */
}
diff --git a/ir_copy_propagation.cpp b/ir_copy_propagation.cpp
index 16a2ba79bf6..46ef6679d9f 100644
--- a/ir_copy_propagation.cpp
+++ b/ir_copy_propagation.cpp
@@ -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);
}
}
diff --git a/ir_dead_code.cpp b/ir_dead_code.cpp
index 8465d863aa3..01b7d2d832a 100644
--- a/ir_dead_code.cpp
+++ b/ir_dead_code.cpp
@@ -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;
}
diff --git a/ir_dead_code_local.cpp b/ir_dead_code_local.cpp
index d3b3858617d..e01877077c9 100644
--- a/ir_dead_code_local.cpp
+++ b/ir_dead_code_local.cpp
@@ -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) {
diff --git a/ir_expression_flattening.cpp b/ir_expression_flattening.cpp
index 3089f17ae14..5ba24e390b4 100644
--- a/ir_expression_flattening.cpp
+++ b/ir_expression_flattening.cpp
@@ -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
diff --git a/ir_function_inlining.cpp b/ir_function_inlining.cpp
index effb01c8f68..8a1cf4f1d24 100644
--- a/ir_function_inlining.cpp
+++ b/ir_function_inlining.cpp
@@ -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;
}
diff --git a/ir_reader.cpp b/ir_reader.cpp
index ee320ddac28..d6985c4981c 100644
--- a/ir_reader.cpp
+++ b/ir_reader.cpp
@@ -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;
diff --git a/ir_variable.cpp b/ir_variable.cpp
index efebe9199fa..fabd856591a 100644
--- a/ir_variable.cpp
+++ b/ir_variable.cpp
@@ -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) {
diff --git a/ir_vec_index_to_swizzle.cpp b/ir_vec_index_to_swizzle.cpp
index eb0e556c9db..bbd873791a1 100644
--- a/ir_vec_index_to_swizzle.cpp
+++ b/ir_vec_index_to_swizzle.cpp
@@ -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 0b91647be4f..7732d66d7a6 100644
--- a/list.h
+++ b/list.h
@@ -66,7 +66,13 @@
#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 */
diff --git a/s_expression.cpp b/s_expression.cpp
index 0fb296ef671..875d739d842 100644
--- a/s_expression.cpp
+++ b/s_expression.cpp
@@ -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 != ')') {
diff --git a/s_expression.h b/s_expression.h
index 8a4eda28dae..1a0c03c2189 100644
--- a/s_expression.h
+++ b/s_expression.h
@@ -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.