summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/hir/from_ast.cpp2
-rw-r--r--src/hir/item_path.hpp14
-rw-r--r--src/hir/type.cpp4
-rw-r--r--src/hir/type.hpp1
-rw-r--r--src/hir_typeck/common.cpp2
-rw-r--r--src/hir_typeck/expr_cs.cpp8
-rw-r--r--src/hir_typeck/helpers.cpp73
-rw-r--r--src/hir_typeck/outer.cpp52
8 files changed, 107 insertions, 49 deletions
diff --git a/src/hir/from_ast.cpp b/src/hir/from_ast.cpp
index 78f6b683..af5e6118 100644
--- a/src/hir/from_ast.cpp
+++ b/src/hir/from_ast.cpp
@@ -749,7 +749,7 @@
}
// Leave `m_origin` until the bind pass
return ::HIR::TypeRef( ::HIR::TypeRef::Data::make_ErasedType(::HIR::TypeRef::Data::Data_ErasedType {
- ::HIR::Path(::HIR::SimplePath()),
+ ::HIR::Path(::HIR::SimplePath()), 0,
mv$(traits),
::HIR::LifetimeRef() // TODO: Lifetime ref
} ) );
diff --git a/src/hir/item_path.hpp b/src/hir/item_path.hpp
index 576c7755..9b579b72 100644
--- a/src/hir/item_path.hpp
+++ b/src/hir/item_path.hpp
@@ -48,6 +48,20 @@ public:
return ::HIR::SimplePath();
}
}
+ ::HIR::Path get_full_path() const {
+ assert(parent);
+ assert(name);
+
+ if( parent->name ) {
+ return get_simple_path();
+ }
+ else if( parent->trait ) {
+ return ::HIR::Path( parent->ty->clone(), ::HIR::GenericPath(parent->trait->clone(), parent->trait_params->clone()), ::std::string(name) );
+ }
+ else {
+ return ::HIR::Path( parent->ty->clone(), ::std::string(name) );
+ }
+ }
const char* get_name() const {
return name ? name : "";
}
diff --git a/src/hir/type.cpp b/src/hir/type.cpp
index e1d701ef..865607bc 100644
--- a/src/hir/type.cpp
+++ b/src/hir/type.cpp
@@ -119,7 +119,7 @@ void ::HIR::TypeRef::fmt(::std::ostream& os) const
}
if( e.m_lifetime.name != "" )
os << "+ '" << e.m_lifetime.name;
- os << "/*" << e.m_origin << "*/";
+ os << "/*" << e.m_origin << "#" << e.m_index << "*/";
),
(Array,
os << "[" << *e.inner << "; ";
@@ -786,7 +786,7 @@ bool ::HIR::TypeRef::match_test_generics(const Span& sp, const ::HIR::TypeRef& x
for(const auto& trait : e.m_traits)
traits.push_back( trait.clone() );
return ::HIR::TypeRef( Data::make_ErasedType({
- e.m_origin.clone(),
+ e.m_origin.clone(), e.m_index,
mv$(traits),
e.m_lifetime
}) );
diff --git a/src/hir/type.hpp b/src/hir/type.hpp
index 60ea04bd..653777db 100644
--- a/src/hir/type.hpp
+++ b/src/hir/type.hpp
@@ -141,6 +141,7 @@ public:
}),
(ErasedType, struct {
::HIR::Path m_origin;
+ unsigned int m_index;
::std::vector< ::HIR::TraitPath> m_traits;
::HIR::LifetimeRef m_lifetime;
}),
diff --git a/src/hir_typeck/common.cpp b/src/hir_typeck/common.cpp
index 8c902bd2..79e1095e 100644
--- a/src/hir_typeck/common.cpp
+++ b/src/hir_typeck/common.cpp
@@ -218,7 +218,7 @@ bool monomorphise_type_needed(const ::HIR::TypeRef& tpl)
traits.push_back( monomorphise_traitpath_with(sp, trait, callback, allow_infer) );
rv = ::HIR::TypeRef( ::HIR::TypeRef::Data::Data_ErasedType {
- mv$(origin),
+ mv$(origin), e.m_index,
mv$(traits),
e.m_lifetime
} );
diff --git a/src/hir_typeck/expr_cs.cpp b/src/hir_typeck/expr_cs.cpp
index 45de4850..2996a92a 100644
--- a/src/hir_typeck/expr_cs.cpp
+++ b/src/hir_typeck/expr_cs.cpp
@@ -2918,6 +2918,7 @@ namespace {
}
),
(ErasedType,
+ ASSERT_BUG(sp, e.m_origin != ::HIR::SimplePath(), "ErasedType " << ty << " wasn't bound to its origin");
check_type_resolved_path(sp, e.m_origin, top_type);
),
(Array,
@@ -3144,7 +3145,12 @@ void Context::equate_types(const Span& sp, const ::HIR::TypeRef& li, const ::HIR
// NOTE: Lifetime is ignored
),
(ErasedType,
- TODO(sp, "ErasedType");
+ ASSERT_BUG(sp, l_e.m_origin != ::HIR::SimplePath(), "ErasedType " << l_t << " wasn't bound to its origin");
+ ASSERT_BUG(sp, r_e.m_origin != ::HIR::SimplePath(), "ErasedType " << r_t << " wasn't bound to its origin");
+ // TODO: Ivar equate origin
+ if( l_e.m_origin != r_e.m_origin ) {
+ ERROR(sp, E0000, "Type mismatch between " << l_t << " and " << r_t << " - different source");
+ }
),
(Array,
this->equate_types(sp, *l_e.inner, *r_e.inner);
diff --git a/src/hir_typeck/helpers.cpp b/src/hir_typeck/helpers.cpp
index 48152b11..8eaf031c 100644
--- a/src/hir_typeck/helpers.cpp
+++ b/src/hir_typeck/helpers.cpp
@@ -340,6 +340,29 @@ void HMTypeInferrence::print_pathparams(::std::ostream& os, const ::HIR::PathPar
void HMTypeInferrence::expand_ivars(::HIR::TypeRef& type)
{
+ struct H {
+ static void expand_ivars_path(/*const*/ HMTypeInferrence& self, ::HIR::Path& path)
+ {
+ TU_MATCH(::HIR::Path::Data, (path.m_data), (e2),
+ (Generic,
+ self.expand_ivars_params(e2.m_params);
+ ),
+ (UfcsKnown,
+ self.expand_ivars(*e2.type);
+ self.expand_ivars_params(e2.trait.m_params);
+ self.expand_ivars_params(e2.params);
+ ),
+ (UfcsUnknown,
+ self.expand_ivars(*e2.type);
+ self.expand_ivars_params(e2.params);
+ ),
+ (UfcsInherent,
+ self.expand_ivars(*e2.type);
+ self.expand_ivars_params(e2.params);
+ )
+ )
+ }
+ };
TU_MATCH(::HIR::TypeRef::Data, (type.m_data), (e),
(Infer,
const auto& t = this->get_type(type);
@@ -353,24 +376,7 @@ void HMTypeInferrence::expand_ivars(::HIR::TypeRef& type)
),
(Path,
// Iterate all arguments
- TU_MATCH(::HIR::Path::Data, (e.path.m_data), (e2),
- (Generic,
- this->expand_ivars_params(e2.m_params);
- ),
- (UfcsKnown,
- this->expand_ivars(*e2.type);
- this->expand_ivars_params(e2.trait.m_params);
- this->expand_ivars_params(e2.params);
- ),
- (UfcsUnknown,
- this->expand_ivars(*e2.type);
- this->expand_ivars_params(e2.params);
- ),
- (UfcsInherent,
- this->expand_ivars(*e2.type);
- this->expand_ivars_params(e2.params);
- )
- )
+ H::expand_ivars_path(*this, e.path);
),
(Generic,
),
@@ -378,26 +384,15 @@ void HMTypeInferrence::expand_ivars(::HIR::TypeRef& type)
this->expand_ivars_params(e.m_trait.m_path.m_params);
for(auto& marker : e.m_markers)
this->expand_ivars_params(marker.m_params);
+ // TODO: Associated types
),
(ErasedType,
- TU_MATCH(::HIR::Path::Data, (e.m_origin.m_data), (e2),
- (Generic,
- this->expand_ivars_params(e2.m_params);
- ),
- (UfcsKnown,
- this->expand_ivars(*e2.type);
- this->expand_ivars_params(e2.trait.m_params);
- this->expand_ivars_params(e2.params);
- ),
- (UfcsUnknown,
- this->expand_ivars(*e2.type);
- this->expand_ivars_params(e2.params);
- ),
- (UfcsInherent,
- this->expand_ivars(*e2.type);
- this->expand_ivars_params(e2.params);
- )
- )
+ H::expand_ivars_path(*this, e.m_origin);
+ for(auto& trait : e.m_traits)
+ {
+ this->expand_ivars_params(trait.m_path.m_params);
+ // TODO: Associated types
+ }
),
(Array,
this->expand_ivars(*e.inner);
@@ -1498,7 +1493,11 @@ bool TraitResolution::has_associated_type(const ::HIR::TypeRef& input) const
return H::check_pathparams(r, e2.m_params);
),
(UfcsInherent,
- TODO(Span(), "Path - UfcsInherent - " << p);
+ if( r.has_associated_type(*e2.type) )
+ return true;
+ if( H::check_pathparams(r, e2.params) )
+ return true;
+ return false;
),
(UfcsKnown,
if( r.has_associated_type(*e2.type) )
diff --git a/src/hir_typeck/outer.cpp b/src/hir_typeck/outer.cpp
index 2ab0de6e..e16869bc 100644
--- a/src/hir_typeck/outer.cpp
+++ b/src/hir_typeck/outer.cpp
@@ -80,9 +80,14 @@ namespace {
::HIR::Crate& crate;
StaticTraitResolve m_resolve;
- const ::HIR::Trait* m_current_trait;
- const ::HIR::ItemPath* m_current_trait_path;
-
+ const ::HIR::Trait* m_current_trait = nullptr;
+ const ::HIR::ItemPath* m_current_trait_path = nullptr;
+
+
+ ::HIR::ItemPath* m_fcn_path = nullptr;
+ ::HIR::Function* m_fcn_ptr = nullptr;
+ unsigned int m_fcn_erased_count = 0;
+
::std::vector< ::HIR::TypeRef* > m_self_types;
typedef ::std::vector< ::std::pair< const ::HIR::SimplePath*, const ::HIR::Trait* > > t_trait_imports;
@@ -90,8 +95,7 @@ namespace {
public:
Visitor(::HIR::Crate& crate):
crate(crate),
- m_resolve(crate),
- m_current_trait(nullptr)
+ m_resolve(crate)
{
}
@@ -271,6 +275,29 @@ namespace {
)
)
)
+
+ // If an ErasedType is encountered, check if it has an origin set.
+ TU_IFLET(::HIR::TypeRef::Data, ty.m_data, ErasedType, e,
+ if( e.m_origin == ::HIR::SimplePath() )
+ {
+ // If not, ensure taht we're checking a function return type, and error if not
+ if( ! m_fcn_path )
+ ERROR(sp, E0000, "Use of an erased type outside of a function return - " << ty);
+
+ ::HIR::PathParams params;
+ for(unsigned int i = 0; i < m_fcn_ptr->m_params.m_types.size(); i ++)
+ params.m_types.push_back(::HIR::TypeRef(m_fcn_ptr->m_params.m_types[i].m_name, 256+i));
+ // Populate with function path
+ e.m_origin = m_fcn_path->get_full_path();
+ TU_MATCHA( (e.m_origin.m_data), (e2),
+ (Generic, e2.m_params = mv$(params); ),
+ (UfcsInherent, e2.params = mv$(params); ),
+ (UfcsKnown, e2.params = mv$(params); ),
+ (UfcsUnknown, throw ""; )
+ )
+ e.m_index = m_fcn_erased_count++;
+ }
+ )
}
void visit_generic_path(::HIR::GenericPath& p, PathContext pc) override
@@ -489,7 +516,7 @@ namespace {
public:
void visit_path(::HIR::Path& p, ::HIR::Visitor::PathContext pc) override
{
- assert(pc == ::HIR::Visitor::PathContext::TYPE);
+ //assert(pc == ::HIR::Visitor::PathContext::TYPE);
TU_MATCH(::HIR::Path::Data, (p.m_data), (e),
(Generic,
this->visit_generic_path(e, pc);
@@ -497,7 +524,7 @@ namespace {
(UfcsKnown,
this->visit_type(*e.type);
m_self_types.push_back(&*e.type);
- this->visit_generic_path(e.trait, ::HIR::Visitor::PathContext::TYPE);
+ this->visit_generic_path(e.trait, pc);
m_self_types.pop_back();
// TODO: Locate impl block and check parameters
),
@@ -600,6 +627,17 @@ namespace {
m_self_types.pop_back();
}
+
+ void visit_function(::HIR::ItemPath p, ::HIR::Function& item) override {
+
+ m_fcn_path = &p;
+ m_fcn_ptr = &item;
+ m_fcn_erased_count = 0;
+ visit_type(item.m_return);
+ m_fcn_path = nullptr;
+
+ ::HIR::Visitor::visit_function(p, item);
+ }
};
}