@@ -2,6 +2,7 @@ use rustc_ast::token::{self, Delimiter, Token};
22use rustc_ast:: tokenstream:: { DelimSpacing , DelimSpan , Spacing , TokenStream , TokenTree } ;
33use rustc_ast_pretty:: pprust:: token_to_string;
44use rustc_errors:: Diag ;
5+ use rustc_span:: Span ;
56
67use super :: diagnostics:: { report_suspicious_mismatch_block, same_indentation_level} ;
78use super :: { Lexer , UnmatchedDelim } ;
@@ -23,7 +24,7 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
2324 // Invisible delimiters cannot occur here because `TokenTreesReader` parses
2425 // code directly from strings, with no macro expansion involved.
2526 debug_assert ! ( !matches!( delim, Delimiter :: Invisible ( _) ) ) ;
26- buf. push ( match self . lex_token_tree_open_delim ( delim) {
27+ buf. push ( match self . lex_token_tree_open_delim ( delim, self . token . span ) {
2728 Ok ( val) => val,
2829 Err ( errs) => return Err ( errs) ,
2930 } )
@@ -59,8 +60,8 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
5960 let mut err = self . dcx ( ) . struct_span_err ( self . token . span , msg) ;
6061
6162 let unclosed_delimiter_show_limit = 5 ;
62- let len = usize:: min ( unclosed_delimiter_show_limit, self . diag_info . open_braces . len ( ) ) ;
63- for & ( _, span) in & self . diag_info . open_braces [ ..len] {
63+ let len = usize:: min ( unclosed_delimiter_show_limit, self . diag_info . open_delimiters . len ( ) ) ;
64+ for & ( _, span) in & self . diag_info . open_delimiters [ ..len] {
6465 err. span_label ( span, "unclosed delimiter" ) ;
6566 self . diag_info . unmatched_delims . push ( UnmatchedDelim {
6667 found_delim : None ,
@@ -70,19 +71,19 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
7071 } ) ;
7172 }
7273
73- if let Some ( ( _, span) ) = self . diag_info . open_braces . get ( unclosed_delimiter_show_limit)
74- && self . diag_info . open_braces . len ( ) >= unclosed_delimiter_show_limit + 2
74+ if let Some ( ( _, span) ) = self . diag_info . open_delimiters . get ( unclosed_delimiter_show_limit)
75+ && self . diag_info . open_delimiters . len ( ) >= unclosed_delimiter_show_limit + 2
7576 {
7677 err. span_label (
7778 * span,
7879 format ! (
7980 "another {} unclosed delimiters begin from here" ,
80- self . diag_info. open_braces . len( ) - unclosed_delimiter_show_limit
81+ self . diag_info. open_delimiters . len( ) - unclosed_delimiter_show_limit
8182 ) ,
8283 ) ;
8384 }
8485
85- if let Some ( ( delim, _) ) = self . diag_info . open_braces . last ( ) {
86+ if let Some ( ( delim, _) ) = self . diag_info . open_delimiters . last ( ) {
8687 report_suspicious_mismatch_block (
8788 & mut err,
8889 & self . diag_info ,
@@ -96,11 +97,12 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
9697 fn lex_token_tree_open_delim (
9798 & mut self ,
9899 open_delim : Delimiter ,
100+ open_delim_span : Span ,
99101 ) -> Result < TokenTree , Vec < Diag < ' psess > > > {
100102 // The span for beginning of the delimited section.
101103 let pre_span = self . token . span ;
102104
103- self . diag_info . open_braces . push ( ( open_delim, self . token . span ) ) ;
105+ self . diag_info . open_delimiters . push ( ( open_delim, self . token . span ) ) ;
104106
105107 // Lex the token trees within the delimiters.
106108 // We stop at any delimiter so we can try to recover if the user
@@ -114,11 +116,12 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
114116 let close_spacing = match self . token . kind {
115117 // Correct delimiter.
116118 token:: CloseDelim ( close_delim) if close_delim == open_delim => {
117- let ( open_brace, open_brace_span) = self . diag_info . open_braces . pop ( ) . unwrap ( ) ;
118- let close_brace_span = self . token . span ;
119+ let ( open_delimiter, open_delimiter_span) =
120+ self . diag_info . open_delimiters . pop ( ) . unwrap ( ) ;
121+ let close_delim_span = self . token . span ;
119122
120123 if tts. is_empty ( ) && close_delim == Delimiter :: Brace {
121- let empty_block_span = open_brace_span . to ( close_brace_span ) ;
124+ let empty_block_span = open_delimiter_span . to ( close_delim_span ) ;
122125 if !sm. is_multiline ( empty_block_span) {
123126 // Only track if the block is in the form of `{}`, otherwise it is
124127 // likely that it was written on purpose.
@@ -127,9 +130,11 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
127130 }
128131
129132 // only add braces
130- if let ( Delimiter :: Brace , Delimiter :: Brace ) = ( open_brace, open_delim) {
133+ if let ( Delimiter :: Brace , Delimiter :: Brace ) = ( open_delimiter, open_delim)
134+ && open_delimiter_span == open_delim_span
135+ {
131136 // Add all the matching spans, we will sort by span later
132- self . diag_info . matching_block_spans . push ( ( open_brace_span , close_brace_span ) ) ;
137+ self . diag_info . matching_block_spans . push ( ( open_delim_span , close_delim_span ) ) ;
133138 }
134139
135140 // Move past the closing delimiter.
@@ -146,26 +151,26 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
146151 // This is a conservative error: only report the last unclosed
147152 // delimiter. The previous unclosed delimiters could actually be
148153 // closed! The lexer just hasn't gotten to them yet.
149- if let Some ( & ( _, sp) ) = self . diag_info . open_braces . last ( ) {
154+ if let Some ( & ( _, sp) ) = self . diag_info . open_delimiters . last ( ) {
150155 unclosed_delimiter = Some ( sp) ;
151156 } ;
152- for ( brace , brace_span ) in & self . diag_info . open_braces {
153- if same_indentation_level ( sm, self . token . span , * brace_span )
154- && brace == & close_delim
157+ for ( delim , delim_span ) in & self . diag_info . open_delimiters {
158+ if same_indentation_level ( sm, self . token . span , * delim_span )
159+ && delim == & close_delim
155160 {
156161 // high likelihood of these two corresponding
157- candidate = Some ( * brace_span ) ;
162+ candidate = Some ( * delim_span ) ;
158163 }
159164 }
160- let ( _, _) = self . diag_info . open_braces . pop ( ) . unwrap ( ) ;
165+ let ( _, _) = self . diag_info . open_delimiters . pop ( ) . unwrap ( ) ;
161166 self . diag_info . unmatched_delims . push ( UnmatchedDelim {
162167 found_delim : Some ( close_delim) ,
163168 found_span : self . token . span ,
164169 unclosed_span : unclosed_delimiter,
165170 candidate_span : candidate,
166171 } ) ;
167172 } else {
168- self . diag_info . open_braces . pop ( ) ;
173+ self . diag_info . open_delimiters . pop ( ) ;
169174 }
170175
171176 // If the incorrect delimiter matches an earlier opening
@@ -175,7 +180,7 @@ impl<'psess, 'src> Lexer<'psess, 'src> {
175180 // fn foo() {
176181 // bar(baz(
177182 // } // Incorrect delimiter but matches the earlier `{`
178- if !self . diag_info . open_braces . iter ( ) . any ( |& ( b , _) | b == close_delim) {
183+ if !self . diag_info . open_delimiters . iter ( ) . any ( |& ( d , _) | d == close_delim) {
179184 self . bump_minimal ( )
180185 } else {
181186 // The choice of value here doesn't matter.
0 commit comments