Fix duplicate derive clone suggestion
This commit is contained in:
parent
14c1e71d09
commit
0198ea47d8
3 changed files with 96 additions and 16 deletions
|
@ -1175,11 +1175,11 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
||||||
fn suggest_derive(
|
fn suggest_derive(
|
||||||
&self,
|
&self,
|
||||||
err: &mut DiagnosticBuilder<'_>,
|
err: &mut DiagnosticBuilder<'_>,
|
||||||
unsatisfied_predicates: &Vec<(
|
unsatisfied_predicates: &[(
|
||||||
ty::Predicate<'tcx>,
|
ty::Predicate<'tcx>,
|
||||||
Option<ty::Predicate<'tcx>>,
|
Option<ty::Predicate<'tcx>>,
|
||||||
Option<ObligationCause<'tcx>>,
|
Option<ObligationCause<'tcx>>,
|
||||||
)>,
|
)],
|
||||||
) {
|
) {
|
||||||
let mut derives = Vec::<(String, Span, String)>::new();
|
let mut derives = Vec::<(String, Span, String)>::new();
|
||||||
let mut traits = Vec::<Span>::new();
|
let mut traits = Vec::<Span>::new();
|
||||||
|
@ -1216,23 +1216,24 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
||||||
traits.push(self.tcx.def_span(trait_pred.def_id()));
|
traits.push(self.tcx.def_span(trait_pred.def_id()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
derives.sort();
|
|
||||||
let derives_grouped = derives.into_iter().fold(
|
|
||||||
Vec::<(String, Span, String)>::new(),
|
|
||||||
|mut acc, (self_name, self_span, trait_name)| {
|
|
||||||
if let Some((acc_self_name, _, ref mut traits)) = acc.last_mut() {
|
|
||||||
if acc_self_name == &self_name {
|
|
||||||
traits.push_str(format!(", {}", trait_name).as_str());
|
|
||||||
return acc;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
acc.push((self_name, self_span, trait_name));
|
|
||||||
acc
|
|
||||||
},
|
|
||||||
);
|
|
||||||
traits.sort();
|
traits.sort();
|
||||||
traits.dedup();
|
traits.dedup();
|
||||||
|
|
||||||
|
derives.sort();
|
||||||
|
derives.dedup();
|
||||||
|
|
||||||
|
let mut derives_grouped = Vec::<(String, Span, String)>::new();
|
||||||
|
for (self_name, self_span, trait_name) in derives.into_iter() {
|
||||||
|
if let Some((last_self_name, _, ref mut last_trait_names)) = derives_grouped.last_mut()
|
||||||
|
{
|
||||||
|
if last_self_name == &self_name {
|
||||||
|
last_trait_names.push_str(format!(", {}", trait_name).as_str());
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
derives_grouped.push((self_name, self_span, trait_name));
|
||||||
|
}
|
||||||
|
|
||||||
let len = traits.len();
|
let len = traits.len();
|
||||||
if len > 0 {
|
if len > 0 {
|
||||||
let span: MultiSpan = traits.into();
|
let span: MultiSpan = traits.into();
|
||||||
|
|
25
src/test/ui/derives/issue-91492.rs
Normal file
25
src/test/ui/derives/issue-91492.rs
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
// Reproduce the issue with vec
|
||||||
|
pub struct NoDerives;
|
||||||
|
fn fun1(foo: &mut Vec<NoDerives>, bar: &[NoDerives]) {
|
||||||
|
foo.extend_from_slice(bar); //~ ERROR
|
||||||
|
}
|
||||||
|
|
||||||
|
// Reproduce the issue with vec
|
||||||
|
// and demonstrate that other derives are ignored in the suggested output
|
||||||
|
#[derive(Default, PartialEq)]
|
||||||
|
pub struct SomeDerives;
|
||||||
|
fn fun2(foo: &mut Vec<SomeDerives>, bar: &[SomeDerives]) {
|
||||||
|
foo.extend_from_slice(bar); //~ ERROR
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try and fail to reproduce the issue without vec.
|
||||||
|
// No idea why it doesnt reproduce the issue but its still a useful test case.
|
||||||
|
struct Object<T, A>(T, A);
|
||||||
|
impl<T: Clone, A: Default> Object<T, A> {
|
||||||
|
fn use_clone(&self) {}
|
||||||
|
}
|
||||||
|
fn fun3(foo: Object<NoDerives, SomeDerives>) {
|
||||||
|
foo.use_clone(); //~ ERROR
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {}
|
54
src/test/ui/derives/issue-91492.stderr
Normal file
54
src/test/ui/derives/issue-91492.stderr
Normal file
|
@ -0,0 +1,54 @@
|
||||||
|
error[E0599]: the method `extend_from_slice` exists for mutable reference `&mut Vec<NoDerives>`, but its trait bounds were not satisfied
|
||||||
|
--> $DIR/issue-91492.rs:4:9
|
||||||
|
|
|
||||||
|
LL | pub struct NoDerives;
|
||||||
|
| --------------------- doesn't satisfy `NoDerives: Clone`
|
||||||
|
LL | fn fun1(foo: &mut Vec<NoDerives>, bar: &[NoDerives]) {
|
||||||
|
LL | foo.extend_from_slice(bar);
|
||||||
|
| ^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= note: the following trait bounds were not satisfied:
|
||||||
|
`NoDerives: Clone`
|
||||||
|
help: consider annotating `NoDerives` with `#[derive(Clone)]`
|
||||||
|
|
|
||||||
|
LL | #[derive(Clone)]
|
||||||
|
|
|
||||||
|
|
||||||
|
error[E0599]: the method `extend_from_slice` exists for mutable reference `&mut Vec<SomeDerives>`, but its trait bounds were not satisfied
|
||||||
|
--> $DIR/issue-91492.rs:12:9
|
||||||
|
|
|
||||||
|
LL | pub struct SomeDerives;
|
||||||
|
| ----------------------- doesn't satisfy `SomeDerives: Clone`
|
||||||
|
LL | fn fun2(foo: &mut Vec<SomeDerives>, bar: &[SomeDerives]) {
|
||||||
|
LL | foo.extend_from_slice(bar);
|
||||||
|
| ^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= note: the following trait bounds were not satisfied:
|
||||||
|
`SomeDerives: Clone`
|
||||||
|
help: consider annotating `SomeDerives` with `#[derive(Clone)]`
|
||||||
|
|
|
||||||
|
LL | #[derive(Clone)]
|
||||||
|
|
|
||||||
|
|
||||||
|
error[E0599]: the method `use_clone` exists for struct `Object<NoDerives, SomeDerives>`, but its trait bounds were not satisfied
|
||||||
|
--> $DIR/issue-91492.rs:22:9
|
||||||
|
|
|
||||||
|
LL | pub struct NoDerives;
|
||||||
|
| --------------------- doesn't satisfy `NoDerives: Clone`
|
||||||
|
...
|
||||||
|
LL | struct Object<T, A>(T, A);
|
||||||
|
| -------------------------- method `use_clone` not found for this
|
||||||
|
...
|
||||||
|
LL | foo.use_clone();
|
||||||
|
| ^^^^^^^^^ method cannot be called on `Object<NoDerives, SomeDerives>` due to unsatisfied trait bounds
|
||||||
|
|
|
||||||
|
= note: the following trait bounds were not satisfied:
|
||||||
|
`NoDerives: Clone`
|
||||||
|
help: consider annotating `NoDerives` with `#[derive(Clone)]`
|
||||||
|
|
|
||||||
|
LL | #[derive(Clone)]
|
||||||
|
|
|
||||||
|
|
||||||
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0599`.
|
Loading…
Add table
Add a link
Reference in a new issue