@@ -86,7 +86,7 @@ use self::TokenTreeOrTokenTreeVec::*;
86
86
87
87
use ast:: Ident ;
88
88
use syntax_pos:: { self , BytePos , Span } ;
89
- use codemap:: Spanned ;
89
+ use codemap:: respan ;
90
90
use errors:: FatalError ;
91
91
use ext:: tt:: quoted:: { self , TokenTree } ;
92
92
use parse:: { Directory , ParseSess } ;
@@ -709,6 +709,15 @@ pub fn parse(
709
709
}
710
710
}
711
711
712
+ /// The token is an identifier, but not `_`.
713
+ /// We prohibit passing `_` to macros expecting `ident` for now.
714
+ fn get_macro_ident ( token : & Token ) -> Option < Ident > {
715
+ match * token {
716
+ token:: Ident ( ident) if ident. name != keywords:: Underscore . name ( ) => Some ( ident) ,
717
+ _ => None ,
718
+ }
719
+ }
720
+
712
721
/// Checks whether a non-terminal may begin with a particular token.
713
722
///
714
723
/// Returning `false` is a *stability guarantee* that such a matcher will *never* begin with that
@@ -725,7 +734,7 @@ fn may_begin_with(name: &str, token: &Token) -> bool {
725
734
match name {
726
735
"expr" => token. can_begin_expr ( ) ,
727
736
"ty" => token. can_begin_type ( ) ,
728
- "ident" => token. is_ident ( ) ,
737
+ "ident" => get_macro_ident ( token) . is_some ( ) ,
729
738
"vis" => match * token {
730
739
// The follow-set of :vis + "priv" keyword + interpolated
731
740
Token :: Comma | Token :: Ident ( _) | Token :: Interpolated ( _) => true ,
@@ -814,21 +823,14 @@ fn parse_nt<'a>(p: &mut Parser<'a>, sp: Span, name: &str) -> Nonterminal {
814
823
"expr" => token:: NtExpr ( panictry ! ( p. parse_expr( ) ) ) ,
815
824
"ty" => token:: NtTy ( panictry ! ( p. parse_ty( ) ) ) ,
816
825
// this could be handled like a token, since it is one
817
- "ident" => match p. token {
818
- token:: Ident ( sn) => {
819
- p. bump ( ) ;
820
- token:: NtIdent ( Spanned :: < Ident > {
821
- node : sn,
822
- span : p. prev_span ,
823
- } )
824
- }
825
- _ => {
826
- let token_str = pprust:: token_to_string ( & p. token ) ;
827
- p. fatal ( & format ! ( "expected ident, found {}" , & token_str[ ..] ) )
828
- . emit ( ) ;
829
- FatalError . raise ( )
830
- }
831
- } ,
826
+ "ident" => if let Some ( ident) = get_macro_ident ( & p. token ) {
827
+ p. bump ( ) ;
828
+ token:: NtIdent ( respan ( p. prev_span , ident) )
829
+ } else {
830
+ let token_str = pprust:: token_to_string ( & p. token ) ;
831
+ p. fatal ( & format ! ( "expected ident, found {}" , & token_str) ) . emit ( ) ;
832
+ FatalError . raise ( )
833
+ }
832
834
"path" => token:: NtPath ( panictry ! ( p. parse_path_common( PathStyle :: Type , false ) ) ) ,
833
835
"meta" => token:: NtMeta ( panictry ! ( p. parse_meta_item( ) ) ) ,
834
836
"vis" => token:: NtVis ( panictry ! ( p. parse_visibility( true ) ) ) ,
0 commit comments