transfer work on interpreted closures

This commit is contained in:
Nathan Braswell
2016-06-30 09:57:41 -07:00
parent 4195da6492
commit 76e78a2ac0
2 changed files with 36 additions and 22 deletions

View File

@@ -25,9 +25,6 @@ fun adt_lower(name_ast_map: *map<string, pair<*tree<symbol>,*ast_node>>, ast_to_
var replacement_this = make_this_noncached(replacement)
var option_union = ast_type_def_ptr(backing.name + "_union", true);
node->adt_def.options.for_each(fun(opt: *ast_node) {
// want to keep them around
/*if (opt->identifier.type->is_empty_adt_option())*/
/*opt->identifier.type = type_ptr(base_type::character())*/
if (!opt->identifier.type->is_empty_adt_option())
option_union->type_def.variables.add(ast_declaration_statement_ptr(opt, null<ast_node>(), false))
type_def_option_map[node].add(opt)
@@ -52,17 +49,12 @@ fun adt_lower(name_ast_map: *map<string, pair<*tree<symbol>,*ast_node>>, ast_to_
var value = ast_value_ptr(to_string(idx), type_ptr(base_type::integer()))
block->code_block.children.add(ast_statement_ptr(ast_assignment_statement_ptr(make_operator_call(".", vector(to_ret, flag)), value)))
/*var opt = option_union->type_def.variables[idx]->declaration_statement.identifier*/
var opt = type_def_option_map[node][idx]
var lvalue = make_operator_call(".", vector(make_operator_call(".", vector(to_ret, option_union_ident)), opt))
if (func->function.parameters.size) {
// do copy_construct if it should
block->code_block.children.add(ast_statement_ptr(assign_or_copy_construct_statement(lvalue, func->function.parameters[0])))
}
/*} else {*/
/*// init our placeholders with 0 for equality, etc*/
/*block->code_block.children.add(ast_statement_ptr(ast_assignment_statement_ptr(lvalue, ast_value_ptr(string("0"), type_ptr(base_type::character())))))*/
/*}*/
block->code_block.children.add(ast_statement_ptr(ast_return_statement_ptr(to_ret)))
add_before_in(func, node, parent_chain)
add_to_scope(func->function.name, func, enclosing_scope)
@@ -78,12 +70,10 @@ fun adt_lower(name_ast_map: *map<string, pair<*tree<symbol>,*ast_node>>, ast_to_
if_stmt->if_statement.then_part = ast_statement_ptr(ast_return_statement_ptr(ast_value_ptr(string("false"), type_ptr(base_type::boolean()))))
block->code_block.children.add(if_stmt)
/*for (var i = 0; i < option_union->type_def.variables.size; i++;) {*/
for (var i = 0; i < type_def_option_map[node].size; i++;) {
if (get_ast_type(type_def_option_map[node][i])->is_empty_adt_option())
continue
var if_stmt_inner = ast_if_statement_ptr(make_operator_call("==", vector(make_operator_call("->", vector(replacement_this, flag)), ast_value_ptr(to_string(i), type_ptr(base_type::integer())))))
/*var option = option_union->type_def.variables[i]->declaration_statement.identifier*/
var option = type_def_option_map[node][i]
var our_option = make_operator_call(".", vector(make_operator_call("->", vector(replacement_this, option_union_ident)), option))
var their_option = make_operator_call(".", vector(make_operator_call(".", vector(other, option_union_ident)), option))
@@ -101,12 +91,10 @@ fun adt_lower(name_ast_map: *map<string, pair<*tree<symbol>,*ast_node>>, ast_to_
} else if (func->function.name == "copy_construct") {
var other = func->function.parameters[0]
block->code_block.children.add(ast_statement_ptr(ast_assignment_statement_ptr(make_operator_call("->", vector(replacement_this, flag)), make_operator_call("->", vector(other, flag)))))
/*for (var i = 0; i < option_union->type_def.variables.size; i++;) {*/
for (var i = 0; i < type_def_option_map[node].size; i++;) {
if (get_ast_type(type_def_option_map[node][i])->is_empty_adt_option())
continue
var if_stmt_inner = ast_if_statement_ptr(make_operator_call("==", vector(make_operator_call("->", vector(replacement_this, flag)), ast_value_ptr(to_string(i), type_ptr(base_type::integer())))))
/*var option = option_union->type_def.variables[i]->declaration_statement.identifier*/
var option = type_def_option_map[node][i]
var our_option = make_operator_call(".", vector(make_operator_call("->", vector(replacement_this, option_union_ident)), option))
var their_option = make_operator_call(".", vector(make_operator_call("->", vector(other, option_union_ident)), option))

View File

@@ -307,7 +307,6 @@ fun store_into_variable(to: ref value, from: value) {
base_type::ulong_int() { assert(is_ulong_int(from), "mismatching assignemnt types - from is not ulong_int"); *(variable.first) cast *ulong = from.ulong_int; }
base_type::floating() { assert(is_floating(from), "mismatching assignemnt types - from is not floating"); *(variable.first) cast *float = from.floating; }
base_type::double_precision() { assert(is_double_precision(from), "mismatching assignemnt types - from is not double"); *(variable.first) cast *double = from.double_precision; }
base_type::function() { assert(is_function(from), "mismatching assignemnt types - from is not function"); *(variable.first) cast *pair<*ast_node,map<*ast_node,value>> = from.function; }
}
}
fun get_real_value(v: value): value {
@@ -322,8 +321,6 @@ fun get_real_value(v: value): value {
match (var_type->base) {
// really this could just be make_pair(variable)
base_type::object() return value::object_like(make_pair(var_ptr, var_type))
/*base_type::adt() return #sizeof<>*/
/*base_type::function() return #sizeof<>*/
base_type::boolean() return value::boolean(*(var_ptr) cast *bool)
base_type::character() return value::character(*(var_ptr) cast *char)
base_type::ucharacter() return value::ucharacter(*(var_ptr) cast *uchar)
@@ -470,7 +467,6 @@ fun type_size(t: *type): ulong {
})
return size
}
/*base_type::adt() return #sizeof<>*/
base_type::function() return #sizeof<pair<*ast_node,map<*ast_node,value>>>
base_type::boolean() return #sizeof<bool>
base_type::character() return #sizeof<char>
@@ -553,7 +549,7 @@ obj interpreter (Object) {
printlnerr("=============")
var var_stack = stack<map<*ast_node, value>>()
var_stack.push(map<*ast_node,value>())
var result = call_function(results[0], vector<value>(), vector<*ast_node>(), &var_stack, value::void_nothing(), value::void_nothing(), null<ast_node>())
var result = call_function(results[0], vector<value>(), vector<*ast_node>(), &var_stack, map<*ast_node,value>(), value::void_nothing(), value::void_nothing(), null<ast_node>())
printlnerr("=============")
printlnerr("Done!")
printlnerr("=============")
@@ -588,11 +584,18 @@ obj interpreter (Object) {
var func_call_func = func_call->function_call.func
var new_enclosing_object = value::void_nothing()
var dot_style_method_call = is_dot_style_method_call(func_call)
var possible_closure_map = map<*ast_node,value>()
// test for function value
if (!dot_style_method_call && !is_function(func_call_func)) {
/*error("func_call_func is not a function")*/
/*println(string("func_call_func is not a function: ") + get_ast_name(func_call_func))*/
func_call_func = get_real_value(interpret(func_call_func, var_stack, enclosing_object, enclosing_func).first).function.first
var func_value = get_real_value(interpret(func_call_func, var_stack, enclosing_object, enclosing_func).first)
func_call_func = func_value.function.first
possible_closure_map = func_value.function.second
println("possible_closure_map is")
possible_closure_map.for_each(fun(key: *ast_node, v: value) print(get_ast_name(key) + " ");)
println()
println("end pcm")
/*println(string("calling func we got from interpreting: ") + get_ast_name(func_call_func))*/
}
// note here also that this is likely not a foolproof method
@@ -676,19 +679,27 @@ obj interpreter (Object) {
// not the operator & and at least one object like parameter
parameter_sources = func_call_parameters
}
return make_pair(call_function(func_call_func, parameters, parameter_sources, var_stack, enclosing_object, new_enclosing_object, enclosing_func), control_flow::nor())
return make_pair(call_function(func_call_func, parameters, parameter_sources, var_stack, possible_closure_map, enclosing_object, new_enclosing_object, enclosing_func), control_flow::nor())
}
// call_function can be called with either parameter values in parameters or ast expressions in parameter_sources
// this is to allow easy function calling if we already have the values (for main, say, or to make our job if it's not
// an operator easier), but we need to be able to be called with ast_expressions too so we can properly copy_construct once
fun call_function(func: *ast_node, parameters: vector<value>, parameter_sources: vector<*ast_node>, var_stack: *stack<map<*ast_node, value>>, enclosing_object: value, new_enclosing_object: value, enclosing_func: *ast_node): value {
fun call_function(func: *ast_node, parameters: vector<value>, parameter_sources: vector<*ast_node>, var_stack: *stack<map<*ast_node, value>>, possible_closure_map: ref map<*ast_node, value>, enclosing_object: value, new_enclosing_object: value, enclosing_func: *ast_node): value {
// will need adjustment
if (!is_function(func))
error("Can't handle not function function calls (can do regular method, is this chained or something?)")
var func_name = func->function.name
// do regular function
var new_var_stack = stack<map<*ast_node, value>>()
// start out with the possible closure map as the highest scope (gloabals checked seperately)
var new_var_stack = stack(possible_closure_map)
new_var_stack.push(map<*ast_node,value>())
println("stack after pcm and new m is")
for (var i = 0; i < new_var_stack.size(); i++;) {
println(string("level: ") + i)
new_var_stack.from_top(i).for_each(fun(key: *ast_node, v: value) print(get_ast_name(key) + " ");)
println()
}
println("end stack after")
// if this is a value based call, pull from parameters
if (parameter_sources.size == 0) {
/*println(func_name + " being called with parameter values")*/
@@ -814,7 +825,16 @@ obj interpreter (Object) {
return value::void_nothing()
}
fun interpret_function(function: *ast_node, var_stack: *stack<map<*ast_node, value>>, enclosing_object: value, enclosing_func: *ast_node): pair<value, control_flow> {
return make_pair(value::function(make_pair(function, map<*ast_node,value>())), control_flow::nor())
var possible_closure_map = map<*ast_node,value>()
function->function.closed_variables.for_each(fun(v: *ast_node) {
possible_closure_map[v] = interpret_identifier(v, var_stack, enclosing_object, enclosing_func).first
println(string("closing over ") + get_ast_name(v))
})
println("in interpret function possible_closure_map is")
possible_closure_map.for_each(fun(key: *ast_node, v: value) print(get_ast_name(key) + " ");)
println()
println("end in inteprret function pcm")
return make_pair(value::function(make_pair(function, possible_closure_map)), control_flow::nor())
}
fun interpret_statement(stmt: *ast_node, var_stack: *stack<map<*ast_node, value>>, enclosing_object: value, enclosing_func: *ast_node): pair<value, control_flow> {
return interpret(stmt->statement.child, var_stack, enclosing_object, enclosing_func)
@@ -960,6 +980,12 @@ obj interpreter (Object) {
// check for global
if (globals.contains_key(ident))
return make_pair(globals[ident], control_flow::nor())
println("couldn't find it in interpret identifier")
for (var i = 0; i < var_stack->size(); i++;) {
println(string("level: ") + i)
var_stack->from_top(i).for_each(fun(key: *ast_node, v: value) print(get_ast_name(key) + " ");)
println()
}
error(string("Cannot find variable: ") + ident->identifier.name)
}
fun interpret_cast(node: *ast_node, var_stack: *stack<map<*ast_node, value>>, enclosing_object: value, enclosing_func: *ast_node): pair<value, control_flow> {