diff --git a/compiler/rustc_parse_format/src/lib.rs b/compiler/rustc_parse_format/src/lib.rs index c59e6cb5c33f7..999e715927456 100644 --- a/compiler/rustc_parse_format/src/lib.rs +++ b/compiler/rustc_parse_format/src/lib.rs @@ -100,6 +100,30 @@ pub struct Argument<'a> { pub format: FormatSpec<'a>, } +impl<'a> Argument<'a> { + pub fn is_identifier(&self) -> bool { + matches!(self.position, Position::ArgumentNamed(_)) + && matches!( + self.format, + FormatSpec { + fill: None, + fill_span: None, + align: AlignUnknown, + sign: None, + alternate: false, + zero_pad: false, + debug_hex: None, + precision: CountImplied, + precision_span: None, + width: CountImplied, + width_span: None, + ty: "", + ty_span: None, + }, + ) + } +} + /// Specification for the formatting of an argument in the format string. #[derive(Copy, Clone, Debug, PartialEq)] pub struct FormatSpec<'a> { @@ -894,6 +918,11 @@ impl<'a> Parser<'a> { } fn suggest_positional_arg_instead_of_captured_arg(&mut self, arg: Argument<'a>) { + // If the argument is not an identifier, it is not a field access. + if !arg.is_identifier() { + return; + } + if let Some(end) = self.consume_pos('.') { let byte_pos = self.to_span_index(end); let start = InnerOffset(byte_pos.0 + 1); diff --git a/tests/ui/parser/issues/invalid-parse-format-issue-139104.rs b/tests/ui/parser/issues/invalid-parse-format-issue-139104.rs new file mode 100644 index 0000000000000..7644df8be49a0 --- /dev/null +++ b/tests/ui/parser/issues/invalid-parse-format-issue-139104.rs @@ -0,0 +1,13 @@ +fn main() { + println!("{foo:_1.4}", foo = 3.14); //~ ERROR invalid format string: expected `}`, found `.` + println!("{0:_1.4}", 1.11); //~ ERROR invalid format string: expected `}`, found `.` + println!("{:_1.4}", 3.14); //~ ERROR invalid format string: expected `}`, found `.` + + println!("{foo:_1.4", foo = 3.14); //~ ERROR invalid format string: expected `}`, found `.` + println!("{0:_1.4", 1.11); //~ ERROR invalid format string: expected `}`, found `.` + println!("{:_1.4", 3.14); //~ ERROR invalid format string: expected `}`, found `.` + + println!("{ 0", 1.11); //~ ERROR invalid format string: expected `}`, found `0` + println!("{foo:1.4_1.4}", foo = 3.14); //~ ERROR invalid format string: expected `}`, found `.` + println!("{0:1.4_1.4}", 3.14); //~ ERROR invalid format string: expected `}`, found `.` +} diff --git a/tests/ui/parser/issues/invalid-parse-format-issue-139104.stderr b/tests/ui/parser/issues/invalid-parse-format-issue-139104.stderr new file mode 100644 index 0000000000000..202aa450cab71 --- /dev/null +++ b/tests/ui/parser/issues/invalid-parse-format-issue-139104.stderr @@ -0,0 +1,92 @@ +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:2:22 + | +LL | println!("{foo:_1.4}", foo = 3.14); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:3:20 + | +LL | println!("{0:_1.4}", 1.11); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:4:19 + | +LL | println!("{:_1.4}", 3.14); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:6:22 + | +LL | println!("{foo:_1.4", foo = 3.14); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:7:20 + | +LL | println!("{0:_1.4", 1.11); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:8:19 + | +LL | println!("{:_1.4", 3.14); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `0` + --> $DIR/invalid-parse-format-issue-139104.rs:10:18 + | +LL | println!("{ 0", 1.11); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:11:25 + | +LL | println!("{foo:1.4_1.4}", foo = 3.14); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: invalid format string: expected `}`, found `.` + --> $DIR/invalid-parse-format-issue-139104.rs:12:23 + | +LL | println!("{0:1.4_1.4}", 3.14); + | - ^ expected `}` in format string + | | + | because of this opening brace + | + = note: if you intended to print `{`, you can escape it using `{{` + +error: aborting due to 9 previous errors +