Rollup merge of #59421 - estebank:tuple-index-suffix, r=petrochenkov
Reject integer suffix when tuple indexing Fix #59418. r? @varkor
This commit is contained in:
commit
be34621ffc
@ -1119,9 +1119,8 @@ impl<'a> Parser<'a> {
|
||||
if text.is_empty() {
|
||||
self.span_bug(sp, "found empty literal suffix in Some")
|
||||
}
|
||||
let msg = format!("{} with a suffix is invalid", kind);
|
||||
self.struct_span_err(sp, &msg)
|
||||
.span_label(sp, msg)
|
||||
self.struct_span_err(sp, &format!("suffixes on {} are invalid", kind))
|
||||
.span_label(sp, format!("invalid suffix `{}`", text))
|
||||
.emit();
|
||||
}
|
||||
}
|
||||
@ -2150,7 +2149,7 @@ impl<'a> Parser<'a> {
|
||||
|
||||
if suffix_illegal {
|
||||
let sp = self.span;
|
||||
self.expect_no_suffix(sp, lit.literal_name(), suf)
|
||||
self.expect_no_suffix(sp, &format!("a {}", lit.literal_name()), suf)
|
||||
}
|
||||
|
||||
result.unwrap()
|
||||
@ -2481,7 +2480,8 @@ impl<'a> Parser<'a> {
|
||||
}
|
||||
|
||||
fn parse_field_name(&mut self) -> PResult<'a, Ident> {
|
||||
if let token::Literal(token::Integer(name), None) = self.token {
|
||||
if let token::Literal(token::Integer(name), suffix) = self.token {
|
||||
self.expect_no_suffix(self.span, "a tuple index", suffix);
|
||||
self.bump();
|
||||
Ok(Ident::new(name, self.prev_span))
|
||||
} else {
|
||||
@ -3185,51 +3185,53 @@ impl<'a> Parser<'a> {
|
||||
// expr.f
|
||||
if self.eat(&token::Dot) {
|
||||
match self.token {
|
||||
token::Ident(..) => {
|
||||
e = self.parse_dot_suffix(e, lo)?;
|
||||
}
|
||||
token::Literal(token::Integer(name), _) => {
|
||||
let span = self.span;
|
||||
self.bump();
|
||||
let field = ExprKind::Field(e, Ident::new(name, span));
|
||||
e = self.mk_expr(lo.to(span), field, ThinVec::new());
|
||||
}
|
||||
token::Literal(token::Float(n), _suf) => {
|
||||
self.bump();
|
||||
let fstr = n.as_str();
|
||||
let mut err = self.diagnostic()
|
||||
.struct_span_err(self.prev_span, &format!("unexpected token: `{}`", n));
|
||||
err.span_label(self.prev_span, "unexpected token");
|
||||
if fstr.chars().all(|x| "0123456789.".contains(x)) {
|
||||
let float = match fstr.parse::<f64>().ok() {
|
||||
Some(f) => f,
|
||||
None => continue,
|
||||
};
|
||||
let sugg = pprust::to_string(|s| {
|
||||
use crate::print::pprust::PrintState;
|
||||
s.popen()?;
|
||||
s.print_expr(&e)?;
|
||||
s.s.word( ".")?;
|
||||
s.print_usize(float.trunc() as usize)?;
|
||||
s.pclose()?;
|
||||
s.s.word(".")?;
|
||||
s.s.word(fstr.splitn(2, ".").last().unwrap().to_string())
|
||||
});
|
||||
err.span_suggestion(
|
||||
lo.to(self.prev_span),
|
||||
"try parenthesizing the first index",
|
||||
sugg,
|
||||
Applicability::MachineApplicable
|
||||
);
|
||||
token::Ident(..) => {
|
||||
e = self.parse_dot_suffix(e, lo)?;
|
||||
}
|
||||
return Err(err);
|
||||
token::Literal(token::Integer(name), suffix) => {
|
||||
let span = self.span;
|
||||
self.bump();
|
||||
let field = ExprKind::Field(e, Ident::new(name, span));
|
||||
e = self.mk_expr(lo.to(span), field, ThinVec::new());
|
||||
|
||||
}
|
||||
_ => {
|
||||
// FIXME Could factor this out into non_fatal_unexpected or something.
|
||||
let actual = self.this_token_to_string();
|
||||
self.span_err(self.span, &format!("unexpected token: `{}`", actual));
|
||||
}
|
||||
self.expect_no_suffix(span, "a tuple index", suffix);
|
||||
}
|
||||
token::Literal(token::Float(n), _suf) => {
|
||||
self.bump();
|
||||
let fstr = n.as_str();
|
||||
let mut err = self.diagnostic()
|
||||
.struct_span_err(self.prev_span, &format!("unexpected token: `{}`", n));
|
||||
err.span_label(self.prev_span, "unexpected token");
|
||||
if fstr.chars().all(|x| "0123456789.".contains(x)) {
|
||||
let float = match fstr.parse::<f64>().ok() {
|
||||
Some(f) => f,
|
||||
None => continue,
|
||||
};
|
||||
let sugg = pprust::to_string(|s| {
|
||||
use crate::print::pprust::PrintState;
|
||||
s.popen()?;
|
||||
s.print_expr(&e)?;
|
||||
s.s.word( ".")?;
|
||||
s.print_usize(float.trunc() as usize)?;
|
||||
s.pclose()?;
|
||||
s.s.word(".")?;
|
||||
s.s.word(fstr.splitn(2, ".").last().unwrap().to_string())
|
||||
});
|
||||
err.span_suggestion(
|
||||
lo.to(self.prev_span),
|
||||
"try parenthesizing the first index",
|
||||
sugg,
|
||||
Applicability::MachineApplicable
|
||||
);
|
||||
}
|
||||
return Err(err);
|
||||
|
||||
}
|
||||
_ => {
|
||||
// FIXME Could factor this out into non_fatal_unexpected or something.
|
||||
let actual = self.this_token_to_string();
|
||||
self.span_err(self.span, &format!("unexpected token: `{}`", actual));
|
||||
}
|
||||
}
|
||||
continue;
|
||||
}
|
||||
@ -7827,7 +7829,7 @@ impl<'a> Parser<'a> {
|
||||
match self.token {
|
||||
token::Literal(token::Str_(s), suf) | token::Literal(token::StrRaw(s, _), suf) => {
|
||||
let sp = self.span;
|
||||
self.expect_no_suffix(sp, "ABI spec", suf);
|
||||
self.expect_no_suffix(sp, "an ABI spec", suf);
|
||||
self.bump();
|
||||
match abi::lookup(&s.as_str()) {
|
||||
Some(abi) => Ok(Some(abi)),
|
||||
@ -8648,7 +8650,7 @@ impl<'a> Parser<'a> {
|
||||
match self.parse_optional_str() {
|
||||
Some((s, style, suf)) => {
|
||||
let sp = self.prev_span;
|
||||
self.expect_no_suffix(sp, "string literal", suf);
|
||||
self.expect_no_suffix(sp, "a string literal", suf);
|
||||
Ok((s, style))
|
||||
}
|
||||
_ => {
|
||||
|
@ -2,20 +2,20 @@
|
||||
|
||||
|
||||
extern
|
||||
"C"suffix //~ ERROR ABI spec with a suffix is invalid
|
||||
"C"suffix //~ ERROR suffixes on an ABI spec are invalid
|
||||
fn foo() {}
|
||||
|
||||
extern
|
||||
"C"suffix //~ ERROR ABI spec with a suffix is invalid
|
||||
"C"suffix //~ ERROR suffixes on an ABI spec are invalid
|
||||
{}
|
||||
|
||||
fn main() {
|
||||
""suffix; //~ ERROR string literal with a suffix is invalid
|
||||
b""suffix; //~ ERROR byte string literal with a suffix is invalid
|
||||
r#""#suffix; //~ ERROR string literal with a suffix is invalid
|
||||
br#""#suffix; //~ ERROR byte string literal with a suffix is invalid
|
||||
'a'suffix; //~ ERROR char literal with a suffix is invalid
|
||||
b'a'suffix; //~ ERROR byte literal with a suffix is invalid
|
||||
""suffix; //~ ERROR suffixes on a string literal are invalid
|
||||
b""suffix; //~ ERROR suffixes on a byte string literal are invalid
|
||||
r#""#suffix; //~ ERROR suffixes on a string literal are invalid
|
||||
br#""#suffix; //~ ERROR suffixes on a byte string literal are invalid
|
||||
'a'suffix; //~ ERROR suffixes on a char literal are invalid
|
||||
b'a'suffix; //~ ERROR suffixes on a byte literal are invalid
|
||||
|
||||
1234u1024; //~ ERROR invalid width `1024` for integer literal
|
||||
1234i1024; //~ ERROR invalid width `1024` for integer literal
|
||||
|
@ -1,50 +1,50 @@
|
||||
error: ABI spec with a suffix is invalid
|
||||
error: suffixes on an ABI spec are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:5:5
|
||||
|
|
||||
LL | "C"suffix
|
||||
| ^^^^^^^^^ ABI spec with a suffix is invalid
|
||||
| ^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: ABI spec with a suffix is invalid
|
||||
error: suffixes on an ABI spec are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:9:5
|
||||
|
|
||||
LL | "C"suffix
|
||||
| ^^^^^^^^^ ABI spec with a suffix is invalid
|
||||
| ^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: string literal with a suffix is invalid
|
||||
error: suffixes on a string literal are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:13:5
|
||||
|
|
||||
LL | ""suffix;
|
||||
| ^^^^^^^^ string literal with a suffix is invalid
|
||||
| ^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: byte string literal with a suffix is invalid
|
||||
error: suffixes on a byte string literal are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:14:5
|
||||
|
|
||||
LL | b""suffix;
|
||||
| ^^^^^^^^^ byte string literal with a suffix is invalid
|
||||
| ^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: string literal with a suffix is invalid
|
||||
error: suffixes on a string literal are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:15:5
|
||||
|
|
||||
LL | r#""#suffix;
|
||||
| ^^^^^^^^^^^ string literal with a suffix is invalid
|
||||
| ^^^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: byte string literal with a suffix is invalid
|
||||
error: suffixes on a byte string literal are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:16:5
|
||||
|
|
||||
LL | br#""#suffix;
|
||||
| ^^^^^^^^^^^^ byte string literal with a suffix is invalid
|
||||
| ^^^^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: char literal with a suffix is invalid
|
||||
error: suffixes on a char literal are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:17:5
|
||||
|
|
||||
LL | 'a'suffix;
|
||||
| ^^^^^^^^^ char literal with a suffix is invalid
|
||||
| ^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: byte literal with a suffix is invalid
|
||||
error: suffixes on a byte literal are invalid
|
||||
--> $DIR/bad-lit-suffixes.rs:18:5
|
||||
|
|
||||
LL | b'a'suffix;
|
||||
| ^^^^^^^^^^ byte literal with a suffix is invalid
|
||||
| ^^^^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: invalid width `1024` for integer literal
|
||||
--> $DIR/bad-lit-suffixes.rs:20:5
|
||||
|
18
src/test/ui/parser/issue-59418.rs
Normal file
18
src/test/ui/parser/issue-59418.rs
Normal file
@ -0,0 +1,18 @@
|
||||
struct X(i32,i32,i32);
|
||||
|
||||
fn main() {
|
||||
let a = X(1, 2, 3);
|
||||
let b = a.1suffix;
|
||||
//~^ ERROR suffixes on a tuple index are invalid
|
||||
println!("{}", b);
|
||||
let c = (1, 2, 3);
|
||||
let d = c.1suffix;
|
||||
//~^ ERROR suffixes on a tuple index are invalid
|
||||
println!("{}", d);
|
||||
let s = X { 0suffix: 0, 1: 1, 2: 2 };
|
||||
//~^ ERROR suffixes on a tuple index are invalid
|
||||
match s {
|
||||
X { 0suffix: _, .. } => {}
|
||||
//~^ ERROR suffixes on a tuple index are invalid
|
||||
}
|
||||
}
|
26
src/test/ui/parser/issue-59418.stderr
Normal file
26
src/test/ui/parser/issue-59418.stderr
Normal file
@ -0,0 +1,26 @@
|
||||
error: suffixes on a tuple index are invalid
|
||||
--> $DIR/issue-59418.rs:5:15
|
||||
|
|
||||
LL | let b = a.1suffix;
|
||||
| ^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: suffixes on a tuple index are invalid
|
||||
--> $DIR/issue-59418.rs:9:15
|
||||
|
|
||||
LL | let d = c.1suffix;
|
||||
| ^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: suffixes on a tuple index are invalid
|
||||
--> $DIR/issue-59418.rs:12:17
|
||||
|
|
||||
LL | let s = X { 0suffix: 0, 1: 1, 2: 2 };
|
||||
| ^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: suffixes on a tuple index are invalid
|
||||
--> $DIR/issue-59418.rs:15:13
|
||||
|
|
||||
LL | X { 0suffix: _, .. } => {}
|
||||
| ^^^^^^^ invalid suffix `suffix`
|
||||
|
||||
error: aborting due to 4 previous errors
|
||||
|
Loading…
Reference in New Issue
Block a user