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 replacement_this = make_this_noncached(replacement)
var option_union = ast_type_def_ptr(backing.name + "_union", true); var option_union = ast_type_def_ptr(backing.name + "_union", true);
node->adt_def.options.for_each(fun(opt: *ast_node) { 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()) if (!opt->identifier.type->is_empty_adt_option())
option_union->type_def.variables.add(ast_declaration_statement_ptr(opt, null<ast_node>(), false)) option_union->type_def.variables.add(ast_declaration_statement_ptr(opt, null<ast_node>(), false))
type_def_option_map[node].add(opt) 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())) 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))) 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 opt = type_def_option_map[node][idx]
var lvalue = make_operator_call(".", vector(make_operator_call(".", vector(to_ret, option_union_ident)), opt)) var lvalue = make_operator_call(".", vector(make_operator_call(".", vector(to_ret, option_union_ident)), opt))
if (func->function.parameters.size) { if (func->function.parameters.size) {
// do copy_construct if it should // do copy_construct if it should
block->code_block.children.add(ast_statement_ptr(assign_or_copy_construct_statement(lvalue, func->function.parameters[0]))) 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))) block->code_block.children.add(ast_statement_ptr(ast_return_statement_ptr(to_ret)))
add_before_in(func, node, parent_chain) add_before_in(func, node, parent_chain)
add_to_scope(func->function.name, func, enclosing_scope) 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())))) 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) 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++;) { 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()) if (get_ast_type(type_def_option_map[node][i])->is_empty_adt_option())
continue 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 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 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 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)) 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") { } else if (func->function.name == "copy_construct") {
var other = func->function.parameters[0] 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))))) 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++;) { 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()) if (get_ast_type(type_def_option_map[node][i])->is_empty_adt_option())
continue 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 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 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 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)) 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::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::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::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 { fun get_real_value(v: value): value {
@@ -322,8 +321,6 @@ fun get_real_value(v: value): value {
match (var_type->base) { match (var_type->base) {
// really this could just be make_pair(variable) // really this could just be make_pair(variable)
base_type::object() return value::object_like(make_pair(var_ptr, var_type)) 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::boolean() return value::boolean(*(var_ptr) cast *bool)
base_type::character() return value::character(*(var_ptr) cast *char) base_type::character() return value::character(*(var_ptr) cast *char)
base_type::ucharacter() return value::ucharacter(*(var_ptr) cast *uchar) base_type::ucharacter() return value::ucharacter(*(var_ptr) cast *uchar)
@@ -470,7 +467,6 @@ fun type_size(t: *type): ulong {
}) })
return size return size
} }
/*base_type::adt() return #sizeof<>*/
base_type::function() return #sizeof<pair<*ast_node,map<*ast_node,value>>> base_type::function() return #sizeof<pair<*ast_node,map<*ast_node,value>>>
base_type::boolean() return #sizeof<bool> base_type::boolean() return #sizeof<bool>
base_type::character() return #sizeof<char> base_type::character() return #sizeof<char>
@@ -553,7 +549,7 @@ obj interpreter (Object) {
printlnerr("=============") printlnerr("=============")
var var_stack = stack<map<*ast_node, value>>() var var_stack = stack<map<*ast_node, value>>()
var_stack.push(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("=============")
printlnerr("Done!") printlnerr("Done!")
printlnerr("=============") printlnerr("=============")
@@ -588,11 +584,18 @@ obj interpreter (Object) {
var func_call_func = func_call->function_call.func var func_call_func = func_call->function_call.func
var new_enclosing_object = value::void_nothing() var new_enclosing_object = value::void_nothing()
var dot_style_method_call = is_dot_style_method_call(func_call) var dot_style_method_call = is_dot_style_method_call(func_call)
var possible_closure_map = map<*ast_node,value>()
// test for function value // test for function value
if (!dot_style_method_call && !is_function(func_call_func)) { if (!dot_style_method_call && !is_function(func_call_func)) {
/*error("func_call_func is not a function")*/ /*error("func_call_func is not a function")*/
/*println(string("func_call_func is not a function: ") + get_ast_name(func_call_func))*/ /*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))*/ /*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 // 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 // not the operator & and at least one object like parameter
parameter_sources = func_call_parameters 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 // 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 // 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 // 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 // will need adjustment
if (!is_function(func)) if (!is_function(func))
error("Can't handle not function function calls (can do regular method, is this chained or something?)") error("Can't handle not function function calls (can do regular method, is this chained or something?)")
var func_name = func->function.name var func_name = func->function.name
// do regular function // 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>()) 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 this is a value based call, pull from parameters
if (parameter_sources.size == 0) { if (parameter_sources.size == 0) {
/*println(func_name + " being called with parameter values")*/ /*println(func_name + " being called with parameter values")*/
@@ -814,7 +825,16 @@ obj interpreter (Object) {
return value::void_nothing() 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> { 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> { 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) return interpret(stmt->statement.child, var_stack, enclosing_object, enclosing_func)
@@ -960,6 +980,12 @@ obj interpreter (Object) {
// check for global // check for global
if (globals.contains_key(ident)) if (globals.contains_key(ident))
return make_pair(globals[ident], control_flow::nor()) 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) 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> { fun interpret_cast(node: *ast_node, var_stack: *stack<map<*ast_node, value>>, enclosing_object: value, enclosing_func: *ast_node): pair<value, control_flow> {