Coerce two FnDef
s to fn pointers even if they are the same, if they are subtypes
That's because they can be the same function but still different substs, which mandates them to coerce to fn pointers in order to unify.
This commit is contained in:
parent
39aab9839c
commit
1907786038
2 changed files with 21 additions and 1 deletions
|
@ -125,7 +125,11 @@ impl CoerceMany {
|
|||
// pointers to have a chance at getting a match. See
|
||||
// https://github.com/rust-lang/rust/blob/7b805396bf46dce972692a6846ce2ad8481c5f85/src/librustc_typeck/check/coercion.rs#L877-L916
|
||||
let sig = match (self.merged_ty().kind(Interner), expr_ty.kind(Interner)) {
|
||||
(TyKind::FnDef(x, _), TyKind::FnDef(y, _)) if x == y => None,
|
||||
(TyKind::FnDef(x, _), TyKind::FnDef(y, _))
|
||||
if x == y && ctx.table.unify(&self.merged_ty(), &expr_ty) =>
|
||||
{
|
||||
None
|
||||
}
|
||||
(TyKind::Closure(x, _), TyKind::Closure(y, _)) if x == y => None,
|
||||
(TyKind::FnDef(..) | TyKind::Closure(..), TyKind::FnDef(..) | TyKind::Closure(..)) => {
|
||||
// FIXME: we're ignoring safety here. To be more correct, if we have one FnDef and one Closure,
|
||||
|
|
|
@ -942,3 +942,19 @@ fn main() {
|
|||
"#,
|
||||
)
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn regression_18626() {
|
||||
check_no_mismatches(
|
||||
r#"
|
||||
fn f() {
|
||||
trait T {
|
||||
fn f() {}
|
||||
}
|
||||
impl T for i32 {}
|
||||
impl T for u32 {}
|
||||
&[i32::f, u32::f] as &[fn()];
|
||||
}
|
||||
"#,
|
||||
);
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue