11use rustc_ast:: token:: { self , Delimiter , Token } ;
22use rustc_ast:: tokenstream:: { DelimSpacing , DelimSpan , Spacing , TokenStream , TokenTree } ;
33use rustc_ast_pretty:: pprust:: token_to_string;
4- use rustc_errors:: { Applicability , Diag } ;
5- use rustc_span:: symbol:: kw;
4+ use rustc_errors:: Diag ;
65
76use super :: diagnostics:: { report_suspicious_mismatch_block, same_indentation_level} ;
87use super :: { Lexer , UnmatchedDelim } ;
9- use crate :: Parser ;
108
119impl < ' psess , ' src > Lexer < ' psess , ' src > {
1210 // Lex into a token stream. The `Spacing` in the result is that of the
1311 // opening delimiter.
1412 pub ( super ) fn lex_token_trees (
1513 & mut self ,
1614 is_delimited : bool ,
17- ) -> ( Spacing , TokenStream , Result < ( ) , Vec < Diag < ' psess > > > ) {
15+ ) -> Result < ( Spacing , TokenStream ) , Vec < Diag < ' psess > > > {
1816 // Move past the opening delimiter.
1917 let open_spacing = self . bump_minimal ( ) ;
2018
@@ -27,25 +25,25 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
2725 debug_assert ! ( !matches!( delim, Delimiter :: Invisible ( _) ) ) ;
2826 buf. push ( match self . lex_token_tree_open_delim ( delim) {
2927 Ok ( val) => val,
30- Err ( errs) => return ( open_spacing , TokenStream :: new ( buf ) , Err ( errs) ) ,
28+ Err ( errs) => return Err ( errs) ,
3129 } )
3230 }
3331 token:: CloseDelim ( delim) => {
3432 // Invisible delimiters cannot occur here because `TokenTreesReader` parses
3533 // code directly from strings, with no macro expansion involved.
3634 debug_assert ! ( !matches!( delim, Delimiter :: Invisible ( _) ) ) ;
37- return (
38- open_spacing,
39- TokenStream :: new ( buf ) ,
40- if is_delimited { Ok ( ( ) ) } else { Err ( vec ! [ self . close_delim_err( delim) ] ) } ,
41- ) ;
35+ return if is_delimited {
36+ Ok ( ( open_spacing, TokenStream :: new ( buf ) ) )
37+ } else {
38+ Err ( vec ! [ self . close_delim_err( delim) ] )
39+ } ;
4240 }
4341 token:: Eof => {
44- return (
45- open_spacing ,
46- TokenStream :: new ( buf ) ,
47- if is_delimited { Err ( vec ! [ self . eof_err ( ) ] ) } else { Ok ( ( ) ) } ,
48- ) ;
42+ return if is_delimited {
43+ Err ( vec ! [ self . eof_err ( ) ] )
44+ } else {
45+ Ok ( ( open_spacing , TokenStream :: new ( buf ) ) )
46+ } ;
4947 }
5048 _ => {
5149 // Get the next normal token.
@@ -107,10 +105,7 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
107105 // Lex the token trees within the delimiters.
108106 // We stop at any delimiter so we can try to recover if the user
109107 // uses an incorrect delimiter.
110- let ( open_spacing, tts, res) = self . lex_token_trees ( /* is_delimited */ true ) ;
111- if let Err ( errs) = res {
112- return Err ( self . unclosed_delim_err ( tts, errs) ) ;
113- }
108+ let ( open_spacing, tts) = self . lex_token_trees ( /* is_delimited */ true ) ?;
114109
115110 // Expand to cover the entire delimited token tree.
116111 let delim_span = DelimSpan :: from_pair ( pre_span, self . token . span ) ;
@@ -247,67 +242,6 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
247242 this_spacing
248243 }
249244
250- fn unclosed_delim_err (
251- & mut self ,
252- tts : TokenStream ,
253- mut errs : Vec < Diag < ' psess > > ,
254- ) -> Vec < Diag < ' psess > > {
255- // If there are unclosed delims, see if there are diff markers and if so, point them
256- // out instead of complaining about the unclosed delims.
257- let mut parser = Parser :: new ( self . psess , tts, None ) ;
258- let mut diff_errs = vec ! [ ] ;
259- // Suggest removing a `{` we think appears in an `if`/`while` condition.
260- // We want to suggest removing a `{` only if we think we're in an `if`/`while` condition,
261- // but we have no way of tracking this in the lexer itself, so we piggyback on the parser.
262- let mut in_cond = false ;
263- while parser. token != token:: Eof {
264- if let Err ( diff_err) = parser. err_vcs_conflict_marker ( ) {
265- diff_errs. push ( diff_err) ;
266- } else if parser. is_keyword_ahead ( 0 , & [ kw:: If , kw:: While ] ) {
267- in_cond = true ;
268- } else if matches ! (
269- parser. token. kind,
270- token:: CloseDelim ( Delimiter :: Brace ) | token:: FatArrow
271- ) {
272- // End of the `if`/`while` body, or the end of a `match` guard.
273- in_cond = false ;
274- } else if in_cond && parser. token == token:: OpenDelim ( Delimiter :: Brace ) {
275- // Store the `&&` and `let` to use their spans later when creating the diagnostic
276- let maybe_andand = parser. look_ahead ( 1 , |t| t. clone ( ) ) ;
277- let maybe_let = parser. look_ahead ( 2 , |t| t. clone ( ) ) ;
278- if maybe_andand == token:: OpenDelim ( Delimiter :: Brace ) {
279- // This might be the beginning of the `if`/`while` body (i.e., the end of the
280- // condition).
281- in_cond = false ;
282- } else if maybe_andand == token:: AndAnd && maybe_let. is_keyword ( kw:: Let ) {
283- let mut err = parser. dcx ( ) . struct_span_err (
284- parser. token . span ,
285- "found a `{` in the middle of a let-chain" ,
286- ) ;
287- err. span_suggestion (
288- parser. token . span ,
289- "consider removing this brace to parse the `let` as part of the same chain" ,
290- "" ,
291- Applicability :: MachineApplicable ,
292- ) ;
293- err. span_label (
294- maybe_andand. span . to ( maybe_let. span ) ,
295- "you might have meant to continue the let-chain here" ,
296- ) ;
297- errs. push ( err) ;
298- }
299- }
300- parser. bump ( ) ;
301- }
302- if !diff_errs. is_empty ( ) {
303- for err in errs {
304- err. cancel ( ) ;
305- }
306- return diff_errs;
307- }
308- errs
309- }
310-
311245 fn close_delim_err ( & mut self , delim : Delimiter ) -> Diag < ' psess > {
312246 // An unexpected closing delimiter (i.e., there is no matching opening delimiter).
313247 let token_str = token_to_string ( & self . token ) ;
0 commit comments