@@ -237,6 +237,15 @@ fn maybe_append(mut lhs: Vec<Attribute>, rhs: Option<Vec<Attribute>>)
237237 lhs
238238}
239239
240+ #[ derive( PartialEq ) ]
241+ enum LastTokenKind {
242+ DocComment ,
243+ Comma ,
244+ Interpolated ,
245+ Eof ,
246+ Other ,
247+ }
248+
240249/* ident is handled by common.rs */
241250
242251pub struct Parser < ' a > {
@@ -248,10 +257,8 @@ pub struct Parser<'a> {
248257 /// the span of the prior token:
249258 pub last_span : Span ,
250259 pub cfg : CrateConfig ,
251- /// the previous token or None (only stashed sometimes).
252- pub last_token : Option < Box < token:: Token > > ,
253- last_token_interpolated : bool ,
254- last_token_eof : bool ,
260+ /// the previous token kind
261+ last_token_kind : LastTokenKind ,
255262 pub buffer : [ TokenAndSpan ; 4 ] ,
256263 pub buffer_start : isize ,
257264 pub buffer_end : isize ,
@@ -362,9 +369,7 @@ impl<'a> Parser<'a> {
362369 token : tok0. tok ,
363370 span : span,
364371 last_span : span,
365- last_token : None ,
366- last_token_interpolated : false ,
367- last_token_eof : false ,
372+ last_token_kind : LastTokenKind :: Other ,
368373 buffer : [
369374 placeholder. clone ( ) ,
370375 placeholder. clone ( ) ,
@@ -500,7 +505,7 @@ impl<'a> Parser<'a> {
500505 expr : PResult < ' a , P < Expr > > )
501506 -> PResult < ' a , ( Span , P < Expr > ) > {
502507 expr. map ( |e| {
503- if self . last_token_interpolated {
508+ if self . last_token_kind == LastTokenKind :: Interpolated {
504509 ( self . last_span , e)
505510 } else {
506511 ( e. span , e)
@@ -520,21 +525,19 @@ impl<'a> Parser<'a> {
520525 self . bug ( "ident interpolation not converted to real token" ) ;
521526 }
522527 _ => {
523- let last_token = self . last_token . clone ( ) . map ( |t| * t) ;
524- Err ( match last_token {
525- Some ( token:: DocComment ( _) ) => self . span_fatal_help ( self . last_span ,
528+ Err ( if self . last_token_kind == LastTokenKind :: DocComment {
529+ self . span_fatal_help ( self . last_span ,
526530 "found a documentation comment that doesn't document anything" ,
527531 "doc comments must come before what they document, maybe a comment was \
528- intended with `//`?") ,
529- _ => {
532+ intended with `//`?")
533+ } else {
530534 let mut err = self . fatal ( & format ! ( "expected identifier, found `{}`" ,
531535 self . this_token_to_string( ) ) ) ;
532536 if self . token == token:: Underscore {
533537 err. note ( "`_` is a wildcard pattern, not an identifier" ) ;
534538 }
535539 err
536- }
537- } )
540+ } )
538541 }
539542 }
540543 }
@@ -923,26 +926,22 @@ impl<'a> Parser<'a> {
923926
924927 /// Advance the parser by one token
925928 pub fn bump ( & mut self ) {
926- if self . last_token_eof {
929+ if self . last_token_kind == LastTokenKind :: Eof {
927930 // Bumping after EOF is a bad sign, usually an infinite loop.
928931 self . bug ( "attempted to bump the parser past EOF (may be stuck in a loop)" ) ;
929932 }
930933
931- if self . token == token:: Eof {
932- self . last_token_eof = true ;
933- }
934-
935934 self . last_span = self . span ;
936- // Stash token for error recovery (sometimes; clone is not necessarily cheap).
937- self . last_token = if self . token . is_ident ( ) ||
938- self . token . is_path ( ) ||
939- self . token . is_doc_comment ( ) ||
940- self . token == token :: Comma {
941- Some ( Box :: new ( self . token . clone ( ) ) )
942- } else {
943- None
935+
936+ // Record last token kind for possible error recovery.
937+ self . last_token_kind = match self . token {
938+ token:: DocComment ( .. ) => LastTokenKind :: DocComment ,
939+ token:: Comma => LastTokenKind :: Comma ,
940+ token :: Interpolated ( .. ) => LastTokenKind :: Interpolated ,
941+ token :: Eof => LastTokenKind :: Eof ,
942+ _ => LastTokenKind :: Other ,
944943 } ;
945- self . last_token_interpolated = self . token . is_interpolated ( ) ;
944+
946945 let next = if self . buffer_start == self . buffer_end {
947946 self . reader . real_token ( )
948947 } else {
@@ -979,11 +978,10 @@ impl<'a> Parser<'a> {
979978 lo : BytePos ,
980979 hi : BytePos ) {
981980 self . last_span = mk_sp ( self . span . lo , lo) ;
982- // It would be incorrect to just stash current token, but fortunately
983- // for tokens currently using `bump_with`, last_token will be of no
984- // use anyway.
985- self . last_token = None ;
986- self . last_token_interpolated = false ;
981+ // It would be incorrect to record the kind of the current token, but
982+ // fortunately for tokens currently using `bump_with`, the
983+ // last_token_kind will be of no use anyway.
984+ self . last_token_kind = LastTokenKind :: Other ;
987985 self . span = mk_sp ( lo, hi) ;
988986 self . token = next;
989987 self . expected_tokens . clear ( ) ;
@@ -2974,7 +2972,7 @@ impl<'a> Parser<'a> {
29742972 self . expected_tokens . push ( TokenType :: Operator ) ;
29752973 while let Some ( op) = AssocOp :: from_token ( & self . token ) {
29762974
2977- let lhs_span = if self . last_token_interpolated {
2975+ let lhs_span = if self . last_token_kind == LastTokenKind :: Interpolated {
29782976 self . last_span
29792977 } else {
29802978 lhs. span
@@ -4036,13 +4034,13 @@ impl<'a> Parser<'a> {
40364034 None => {
40374035 let unused_attrs = |attrs : & [ _ ] , s : & mut Self | {
40384036 if attrs. len ( ) > 0 {
4039- let last_token = s. last_token . clone ( ) . map ( |t| * t) ;
4040- match last_token {
4041- Some ( token:: DocComment ( _) ) => s. span_err_help ( s. last_span ,
4037+ if s. last_token_kind == LastTokenKind :: DocComment {
4038+ s. span_err_help ( s. last_span ,
40424039 "found a documentation comment that doesn't document anything" ,
40434040 "doc comments must come before what they document, maybe a \
4044- comment was intended with `//`?") ,
4045- _ => s. span_err ( s. span , "expected statement after outer attribute" ) ,
4041+ comment was intended with `//`?") ;
4042+ } else {
4043+ s. span_err ( s. span , "expected statement after outer attribute" ) ;
40464044 }
40474045 }
40484046 } ;
@@ -4332,9 +4330,7 @@ impl<'a> Parser<'a> {
43324330
43334331 let missing_comma = !lifetimes. is_empty ( ) &&
43344332 !self . token . is_like_gt ( ) &&
4335- self . last_token
4336- . as_ref ( ) . map_or ( true ,
4337- |x| & * * x != & token:: Comma ) ;
4333+ self . last_token_kind != LastTokenKind :: Comma ;
43384334
43394335 if missing_comma {
43404336
0 commit comments