Skip to content

Commit ae8c677

Browse files
committed
Properly account for self ty in method disambiguation suggestion
Fix #116703.
1 parent df4379b commit ae8c677

File tree

5 files changed

+115
-3
lines changed

5 files changed

+115
-3
lines changed

Diff for: compiler/rustc_hir_typeck/src/method/suggest.rs

+6-3
Original file line numberDiff line numberDiff line change
@@ -1311,7 +1311,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
13111311
let path = self.tcx.def_path_str(trait_ref.skip_binder().def_id);
13121312

13131313
let ty = match item.kind {
1314-
ty::AssocKind::Const | ty::AssocKind::Type => rcvr_ty,
1314+
ty::AssocKind::Const | ty::AssocKind::Type => impl_ty,
13151315
ty::AssocKind::Fn => self
13161316
.tcx
13171317
.fn_sig(item.def_id)
@@ -1329,6 +1329,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
13291329
err,
13301330
path,
13311331
ty,
1332+
impl_ty,
13321333
item.kind,
13331334
self.tcx.def_kind_descr(item.kind.as_def_kind(), item.def_id),
13341335
sugg_span,
@@ -1365,6 +1366,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
13651366
err,
13661367
path,
13671368
rcvr_ty,
1369+
rcvr_ty,
13681370
item.kind,
13691371
self.tcx.def_kind_descr(item.kind.as_def_kind(), item.def_id),
13701372
sugg_span,
@@ -3107,6 +3109,7 @@ fn print_disambiguation_help<'tcx>(
31073109
err: &mut Diagnostic,
31083110
trait_name: String,
31093111
rcvr_ty: Ty<'_>,
3112+
self_ty: Ty<'_>,
31103113
kind: ty::AssocKind,
31113114
def_kind_descr: &'static str,
31123115
span: Span,
@@ -3133,13 +3136,13 @@ fn print_disambiguation_help<'tcx>(
31333136
.join(", "),
31343137
);
31353138
let trait_name = if !fn_has_self_parameter {
3136-
format!("<{rcvr_ty} as {trait_name}>")
3139+
format!("<{self_ty} as {trait_name}>")
31373140
} else {
31383141
trait_name
31393142
};
31403143
(span, format!("{trait_name}::{item_name}{args}"))
31413144
} else {
3142-
(span.with_hi(item_name.span.lo()), format!("<{rcvr_ty} as {trait_name}>::"))
3145+
(span.with_hi(item_name.span.lo()), format!("<{self_ty} as {trait_name}>::"))
31433146
};
31443147
err.span_suggestion_verbose(
31453148
span,
+27
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
trait A {
2+
fn foo(&self);
3+
}
4+
5+
trait B {
6+
fn foo(&self);
7+
}
8+
9+
#[derive(Debug)]
10+
struct S;
11+
12+
impl<T: std::fmt::Debug> A for T {
13+
fn foo(&self) {} //~ NOTE candidate #1
14+
}
15+
16+
impl<T: std::fmt::Debug> B for T {
17+
fn foo(&self) {} //~ NOTE candidate #2
18+
}
19+
20+
fn main() {
21+
let s = S;
22+
S::foo(&s); //~ ERROR multiple applicable items in scope
23+
//~^ NOTE multiple `foo` found
24+
//~| HELP disambiguate
25+
//~| HELP disambiguate
26+
}
27+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
error[E0034]: multiple applicable items in scope
2+
--> $DIR/disambiguate-multiple-blanket-impl.rs:22:8
3+
|
4+
LL | S::foo(&s);
5+
| ^^^ multiple `foo` found
6+
|
7+
note: candidate #1 is defined in an impl of the trait `A` for the type `T`
8+
--> $DIR/disambiguate-multiple-blanket-impl.rs:13:5
9+
|
10+
LL | fn foo(&self) {}
11+
| ^^^^^^^^^^^^^
12+
note: candidate #2 is defined in an impl of the trait `B` for the type `T`
13+
--> $DIR/disambiguate-multiple-blanket-impl.rs:17:5
14+
|
15+
LL | fn foo(&self) {}
16+
| ^^^^^^^^^^^^^
17+
help: disambiguate the method for candidate #1
18+
|
19+
LL | <T as A>::foo(&s);
20+
| ~~~~~~~~~~
21+
help: disambiguate the method for candidate #2
22+
|
23+
LL | <T as B>::foo(&s);
24+
| ~~~~~~~~~~
25+
26+
error: aborting due to previous error
27+
28+
For more information about this error, try `rustc --explain E0034`.

Diff for: tests/ui/methods/disambiguate-multiple-impl.rs

+26
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
trait A {
2+
fn foo(&self);
3+
}
4+
5+
trait B {
6+
fn foo(&self);
7+
}
8+
9+
struct S;
10+
11+
impl A for S {
12+
fn foo(&self) {} //~ NOTE candidate #1
13+
}
14+
15+
impl B for S {
16+
fn foo(&self) {} //~ NOTE candidate #2
17+
}
18+
19+
fn main() {
20+
let s = S;
21+
S::foo(&s); //~ ERROR multiple applicable items in scope
22+
//~^ NOTE multiple `foo` found
23+
//~| HELP disambiguate
24+
//~| HELP disambiguate
25+
}
26+

Diff for: tests/ui/methods/disambiguate-multiple-impl.stderr

+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
error[E0034]: multiple applicable items in scope
2+
--> $DIR/disambiguate-multiple-impl.rs:21:8
3+
|
4+
LL | S::foo(&s);
5+
| ^^^ multiple `foo` found
6+
|
7+
note: candidate #1 is defined in an impl of the trait `A` for the type `S`
8+
--> $DIR/disambiguate-multiple-impl.rs:12:5
9+
|
10+
LL | fn foo(&self) {}
11+
| ^^^^^^^^^^^^^
12+
note: candidate #2 is defined in an impl of the trait `B` for the type `S`
13+
--> $DIR/disambiguate-multiple-impl.rs:16:5
14+
|
15+
LL | fn foo(&self) {}
16+
| ^^^^^^^^^^^^^
17+
help: disambiguate the method for candidate #1
18+
|
19+
LL | <S as A>::foo(&s);
20+
| ~~~~~~~~~~
21+
help: disambiguate the method for candidate #2
22+
|
23+
LL | <S as B>::foo(&s);
24+
| ~~~~~~~~~~
25+
26+
error: aborting due to previous error
27+
28+
For more information about this error, try `rustc --explain E0034`.

0 commit comments

Comments
 (0)