@@ -974,11 +974,12 @@ impl<'a> Parser<'a> {
974974 pub fn eat_to_tokens ( & mut self , kets : & [ & token:: Token ] ) {
975975 let handler = self . diagnostic ( ) ;
976976
977- self . parse_seq_to_before_tokens ( kets,
978- SeqSep :: none ( ) ,
979- TokenExpectType :: Expect ,
980- |p| Ok ( p. parse_token_tree ( ) ) ,
981- |mut e| handler. cancel ( & mut e) ) ;
977+ if let Err ( ref mut err) = self . parse_seq_to_before_tokens ( kets,
978+ SeqSep :: none ( ) ,
979+ TokenExpectType :: Expect ,
980+ |p| Ok ( p. parse_token_tree ( ) ) ) {
981+ handler. cancel ( err) ;
982+ }
982983 }
983984
984985 /// Parse a sequence, including the closing delimiter. The function
@@ -991,7 +992,7 @@ impl<'a> Parser<'a> {
991992 -> PResult < ' a , Vec < T > > where
992993 F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , T > ,
993994 {
994- let val = self . parse_seq_to_before_end ( ket, sep, f) ;
995+ let val = self . parse_seq_to_before_end ( ket, sep, f) ? ;
995996 self . bump ( ) ;
996997 Ok ( val)
997998 }
@@ -1003,22 +1004,19 @@ impl<'a> Parser<'a> {
10031004 ket : & token:: Token ,
10041005 sep : SeqSep ,
10051006 f : F )
1006- -> Vec < T >
1007- where F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , T >
1007+ -> PResult < ' a , Vec < T > >
1008+ where F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , T >
10081009 {
1009- self . parse_seq_to_before_tokens ( & [ ket] , sep, TokenExpectType :: Expect , f, | mut e| e . emit ( ) )
1010+ self . parse_seq_to_before_tokens ( & [ ket] , sep, TokenExpectType :: Expect , f)
10101011 }
10111012
1012- // `fe` is an error handler.
1013- fn parse_seq_to_before_tokens < T , F , Fe > ( & mut self ,
1013+ fn parse_seq_to_before_tokens < T , F > ( & mut self ,
10141014 kets : & [ & token:: Token ] ,
10151015 sep : SeqSep ,
10161016 expect : TokenExpectType ,
1017- mut f : F ,
1018- mut fe : Fe )
1019- -> Vec < T >
1020- where F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , T > ,
1021- Fe : FnMut ( DiagnosticBuilder )
1017+ mut f : F )
1018+ -> PResult < ' a , Vec < T > >
1019+ where F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , T >
10221020 {
10231021 let mut first: bool = true ;
10241022 let mut v = vec ! [ ] ;
@@ -1031,14 +1029,14 @@ impl<'a> Parser<'a> {
10311029 if first {
10321030 first = false ;
10331031 } else {
1034- if let Err ( e) = self . expect ( t) {
1035- fe ( e) ;
1032+ if let Err ( mut e) = self . expect ( t) {
10361033 // Attempt to keep parsing if it was a similar separator
10371034 if let Some ( ref tokens) = t. similar_tokens ( ) {
10381035 if tokens. contains ( & self . token ) {
10391036 self . bump ( ) ;
10401037 }
10411038 }
1039+ e. emit ( ) ;
10421040 // Attempt to keep parsing if it was an omitted separator
10431041 match f ( self ) {
10441042 Ok ( t) => {
@@ -1062,16 +1060,11 @@ impl<'a> Parser<'a> {
10621060 break ;
10631061 }
10641062
1065- match f ( self ) {
1066- Ok ( t) => v. push ( t) ,
1067- Err ( e) => {
1068- fe ( e) ;
1069- break ;
1070- }
1071- }
1063+ let t = f ( self ) ?;
1064+ v. push ( t) ;
10721065 }
10731066
1074- v
1067+ Ok ( v )
10751068 }
10761069
10771070 /// Parse a sequence, including the closing delimiter. The function
@@ -1086,7 +1079,7 @@ impl<'a> Parser<'a> {
10861079 F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , T > ,
10871080 {
10881081 self . expect ( bra) ?;
1089- let result = self . parse_seq_to_before_end ( ket, sep, f) ;
1082+ let result = self . parse_seq_to_before_end ( ket, sep, f) ? ;
10901083 if self . token == * ket {
10911084 self . bump ( ) ;
10921085 }
@@ -1105,7 +1098,7 @@ impl<'a> Parser<'a> {
11051098 {
11061099 let lo = self . span ;
11071100 self . expect ( bra) ?;
1108- let result = self . parse_seq_to_before_end ( ket, sep, f) ;
1101+ let result = self . parse_seq_to_before_end ( ket, sep, f) ? ;
11091102 let hi = self . span ;
11101103 self . bump ( ) ;
11111104 Ok ( respan ( lo. to ( hi) , result) )
@@ -1551,7 +1544,7 @@ impl<'a> Parser<'a> {
15511544 } ;
15521545
15531546 let span = lo. to ( self . prev_span ) ;
1554- let ty = Ty { node : node , span : span, id : ast:: DUMMY_NODE_ID } ;
1547+ let ty = Ty { node, span, id : ast:: DUMMY_NODE_ID } ;
15551548
15561549 // Try to recover from use of `+` with incorrect priority.
15571550 self . maybe_recover_from_bad_type_plus ( allow_plus, & ty) ?;
@@ -1868,8 +1861,11 @@ impl<'a> Parser<'a> {
18681861 self . parse_path ( style)
18691862 }
18701863
1871- fn parse_path_segments ( & mut self , segments : & mut Vec < PathSegment > , style : PathStyle ,
1872- enable_warning : bool ) -> PResult < ' a , ( ) > {
1864+ fn parse_path_segments ( & mut self ,
1865+ segments : & mut Vec < PathSegment > ,
1866+ style : PathStyle ,
1867+ enable_warning : bool )
1868+ -> PResult < ' a , ( ) > {
18731869 loop {
18741870 segments. push ( self . parse_path_segment ( style, enable_warning) ?) ;
18751871
@@ -1914,9 +1910,12 @@ impl<'a> Parser<'a> {
19141910 } else {
19151911 // `(T, U) -> R`
19161912 self . bump ( ) ; // `(`
1917- let inputs = self . parse_seq_to_end ( & token:: CloseDelim ( token:: Paren ) ,
1918- SeqSep :: trailing_allowed ( token:: Comma ) ,
1919- |p| p. parse_ty ( ) ) ?;
1913+ let inputs = self . parse_seq_to_before_tokens (
1914+ & [ & token:: CloseDelim ( token:: Paren ) ] ,
1915+ SeqSep :: trailing_allowed ( token:: Comma ) ,
1916+ TokenExpectType :: Expect ,
1917+ |p| p. parse_ty ( ) ) ?;
1918+ self . bump ( ) ; // `)`
19201919 let output = if self . eat ( & token:: RArrow ) {
19211920 Some ( self . parse_ty_no_plus ( ) ?)
19221921 } else {
@@ -3315,10 +3314,12 @@ impl<'a> Parser<'a> {
33153314 }
33163315
33173316 /// Parse the RHS of a local variable declaration (e.g. '= 14;')
3318- fn parse_initializer ( & mut self ) -> PResult < ' a , Option < P < Expr > > > {
3317+ fn parse_initializer ( & mut self , skip_eq : bool ) -> PResult < ' a , Option < P < Expr > > > {
33193318 if self . check ( & token:: Eq ) {
33203319 self . bump ( ) ;
33213320 Ok ( Some ( self . parse_expr ( ) ?) )
3321+ } else if skip_eq {
3322+ Ok ( Some ( self . parse_expr ( ) ?) )
33223323 } else {
33233324 Ok ( None )
33243325 }
@@ -3725,12 +3726,56 @@ impl<'a> Parser<'a> {
37253726 let lo = self . prev_span ;
37263727 let pat = self . parse_pat ( ) ?;
37273728
3728- let ty = if self . eat ( & token:: Colon ) {
3729- Some ( self . parse_ty ( ) ?)
3729+ let ( err, ty) = if self . eat ( & token:: Colon ) {
3730+ // Save the state of the parser before parsing type normally, in case there is a `:`
3731+ // instead of an `=` typo.
3732+ let parser_snapshot_before_type = self . clone ( ) ;
3733+ let colon_sp = self . prev_span ;
3734+ match self . parse_ty ( ) {
3735+ Ok ( ty) => ( None , Some ( ty) ) ,
3736+ Err ( mut err) => {
3737+ // Rewind to before attempting to parse the type and continue parsing
3738+ let parser_snapshot_after_type = self . clone ( ) ;
3739+ mem:: replace ( self , parser_snapshot_before_type) ;
3740+
3741+ let snippet = self . sess . codemap ( ) . span_to_snippet ( pat. span ) . unwrap ( ) ;
3742+ err. span_label ( pat. span , format ! ( "while parsing the type for `{}`" , snippet) ) ;
3743+ ( Some ( ( parser_snapshot_after_type, colon_sp, err) ) , None )
3744+ }
3745+ }
37303746 } else {
3731- None
3747+ ( None , None )
3748+ } ;
3749+ let init = match ( self . parse_initializer ( err. is_some ( ) ) , err) {
3750+ ( Ok ( init) , None ) => { // init parsed, ty parsed
3751+ init
3752+ }
3753+ ( Ok ( init) , Some ( ( _, colon_sp, mut err) ) ) => { // init parsed, ty error
3754+ // Could parse the type as if it were the initializer, it is likely there was a
3755+ // typo in the code: `:` instead of `=`. Add suggestion and emit the error.
3756+ err. span_suggestion_short ( colon_sp,
3757+ "use `=` if you meant to assign" ,
3758+ "=" . to_string ( ) ) ;
3759+ err. emit ( ) ;
3760+ // As this was parsed successfuly, continue as if the code has been fixed for the
3761+ // rest of the file. It will still fail due to the emitted error, but we avoid
3762+ // extra noise.
3763+ init
3764+ }
3765+ ( Err ( mut init_err) , Some ( ( snapshot, _, ty_err) ) ) => { // init error, ty error
3766+ init_err. cancel ( ) ;
3767+ // Couldn't parse the type nor the initializer, only raise the type error and
3768+ // return to the parser state before parsing the type as the initializer.
3769+ // let x: <parse_error>;
3770+ mem:: replace ( self , snapshot) ;
3771+ return Err ( ty_err) ;
3772+ }
3773+ ( Err ( err) , None ) => { // init error, ty parsed
3774+ // Couldn't parse the initializer and we're not attempting to recover a failed
3775+ // parse of the type, return the error.
3776+ return Err ( err) ;
3777+ }
37323778 } ;
3733- let init = self . parse_initializer ( ) ?;
37343779 let hi = if self . token == token:: Semi {
37353780 self . span
37363781 } else {
@@ -4797,14 +4842,14 @@ impl<'a> Parser<'a> {
47974842 } else if self . eat ( & token:: Comma ) {
47984843 let mut fn_inputs = vec ! [ self_arg] ;
47994844 fn_inputs. append ( & mut self . parse_seq_to_before_end (
4800- & token:: CloseDelim ( token:: Paren ) , sep, parse_arg_fn)
4845+ & token:: CloseDelim ( token:: Paren ) , sep, parse_arg_fn) ?
48014846 ) ;
48024847 fn_inputs
48034848 } else {
48044849 return self . unexpected ( ) ;
48054850 }
48064851 } else {
4807- self . parse_seq_to_before_end ( & token:: CloseDelim ( token:: Paren ) , sep, parse_arg_fn)
4852+ self . parse_seq_to_before_end ( & token:: CloseDelim ( token:: Paren ) , sep, parse_arg_fn) ?
48084853 } ;
48094854
48104855 // Parse closing paren and return type.
@@ -4827,9 +4872,8 @@ impl<'a> Parser<'a> {
48274872 & [ & token:: BinOp ( token:: Or ) , & token:: OrOr ] ,
48284873 SeqSep :: trailing_allowed ( token:: Comma ) ,
48294874 TokenExpectType :: NoExpect ,
4830- |p| p. parse_fn_block_arg ( ) ,
4831- |mut e| e. emit ( )
4832- ) ;
4875+ |p| p. parse_fn_block_arg ( )
4876+ ) ?;
48334877 self . expect_or ( ) ?;
48344878 args
48354879 }
0 commit comments