Skip to content

Commit

Permalink
Point at definition when misusing ADT
Browse files Browse the repository at this point in the history
When given `struct Foo(usize)` and using it as `Foo {}` or `Foo`, point at
`Foo`'s definition in the error.
  • Loading branch information
estebank committed Sep 22, 2019
1 parent 4ff32c0 commit 2ae9016
Show file tree
Hide file tree
Showing 20 changed files with 126 additions and 24 deletions.
22 changes: 14 additions & 8 deletions src/librustc_resolve/late/diagnostics.rs
Original file line number Diff line number Diff line change
Expand Up @@ -348,7 +348,7 @@ impl<'a> LateResolutionVisitor<'a, '_> {
_ => false,
};

let mut bad_struct_syntax_suggestion = || {
let mut bad_struct_syntax_suggestion = |def_id: DefId| {
let (followed_by_brace, closing_brace) = self.followed_by_brace(span);
let mut suggested = false;
match source {
Expand All @@ -374,6 +374,9 @@ impl<'a> LateResolutionVisitor<'a, '_> {
_ => {}
}
if !suggested {
if let Some(span) = self.r.definitions.opt_span(def_id) {
err.span_label(span, &format!("`{}` defined here", path_str));
}
err.span_label(
span,
format!("did you mean `{} {{ /* fields */ }}`?", path_str),
Expand Down Expand Up @@ -437,18 +440,21 @@ impl<'a> LateResolutionVisitor<'a, '_> {
);
}
} else {
bad_struct_syntax_suggestion();
bad_struct_syntax_suggestion(def_id);
}
}
(Res::Def(DefKind::Union, _), _) |
(Res::Def(DefKind::Variant, _), _) |
(Res::Def(DefKind::Ctor(_, CtorKind::Fictive), _), _) if ns == ValueNS => {
bad_struct_syntax_suggestion();
(Res::Def(DefKind::Union, def_id), _) |
(Res::Def(DefKind::Variant, def_id), _) |
(Res::Def(DefKind::Ctor(_, CtorKind::Fictive), def_id), _) if ns == ValueNS => {
bad_struct_syntax_suggestion(def_id);
}
(Res::Def(DefKind::Ctor(_, CtorKind::Fn), _), _) if ns == ValueNS => {
(Res::Def(DefKind::Ctor(_, CtorKind::Fn), def_id), _) if ns == ValueNS => {
if let Some(span) = self.r.definitions.opt_span(def_id) {
err.span_label(span, &format!("`{}` defined here", path_str));
}
err.span_label(
span,
format!("did you mean `{} ( /* fields */ )`?", path_str),
format!("did you mean `{}( /* fields */ )`?", path_str),
);
}
(Res::SelfTy(..), _) if ns == ValueNS => {
Expand Down
12 changes: 12 additions & 0 deletions src/test/ui/empty/empty-struct-braces-expr.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0423]: expected value, found struct `Empty1`
--> $DIR/empty-struct-braces-expr.rs:15:14
|
LL | struct Empty1 {}
| ---------------- `Empty1` defined here
...
LL | let e1 = Empty1;
| ^^^^^^
| |
Expand All @@ -10,6 +13,9 @@ LL | let e1 = Empty1;
error[E0423]: expected function, found struct `Empty1`
--> $DIR/empty-struct-braces-expr.rs:16:14
|
LL | struct Empty1 {}
| ---------------- `Empty1` defined here
...
LL | let e1 = Empty1();
| ^^^^^^
| |
Expand All @@ -19,12 +25,18 @@ LL | let e1 = Empty1();
error[E0423]: expected value, found struct variant `E::Empty3`
--> $DIR/empty-struct-braces-expr.rs:17:14
|
LL | Empty3 {}
| --------- `E::Empty3` defined here
...
LL | let e3 = E::Empty3;
| ^^^^^^^^^ did you mean `E::Empty3 { /* fields */ }`?

error[E0423]: expected function, found struct variant `E::Empty3`
--> $DIR/empty-struct-braces-expr.rs:18:14
|
LL | Empty3 {}
| --------- `E::Empty3` defined here
...
LL | let e3 = E::Empty3();
| ^^^^^^^^^ did you mean `E::Empty3 { /* fields */ }`?

Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/empty/empty-struct-braces-pat-1.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0532]: expected unit struct/variant or constant, found struct variant `E::Empty3`
--> $DIR/empty-struct-braces-pat-1.rs:24:9
|
LL | Empty3 {}
| --------- `E::Empty3` defined here
...
LL | E::Empty3 => ()
| ^^^^^^^^^ did you mean `E::Empty3 { /* fields */ }`?

Expand Down
6 changes: 6 additions & 0 deletions src/test/ui/empty/empty-struct-braces-pat-2.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0532]: expected tuple struct/variant, found struct `Empty1`
--> $DIR/empty-struct-braces-pat-2.rs:15:9
|
LL | struct Empty1 {}
| ---------------- `Empty1` defined here
...
LL | Empty1() => ()
| ^^^^^^
| |
Expand All @@ -19,6 +22,9 @@ LL | XEmpty1() => ()
error[E0532]: expected tuple struct/variant, found struct `Empty1`
--> $DIR/empty-struct-braces-pat-2.rs:21:9
|
LL | struct Empty1 {}
| ---------------- `Empty1` defined here
...
LL | Empty1(..) => ()
| ^^^^^^
| |
Expand Down
6 changes: 6 additions & 0 deletions src/test/ui/empty/empty-struct-braces-pat-3.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0532]: expected tuple struct/variant, found struct variant `E::Empty3`
--> $DIR/empty-struct-braces-pat-3.rs:17:9
|
LL | Empty3 {}
| --------- `E::Empty3` defined here
...
LL | E::Empty3() => ()
| ^^^^^^^^^ did you mean `E::Empty3 { /* fields */ }`?

Expand All @@ -16,6 +19,9 @@ LL | XE::XEmpty3() => ()
error[E0532]: expected tuple struct/variant, found struct variant `E::Empty3`
--> $DIR/empty-struct-braces-pat-3.rs:25:9
|
LL | Empty3 {}
| --------- `E::Empty3` defined here
...
LL | E::Empty3(..) => ()
| ^^^^^^^^^ did you mean `E::Empty3 { /* fields */ }`?

Expand Down
7 changes: 5 additions & 2 deletions src/test/ui/empty/empty-struct-tuple-pat.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,11 @@ LL | XEmpty6 => ()
error[E0532]: expected unit struct/variant or constant, found tuple variant `E::Empty4`
--> $DIR/empty-struct-tuple-pat.rs:29:9
|
LL | Empty4()
| -------- `E::Empty4` defined here
...
LL | E::Empty4 => ()
| ^^^^^^^^^ did you mean `E::Empty4 ( /* fields */ )`?
| ^^^^^^^^^ did you mean `E::Empty4( /* fields */ )`?

error[E0532]: expected unit struct/variant or constant, found tuple variant `XE::XEmpty5`
--> $DIR/empty-struct-tuple-pat.rs:33:9
Expand All @@ -29,7 +32,7 @@ LL | XE::XEmpty5 => (),
| ^^^^-------
| | |
| | help: a unit variant with a similar name exists: `XEmpty4`
| did you mean `XE::XEmpty5 ( /* fields */ )`?
| did you mean `XE::XEmpty5( /* fields */ )`?

error: aborting due to 4 previous errors

Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/error-codes/E0423.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ LL | for _ in (std::ops::Range { start: 0, end: 10 }) {}
error[E0423]: expected function, found struct `Foo`
--> $DIR/E0423.rs:4:13
|
LL | struct Foo { a: bool };
| ---------------------- `Foo` defined here
LL |
LL | let f = Foo();
| ^^^
| |
Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/issues/issue-19086.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0532]: expected tuple struct/variant, found struct variant `FooB`
--> $DIR/issue-19086.rs:10:9
|
LL | FooB { x: i32, y: i32 }
| ----------------------- `FooB` defined here
...
LL | FooB(a, b) => println!("{} {}", a, b),
| ^^^^ did you mean `FooB { /* fields */ }`?

Expand Down
5 changes: 4 additions & 1 deletion src/test/ui/issues/issue-32004.stderr
Original file line number Diff line number Diff line change
@@ -1,11 +1,14 @@
error[E0532]: expected unit struct/variant or constant, found tuple variant `Foo::Bar`
--> $DIR/issue-32004.rs:10:9
|
LL | Bar(i32),
| -------- `Foo::Bar` defined here
...
LL | Foo::Bar => {}
| ^^^^^---
| | |
| | help: a unit variant with a similar name exists: `Baz`
| did you mean `Foo::Bar ( /* fields */ )`?
| did you mean `Foo::Bar( /* fields */ )`?

error[E0532]: expected tuple struct/variant, found unit struct `S`
--> $DIR/issue-32004.rs:16:9
Expand Down
8 changes: 7 additions & 1 deletion src/test/ui/issues/issue-63983.stderr
Original file line number Diff line number Diff line change
@@ -1,12 +1,18 @@
error[E0532]: expected unit struct/variant or constant, found tuple variant `MyEnum::Tuple`
--> $DIR/issue-63983.rs:8:9
|
LL | Tuple(i32),
| ---------- `MyEnum::Tuple` defined here
...
LL | MyEnum::Tuple => "",
| ^^^^^^^^^^^^^ did you mean `MyEnum::Tuple ( /* fields */ )`?
| ^^^^^^^^^^^^^ did you mean `MyEnum::Tuple( /* fields */ )`?

error[E0532]: expected unit struct/variant or constant, found struct variant `MyEnum::Struct`
--> $DIR/issue-63983.rs:10:9
|
LL | Struct{ s: i32 },
| ---------------- `MyEnum::Struct` defined here
...
LL | MyEnum::Struct => "",
| ^^^^^^^^^^^^^^ did you mean `MyEnum::Struct { /* fields */ }`?

Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/namespace/namespace-mix.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,9 @@ LL | use namespace_mix::xm2::S;
error[E0423]: expected value, found struct variant `m7::V`
--> $DIR/namespace-mix.rs:100:11
|
LL | V {},
| ---- `m7::V` defined here
...
LL | check(m7::V);
| ^^^^^ did you mean `m7::V { /* fields */ }`?
help: a tuple variant with a similar name exists
Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/parser/recover-from-bad-variant.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@ LL | let x = Enum::Foo(a: 3, b: 4);
error[E0532]: expected tuple struct/variant, found struct variant `Enum::Foo`
--> $DIR/recover-from-bad-variant.rs:10:9
|
LL | Foo { a: usize, b: usize },
| -------------------------- `Enum::Foo` defined here
...
LL | Enum::Foo(a, b) => {}
| ^^^^^^^^^ did you mean `Enum::Foo { /* fields */ }`?

Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/resolve/issue-18252.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0423]: expected function, found struct variant `Foo::Variant`
--> $DIR/issue-18252.rs:6:13
|
LL | Variant { x: usize }
| -------------------- `Foo::Variant` defined here
...
LL | let f = Foo::Variant(42);
| ^^^^^^^^^^^^ did you mean `Foo::Variant { /* fields */ }`?

Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/resolve/issue-19452.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0423]: expected value, found struct variant `Homura::Madoka`
--> $DIR/issue-19452.rs:10:18
|
LL | Madoka { age: u32 }
| ------------------- `Homura::Madoka` defined here
...
LL | let homura = Homura::Madoka;
| ^^^^^^^^^^^^^^ did you mean `Homura::Madoka { /* fields */ }`?

Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/resolve/issue-39226.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0423]: expected value, found struct `Handle`
--> $DIR/issue-39226.rs:11:17
|
LL | struct Handle {}
| ---------------- `Handle` defined here
...
LL | handle: Handle
| ^^^^^^
| |
Expand Down
9 changes: 7 additions & 2 deletions src/test/ui/resolve/issue-6702.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,13 @@
error[E0423]: expected function, found struct `Monster`
--> $DIR/issue-6702.rs:7:14
|
LL | let _m = Monster();
| ^^^^^^^ did you mean `Monster { /* fields */ }`?
LL | / struct Monster {
LL | | damage: isize
LL | | }
| |_- `Monster` defined here
...
LL | let _m = Monster();
| ^^^^^^^ did you mean `Monster { /* fields */ }`?

error: aborting due to previous error

Expand Down
36 changes: 28 additions & 8 deletions src/test/ui/resolve/privacy-enum-ctor.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,13 @@ LL | m::Z::Unit;
error[E0423]: expected value, found struct variant `Z::Struct`
--> $DIR/privacy-enum-ctor.rs:29:20
|
LL | let _: Z = Z::Struct;
| ^^^^^^^^^ did you mean `Z::Struct { /* fields */ }`?
LL | / Struct {
LL | | s: u8,
LL | | },
| |_____________- `Z::Struct` defined here
...
LL | let _: Z = Z::Struct;
| ^^^^^^^^^ did you mean `Z::Struct { /* fields */ }`?

error[E0423]: expected value, found enum `m::E`
--> $DIR/privacy-enum-ctor.rs:41:16
Expand Down Expand Up @@ -63,8 +68,13 @@ LL | use std::f64::consts::E;
error[E0423]: expected value, found struct variant `m::E::Struct`
--> $DIR/privacy-enum-ctor.rs:45:16
|
LL | let _: E = m::E::Struct;
| ^^^^^^^^^^^^ did you mean `m::E::Struct { /* fields */ }`?
LL | / Struct {
LL | | s: u8,
LL | | },
| |_________- `m::E::Struct` defined here
...
LL | let _: E = m::E::Struct;
| ^^^^^^^^^^^^ did you mean `m::E::Struct { /* fields */ }`?

error[E0423]: expected value, found enum `E`
--> $DIR/privacy-enum-ctor.rs:49:16
Expand All @@ -89,8 +99,13 @@ LL | use std::f64::consts::E;
error[E0423]: expected value, found struct variant `E::Struct`
--> $DIR/privacy-enum-ctor.rs:53:16
|
LL | let _: E = E::Struct;
| ^^^^^^^^^ did you mean `E::Struct { /* fields */ }`?
LL | / Struct {
LL | | s: u8,
LL | | },
| |_________- `E::Struct` defined here
...
LL | let _: E = E::Struct;
| ^^^^^^^^^ did you mean `E::Struct { /* fields */ }`?

error[E0412]: cannot find type `Z` in this scope
--> $DIR/privacy-enum-ctor.rs:57:12
Expand Down Expand Up @@ -151,8 +166,13 @@ LL | use m::n::Z;
error[E0423]: expected value, found struct variant `m::n::Z::Struct`
--> $DIR/privacy-enum-ctor.rs:64:16
|
LL | let _: Z = m::n::Z::Struct;
| ^^^^^^^^^^^^^^^ did you mean `m::n::Z::Struct { /* fields */ }`?
LL | / Struct {
LL | | s: u8,
LL | | },
| |_____________- `m::n::Z::Struct` defined here
...
LL | let _: Z = m::n::Z::Struct;
| ^^^^^^^^^^^^^^^ did you mean `m::n::Z::Struct { /* fields */ }`?

error[E0412]: cannot find type `Z` in this scope
--> $DIR/privacy-enum-ctor.rs:68:12
Expand Down
9 changes: 7 additions & 2 deletions src/test/ui/resolve/privacy-struct-ctor.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,13 @@ LL | S;
error[E0423]: expected value, found struct `S2`
--> $DIR/privacy-struct-ctor.rs:38:5
|
LL | S2;
| ^^ did you mean `S2 { /* fields */ }`?
LL | / pub struct S2 {
LL | | s: u8
LL | | }
| |_____- `S2` defined here
...
LL | S2;
| ^^ did you mean `S2 { /* fields */ }`?

error[E0423]: expected value, found struct `xcrate::S`
--> $DIR/privacy-struct-ctor.rs:43:5
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0423]: expected value, found struct variant `E::B`
--> $DIR/fn-or-tuple-struct-without-args.rs:36:16
|
LL | B { a: usize },
| -------------- `E::B` defined here
...
LL | let _: E = E::B;
| ^^^-
| | |
Expand Down
3 changes: 3 additions & 0 deletions src/test/ui/suggestions/issue-61226.stderr
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
error[E0423]: expected value, found struct `X`
--> $DIR/issue-61226.rs:3:10
|
LL | struct X {}
| ----------- `X` defined here
LL | fn main() {
LL | vec![X]; //…
| ^ did you mean `X { /* fields */ }`?

Expand Down

0 comments on commit 2ae9016

Please sign in to comment.