@@ -91,24 +91,29 @@ impl<'a> Parser<'a> {
91
91
self . parse_expr_res ( Restrictions :: empty ( ) , None )
92
92
}
93
93
94
+ fn parse_expr_catch_underscore ( & mut self ) -> PResult < ' a , P < Expr > > {
95
+ match self . parse_expr ( ) {
96
+ Ok ( expr) => Ok ( expr) ,
97
+ Err ( mut err) => match self . token . kind {
98
+ token:: Ident ( name, false )
99
+ if name == kw:: Underscore && self . look_ahead ( 1 , |t| {
100
+ t == & token:: Comma
101
+ } ) => {
102
+ // Special-case handling of `foo(_, _, _)`
103
+ err. emit ( ) ;
104
+ let sp = self . token . span ;
105
+ self . bump ( ) ;
106
+ Ok ( self . mk_expr ( sp, ExprKind :: Err , ThinVec :: new ( ) ) )
107
+ }
108
+ _ => Err ( err) ,
109
+ } ,
110
+ }
111
+ }
112
+
113
+ /// Parses a sequence of expressions bounded by parentheses.
94
114
fn parse_paren_expr_seq ( & mut self ) -> PResult < ' a , Vec < P < Expr > > > {
95
115
self . parse_paren_comma_seq ( |p| {
96
- match p. parse_expr ( ) {
97
- Ok ( expr) => Ok ( expr) ,
98
- Err ( mut err) => match p. token . kind {
99
- token:: Ident ( name, false )
100
- if name == kw:: Underscore && p. look_ahead ( 1 , |t| {
101
- t == & token:: Comma
102
- } ) => {
103
- // Special-case handling of `foo(_, _, _)`
104
- err. emit ( ) ;
105
- let sp = p. token . span ;
106
- p. bump ( ) ;
107
- Ok ( p. mk_expr ( sp, ExprKind :: Err , ThinVec :: new ( ) ) )
108
- }
109
- _ => Err ( err) ,
110
- } ,
111
- }
116
+ p. parse_expr_catch_underscore ( )
112
117
} ) . map ( |( r, _) | r)
113
118
}
114
119
@@ -845,51 +850,25 @@ impl<'a> Parser<'a> {
845
850
parse_lit ! ( )
846
851
}
847
852
token:: OpenDelim ( token:: Paren ) => {
848
- self . bump ( ) ;
849
-
850
- attrs. extend ( self . parse_inner_attributes ( ) ?) ;
851
-
852
- // `(e)` is parenthesized `e`.
853
- // `(e,)` is a tuple with only one field, `e`.
854
- let mut es = vec ! [ ] ;
855
- let mut trailing_comma = false ;
856
- let mut recovered = false ;
857
- while self . token != token:: CloseDelim ( token:: Paren ) {
858
- es. push ( match self . parse_expr ( ) {
859
- Ok ( es) => es,
860
- Err ( mut err) => {
861
- // Recover from parse error in tuple list.
862
- match self . token . kind {
863
- token:: Ident ( name, false )
864
- if name == kw:: Underscore && self . look_ahead ( 1 , |t| {
865
- t == & token:: Comma
866
- } ) => {
867
- // Special-case handling of `Foo<(_, _, _)>`
868
- err. emit ( ) ;
869
- let sp = self . token . span ;
870
- self . bump ( ) ;
871
- self . mk_expr ( sp, ExprKind :: Err , ThinVec :: new ( ) )
872
- }
873
- _ => return Ok (
874
- self . recover_seq_parse_error ( token:: Paren , lo, Err ( err) ) ,
875
- ) ,
876
- }
877
- }
878
- } ) ;
879
- recovered = self . expect_one_of (
880
- & [ ] ,
881
- & [ token:: Comma , token:: CloseDelim ( token:: Paren ) ] ,
882
- ) ?;
883
- if self . eat ( & token:: Comma ) {
884
- trailing_comma = true ;
885
- } else {
886
- trailing_comma = false ;
887
- break ;
853
+ let mut first = true ;
854
+ let parse_leading_attr_expr = |this : & mut Parser < ' a > | {
855
+ if first {
856
+ attrs. extend ( this. parse_inner_attributes ( ) ?) ;
857
+ first = false ;
888
858
}
889
- }
890
- if !recovered {
891
- self . bump ( ) ;
892
- }
859
+ this. parse_expr_catch_underscore ( )
860
+ } ;
861
+
862
+ // (e) is parenthesized e
863
+ // (e,) is a tuple with only one field, e
864
+ let ( es, trailing_comma) =
865
+ match self . parse_paren_comma_seq ( parse_leading_attr_expr)
866
+ {
867
+ Ok ( x) => x,
868
+ Err ( err) => return Ok (
869
+ self . recover_seq_parse_error ( token:: Paren , lo, Err ( err) ) ,
870
+ ) ,
871
+ } ;
893
872
894
873
hi = self . prev_span ;
895
874
ex = if es. len ( ) == 1 && !trailing_comma {
0 commit comments