diff options
author | John Hodge <tpg@mutabah.net> | 2016-02-27 09:47:04 +0800 |
---|---|---|
committer | John Hodge <tpg@mutabah.net> | 2016-02-27 09:47:04 +0800 |
commit | 3057d238db0d80286d77b9341fc6f84e594229c4 (patch) | |
tree | 0a377fbcdd643c327d6a3abea07ab396ff47ec80 | |
parent | 904a9eddbdd95f345e5ea6737a110cf657f5ddcf (diff) | |
download | mrust-3057d238db0d80286d77b9341fc6f84e594229c4.tar.gz |
Patterns - Clean up handling of ref/mut/ref mut
-rw-r--r-- | src/ast/pattern.hpp | 11 | ||||
-rw-r--r-- | src/convert/resolve.cpp | 2 | ||||
-rw-r--r-- | src/parse/pattern.cpp | 43 |
3 files changed, 49 insertions, 7 deletions
diff --git a/src/ast/pattern.hpp b/src/ast/pattern.hpp index ce4844f9..b844eba9 100644 --- a/src/ast/pattern.hpp +++ b/src/ast/pattern.hpp @@ -19,6 +19,11 @@ class Pattern: public Serialisable { public: + enum BindType { + BIND_MOVE, + BIND_REF, + BIND_MUTREF, + }; TAGGED_UNION(Data, Any, (MaybeBind, () ), (Macro, (unique_ptr<::AST::MacroInvocation> inv;) ), @@ -33,6 +38,8 @@ public: ); private: ::std::string m_binding; + BindType m_binding_type; + bool m_binding_mut; Data m_data; public: @@ -101,8 +108,10 @@ public: {} // Mutators - void set_bind(::std::string name, bool is_ref, bool is_mut) { + void set_bind(::std::string name, BindType type, bool is_mut) { m_binding = name; + m_binding_type = type; + m_binding_mut = is_mut; } ::std::unique_ptr<ExprNode> take_node() { diff --git a/src/convert/resolve.cpp b/src/convert/resolve.cpp index 5072f57f..20785af5 100644 --- a/src/convert/resolve.cpp +++ b/src/convert/resolve.cpp @@ -1630,7 +1630,7 @@ void CPathResolver::handle_pattern(AST::Pattern& pat, const TypeRef& type_hint) {
// It's a name binding (desugar to 'name @ _')
pat = AST::Pattern();
- pat.set_bind(name, false, false);
+ pat.set_bind(name, AST::Pattern::BIND_MOVE, false);
}
else
{
diff --git a/src/parse/pattern.cpp b/src/parse/pattern.cpp index 88abe196..c872cbaf 100644 --- a/src/parse/pattern.cpp +++ b/src/parse/pattern.cpp @@ -47,21 +47,33 @@ AST::Pattern Parse_Pattern(TokenStream& lex, bool is_refutable) } bool expect_bind = false; + ::AST::Pattern::BindType bind_type = AST::Pattern::BIND_MOVE; bool is_mut = false; - bool is_ref = false; // 1. Mutablity + Reference if( tok.type() == TOK_RWORD_REF ) { - is_ref = true; expect_bind = true; tok = lex.getToken(); + if( tok.type() == TOK_RWORD_MUT ) + { + bind_type = AST::Pattern::BIND_MUTREF; + GET_TOK(tok, lex); + } + else + { + bind_type = AST::Pattern::BIND_REF; + } } - if( tok.type() == TOK_RWORD_MUT ) + else if( tok.type() == TOK_RWORD_MUT ) { is_mut = true; expect_bind = true; tok = lex.getToken(); } + else + { + // Fall through + } ::std::string bind_name; // If a 'ref' or 'mut' annotation was seen, the next name must be a binding name @@ -133,7 +145,7 @@ AST::Pattern Parse_Pattern(TokenStream& lex, bool is_refutable) lex.putback(tok); AST::Pattern pat = Parse_PatternReal(lex, is_refutable); - pat.set_bind(bind_name, is_ref, is_mut); + pat.set_bind(bind_name, bind_type, is_mut); return ::std::move(pat); } @@ -326,11 +338,27 @@ AST::Pattern Parse_PatternStruct(TokenStream& lex, AST::Path path, bool is_refut } bool is_short_bind = false; + bool is_box = false; + AST::Pattern::BindType bind_type = AST::Pattern::BIND_MOVE; + bool is_mut = false; + if( tok.type() == TOK_RWORD_BOX ) { + is_box = true; + is_short_bind = true; + GET_TOK(tok, lex); + } if( tok.type() == TOK_RWORD_REF ) { is_short_bind = true; GET_TOK(tok, lex); + if( tok.type() == TOK_RWORD_MUT ) { + bind_type = AST::Pattern::BIND_MUTREF; + GET_TOK(tok, lex); + } + else { + bind_type = AST::Pattern::BIND_REF; + } } - if( tok.type() == TOK_RWORD_MUT ) { + else if( tok.type() == TOK_RWORD_MUT ) { + is_mut = true; is_short_bind = true; GET_TOK(tok, lex); } @@ -343,6 +371,11 @@ AST::Pattern Parse_PatternStruct(TokenStream& lex, AST::Path path, bool is_refut if( is_short_bind || tok.type() != TOK_COLON ) { lex.putback(tok); pat = AST::Pattern(AST::Pattern::TagBind(), field); + pat.set_bind(field, bind_type, is_mut); + if( is_box ) + { + pat = AST::Pattern(AST::Pattern::TagBox(), mv$(pat)); + } } else { CHECK_TOK(tok, TOK_COLON); |