diff options
Diffstat (limited to 'compiler/rustc_trait_selection/src')
| -rw-r--r-- | compiler/rustc_trait_selection/src/traits/engine.rs | 2 | ||||
| -rw-r--r-- | compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs | 22 | ||||
| -rw-r--r-- | compiler/rustc_trait_selection/src/traits/mod.rs | 2 |
3 files changed, 21 insertions, 5 deletions
diff --git a/compiler/rustc_trait_selection/src/traits/engine.rs b/compiler/rustc_trait_selection/src/traits/engine.rs index 015e38b2ac0..88f47b03cc8 100644 --- a/compiler/rustc_trait_selection/src/traits/engine.rs +++ b/compiler/rustc_trait_selection/src/traits/engine.rs @@ -218,7 +218,7 @@ impl<'a, 'tcx> ObligationCtxt<'a, 'tcx> { def_id: LocalDefId, ) -> Result<FxIndexSet<Ty<'tcx>>, ErrorGuaranteed> { self.assumed_wf_types(param_env, def_id) - .map_err(|errors| self.infcx.err_ctxt().report_fulfillment_errors(&errors)) + .map_err(|errors| self.infcx.err_ctxt().report_fulfillment_errors(errors)) } pub fn assumed_wf_types( 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 ae56e3d3d4f..5e77b5904f6 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs @@ -137,7 +137,7 @@ pub trait TypeErrCtxtExt<'tcx> { fn report_overflow_no_abort(&self, obligation: PredicateObligation<'tcx>) -> ErrorGuaranteed; - fn report_fulfillment_errors(&self, errors: &[FulfillmentError<'tcx>]) -> ErrorGuaranteed; + fn report_fulfillment_errors(&self, errors: Vec<FulfillmentError<'tcx>>) -> ErrorGuaranteed; fn report_overflow_obligation<T>( &self, @@ -401,7 +401,10 @@ impl<'tcx> InferCtxtExt<'tcx> for InferCtxt<'tcx> { } impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> { - fn report_fulfillment_errors(&self, errors: &[FulfillmentError<'tcx>]) -> ErrorGuaranteed { + fn report_fulfillment_errors( + &self, + mut errors: Vec<FulfillmentError<'tcx>>, + ) -> ErrorGuaranteed { #[derive(Debug)] struct ErrorDescriptor<'tcx> { predicate: ty::Predicate<'tcx>, @@ -423,6 +426,19 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> { }) .collect(); + // Ensure `T: Sized` and `T: WF` obligations come last. This lets us display diagnostics + // with more relevant type information and hide redundant E0282 errors. + errors.sort_by_key(|e| match e.obligation.predicate.kind().skip_binder() { + ty::PredicateKind::Clause(ty::ClauseKind::Trait(pred)) + if Some(pred.def_id()) == self.tcx.lang_items().sized_trait() => + { + 1 + } + ty::PredicateKind::Clause(ty::ClauseKind::WellFormed(_)) => 3, + ty::PredicateKind::Coerce(_) => 2, + _ => 0, + }); + for (index, error) in errors.iter().enumerate() { // We want to ignore desugarings here: spans are equivalent even // if one is the result of a desugaring and the other is not. @@ -476,7 +492,7 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> { } for from_expansion in [false, true] { - for (error, suppressed) in iter::zip(errors, &is_suppressed) { + for (error, suppressed) in iter::zip(&errors, &is_suppressed) { if !suppressed && error.obligation.cause.span.from_expansion() == from_expansion { self.report_fulfillment_error(error); } diff --git a/compiler/rustc_trait_selection/src/traits/mod.rs b/compiler/rustc_trait_selection/src/traits/mod.rs index 956f8e047d7..ab81d77a268 100644 --- a/compiler/rustc_trait_selection/src/traits/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/mod.rs @@ -204,7 +204,7 @@ fn do_normalize_predicates<'tcx>( let predicates = match fully_normalize(&infcx, cause, elaborated_env, predicates) { Ok(predicates) => predicates, Err(errors) => { - let reported = infcx.err_ctxt().report_fulfillment_errors(&errors); + let reported = infcx.err_ctxt().report_fulfillment_errors(errors); return Err(reported); } }; |
