Skip to content

Commit 0936b1c

Browse files
authored
Rollup merge of rust-lang#122038 - Alexendoo:unused-qualifications, r=petrochenkov
Fix linting paths with qself in `unused_qualifications` Fixes rust-lang#121999 `resolve_qpath` ends up being called again with `qself` set to `None` to check trait items from fully qualified paths. To avoid this the lint is moved to a place that accounts for this already https://github.com/rust-lang/rust/blob/96561a8fd134e8f2b205769a4fca03b392d9f484/compiler/rustc_resolve/src/late.rs#L4074-L4088 r? `@petrochenkov`
2 parents 90a9718 + 6120de9 commit 0936b1c

File tree

4 files changed

+56
-34
lines changed

4 files changed

+56
-34
lines changed

compiler/rustc_resolve/src/late.rs

+37-33
Original file line numberDiff line numberDiff line change
@@ -3954,6 +3954,7 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
39543954
// Avoid recording definition of `A::B` in `<T as A>::B::C`.
39553955
self.r.record_partial_res(node_id, partial_res);
39563956
self.resolve_elided_lifetimes_in_path(partial_res, path, source, path_span);
3957+
self.lint_unused_qualifications(path, ns, finalize);
39573958
}
39583959

39593960
partial_res
@@ -4165,39 +4166,6 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
41654166
PathResult::Indeterminate => bug!("indeterminate path result in resolve_qpath"),
41664167
};
41674168

4168-
if path.iter().all(|seg| !seg.ident.span.from_expansion()) {
4169-
let end_pos =
4170-
path.iter().position(|seg| seg.has_generic_args).map_or(path.len(), |pos| pos + 1);
4171-
let unqualified =
4172-
path[..end_pos].iter().enumerate().skip(1).rev().find_map(|(i, seg)| {
4173-
// Preserve the current namespace for the final path segment, but use the type
4174-
// namespace for all preceding segments
4175-
//
4176-
// e.g. for `std::env::args` check the `ValueNS` for `args` but the `TypeNS` for
4177-
// `std` and `env`
4178-
//
4179-
// If the final path segment is beyond `end_pos` all the segments to check will
4180-
// use the type namespace
4181-
let ns = if i + 1 == path.len() { ns } else { TypeNS };
4182-
let res = self.r.partial_res_map.get(&seg.id?)?.full_res()?;
4183-
let binding = self.resolve_ident_in_lexical_scope(seg.ident, ns, None, None)?;
4184-
4185-
(res == binding.res()).then_some(seg)
4186-
});
4187-
4188-
if let Some(unqualified) = unqualified {
4189-
self.r.lint_buffer.buffer_lint_with_diagnostic(
4190-
lint::builtin::UNUSED_QUALIFICATIONS,
4191-
finalize.node_id,
4192-
finalize.path_span,
4193-
"unnecessary qualification",
4194-
lint::BuiltinLintDiag::UnusedQualifications {
4195-
removal_span: finalize.path_span.until(unqualified.ident.span),
4196-
},
4197-
);
4198-
}
4199-
}
4200-
42014169
Ok(Some(result))
42024170
}
42034171

@@ -4676,6 +4644,42 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
46764644
self.r.doc_link_traits_in_scope = doc_link_traits_in_scope;
46774645
}
46784646
}
4647+
4648+
fn lint_unused_qualifications(&mut self, path: &[Segment], ns: Namespace, finalize: Finalize) {
4649+
if path.iter().any(|seg| seg.ident.span.from_expansion()) {
4650+
return;
4651+
}
4652+
4653+
let end_pos =
4654+
path.iter().position(|seg| seg.has_generic_args).map_or(path.len(), |pos| pos + 1);
4655+
let unqualified = path[..end_pos].iter().enumerate().skip(1).rev().find_map(|(i, seg)| {
4656+
// Preserve the current namespace for the final path segment, but use the type
4657+
// namespace for all preceding segments
4658+
//
4659+
// e.g. for `std::env::args` check the `ValueNS` for `args` but the `TypeNS` for
4660+
// `std` and `env`
4661+
//
4662+
// If the final path segment is beyond `end_pos` all the segments to check will
4663+
// use the type namespace
4664+
let ns = if i + 1 == path.len() { ns } else { TypeNS };
4665+
let res = self.r.partial_res_map.get(&seg.id?)?.full_res()?;
4666+
let binding = self.resolve_ident_in_lexical_scope(seg.ident, ns, None, None)?;
4667+
4668+
(res == binding.res()).then_some(seg)
4669+
});
4670+
4671+
if let Some(unqualified) = unqualified {
4672+
self.r.lint_buffer.buffer_lint_with_diagnostic(
4673+
lint::builtin::UNUSED_QUALIFICATIONS,
4674+
finalize.node_id,
4675+
finalize.path_span,
4676+
"unnecessary qualification",
4677+
lint::BuiltinLintDiag::UnusedQualifications {
4678+
removal_span: path[0].ident.span.until(unqualified.ident.span),
4679+
},
4680+
);
4681+
}
4682+
}
46794683
}
46804684

46814685
/// Walks the whole crate in DFS order, visiting each item, counting the declared number of

tests/ui/lint/lint-qualification.fixed

+3
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@ fn main() {
2424
use std::fmt;
2525
let _: fmt::Result = Ok(()); //~ ERROR: unnecessary qualification
2626

27+
let _ = <bool as Default>::default(); // issue #121999
28+
//~^ ERROR: unnecessary qualification
29+
2730
macro_rules! m { ($a:ident, $b:ident) => {
2831
$crate::foo::bar(); // issue #37357
2932
::foo::bar(); // issue #38682

tests/ui/lint/lint-qualification.rs

+3
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@ fn main() {
2424
use std::fmt;
2525
let _: std::fmt::Result = Ok(()); //~ ERROR: unnecessary qualification
2626

27+
let _ = <bool as ::std::default::Default>::default(); // issue #121999
28+
//~^ ERROR: unnecessary qualification
29+
2730
macro_rules! m { ($a:ident, $b:ident) => {
2831
$crate::foo::bar(); // issue #37357
2932
::foo::bar(); // issue #38682

tests/ui/lint/lint-qualification.stderr

+13-1
Original file line numberDiff line numberDiff line change
@@ -87,5 +87,17 @@ LL - let _: std::fmt::Result = Ok(());
8787
LL + let _: fmt::Result = Ok(());
8888
|
8989

90-
error: aborting due to 7 previous errors
90+
error: unnecessary qualification
91+
--> $DIR/lint-qualification.rs:27:13
92+
|
93+
LL | let _ = <bool as ::std::default::Default>::default(); // issue #121999
94+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
95+
|
96+
help: remove the unnecessary path segments
97+
|
98+
LL - let _ = <bool as ::std::default::Default>::default(); // issue #121999
99+
LL + let _ = <bool as Default>::default(); // issue #121999
100+
|
101+
102+
error: aborting due to 8 previous errors
91103

0 commit comments

Comments
 (0)