Add sources for unification type errors.

This commit is contained in:
2020-09-09 15:26:04 -07:00
parent d5c3a44041
commit e337992410
3 changed files with 25 additions and 15 deletions

View File

@@ -99,11 +99,19 @@ type_ptr ast_binop::typecheck(type_mgr& mgr, type_env_ptr& env) {
type_ptr ftype = env->lookup(op_name(op))->instantiate(mgr);
if(!ftype) throw type_error(std::string("unknown binary operator ") + op_name(op), loc);
type_ptr return_type = mgr.new_type();
type_ptr arrow_one = type_ptr(new type_arr(rtype, return_type));
type_ptr arrow_two = type_ptr(new type_arr(ltype, arrow_one));
// For better type errors, we first require binary function,
// and only then unify each argument. This way, we can
// precisely point out which argument is "wrong".
mgr.unify(arrow_two, ftype);
type_ptr return_type = mgr.new_type();
type_ptr second_type = mgr.new_type();
type_ptr first_type = mgr.new_type();
type_ptr arrow_one = type_ptr(new type_arr(second_type, return_type));
type_ptr arrow_two = type_ptr(new type_arr(first_type, arrow_one));
mgr.unify(ftype, arrow_two, loc);
mgr.unify(first_type, ltype, left->loc);
mgr.unify(second_type, rtype, right->loc);
return return_type;
}
@@ -140,7 +148,7 @@ type_ptr ast_app::typecheck(type_mgr& mgr, type_env_ptr& env) {
type_ptr return_type = mgr.new_type();
type_ptr arrow = type_ptr(new type_arr(rtype, return_type));
mgr.unify(arrow, ltype);
mgr.unify(arrow, ltype, left->loc);
return return_type;
}
@@ -190,7 +198,7 @@ type_ptr ast_case::typecheck(type_mgr& mgr, type_env_ptr& env) {
type_env_ptr new_env = type_scope(env);
branch->pat->typecheck(case_type, mgr, new_env);
type_ptr curr_branch_type = branch->expr->typecheck(mgr, new_env);
mgr.unify(branch_type, curr_branch_type);
mgr.unify(curr_branch_type, branch_type, branch->expr->loc);
}
input_type = mgr.resolve(case_type, var);
@@ -361,7 +369,7 @@ type_ptr ast_lambda::typecheck(type_mgr& mgr, type_env_ptr& env) {
full_type = type_ptr(new type_arr(std::move(param_type), full_type));
}
mgr.unify(return_type, body->typecheck(mgr, var_env));
mgr.unify(return_type, body->typecheck(mgr, var_env), body->loc);
return full_type;
}
@@ -433,5 +441,5 @@ void pattern_constr::typecheck(type_ptr t, type_mgr& mgr, type_env_ptr& env) con
constructor_type = arr->right;
}
mgr.unify(t, constructor_type);
mgr.unify(constructor_type, t, loc);
}