Skip to content

Commit 0fae4ea

Browse files
committed
deduplicate warnings (attempt 2)
1 parent 0a00c74 commit 0fae4ea

File tree

3 files changed

+38
-23
lines changed

3 files changed

+38
-23
lines changed

compiler/rustc_passes/src/stability.rs

Lines changed: 32 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,12 +8,12 @@ use rustc_data_structures::fx::FxIndexMap;
88
use rustc_data_structures::unord::{ExtendUnord, UnordMap, UnordSet};
99
use rustc_feature::{EnabledLangFeature, EnabledLibFeature};
1010
use rustc_hir::attrs::{AttributeKind, DeprecatedSince};
11-
use rustc_hir::def::{DefKind, Res};
11+
use rustc_hir::def::{CtorOf, DefKind, Res};
1212
use rustc_hir::def_id::{CRATE_DEF_ID, LOCAL_CRATE, LocalDefId, LocalModDefId};
1313
use rustc_hir::intravisit::{self, Visitor, VisitorExt};
1414
use rustc_hir::{
15-
self as hir, AmbigArg, ConstStability, DefaultBodyStability, FieldDef, Item, ItemKind,
16-
Stability, StabilityLevel, StableSince, TraitRef, Ty, TyKind, UnstableReason,
15+
self as hir, AmbigArg, ConstStability, DefaultBodyStability, FieldDef, HirId, Item, ItemKind,
16+
Path, Stability, StabilityLevel, StableSince, TraitRef, Ty, TyKind, UnstableReason, UsePath,
1717
VERSION_PLACEHOLDER, Variant, find_attr,
1818
};
1919
use rustc_middle::hir::nested_filter;
@@ -739,6 +739,35 @@ impl<'tcx> Visitor<'tcx> for Checker<'tcx> {
739739
intravisit::walk_poly_trait_ref(self, t);
740740
}
741741

742+
fn visit_use(&mut self, path: &'tcx UsePath<'tcx>, hir_id: HirId) {
743+
let UsePath { segments, ref res, span } = *path;
744+
745+
// the first resolution of a path, to deduplicate
746+
let mut first_resolution = None;
747+
748+
for res in res.present_items() {
749+
// A use item can import something from two namespaces at the same time.
750+
// For deprecation/stability we don't want to warn twice.
751+
// This specifically happens with constructors for unit/tuple structs.
752+
if let Some(did) = res.opt_def_id() {
753+
// If it's a ctor, we need the parent did.
754+
// The parent defid of a constructor is that of the struct it constructs.
755+
let did = match self.tcx.def_kind(did) {
756+
DefKind::Ctor(CtorOf::Struct, _) => self.tcx.parent(did),
757+
_ => did,
758+
};
759+
760+
// When we've already seen a defid, don't walk this path.
761+
// This avoids the duplicate deprecation warnings.
762+
if first_resolution.replace(did).is_some_and(|first| first == did) {
763+
continue;
764+
}
765+
}
766+
767+
self.visit_path(&Path { segments, res, span }, hir_id);
768+
}
769+
}
770+
742771
fn visit_path(&mut self, path: &hir::Path<'tcx>, id: hir::HirId) {
743772
if let Some(def_id) = path.res.opt_def_id() {
744773
let method_span = path.segments.last().map(|s| s.ident.span);

tests/ui/deprecation/unit_and_tuple_struct.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,8 @@ pub mod a {
1111

1212
use a::Foo;
1313
//~^ ERROR use of deprecated struct `a::Foo`
14-
//~| ERROR use of deprecated unit struct `a::Foo`
1514
use a::Bar;
1615
//~^ ERROR use of deprecated struct `a::Bar`
17-
//~| ERROR use of deprecated tuple struct `a::Bar`
1816
use a::Baz;
1917
//~^ ERROR use of deprecated struct `a::Baz`
2018

tests/ui/deprecation/unit_and_tuple_struct.stderr

Lines changed: 6 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -10,47 +10,35 @@ note: the lint level is defined here
1010
LL | #![deny(deprecated)]
1111
| ^^^^^^^^^^
1212

13-
error: use of deprecated unit struct `a::Foo`
14-
--> $DIR/unit_and_tuple_struct.rs:12:8
15-
|
16-
LL | use a::Foo;
17-
| ^^^
18-
1913
error: use of deprecated struct `a::Bar`
20-
--> $DIR/unit_and_tuple_struct.rs:15:8
21-
|
22-
LL | use a::Bar;
23-
| ^^^
24-
25-
error: use of deprecated tuple struct `a::Bar`
26-
--> $DIR/unit_and_tuple_struct.rs:15:8
14+
--> $DIR/unit_and_tuple_struct.rs:14:8
2715
|
2816
LL | use a::Bar;
2917
| ^^^
3018

3119
error: use of deprecated struct `a::Baz`
32-
--> $DIR/unit_and_tuple_struct.rs:18:8
20+
--> $DIR/unit_and_tuple_struct.rs:16:8
3321
|
3422
LL | use a::Baz;
3523
| ^^^
3624

3725
error: use of deprecated unit struct `a::Foo`
38-
--> $DIR/unit_and_tuple_struct.rs:22:6
26+
--> $DIR/unit_and_tuple_struct.rs:20:6
3927
|
4028
LL | a::Foo;
4129
| ^^^
4230

4331
error: use of deprecated tuple struct `a::Bar`
44-
--> $DIR/unit_and_tuple_struct.rs:24:6
32+
--> $DIR/unit_and_tuple_struct.rs:22:6
4533
|
4634
LL | a::Bar();
4735
| ^^^
4836

4937
error: use of deprecated struct `a::Baz`
50-
--> $DIR/unit_and_tuple_struct.rs:26:6
38+
--> $DIR/unit_and_tuple_struct.rs:24:6
5139
|
5240
LL | a::Baz {};
5341
| ^^^
5442

55-
error: aborting due to 8 previous errors
43+
error: aborting due to 6 previous errors
5644

0 commit comments

Comments
 (0)