rustc: Print out a real error message on unresolved types. Puts out burning tinderbox.
This commit is contained in:
parent
ddec6b5f47
commit
0857d22c04
src
@ -2537,17 +2537,24 @@ mod unify {
|
||||
// Fixups and substitutions
|
||||
|
||||
fn fixup_vars(ty_ctxt tcx, @var_bindings vb, t typ) -> fixup_result {
|
||||
fn subst_vars(ty_ctxt tcx, @var_bindings vb, t typ) -> t {
|
||||
fn subst_vars(ty_ctxt tcx, @var_bindings vb,
|
||||
@mutable option::t[int] unresolved, t typ) -> t {
|
||||
alt (struct(tcx, typ)) {
|
||||
case (ty::ty_var(?vid)) {
|
||||
if ((vid as uint) >= ufind::set_count(vb.sets)) {
|
||||
*unresolved = some[int](vid);
|
||||
ret typ;
|
||||
}
|
||||
|
||||
auto root_id = ufind::find(vb.sets, vid as uint);
|
||||
alt (smallintmap::find[t](vb.types, root_id)) {
|
||||
case (none[t]) {
|
||||
log_err "unresolved type variable";
|
||||
fail;
|
||||
*unresolved = some[int](vid);
|
||||
ret typ;
|
||||
}
|
||||
case (some[t](?rt)) {
|
||||
ret fold_ty(tcx, bind subst_vars(tcx, vb, _), rt);
|
||||
ret fold_ty(tcx,
|
||||
bind subst_vars(tcx, vb, unresolved, _), rt);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -2555,24 +2562,22 @@ mod unify {
|
||||
}
|
||||
}
|
||||
|
||||
// FIXME: Report errors better.
|
||||
ret fix_ok(fold_ty(tcx, bind subst_vars(tcx, vb, _), typ));
|
||||
auto unresolved = @mutable none[int];
|
||||
auto rty = fold_ty(tcx, bind subst_vars(tcx, vb, unresolved, _), typ);
|
||||
|
||||
auto ur = *unresolved;
|
||||
alt (ur) {
|
||||
case (none[int]) { ret fix_ok(rty); }
|
||||
case (some[int](?var_id)) { ret fix_err(var_id); }
|
||||
}
|
||||
}
|
||||
|
||||
fn resolve_type_var(&ty_ctxt tcx, &@var_bindings vb, int vid) -> t {
|
||||
fn resolve_type_var(&ty_ctxt tcx, &@var_bindings vb, int vid)
|
||||
-> fixup_result {
|
||||
auto root_id = ufind::find(vb.sets, vid as uint);
|
||||
alt (smallintmap::find[t](vb.types, root_id)) {
|
||||
case (none[t]) { ret mk_var(tcx, vid); }
|
||||
case (some[t](?rt)) {
|
||||
alt (fixup_vars(tcx, vb, rt)) {
|
||||
case (fix_ok(?rty)) { ret rty; }
|
||||
case (fix_err(_)) {
|
||||
// TODO: antisocial
|
||||
log_err "failed to resolve type var";
|
||||
fail;
|
||||
}
|
||||
}
|
||||
}
|
||||
case (none[t]) { ret fix_ok(mk_var(tcx, vid)); }
|
||||
case (some[t](?rt)) { ret fixup_vars(tcx, vb, rt); }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1387,11 +1387,8 @@ mod writeback {
|
||||
alt (ty::unify::fixup_vars(fcx.ccx.tcx, fcx.var_bindings, typ)) {
|
||||
case (fix_ok(?new_type)) { ret new_type; }
|
||||
case (fix_err(?vid)) {
|
||||
// TODO: We should try to do a variable ID -> local lookup if
|
||||
// we can and display this in terms of the local that had an
|
||||
// incomplete type.
|
||||
fcx.ccx.tcx.sess.span_err(sp, #fmt(
|
||||
"cannot determine type of variable ID `%d`", vid));
|
||||
fcx.ccx.tcx.sess.span_err(sp,
|
||||
"cannot determine a type for this expression");
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1434,11 +1431,19 @@ mod writeback {
|
||||
fn visit_decl_pre(@fn_ctxt fcx, &@ast::decl d) {
|
||||
alt (d.node) {
|
||||
case (ast::decl_local(?l)) {
|
||||
// FIXME: Report errors better.
|
||||
auto var_id = fcx.locals.get(l.id);
|
||||
auto lty = ty::unify::resolve_type_var(fcx.ccx.tcx,
|
||||
auto fix_rslt = ty::unify::resolve_type_var(fcx.ccx.tcx,
|
||||
fcx.var_bindings, var_id);
|
||||
write::ty_only(fcx.ccx.tcx, l.ann.id, lty);
|
||||
alt (fix_rslt) {
|
||||
case (fix_ok(?lty)) {
|
||||
write::ty_only(fcx.ccx.tcx, l.ann.id, lty);
|
||||
}
|
||||
case (fix_err(_)) {
|
||||
fcx.ccx.tcx.sess.span_err(d.span,
|
||||
"cannot determine a type for this local " +
|
||||
"variable");
|
||||
}
|
||||
}
|
||||
}
|
||||
case (_) { /* no-op */ }
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
// xfail-stage0
|
||||
|
||||
// error-pattern:Ambiguous type
|
||||
// error-pattern:cannot determine a type
|
||||
fn main() -> () {
|
||||
auto foo = [];
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user