work on k
This commit is contained in:
70
k.krak
70
k.krak
@@ -202,7 +202,6 @@ fun main(argc: int, argv: **char): int {
|
||||
}
|
||||
for (var i = 0; i < item->children.size; i++;) {
|
||||
var child = item->children[i]
|
||||
if is_type_def(child)
|
||||
match (child->data) {
|
||||
ast::_type_def(name) {
|
||||
println("Found a type_def! - " + name)
|
||||
@@ -210,25 +209,64 @@ fun main(argc: int, argv: **char): int {
|
||||
var grandchild = child->children[j];
|
||||
if is_declaration(grandchild) {
|
||||
var ident = grandchild->children[0]
|
||||
var ident_name = ident->data._identifier.first
|
||||
var ident_type = ident->data._identifier.second
|
||||
var type_def_binding = make_ast_binding(name)
|
||||
set_ast_binding(type_def_binding, child)
|
||||
item->add_child(_compiler_intrinsic(ident->data._identifier.first, binding_p(type::_fun(make_triple(make_pair(vec(
|
||||
item->add_child(_compiler_intrinsic(ident_name, binding_p(type::_fun(make_triple(make_pair(vec(
|
||||
binding_p(type::_obj(type_def_binding))
|
||||
),
|
||||
ident->data._identifier.second
|
||||
ident_type
|
||||
), false, false))), vec<*binding<type>>()))
|
||||
println("adding compiler intrinsic to do " + name + "." + ident->data._identifier.first)
|
||||
println("adding compiler intrinsic to do " + name + "." + ident_name)
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::_template(name_map_pair) {
|
||||
if is_type_def(child->children[0]) {
|
||||
var name = child->children[0]->data._type_def
|
||||
println("Found a templated type_def! - " + name)
|
||||
for (var j = 0; j < child->children[0]->children.size; j++;) {
|
||||
var great_grandchild = child->children[0]->children[j];
|
||||
if is_declaration(great_grandchild) {
|
||||
var ident = great_grandchild->children[0]
|
||||
var ident_name = ident->data._identifier.first
|
||||
|
||||
// inst type?
|
||||
var ident_type = ident->data._identifier.second
|
||||
|
||||
|
||||
// the map retains the order
|
||||
var new_template_type_map = name_map_pair.second.associate(fun(n: str, t: *binding<type>): pair<str, *binding<type>> return make_pair(n, binding_p(type::_template_placeholder()));)
|
||||
var new_ident_type = inst_temp_type(ident_type, name_map_pair.second.associate(fun(n: str, t: *binding<type>): pair<*binding<type>, *binding<type>>
|
||||
return make_pair(t, new_template_type_map[n]);))
|
||||
|
||||
var type_def_binding = make_ast_binding(name, new_template_type_map.values)
|
||||
// do we need to set the binding to the template?
|
||||
/*set_ast_binding(type_def_binding, child)*/
|
||||
|
||||
item->add_child(_template(ident_name, new_template_type_map, vec(_compiler_intrinsic(ident_name, binding_p(type::_fun(make_triple(make_pair(vec(
|
||||
binding_p(type::_obj(type_def_binding))
|
||||
),
|
||||
ident_type
|
||||
), false, false))), vec<*binding<type>>()))))
|
||||
println("adding compiler intrinsic to do " + name + "." + ident_name)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
println("post generative")
|
||||
print_tree(item, 1)
|
||||
}
|
||||
|
||||
// resolves all binding possibilities for one top level item
|
||||
passes[str("name_possibility_resolve")] = fun(item: *tree<ast>) {
|
||||
println("Running name possibility resolver?")
|
||||
var scope_lookup: fun(*tree<ast>, str, bool): OptionVecAst = fun(scope: *tree<ast>, name: str, is_type: bool): OptionVecAst {
|
||||
/*println("doing a scope lookup for " + name + " starting from " + to_string(scope->data))*/
|
||||
var to_ret = vec<*tree<ast>>()
|
||||
for (var i = 0; i < scope->children.size; i++;) {
|
||||
match(scope->children[i]->data) {
|
||||
@@ -267,6 +305,7 @@ fun main(argc: int, argv: **char): int {
|
||||
ast::_compiler_intrinsic(b) if (!is_type && b.first == name)
|
||||
to_ret += scope->children[i]
|
||||
ast::_template(b) if (((!is_type && is_function(scope->children[i]->children[0]))
|
||||
|| (!is_type && is_compiler_intrinsic(scope->children[i]->children[0]))
|
||||
|| ( is_type && is_type_def(scope->children[i]->children[0]))
|
||||
|| ( is_type && is_adt_def( scope->children[i]->children[0]))) && b.first == name)
|
||||
to_ret += scope->children[i]
|
||||
@@ -319,7 +358,7 @@ fun main(argc: int, argv: **char): int {
|
||||
/*_binding: triple<str, vec<*type>, *tree<ast>>,*/
|
||||
ast::_function(b) handle_type(b.second, t)
|
||||
ast::_compiler_intrinsic(b) {
|
||||
/*handle_type(b.second, t)*/
|
||||
handle_type(b.second, t)
|
||||
b.third.for_each(fun(tb: *binding<type>) {
|
||||
handle_type(tb, t)
|
||||
})
|
||||
@@ -352,6 +391,10 @@ fun main(argc: int, argv: **char): int {
|
||||
}
|
||||
ast::_function(b) return b.second
|
||||
ast::_template(b) {
|
||||
println("insting temp type in get_type with map")
|
||||
b.second.for_each(fun(k: str, v: *binding<type>) {
|
||||
println("\t" + k + ": " + to_string(v->bound_to))
|
||||
})
|
||||
return inst_temp_type(get_type(a->children[0]), b.second.associate(fun(k: str, v: *binding<type>): pair<*binding<type>, *binding<type>> return make_pair(v, binding_p(type::_unknown()));))
|
||||
}
|
||||
ast::_compiler_intrinsic(b) return b.second
|
||||
@@ -375,7 +418,7 @@ fun main(argc: int, argv: **char): int {
|
||||
error("Trying to get type of node without one: " + to_string(a->data))
|
||||
}
|
||||
|
||||
// resolves all binding possibilities for one top level item
|
||||
// resolves all binding possibilities to a single one for one top level item
|
||||
passes[str("name_type_resolve")] = fun(item: *tree<ast>) {
|
||||
if !pass_poset.done(make_pair(item, str("name_possibility_resolve"))) {
|
||||
pass_poset.add_open_dep(make_pair(item, str("name_type_resolve")), make_pair(item, str("name_possibility_resolve")))
|
||||
@@ -390,13 +433,17 @@ fun main(argc: int, argv: **char): int {
|
||||
ast::_declaration() if (t->children.size > 1)
|
||||
unify(get_type(t->children[0]), get_type(t->children[1]))
|
||||
ast::_call() {
|
||||
println("traverse_for_unify call - " + to_string(t->data))
|
||||
// we call get type to make sure if it is unknown it is transformed into a function version
|
||||
get_type(t)
|
||||
println("\tpast first get_type")
|
||||
var fun_type = get_type(t->children[0])->bound_to
|
||||
println("\tpast second get_type")
|
||||
if (!is_fun(fun_type))
|
||||
error("trying to call not a function type: " + to_string(fun_type))
|
||||
if (fun_type->_fun.first.first.size != (t->children.size - 1))
|
||||
error("trying to call function with type wrong number of params (" + to_string(fun_type->_fun.first.first.size) + " vs " + to_string(t->children.size - 1) + "): " + to_string(fun_type))
|
||||
println("\titerating through children, matching their type with the param type")
|
||||
for (var i = 1; i < t->children.size; i++;)
|
||||
unify(fun_type->_fun.first.first[i-1], get_type(t->children[i]))
|
||||
}
|
||||
@@ -527,7 +574,8 @@ fun main(argc: int, argv: **char): int {
|
||||
return taken_names[x]
|
||||
var possible = str()
|
||||
match(x->data) {
|
||||
ast::_identifier(b) { possible = b.first; }
|
||||
/*ast::_identifier(b) { possible = b.first; }*/
|
||||
ast::_identifier(b) { return b.first; }
|
||||
ast::_type_def(b) { possible = b; }
|
||||
ast::_function(b) { possible = b.first; }
|
||||
}
|
||||
@@ -612,7 +660,7 @@ fun main(argc: int, argv: **char): int {
|
||||
|
||||
// but not in the case where this is a templated type instead of a function - that doesn't make any sense
|
||||
var binding_type = null<binding<type>>()
|
||||
if is_function(bound_to->children[0]) {
|
||||
if is_function(bound_to->children[0]) || is_compiler_intrinsic(bound_to->children[0]) {
|
||||
// unify in both cases - we need it in the explicit case to make sure our explicit types propegate back
|
||||
binding_type = get_type(t)
|
||||
unify(binding_type, inst_temp_type(get_type(bound_to->children[0]), inst_map))
|
||||
@@ -675,9 +723,9 @@ fun main(argc: int, argv: **char): int {
|
||||
pass_poset.add_close_dep(make_pair(item, str("emit_C")), make_pair(bound_to->parent, str("emit_C")))
|
||||
}
|
||||
// bound_to might have changed from binding
|
||||
if !is_type_def(get_ast_binding(t)) {
|
||||
resolve_type(get_type(t))
|
||||
}
|
||||
/*if !is_type_def(get_ast_binding(t)) {*/
|
||||
/*resolve_type(get_type(t))*/
|
||||
/*}*/
|
||||
}
|
||||
ast::_identifier(p) resolve_type(get_type(t))
|
||||
ast::_function(p) resolve_type(get_type(t))
|
||||
|
||||
@@ -29,6 +29,7 @@ adt type {
|
||||
}
|
||||
|
||||
fun unify(t1: *binding<type>, t2: *binding<type>) {
|
||||
println("attempting to unify " + to_string(t1->bound_to) + " and " + to_string(t2->bound_to))
|
||||
if (is_unknown(t1->bound_to)) {
|
||||
t1->set(t2->bound_to)
|
||||
} else if (is_unknown(t2->bound_to)) {
|
||||
@@ -41,16 +42,45 @@ fun unify(t1: *binding<type>, t2: *binding<type>) {
|
||||
unify(t1->bound_to->_fun.first.first[i], t2->bound_to->_fun.first.first[i])
|
||||
} else if (is_ptr(t1->bound_to)) {
|
||||
unify(t1->bound_to->_ptr, t2->bound_to->_ptr)
|
||||
} else if (is_obj(t1->bound_to)) {
|
||||
for (var i = 0; i < t1->bound_to->_obj->data._binding.second.size; i++;) {
|
||||
unify(t1->bound_to->_obj->data._binding.second[i], t2->bound_to->_obj->data._binding.second[i])
|
||||
}
|
||||
}
|
||||
} else {
|
||||
error("Doesn't typecheck! Attempted to unify " + to_string(t1->bound_to) + " and " + to_string(t2->bound_to))
|
||||
}
|
||||
}
|
||||
}
|
||||
fun shallow_equality(a: *type, b: *type):bool {
|
||||
if (is_ptr(a) != is_ptr(b))
|
||||
return false
|
||||
if (is_ptr(a) && is_ptr(b))
|
||||
return true
|
||||
match(*a) {
|
||||
type::_fun(x) {
|
||||
return is_fun(b) && a->_fun.third == b->_fun.third
|
||||
}
|
||||
type::_obj(x) {
|
||||
return is_obj(b) && (get_ast_binding(x) == get_ast_binding(b->_obj) || ((!ast_bound(x) || !ast_bound(b->_obj))
|
||||
&& x->data._binding.second.size == b->_obj->data._binding.second.size
|
||||
&& x->data._binding.first == b->_obj->data._binding.first))
|
||||
}
|
||||
}
|
||||
return *a == *b
|
||||
}
|
||||
|
||||
fun inst_temp_type(t: *binding<type>, replacements: ref map<*binding<type>, *binding<type>>): *binding<type> {
|
||||
println("inst_temp_type " + to_string(t->bound_to))
|
||||
match (*t->bound_to) {
|
||||
type::_unknown() error("Unknown in temp type")
|
||||
type::_obj(o) {
|
||||
var binding_types = o->data._binding.second.map(fun(b: *binding<type>): *binding<type> return inst_temp_type(b, replacements);)
|
||||
for (var i = 0; i < o->data._binding.second.size; i++;) {
|
||||
if (o->data._binding.second[i] != binding_types[i])
|
||||
return binding_p(type::_obj(_binding(o->data._binding.first, binding_types, o->data._binding.third)))
|
||||
}
|
||||
}
|
||||
type::_ptr(p) {
|
||||
var cp = inst_temp_type(p, replacements)
|
||||
if (cp == p)
|
||||
@@ -82,9 +112,23 @@ fun inst_temp_type(t: *binding<type>, replacements: ref map<*binding<type>, *bin
|
||||
}
|
||||
|
||||
fun equality(a: *type, b: *type, count_unknown_as_equal: bool): bool {
|
||||
println("equality of " + to_string(a) + " and " + to_string(b))
|
||||
if (count_unknown_as_equal && (is_unknown(a) || is_unknown(b)))
|
||||
return true
|
||||
match(*a) {
|
||||
type::_obj(x) {
|
||||
if (!is_obj(b))
|
||||
return false
|
||||
if (get_ast_binding(x) == get_ast_binding(b->_obj))
|
||||
return true
|
||||
if (!count_unknown_as_equal || (ast_bound(x) && ast_bound(b->_obj)) || x->data._binding.first != b->_obj->data._binding.first || x->data._binding.second.size != b->_obj->data._binding.second.size)
|
||||
return false
|
||||
for (var i = 0; i < x->data._binding.second.size; i++;) {
|
||||
if (!equality(x->data._binding.second[i]->bound_to, b->_obj->data._binding.second[i]->bound_to, count_unknown_as_equal))
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
type::_ptr(p) {
|
||||
if (!is_ptr(b))
|
||||
return false
|
||||
@@ -110,21 +154,6 @@ fun equality(a: *type, b: *type, count_unknown_as_equal: bool): bool {
|
||||
}
|
||||
return *a == *b
|
||||
}
|
||||
fun shallow_equality(a: *type, b: *type):bool {
|
||||
if (is_ptr(a) != is_ptr(b))
|
||||
return false
|
||||
if (is_ptr(a) && is_ptr(b))
|
||||
return true
|
||||
match(*a) {
|
||||
type::_fun(x) {
|
||||
return is_fun(b) && a->_fun.third == b->_fun.third
|
||||
}
|
||||
type::_obj(x) {
|
||||
return is_obj(b) && get_ast_binding(x) == get_ast_binding(b->_obj)
|
||||
}
|
||||
}
|
||||
return *a == *b
|
||||
}
|
||||
fun to_string(it: *type): str {
|
||||
match (*it) {
|
||||
type::_unknown() return str("_unknown")
|
||||
|
||||
Reference in New Issue
Block a user