diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-06-07 05:48:48 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-06-07 05:48:48 +0000 |
commit | ef24de24a82fe681581cc130f342363c47c0969a (patch) | |
tree | 0d494f7e1a38b95c92426f58fe6eaa877303a86c /compiler/rustc_parse/src/lexer | |
parent | Releasing progress-linux version 1.74.1+dfsg1-1~progress7.99u1. (diff) | |
download | rustc-ef24de24a82fe681581cc130f342363c47c0969a.tar.xz rustc-ef24de24a82fe681581cc130f342363c47c0969a.zip |
Merging upstream version 1.75.0+dfsg1.
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'compiler/rustc_parse/src/lexer')
-rw-r--r-- | compiler/rustc_parse/src/lexer/diagnostics.rs | 7 | ||||
-rw-r--r-- | compiler/rustc_parse/src/lexer/mod.rs | 14 | ||||
-rw-r--r-- | compiler/rustc_parse/src/lexer/tokentrees.rs | 80 |
3 files changed, 65 insertions, 36 deletions
diff --git a/compiler/rustc_parse/src/lexer/diagnostics.rs b/compiler/rustc_parse/src/lexer/diagnostics.rs index b50bb47f2..b1bd4ac75 100644 --- a/compiler/rustc_parse/src/lexer/diagnostics.rs +++ b/compiler/rustc_parse/src/lexer/diagnostics.rs @@ -111,9 +111,10 @@ pub fn report_suspicious_mismatch_block( // If there is no suspicious span, give the last properly closed block may help if let Some(parent) = diag_info.matching_block_spans.last() && diag_info.open_braces.last().is_none() - && diag_info.empty_block_spans.iter().all(|&sp| sp != parent.0.to(parent.1)) { - err.span_label(parent.0, "this opening brace..."); - err.span_label(parent.1, "...matches this closing brace"); + && diag_info.empty_block_spans.iter().all(|&sp| sp != parent.0.to(parent.1)) + { + err.span_label(parent.0, "this opening brace..."); + err.span_label(parent.1, "...matches this closing brace"); } } } diff --git a/compiler/rustc_parse/src/lexer/mod.rs b/compiler/rustc_parse/src/lexer/mod.rs index a375a1d69..f2eed5c9b 100644 --- a/compiler/rustc_parse/src/lexer/mod.rs +++ b/compiler/rustc_parse/src/lexer/mod.rs @@ -64,10 +64,10 @@ pub(crate) fn parse_token_trees<'a>( override_span, nbsp_is_whitespace: false, }; - let (token_trees, unmatched_delims) = + let (stream, res, unmatched_delims) = tokentrees::TokenTreesReader::parse_all_token_trees(string_reader); - match token_trees { - Ok(stream) if unmatched_delims.is_empty() => Ok(stream), + match res { + Ok(()) if unmatched_delims.is_empty() => Ok(stream), _ => { // Return error if there are unmatched delimiters or unclosed delimiters. // We emit delimiter mismatch errors first, then emit the unclosing delimiter mismatch @@ -79,9 +79,11 @@ pub(crate) fn parse_token_trees<'a>( err.buffer(&mut buffer); } } - if let Err(err) = token_trees { - // Add unclosing delimiter error - err.buffer(&mut buffer); + if let Err(errs) = res { + // Add unclosing delimiter or diff marker errors + for err in errs { + err.buffer(&mut buffer); + } } Err(buffer) } diff --git a/compiler/rustc_parse/src/lexer/tokentrees.rs b/compiler/rustc_parse/src/lexer/tokentrees.rs index 07910113d..31d91fe80 100644 --- a/compiler/rustc_parse/src/lexer/tokentrees.rs +++ b/compiler/rustc_parse/src/lexer/tokentrees.rs @@ -5,7 +5,7 @@ use super::{StringReader, UnmatchedDelim}; use rustc_ast::token::{self, Delimiter, Token}; use rustc_ast::tokenstream::{DelimSpan, Spacing, TokenStream, TokenTree}; use rustc_ast_pretty::pprust::token_to_string; -use rustc_errors::{PErr, PResult}; +use rustc_errors::PErr; pub(super) struct TokenTreesReader<'a> { string_reader: StringReader<'a>, @@ -18,36 +18,42 @@ pub(super) struct TokenTreesReader<'a> { impl<'a> TokenTreesReader<'a> { pub(super) fn parse_all_token_trees( string_reader: StringReader<'a>, - ) -> (PResult<'a, TokenStream>, Vec<UnmatchedDelim>) { + ) -> (TokenStream, Result<(), Vec<PErr<'a>>>, Vec<UnmatchedDelim>) { let mut tt_reader = TokenTreesReader { string_reader, token: Token::dummy(), diag_info: TokenTreeDiagInfo::default(), }; - let res = tt_reader.parse_token_trees(/* is_delimited */ false); - (res, tt_reader.diag_info.unmatched_delims) + let (stream, res) = tt_reader.parse_token_trees(/* is_delimited */ false); + (stream, res, tt_reader.diag_info.unmatched_delims) } // Parse a stream of tokens into a list of `TokenTree`s. - fn parse_token_trees(&mut self, is_delimited: bool) -> PResult<'a, TokenStream> { + fn parse_token_trees( + &mut self, + is_delimited: bool, + ) -> (TokenStream, Result<(), Vec<PErr<'a>>>) { self.token = self.string_reader.next_token().0; let mut buf = Vec::new(); loop { match self.token.kind { - token::OpenDelim(delim) => buf.push(self.parse_token_tree_open_delim(delim)?), + token::OpenDelim(delim) => { + buf.push(match self.parse_token_tree_open_delim(delim) { + Ok(val) => val, + Err(errs) => return (TokenStream::new(buf), Err(errs)), + }) + } token::CloseDelim(delim) => { - return if is_delimited { - Ok(TokenStream::new(buf)) - } else { - Err(self.close_delim_err(delim)) - }; + return ( + TokenStream::new(buf), + if is_delimited { Ok(()) } else { Err(vec![self.close_delim_err(delim)]) }, + ); } token::Eof => { - return if is_delimited { - Err(self.eof_err()) - } else { - Ok(TokenStream::new(buf)) - }; + return ( + TokenStream::new(buf), + if is_delimited { Err(vec![self.eof_err()]) } else { Ok(()) }, + ); } _ => { // Get the next normal token. This might require getting multiple adjacent @@ -55,16 +61,14 @@ impl<'a> TokenTreesReader<'a> { let (this_spacing, next_tok) = loop { let (next_tok, is_next_tok_preceded_by_whitespace) = self.string_reader.next_token(); - if !is_next_tok_preceded_by_whitespace { - if let Some(glued) = self.token.glue(&next_tok) { - self.token = glued; - } else { - let this_spacing = - if next_tok.is_op() { Spacing::Joint } else { Spacing::Alone }; - break (this_spacing, next_tok); - } - } else { + if is_next_tok_preceded_by_whitespace { break (Spacing::Alone, next_tok); + } else if let Some(glued) = self.token.glue(&next_tok) { + self.token = glued; + } else { + let this_spacing = + if next_tok.is_punct() { Spacing::Joint } else { Spacing::Alone }; + break (this_spacing, next_tok); } }; let this_tok = std::mem::replace(&mut self.token, next_tok); @@ -99,7 +103,10 @@ impl<'a> TokenTreesReader<'a> { err } - fn parse_token_tree_open_delim(&mut self, open_delim: Delimiter) -> PResult<'a, TokenTree> { + fn parse_token_tree_open_delim( + &mut self, + open_delim: Delimiter, + ) -> Result<TokenTree, Vec<PErr<'a>>> { // The span for beginning of the delimited section let pre_span = self.token.span; @@ -108,7 +115,26 @@ impl<'a> TokenTreesReader<'a> { // Parse the token trees within the delimiters. // We stop at any delimiter so we can try to recover if the user // uses an incorrect delimiter. - let tts = self.parse_token_trees(/* is_delimited */ true)?; + let (tts, res) = self.parse_token_trees(/* is_delimited */ true); + if let Err(mut errs) = res { + // If there are unclosed delims, see if there are diff markers and if so, point them + // out instead of complaining about the unclosed delims. + let mut parser = crate::stream_to_parser(self.string_reader.sess, tts, None); + let mut diff_errs = vec![]; + while parser.token != token::Eof { + if let Err(diff_err) = parser.err_diff_marker() { + diff_errs.push(diff_err); + } + parser.bump(); + } + if !diff_errs.is_empty() { + errs.iter_mut().for_each(|err| { + err.delay_as_bug(); + }); + return Err(diff_errs); + } + return Err(errs); + } // Expand to cover the entire delimited token tree let delim_span = DelimSpan::from_pair(pre_span, self.token.span); |