summaryrefslogtreecommitdiffstats
path: root/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--compiler/rustc_trait_selection/src/traits/outlives_bounds.rs (renamed from compiler/rustc_typeck/src/outlives/outlives_bounds.rs)41
1 files changed, 33 insertions, 8 deletions
diff --git a/compiler/rustc_typeck/src/outlives/outlives_bounds.rs b/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs
index 229a64650..3008dfcad 100644
--- a/compiler/rustc_typeck/src/outlives/outlives_bounds.rs
+++ b/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs
@@ -1,22 +1,32 @@
+use crate::infer::InferCtxt;
+use crate::traits::query::type_op::{self, TypeOp, TypeOpOutput};
+use crate::traits::query::NoSolution;
+use crate::traits::{ObligationCause, TraitEngine, TraitEngineExt};
+use rustc_data_structures::fx::FxHashSet;
use rustc_hir as hir;
-use rustc_middle::ty::{self, Ty};
-use rustc_trait_selection::infer::InferCtxt;
-use rustc_trait_selection::traits::query::type_op::{self, TypeOp, TypeOpOutput};
-use rustc_trait_selection::traits::query::NoSolution;
-use rustc_trait_selection::traits::{ObligationCause, TraitEngine, TraitEngineExt};
+use rustc_hir::HirId;
+use rustc_middle::ty::{self, ParamEnv, Ty};
pub use rustc_middle::traits::query::OutlivesBound;
-pub trait InferCtxtExt<'tcx> {
+type Bounds<'a, 'tcx: 'a> = impl Iterator<Item = OutlivesBound<'tcx>> + 'a;
+pub trait InferCtxtExt<'a, 'tcx> {
fn implied_outlives_bounds(
&self,
param_env: ty::ParamEnv<'tcx>,
body_id: hir::HirId,
ty: Ty<'tcx>,
) -> Vec<OutlivesBound<'tcx>>;
+
+ fn implied_bounds_tys(
+ &'a self,
+ param_env: ty::ParamEnv<'tcx>,
+ body_id: hir::HirId,
+ tys: FxHashSet<Ty<'tcx>>,
+ ) -> Bounds<'a, 'tcx>;
}
-impl<'cx, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'cx, 'tcx> {
+impl<'a, 'cx, 'tcx: 'a> InferCtxtExt<'a, 'tcx> for InferCtxt<'cx, 'tcx> {
/// Implied bounds are region relationships that we deduce
/// automatically. The idea is that (e.g.) a caller must check that a
/// function's argument types are well-formed immediately before
@@ -36,7 +46,7 @@ impl<'cx, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'cx, 'tcx> {
/// Note that this may cause outlives obligations to be injected
/// into the inference context with this body-id.
/// - `ty`, the type that we are supposed to assume is WF.
- #[instrument(level = "debug", skip(self, param_env, body_id))]
+ #[instrument(level = "debug", skip(self, param_env, body_id), ret)]
fn implied_outlives_bounds(
&self,
param_env: ty::ParamEnv<'tcx>,
@@ -61,6 +71,7 @@ impl<'cx, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'cx, 'tcx> {
let TypeOpOutput { output, constraints, .. } = result;
if let Some(constraints) = constraints {
+ debug!(?constraints);
// Instantiation may have produced new inference variables and constraints on those
// variables. Process these constraints.
let mut fulfill_cx = <dyn TraitEngine<'tcx>>::new(self.tcx);
@@ -87,4 +98,18 @@ impl<'cx, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'cx, 'tcx> {
output
}
+
+ fn implied_bounds_tys(
+ &'a self,
+ param_env: ParamEnv<'tcx>,
+ body_id: HirId,
+ tys: FxHashSet<Ty<'tcx>>,
+ ) -> Bounds<'a, 'tcx> {
+ tys.into_iter()
+ .map(move |ty| {
+ let ty = self.resolve_vars_if_possible(ty);
+ self.implied_outlives_bounds(param_env, body_id, ty)
+ })
+ .flatten()
+ }
}