diff options
author | John Hodge <tpg@mutabah.net> | 2016-06-26 17:42:42 +0800 |
---|---|---|
committer | John Hodge <tpg@mutabah.net> | 2016-06-26 17:42:42 +0800 |
commit | 7be1b3aeb885bb020faddb3b390a49d6d6f206d5 (patch) | |
tree | 006b8aa15ab5ea909ec7e4c6030c4f1a734e039f /src | |
parent | e9714fa625e02047d50d56fdd8c665742a443c73 (diff) | |
download | mrust-7be1b3aeb885bb020faddb3b390a49d6d6f206d5.tar.gz |
HIR Typecheck - Hacking to pieces
Diffstat (limited to 'src')
-rw-r--r-- | src/hir/expr.hpp | 56 | ||||
-rw-r--r-- | src/hir_typeck/expr.cpp | 41 | ||||
-rw-r--r-- | src/hir_typeck/expr_context.cpp | 3 |
3 files changed, 85 insertions, 15 deletions
diff --git a/src/hir/expr.hpp b/src/hir/expr.hpp index 7e43e206..65e5bb0d 100644 --- a/src/hir/expr.hpp +++ b/src/hir/expr.hpp @@ -166,6 +166,25 @@ struct ExprNode_Assign: And, Or , Xor, Shr, Shl, }; + static const char* opname(Op v) { + switch(v) + { + case Op::None: return ""; + case Op::Add: return "+"; + case Op::Sub: return "-"; + case Op::Mul: return "*"; + case Op::Div: return "/"; + case Op::Mod: return "%"; + + case Op::And: return "&"; + case Op::Or: return "|"; + case Op::Xor: return "^"; + + case Op::Shr: return ">>"; + case Op::Shl: return "<<"; + } + throw ""; + } Op m_op; ExprNodeP m_slot; @@ -199,6 +218,34 @@ struct ExprNode_BinOp: And, Or , Xor, Shr, Shl, }; + static const char* opname(Op v) { + switch(v) + { + case Op::CmpEqu: return "=="; + case Op::CmpNEqu: return "!="; + case Op::CmpLt: return "<"; + case Op::CmpLtE: return "<="; + case Op::CmpGt: return ">"; + case Op::CmpGtE: return ">="; + + case Op::BoolAnd: return "&&"; + case Op::BoolOr: return "||"; + + case Op::Add: return "+"; + case Op::Sub: return "-"; + case Op::Mul: return "*"; + case Op::Div: return "/"; + case Op::Mod: return "%"; + + case Op::And: return "&"; + case Op::Or: return "|"; + case Op::Xor: return "^"; + + case Op::Shr: return ">>"; + case Op::Shl: return "<<"; + } + return "??"; + } Op m_op; ::HIR::ExprNodeP m_left; @@ -234,6 +281,15 @@ struct ExprNode_UniOp: Invert, // '!<expr>' Negate, // '-<expr>' }; + static const char* opname(Op v) { + switch(v) { + case Op::Ref: return "&"; + case Op::RefMut:return "&mut"; + case Op::Invert:return "!"; + case Op::Negate:return "-"; + } + throw ""; + } Op m_op; ::HIR::ExprNodeP m_value; diff --git a/src/hir_typeck/expr.cpp b/src/hir_typeck/expr.cpp index 1dc09dce..2a0d7b60 100644 --- a/src/hir_typeck/expr.cpp +++ b/src/hir_typeck/expr.cpp @@ -421,8 +421,9 @@ namespace typeck { this->context.add_ivars( node.m_true->m_res_type ); if( node.m_false ) { this->context.add_ivars( node.m_false->m_res_type ); - this->context.apply_equality(node.span(), node.m_res_type, node.m_true->m_res_type, &node.m_true); - this->context.apply_equality(node.span(), node.m_res_type, node.m_false->m_res_type, &node.m_false); + // NOTE: Removed to work around type inferrence failure in libcore/slice.rs + //this->context.apply_equality(node.span(), node.m_res_type, node.m_true->m_res_type, &node.m_true); + //this->context.apply_equality(node.span(), node.m_res_type, node.m_false->m_res_type, &node.m_false); } else { this->context.apply_equality(node.span(), node.m_res_type, ::HIR::TypeRef::new_unit()); @@ -645,16 +646,19 @@ namespace typeck { // - Assign: both sides equal void visit(::HIR::ExprNode_Assign& node) override { - TRACE_FUNCTION_F("... = ..."); - ::HIR::ExprVisitorDef::visit(node); + TRACE_FUNCTION_F("... "<<::HIR::ExprNode_Assign::opname(node.m_op)<<"= ..."); // Plain assignment can't be overloaded, requires equal types if( node.m_op == ::HIR::ExprNode_Assign::Op::None ) { this->context.apply_equality(node.span(), node.m_slot->m_res_type, node.m_value->m_res_type, &node.m_value ); + + ::HIR::ExprVisitorDef::visit(node); } else { + ::HIR::ExprVisitorDef::visit(node); + const auto& ty_left = this->context.get_type(node.m_slot->m_res_type ); const auto& ty_right = this->context.get_type(node.m_value->m_res_type); @@ -694,24 +698,33 @@ namespace typeck { trait_path_pp.m_types.push_back( ty_right.clone() ); - /*bool rv =*/ this->context.find_trait_impls(node.span(), trait_path,trait_path_pp, ty_left, [&](const auto& args, const auto& a_types) { + unsigned int count = 0; + bool rv = this->context.find_trait_impls(node.span(), trait_path,trait_path_pp, ty_left, [&](const auto& args, const auto& a_types) { assert( args.m_types.size() == 1 ); const auto& impl_right = args.m_types[0]; - + TODO(node.span(), "Check " << impl_right << " vs " << ty_right); - //auto cmp = impl_index.compare_with_placeholders(node.span(), index_ty, this->context.callback_resolve_infer()); - //if( cmp == ::HIR::Compare::Unequal) - // return false; - //if( cmp == ::HIR::Compare::Equal ) { - // return true; - //} + auto cmp = impl_right.compare_with_placeholders(node.span(), ty_right, this->context.callback_resolve_infer()); + if( cmp == ::HIR::Compare::Unequal) + return false; + count += 1; + if( cmp == ::HIR::Compare::Equal ) { + return true; + } //DEBUG("TODO: Handle fuzzy match index operator " << impl_index); return false; }); this->context.dump(); TODO(node.span(), "Search for implementation of " << trait_path << "<" << ty_right << "> for " << ty_left); + + if( rv ) { + } + else if( count > 0 ) { + } + else { + } } else { } @@ -726,7 +739,7 @@ namespace typeck { const auto& ty_right = this->context.get_type(node.m_right->m_res_type); const auto& ty_res = this->context.get_type(node.m_res_type); - TRACE_FUNCTION_FR("BinOp " << ty_left << " <> " << ty_right << " = " << ty_res, "BinOp"); + TRACE_FUNCTION_FR("... {"<<ty_left<<"} "<<::HIR::ExprNode_BinOp::opname(node.m_op)<<" ...{"<<ty_right<<"}", "BinOp"); // Boolean ops can't be overloaded, and require `bool` on both sides if( node.m_op == ::HIR::ExprNode_BinOp::Op::BoolAnd || node.m_op == ::HIR::ExprNode_BinOp::Op::BoolOr ) @@ -1072,6 +1085,7 @@ namespace typeck { // - UniOp: Look for overload or primitive void visit(::HIR::ExprNode_UniOp& node) override { + TRACE_FUNCTION_F(::HIR::ExprNode_UniOp::opname(node.m_op) << "..."); ::HIR::ExprVisitorDef::visit(node); const auto& ty = this->context.get_type(node.m_value->m_res_type); @@ -1193,7 +1207,6 @@ namespace typeck { ) ) ) - // TODO: Check cast validity and do inferrence ::HIR::ExprVisitorDef::visit(node); } // - Index: Look for implementation of the Index trait diff --git a/src/hir_typeck/expr_context.cpp b/src/hir_typeck/expr_context.cpp index 0bef9445..e424d08a 100644 --- a/src/hir_typeck/expr_context.cpp +++ b/src/hir_typeck/expr_context.cpp @@ -1972,11 +1972,12 @@ bool typeck::TypecheckContext::find_trait_impls_crate(const Span& sp, } }; assert( impl.m_trait_args.m_types.size() == params.m_types.size() ); + // TODO: Use a fuzzy-able generic match fail |= !impl.m_type.match_test_generics(sp, type , this->callback_resolve_infer(), cb); for(unsigned int i = 0; i < impl.m_trait_args.m_types.size(); i ++) fail |= !impl.m_trait_args.m_types[i].match_test_generics(sp, params.m_types[i], this->callback_resolve_infer(), cb); if( fail ) { - DEBUG("- Failed to match"); + DEBUG("- Failed to match parameters - " << impl.m_trait_args << " != " << params); return false; } for(const auto& ty : impl_params) |