Skip to content

Commit 84629a5

Browse files
committed
Extend invalid floating point literal suffix suggestion
1 parent 1603a70 commit 84629a5

File tree

3 files changed

+71
-9
lines changed

3 files changed

+71
-9
lines changed

compiler/rustc_typeck/src/check/expr.rs

Lines changed: 22 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2159,7 +2159,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
21592159
E0610,
21602160
"`{expr_t}` is a primitive type and therefore doesn't have fields",
21612161
);
2162-
let is_valid_suffix = |field: String| {
2162+
let is_valid_suffix = |field: &str| {
21632163
if field == "f32" || field == "f64" {
21642164
return true;
21652165
}
@@ -2184,20 +2184,34 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
21842184
let suffix = chars.collect::<String>();
21852185
suffix.is_empty() || suffix == "f32" || suffix == "f64"
21862186
};
2187+
let is_likely_suffix = |fist_chars: &[char], field: &str| {
2188+
field.len() >= 1
2189+
&& field.to_lowercase().starts_with(fist_chars)
2190+
&& field[1..].chars().all(|c| c.is_ascii_digit())
2191+
};
21872192
if let ty::Infer(ty::IntVar(_)) = expr_t.kind()
21882193
&& let ExprKind::Lit(Spanned {
21892194
node: ast::LitKind::Int(_, ast::LitIntType::Unsuffixed),
21902195
..
21912196
}) = base.kind
21922197
&& !base.span.from_expansion()
2193-
&& is_valid_suffix(field_name)
21942198
{
2195-
err.span_suggestion_verbose(
2196-
field.span.shrink_to_lo(),
2197-
"If the number is meant to be a floating point number, consider adding a `0` after the period",
2198-
'0',
2199-
Applicability::MaybeIncorrect,
2200-
);
2199+
let msg = "If the number is meant to be a floating point number, consider adding a `0` after the period";
2200+
if is_valid_suffix(&field_name) {
2201+
err.span_suggestion_verbose(
2202+
field.span.shrink_to_lo(),
2203+
msg,
2204+
'0',
2205+
Applicability::MaybeIncorrect,
2206+
);
2207+
} else if is_likely_suffix(&['f', 'l'], &field_name) {
2208+
err.span_suggestion_verbose(
2209+
field.span,
2210+
format!("{}, valid float format are `f32` and `f64`", msg),
2211+
"0f32",
2212+
Applicability::MaybeIncorrect,
2213+
);
2214+
}
22012215
}
22022216
err.emit();
22032217
}

src/test/ui/attempted-access-non-fatal.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,8 @@ fn main() {
33
let x = 0;
44
let _ = x.foo; //~ `{integer}` is a primitive type and therefore doesn't have fields [E0610]
55
let _ = x.bar; //~ `{integer}` is a primitive type and therefore doesn't have fields [E0610]
6+
let _ = 0.f; //~ `{integer}` is a primitive type and therefore doesn't have fields [E0610]
7+
let _ = 2.l; //~ `{integer}` is a primitive type and therefore doesn't have fields [E0610]
8+
let _ = 12.F; //~ `{integer}` is a primitive type and therefore doesn't have fields [E0610]
9+
let _ = 34.L; //~ `{integer}` is a primitive type and therefore doesn't have fields [E0610]
610
}

src/test/ui/attempted-access-non-fatal.stderr

Lines changed: 45 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,50 @@ error[E0610]: `{integer}` is a primitive type and therefore doesn't have fields
1010
LL | let _ = x.bar;
1111
| ^^^
1212

13-
error: aborting due to 2 previous errors
13+
error[E0610]: `{integer}` is a primitive type and therefore doesn't have fields
14+
--> $DIR/attempted-access-non-fatal.rs:6:15
15+
|
16+
LL | let _ = 0.f;
17+
| ^
18+
|
19+
help: If the number is meant to be a floating point number, consider adding a `0` after the period, valid float format are `f32` and `f64`
20+
|
21+
LL | let _ = 0.0f32;
22+
| ~~~~
23+
24+
error[E0610]: `{integer}` is a primitive type and therefore doesn't have fields
25+
--> $DIR/attempted-access-non-fatal.rs:7:15
26+
|
27+
LL | let _ = 2.l;
28+
| ^
29+
|
30+
help: If the number is meant to be a floating point number, consider adding a `0` after the period, valid float format are `f32` and `f64`
31+
|
32+
LL | let _ = 2.0f32;
33+
| ~~~~
34+
35+
error[E0610]: `{integer}` is a primitive type and therefore doesn't have fields
36+
--> $DIR/attempted-access-non-fatal.rs:8:16
37+
|
38+
LL | let _ = 12.F;
39+
| ^
40+
|
41+
help: If the number is meant to be a floating point number, consider adding a `0` after the period, valid float format are `f32` and `f64`
42+
|
43+
LL | let _ = 12.0f32;
44+
| ~~~~
45+
46+
error[E0610]: `{integer}` is a primitive type and therefore doesn't have fields
47+
--> $DIR/attempted-access-non-fatal.rs:9:16
48+
|
49+
LL | let _ = 34.L;
50+
| ^
51+
|
52+
help: If the number is meant to be a floating point number, consider adding a `0` after the period, valid float format are `f32` and `f64`
53+
|
54+
LL | let _ = 34.0f32;
55+
| ~~~~
56+
57+
error: aborting due to 6 previous errors
1458

1559
For more information about this error, try `rustc --explain E0610`.

0 commit comments

Comments
 (0)