Skip to content

Commit

Permalink
Rollup merge of #104038 - compiler-errors:super-norm-closure-sig, r=lcnr
Browse files Browse the repository at this point in the history
Normalize types when deducing closure signature from supertraits

Elaborated supertraits should be normalized, since there's no guarantee they don't contain projections 😅

Fixes #104025
r? types
  • Loading branch information
Dylan-DPC authored Nov 7, 2022
2 parents c590396 + 9a1043e commit f0bd2cd
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 3 deletions.
10 changes: 7 additions & 3 deletions compiler/rustc_hir_typeck/src/closure.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use rustc_hir_analysis::astconv::AstConv;
use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
use rustc_infer::infer::LateBoundRegionConversionTime;
use rustc_infer::infer::{InferOk, InferResult};
use rustc_macros::{TypeFoldable, TypeVisitable};
use rustc_middle::ty::subst::InternalSubsts;
use rustc_middle::ty::visit::TypeVisitable;
use rustc_middle::ty::{self, Ty};
Expand All @@ -22,7 +23,7 @@ use std::cmp;
use std::iter;

/// What signature do we *expect* the closure to have from context?
#[derive(Debug)]
#[derive(Debug, Clone, TypeFoldable, TypeVisitable)]
struct ExpectedSig<'tcx> {
/// Span that gave us this expectation, if we know that.
cause_span: Option<Span>,
Expand Down Expand Up @@ -241,9 +242,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
if expected_sig.is_none()
&& let ty::PredicateKind::Projection(proj_predicate) = bound_predicate.skip_binder()
{
expected_sig = self.deduce_sig_from_projection(
expected_sig = self.normalize_associated_types_in(
obligation.cause.span,
self.deduce_sig_from_projection(
Some(obligation.cause.span),
bound_predicate.rebind(proj_predicate),
bound_predicate.rebind(proj_predicate),
),
);
}

Expand Down
17 changes: 17 additions & 0 deletions src/test/ui/closures/supertrait-hint-references-assoc-ty.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
// check-pass

pub trait Fn0: Fn(i32) -> Self::Out {
type Out;
}

impl<F: Fn(i32) -> ()> Fn0 for F {
type Out = ();
}

pub fn closure_typer(_: impl Fn0) {}

fn main() {
closure_typer(move |x| {
let _: i64 = x.into();
});
}

0 comments on commit f0bd2cd

Please sign in to comment.