diff options
author | John Hodge <tpg@mutabah.net> | 2016-07-25 20:39:54 +0800 |
---|---|---|
committer | John Hodge <tpg@mutabah.net> | 2016-07-25 20:39:54 +0800 |
commit | 9693673fa336ddf9c29bd0a6bf1ce2853a9ddab1 (patch) | |
tree | 158088e3a80d48aeca5243c0bd72b85fe2b18e0d /src | |
parent | 717e518629c7e4b7a4c5db4a1b4a520bc217e5ee (diff) | |
download | mrust-9693673fa336ddf9c29bd0a6bf1ce2853a9ddab1.tar.gz |
HIR Typecheck - Slowly fixing up with impl specialisation
Diffstat (limited to 'src')
-rw-r--r-- | src/hir_typeck/expr_cs.cpp | 13 | ||||
-rw-r--r-- | src/hir_typeck/helpers.cpp | 28 | ||||
-rw-r--r-- | src/hir_typeck/static.cpp | 5 |
3 files changed, 31 insertions, 15 deletions
diff --git a/src/hir_typeck/expr_cs.cpp b/src/hir_typeck/expr_cs.cpp index c420b388..243f4cfc 100644 --- a/src/hir_typeck/expr_cs.cpp +++ b/src/hir_typeck/expr_cs.cpp @@ -3010,10 +3010,15 @@ namespace { DEBUG("Searching for impl " << v.trait << v.params << " for " << context.m_ivars.fmt_type(v.impl_ty)); bool found = context.m_resolve.find_trait_impls(sp, v.trait, v.params, v.impl_ty, [&](auto impl, auto cmp) { - ::HIR::TypeRef out_ty_o = impl.get_type(v.name.c_str()); - if( v.name != "" && out_ty_o == ::HIR::TypeRef() ) { - auto ty1 = ::HIR::TypeRef( ::HIR::Path(::HIR::Path( v.impl_ty.clone(), ::HIR::GenericPath(v.trait, v.params.clone()), v.name, ::HIR::PathParams() )) ); - out_ty_o = context.m_resolve.expand_associated_types(sp, mv$(ty1)); + DEBUG("Found " << impl); + ::HIR::TypeRef out_ty_o; + if( v.name != "" ) { + out_ty_o = impl.get_type(v.name.c_str()); + if( out_ty_o == ::HIR::TypeRef() ) + { + auto ty1 = ::HIR::TypeRef( ::HIR::Path(::HIR::Path( v.impl_ty.clone(), ::HIR::GenericPath(v.trait, v.params.clone()), v.name, ::HIR::PathParams() )) ); + out_ty_o = context.m_resolve.expand_associated_types(sp, mv$(ty1)); + } //BUG(sp, "Getting associated type '" << v.name << "' which isn't in " << v.trait << " (" << ty << ")"); } const auto& out_ty = (v.name == "" ? v.left_ty : out_ty_o); diff --git a/src/hir_typeck/helpers.cpp b/src/hir_typeck/helpers.cpp index 748559b3..ca30e583 100644 --- a/src/hir_typeck/helpers.cpp +++ b/src/hir_typeck/helpers.cpp @@ -1098,21 +1098,28 @@ bool TraitResolution::find_trait_impls(const Span& sp, const auto& trait_fn = this->m_crate.get_lang_item_path(sp, "fn"); const auto& trait_fn_mut = this->m_crate.get_lang_item_path(sp, "fn_mut"); const auto& trait_fn_once = this->m_crate.get_lang_item_path(sp, "fn_once"); - + // Closures are magical. They're unnamable and all trait impls come from within the compiler TU_IFLET(::HIR::TypeRef::Data, type.m_data, Closure, e, + DEBUG("Closure, "<< trait <<" " << trait_fn << " " << trait_fn_mut << " " << trait_fn_once); if( trait == trait_fn || trait == trait_fn_mut || trait == trait_fn_once ) { if( params.m_types.size() != 1 ) BUG(sp, "Fn* traits require a single tuple argument"); - TU_MATCH_DEF( ::HIR::TypeRef::Data, (params.m_types[0].m_data), (te), - ( - ), - (Tuple, - ) - ) + if( !params.m_types[0].m_data.is_Tuple() ) + BUG(sp, "Fn* traits require a single tuple argument"); + + const auto& args_des = params.m_types[0].m_data.as_Tuple(); + if( args_des.size() != e.m_arg_types.size() ) { + return false; + } + + auto cmp = ::HIR::Compare::Equal; ::std::vector< ::HIR::TypeRef> args; - for(const auto& at : e.m_arg_types) { + for(unsigned int i = 0; i < e.m_arg_types.size(); i ++) + { + const auto& at = e.m_arg_types[i]; args.push_back( at.clone() ); + cmp &= at.compare_with_placeholders(sp, args_des[i], this->m_ivars.callback_resolve_infer()); } // NOTE: This is a conditional "true", we know nothing about the move/mut-ness of this closure yet @@ -1123,7 +1130,7 @@ bool TraitResolution::find_trait_impls(const Span& sp, pp.m_types.push_back( ::HIR::TypeRef(mv$(args)) ); ::std::map< ::std::string, ::HIR::TypeRef> types; types.insert( ::std::make_pair( "Output", e.m_rettype->clone() ) ); - return callback( ImplRef(type.clone(), mv$(pp), mv$(types)), ::HIR::Compare::Equal ); + return callback( ImplRef(type.clone(), mv$(pp), mv$(types)), cmp ); } else { return false; @@ -1494,6 +1501,7 @@ bool TraitResolution::has_associated_type(const ::HIR::TypeRef& input) const BUG(sp, "Cannot find associated type " << pe.item << " anywhere in trait " << pe.trait); //pe.trait = mv$(trait_path); + DEBUG("Searching for impl"); rv = this->find_trait_impls_crate(sp, trait_path.m_path, trait_path.m_params, *pe.type, [&](auto impl, auto qual) { DEBUG("Found " << impl); auto ty = impl.get_type( pe.item.c_str() ); @@ -1853,7 +1861,7 @@ bool TraitResolution::find_trait_impls_crate(const Span& sp, ty_p = &tmp; } else { - ty_p = &tmp; + ty_p = &this->m_ivars.get_type(tmp); } const auto& ty = *ty_p; DEBUG(" - Compare " << ty << " and " << assoc_bound.second << ", matching generics"); diff --git a/src/hir_typeck/static.cpp b/src/hir_typeck/static.cpp index df344c79..0224fb17 100644 --- a/src/hir_typeck/static.cpp +++ b/src/hir_typeck/static.cpp @@ -684,7 +684,10 @@ bool ImplRef::type_is_specializable(const char* name) const } ), (BoundedPtr, - TODO(Span(), name << " - " << *this); + auto it = e.assoc->find(name); + if(it == e.assoc->end()) + return ::HIR::TypeRef(); + return it->second.clone(); ), (Bounded, auto it = e.assoc.find(name); |