diff --git a/check/src/substitution.rs b/check/src/substitution.rs index efa8fe69e2..9c11bd9917 100644 --- a/check/src/substitution.rs +++ b/check/src/substitution.rs @@ -4,11 +4,9 @@ use std::fmt; use union_find::{QuickFindUf, Union, UnionByRank, UnionFind, UnionResult}; -use base::fnv::FnvMap; use base::fixed::{FixedMap, FixedVec}; use base::types; use base::types::{ArcType, Type, Walker}; -use base::symbol::Symbol; #[derive(Debug, PartialEq)] pub enum Error { @@ -29,8 +27,6 @@ where } } -use typecheck::unroll_typ; - pub struct Substitution where T: Substitutable, @@ -338,63 +334,6 @@ pub fn is_variable_unified(subs: &Substitution, var: &ArcType) -> bool } } -impl Substitution { - fn replace_variable_(&self, typ: &Type) -> Option { - match *typ { - Type::Variable(ref id) => self.find_type_for_var(id.id).cloned(), - _ => None, - } - } - - pub fn set_type(&self, t: ArcType) -> ArcType { - self.set_type_(&t).unwrap_or(t) - } - fn set_type_(&self, typ: &ArcType) -> Option { - match **typ { - Type::Forall(ref params, ref typ, Some(ref vars)) => { - let subs = self; - let mut named_variables: FnvMap<_, _> = params - .iter() - .zip(vars) - .filter(|&(_, var)| is_variable_unified(subs, var)) - .map(|(param, var)| (param.id.clone(), var.clone())) - .collect(); - let typ = typ.instantiate_generics(&mut named_variables); - self.set_type_(&typ).map(|typ| { - if params.len() != named_variables.len() { - let mut new_params = Vec::new(); - let mut new_vars = Vec::new(); - for (param, var) in params.iter().zip(vars) { - if !is_variable_unified(subs, var) { - new_params.push(param.clone()); - new_vars.push(var.clone()); - } - } - ArcType::from(Type::Forall(new_params, typ, Some(new_vars))) - } else { - typ - } - }) - } - Type::Variable(_) => { - let replacement = self.replace_variable_(typ); - let result = { - let mut typ = typ; - if let Some(ref t) = replacement { - typ = t; - } - unroll_typ(typ) - }; - result.or(replacement) - } - _ => types::walk_move_type_opt( - typ, - &mut types::ControlVisitation(|typ: &ArcType| self.set_type_(typ)), - ), - } - } -} - impl Substitution { pub fn make_real(&self, typ: &mut T) { *typ = self.real(typ).clone(); diff --git a/check/src/typecheck.rs b/check/src/typecheck.rs index 15e5564706..1e3e36e9ac 100644 --- a/check/src/typecheck.rs +++ b/check/src/typecheck.rs @@ -387,8 +387,6 @@ impl<'a> Typecheck<'a> { fn find(&mut self, id: &Symbol) -> TcResult { match self.environment.find_type(id).map(ArcType::clone) { Some(typ) => { - let typ = self.subs.set_type(typ); - self.named_variables.clear(); let typ = new_skolem_scope(&self.subs, &typ); debug!("Find {} : {}", self.symbols.string(id), typ); @@ -2234,7 +2232,7 @@ impl<'a> Typecheck<'a> { span: Span, level: u32, expected: &ArcType, - mut actual: ArcType, + actual: ArcType, ) -> ArcType { debug!("Merge {} : {}", expected, actual); let expected = self.skolemize(&expected); @@ -2247,16 +2245,13 @@ impl<'a> Typecheck<'a> { &expected, &actual, ) { - Ok(typ) => self.subs.set_type(typ), + Ok(typ) => typ, Err(errors) => { - let mut expected = expected.clone(); - expected = self.subs.set_type(expected); - actual = self.subs.set_type(actual); debug!( "Error '{:?}' between:\n>> {}\n>> {}", errors, expected, actual ); - let err = TypeError::Unification(expected, actual, apply_subs(&self.subs, errors)); + let err = TypeError::Unification(expected, actual, errors.into()); self.errors.push(Spanned { span: span, // TODO Help what caused this unification failure @@ -2281,23 +2276,20 @@ impl<'a> Typecheck<'a> { } } - fn unify(&self, expected: &ArcType, mut actual: ArcType) -> TcResult { + fn unify(&self, expected: &ArcType, actual: ArcType) -> TcResult { debug!("Unify start {} <=> {}", expected, actual); let state = unify_type::State::new(&self.environment, &self.subs); match unify::unify(&self.subs, state, expected, &actual) { - Ok(typ) => Ok(self.subs.set_type(typ)), + Ok(typ) => Ok(typ), Err(errors) => { - let mut expected = expected.clone(); - expected = self.subs.set_type(expected); - actual = self.subs.set_type(actual); debug!( "Error '{:?}' between:\n>> {}\n>> {}", errors, expected, actual ); Err(TypeError::Unification( - expected, + expected.clone(), actual, - apply_subs(&self.subs, errors), + errors.into(), )) } } @@ -2373,27 +2365,6 @@ fn with_pattern_types( } } -fn apply_subs( - subs: &Substitution, - errors: Errors>, -) -> Vec> { - use unify::Error::*; - errors - .into_iter() - .map(|error| match error { - TypeMismatch(expected, actual) => { - TypeMismatch(subs.set_type(expected), subs.set_type(actual)) - } - Substitution(err) => Substitution(match err { - substitution::Error::Occurs(var, typ) => { - substitution::Error::Occurs(var, subs.set_type(typ)) - } - }), - Other(err) => Other(err), - }) - .collect() -} - pub fn extract_generics(args: &[ArcType]) -> Vec> { args.iter() .map(|arg| match **arg {