diff options
| author | bors <bors@rust-lang.org> | 2022-08-16 18:07:02 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2022-08-16 18:07:02 +0000 |
| commit | 5746c752f4e3f294cd252f7dd611a1908b12dd8e (patch) | |
| tree | 4165b48259f23bcc95afeffef17655138dfd2e44 /compiler/rustc_trait_selection/src | |
| parent | a39bdb1d6b9eaf23f2636baee0949d67890abcd8 (diff) | |
| parent | 35bd1d64cfe8efe8c99cb1d413d88603d1fbd56c (diff) | |
| download | rust-5746c752f4e3f294cd252f7dd611a1908b12dd8e.tar.gz rust-5746c752f4e3f294cd252f7dd611a1908b12dd8e.zip | |
Auto merge of #100626 - Dylan-DPC:rollup-mwbm7kj, r=Dylan-DPC
Rollup of 6 pull requests Successful merges: - #99942 (Fix nonsense non-tupled `Fn` trait error) - #100609 (Extend invalid floating point literal suffix suggestion) - #100610 (Ast and parser tweaks) - #100613 (compiletest: fix typo in runtest.rs) - #100616 (:arrow_up: rust-analyzer) - #100622 (Support 128-bit atomics on all aarch64 targets) Failed merges: r? `@ghost` `@rustbot` modify labels: rollup
Diffstat (limited to 'compiler/rustc_trait_selection/src')
| -rw-r--r-- | compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs | 30 |
1 files changed, 27 insertions, 3 deletions
diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs index 4260cb53adc..1a39a168038 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs @@ -22,6 +22,7 @@ use rustc_hir::intravisit::Visitor; use rustc_hir::GenericParam; use rustc_hir::Item; use rustc_hir::Node; +use rustc_infer::infer::TypeTrace; use rustc_infer::traits::TraitEngine; use rustc_middle::traits::select::OverflowError; use rustc_middle::ty::abstract_const::NotConstEvaluatable; @@ -941,9 +942,14 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> { self.reported_closure_mismatch.borrow_mut().insert((span, found_span)); + let mut not_tupled = false; + let found = match found_trait_ref.skip_binder().substs.type_at(1).kind() { ty::Tuple(ref tys) => vec![ArgKind::empty(); tys.len()], - _ => vec![ArgKind::empty()], + _ => { + not_tupled = true; + vec![ArgKind::empty()] + } }; let expected_ty = expected_trait_ref.skip_binder().substs.type_at(1); @@ -951,10 +957,28 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> { ty::Tuple(ref tys) => { tys.iter().map(|t| ArgKind::from_expected_ty(t, Some(span))).collect() } - _ => vec![ArgKind::Arg("_".to_owned(), expected_ty.to_string())], + _ => { + not_tupled = true; + vec![ArgKind::Arg("_".to_owned(), expected_ty.to_string())] + } }; - if found.len() == expected.len() { + // If this is a `Fn` family trait and either the expected or found + // is not tupled, then fall back to just a regular mismatch error. + // This shouldn't be common unless manually implementing one of the + // traits manually, but don't make it more confusing when it does + // happen. + if Some(expected_trait_ref.def_id()) != tcx.lang_items().gen_trait() && not_tupled { + self.report_and_explain_type_error( + TypeTrace::poly_trait_refs( + &obligation.cause, + true, + expected_trait_ref, + found_trait_ref, + ), + ty::error::TypeError::Mismatch, + ) + } else if found.len() == expected.len() { self.report_closure_arg_mismatch( span, found_span, |
