summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/parse/common.hpp1
-rw-r--r--src/parse/root.cpp86
-rw-r--r--src/parse/types.cpp8
3 files changed, 48 insertions, 47 deletions
diff --git a/src/parse/common.hpp b/src/parse/common.hpp
index aa6e8c3d..7bf41d22 100644
--- a/src/parse/common.hpp
+++ b/src/parse/common.hpp
@@ -39,6 +39,7 @@ extern ::std::vector<AST::PathNode> Parse_PathNodes(TokenStream& lex, eParsePath
extern AST::PathParams Parse_Path_GenericList(TokenStream& lex);
+extern ::std::vector< ::std::string> Parse_HRB(TokenStream& lex);
extern AST::MetaItem Parse_MetaItem(TokenStream& lex);
extern ::AST::MacroInvocation Parse_MacroInvocation(ProtoSpan ps, ::std::string name, TokenStream& lex);
extern TypeRef Parse_Type(TokenStream& lex, bool allow_trait_list = true);
diff --git a/src/parse/root.cpp b/src/parse/root.cpp
index 4da47cbe..feb5d37a 100644
--- a/src/parse/root.cpp
+++ b/src/parse/root.cpp
@@ -48,7 +48,18 @@ void Parse_ModRoot(TokenStream& lex, AST::Module& mod, AST::MetaItems& mod_attrs
::std::vector< ::std::string> lifetimes;
GET_CHECK_TOK(tok, lex, TOK_LT);
do {
- switch(GET_TOK(tok, lex))
+ GET_TOK(tok, lex);
+
+ ::AST::MetaItems attrs;
+ while(tok.type() == TOK_ATTR_OPEN)
+ {
+ attrs.push_back( Parse_MetaItem(lex) );
+ GET_CHECK_TOK(tok, lex, TOK_SQUARE_CLOSE);
+ GET_TOK(tok, lex);
+ }
+ (void)attrs; // TODO: Attributes on generic params
+
+ switch(tok.type())
{
case TOK_LIFETIME:
lifetimes.push_back(tok.str());
@@ -68,6 +79,7 @@ void Parse_TypeBound(TokenStream& lex, AST::GenericParams& ret, TypeRef checked_
do
{
+ ::std::vector< ::std::string> hrls;
if(GET_TOK(tok, lex) == TOK_LIFETIME) {
ret.add_bound(AST::GenericBound::make_TypeLifetime( {
checked_type.clone(), tok.str()
@@ -81,22 +93,12 @@ void Parse_TypeBound(TokenStream& lex, AST::GenericParams& ret, TypeRef checked_
else {
if( tok.type() == TOK_RWORD_FOR )
{
- GET_CHECK_TOK(tok, lex, TOK_LT);
- do {
- switch(GET_TOK(tok, lex))
- {
- case TOK_LIFETIME:
- lifetimes.push_back(tok.str());
- break;
- default:
- throw ParseError::Unexpected(lex, tok, Token(TOK_LIFETIME));
- }
- } while( GET_TOK(tok, lex) == TOK_COMMA );
- CHECK_TOK(tok, TOK_GT);
+ hrls = Parse_HRB(lex);
}
else {
PUTBACK(tok, lex);
}
+ (void)hrls; // TODO: HRLs
ret.add_bound( AST::GenericBound::make_IsTrait({
checked_type.clone(), mv$(lifetimes), Parse_Path(lex, PATH_GENERIC_TYPE)
@@ -114,48 +116,52 @@ AST::GenericParams Parse_GenericParams(TokenStream& lex)
AST::GenericParams ret;
Token tok;
do {
- bool is_lifetime = false;
if( GET_TOK(tok, lex) == TOK_GT ) {
break ;
}
- switch( tok.type() )
+
+ ::AST::MetaItems attrs;
+ while(tok.type() == TOK_ATTR_OPEN)
{
- case TOK_IDENT:
- break;
- case TOK_LIFETIME:
- is_lifetime = true;
- break;
- default:
- // Oopsie!
- throw ParseError::Unexpected(lex, tok);
+ attrs.push_back( Parse_MetaItem(lex) );
+ GET_CHECK_TOK(tok, lex, TOK_SQUARE_CLOSE);
+ GET_TOK(tok, lex);
}
- ::std::string param_name = tok.str();
- if( is_lifetime )
- ret.add_lft_param( param_name );
- else
- ret.add_ty_param( AST::TypeParam( param_name ) );
- auto param_ty = TypeRef(lex.getPosition(), param_name);
+ (void)attrs; // TODO: Attributes on generic params
- if( GET_TOK(tok, lex) == TOK_COLON )
+ if( tok.type() == TOK_IDENT )
{
- if( is_lifetime )
+ ::std::string param_name = tok.str();
+ ret.add_ty_param( AST::TypeParam( param_name ) );
+
+ auto param_ty = TypeRef(lex.getPosition(), param_name);
+ if( GET_TOK(tok, lex) == TOK_COLON )
+ {
+ Parse_TypeBound(lex, ret, param_ty);
+ GET_TOK(tok, lex);
+ }
+
+ if( tok.type() == TOK_EQUAL )
+ {
+ ret.ty_params().back().setDefault( Parse_Type(lex) );
+ GET_TOK(tok, lex);
+ }
+ }
+ else if( tok.type() == TOK_LIFETIME )
+ {
+ ::std::string param_name = tok.str();
+ ret.add_lft_param( param_name );
+ if( GET_TOK(tok, lex) == TOK_COLON )
{
do {
GET_CHECK_TOK(tok, lex, TOK_LIFETIME);
ret.add_bound(AST::GenericBound::make_Lifetime( {param_name, tok.str()} ));
} while( GET_TOK(tok, lex) == TOK_PLUS );
}
- else
- {
- Parse_TypeBound(lex, ret, param_ty);
- GET_TOK(tok, lex);
- }
}
-
- if( !is_lifetime && tok.type() == TOK_EQUAL )
+ else
{
- ret.ty_params().back().setDefault( Parse_Type(lex) );
- GET_TOK(tok, lex);
+ throw ParseError::Unexpected(lex, tok, {TOK_IDENT, TOK_LIFETIME});
}
} while( tok.type() == TOK_COMMA );
PUTBACK(tok, lex);
diff --git a/src/parse/types.cpp b/src/parse/types.cpp
index 4b0fe46d..fabb13bc 100644
--- a/src/parse/types.cpp
+++ b/src/parse/types.cpp
@@ -67,13 +67,7 @@ TypeRef Parse_Type_Int(TokenStream& lex, bool allow_trait_list)
}
//
case TOK_RWORD_FOR: {
- GET_CHECK_TOK(tok, lex, TOK_LT);
- ::std::vector<::std::string> hrls;
- do {
- GET_CHECK_TOK(tok, lex, TOK_LIFETIME);
- hrls.push_back( mv$(tok.str()) );
- } while( GET_TOK(tok, lex) == TOK_COMMA );
- CHECK_TOK(tok, TOK_GT);
+ auto hrls = Parse_HRB(lex);
switch(LOOK_AHEAD(lex))
{
case TOK_RWORD_UNSAFE: