diff options
Diffstat (limited to 'compiler/rustc_infer/src/traits/engine.rs')
-rw-r--r-- | compiler/rustc_infer/src/traits/engine.rs | 24 |
1 files changed, 20 insertions, 4 deletions
diff --git a/compiler/rustc_infer/src/traits/engine.rs b/compiler/rustc_infer/src/traits/engine.rs index d3519f4b3..f75344f20 100644 --- a/compiler/rustc_infer/src/traits/engine.rs +++ b/compiler/rustc_infer/src/traits/engine.rs @@ -1,6 +1,5 @@ use crate::infer::InferCtxt; use crate::traits::Obligation; -use rustc_data_structures::fx::FxHashMap; use rustc_hir::def_id::DefId; use rustc_middle::ty::{self, ToPredicate, Ty}; @@ -37,13 +36,19 @@ pub trait TraitEngine<'tcx>: 'tcx { obligation: PredicateObligation<'tcx>, ); - fn select_all_or_error(&mut self, infcx: &InferCtxt<'tcx>) -> Vec<FulfillmentError<'tcx>>; - fn select_where_possible(&mut self, infcx: &InferCtxt<'tcx>) -> Vec<FulfillmentError<'tcx>>; + fn collect_remaining_errors(&mut self) -> Vec<FulfillmentError<'tcx>>; + fn pending_obligations(&self) -> Vec<PredicateObligation<'tcx>>; - fn relationships(&mut self) -> &mut FxHashMap<ty::TyVid, ty::FoundRelationships>; + /// Among all pending obligations, collect those are stalled on a inference variable which has + /// changed since the last call to `select_where_possible`. Those obligations are marked as + /// successful and returned. + fn drain_unstalled_obligations( + &mut self, + infcx: &InferCtxt<'tcx>, + ) -> Vec<PredicateObligation<'tcx>>; } pub trait TraitEngineExt<'tcx> { @@ -52,6 +57,8 @@ pub trait TraitEngineExt<'tcx> { infcx: &InferCtxt<'tcx>, obligations: impl IntoIterator<Item = PredicateObligation<'tcx>>, ); + + fn select_all_or_error(&mut self, infcx: &InferCtxt<'tcx>) -> Vec<FulfillmentError<'tcx>>; } impl<'tcx, T: ?Sized + TraitEngine<'tcx>> TraitEngineExt<'tcx> for T { @@ -64,4 +71,13 @@ impl<'tcx, T: ?Sized + TraitEngine<'tcx>> TraitEngineExt<'tcx> for T { self.register_predicate_obligation(infcx, obligation); } } + + fn select_all_or_error(&mut self, infcx: &InferCtxt<'tcx>) -> Vec<FulfillmentError<'tcx>> { + let errors = self.select_where_possible(infcx); + if !errors.is_empty() { + return errors; + } + + self.collect_remaining_errors() + } } |