Overhaul RegionKind
and Region
.
Specifically, change `Region` from this: ``` pub type Region<'tcx> = &'tcx RegionKind; ``` to this: ``` pub struct Region<'tcx>(&'tcx Interned<RegionKind>); ``` This now matches `Ty` and `Predicate` more closely. Things to note - Regions have always been interned, but we haven't been using pointer-based `Eq` and `Hash`. This is now happening. - I chose to impl `Deref` for `Region` because it makes pattern matching a lot nicer, and `Region` can be viewed as just a smart wrapper for `RegionKind`. - Various methods are moved from `RegionKind` to `Region`. - There is a lot of tedious sigil changes. - A couple of types like `HighlightBuilder`, `RegionHighlightMode` now have a `'tcx` lifetime because they hold a `Ty<'tcx>`, so they can call `mk_region`. - A couple of test outputs change slightly, I'm not sure why, but the new outputs are a little better.
This commit is contained in:
parent
925ec0d3c7
commit
7024dc523a
80 changed files with 443 additions and 346 deletions
|
@ -179,7 +179,7 @@ impl CanonicalizeMode for CanonicalizeQueryResponse {
|
|||
canonicalizer: &mut Canonicalizer<'_, 'tcx>,
|
||||
r: ty::Region<'tcx>,
|
||||
) -> ty::Region<'tcx> {
|
||||
match r {
|
||||
match *r {
|
||||
ty::ReFree(_)
|
||||
| ty::ReErased
|
||||
| ty::ReStatic
|
||||
|
@ -187,12 +187,12 @@ impl CanonicalizeMode for CanonicalizeQueryResponse {
|
|||
| ty::ReEarlyBound(..) => r,
|
||||
|
||||
ty::RePlaceholder(placeholder) => canonicalizer.canonical_var_for_region(
|
||||
CanonicalVarInfo { kind: CanonicalVarKind::PlaceholderRegion(*placeholder) },
|
||||
CanonicalVarInfo { kind: CanonicalVarKind::PlaceholderRegion(placeholder) },
|
||||
r,
|
||||
),
|
||||
|
||||
ty::ReVar(vid) => {
|
||||
let universe = canonicalizer.region_var_universe(*vid);
|
||||
let universe = canonicalizer.region_var_universe(vid);
|
||||
canonicalizer.canonical_var_for_region(
|
||||
CanonicalVarInfo { kind: CanonicalVarKind::Region(universe) },
|
||||
r,
|
||||
|
@ -240,7 +240,7 @@ impl CanonicalizeMode for CanonicalizeUserTypeAnnotation {
|
|||
canonicalizer: &mut Canonicalizer<'_, 'tcx>,
|
||||
r: ty::Region<'tcx>,
|
||||
) -> ty::Region<'tcx> {
|
||||
match r {
|
||||
match *r {
|
||||
ty::ReEarlyBound(_) | ty::ReFree(_) | ty::ReErased | ty::ReStatic => r,
|
||||
ty::ReVar(_) => canonicalizer.canonical_var_for_region_in_root_universe(r),
|
||||
_ => {
|
||||
|
@ -311,11 +311,7 @@ impl CanonicalizeMode for CanonicalizeFreeRegionsOtherThanStatic {
|
|||
canonicalizer: &mut Canonicalizer<'_, 'tcx>,
|
||||
r: ty::Region<'tcx>,
|
||||
) -> ty::Region<'tcx> {
|
||||
if let ty::ReStatic = r {
|
||||
r
|
||||
} else {
|
||||
canonicalizer.canonical_var_for_region_in_root_universe(r)
|
||||
}
|
||||
if r.is_static() { r } else { canonicalizer.canonical_var_for_region_in_root_universe(r) }
|
||||
}
|
||||
|
||||
fn any(&self) -> bool {
|
||||
|
|
|
@ -237,10 +237,9 @@ impl<'cx, 'tcx> InferCtxt<'cx, 'tcx> {
|
|||
v.var_values[BoundVar::new(index)]
|
||||
});
|
||||
match (original_value.unpack(), result_value.unpack()) {
|
||||
(
|
||||
GenericArgKind::Lifetime(ty::ReErased),
|
||||
GenericArgKind::Lifetime(ty::ReErased),
|
||||
) => {
|
||||
(GenericArgKind::Lifetime(re1), GenericArgKind::Lifetime(re2))
|
||||
if re1.is_erased() && re2.is_erased() =>
|
||||
{
|
||||
// No action needed.
|
||||
}
|
||||
|
||||
|
@ -429,7 +428,7 @@ impl<'cx, 'tcx> InferCtxt<'cx, 'tcx> {
|
|||
}
|
||||
GenericArgKind::Lifetime(result_value) => {
|
||||
// e.g., here `result_value` might be `'?1` in the example above...
|
||||
if let &ty::RegionKind::ReLateBound(debruijn, br) = result_value {
|
||||
if let ty::RegionKind::ReLateBound(debruijn, br) = *result_value {
|
||||
// ... in which case we would set `canonical_vars[0]` to `Some('static)`.
|
||||
|
||||
// We only allow a `ty::INNERMOST` index in substitutions.
|
||||
|
@ -558,10 +557,9 @@ impl<'cx, 'tcx> InferCtxt<'cx, 'tcx> {
|
|||
obligations
|
||||
.extend(self.at(cause, param_env).eq(v1, v2)?.into_obligations());
|
||||
}
|
||||
(
|
||||
GenericArgKind::Lifetime(ty::ReErased),
|
||||
GenericArgKind::Lifetime(ty::ReErased),
|
||||
) => {
|
||||
(GenericArgKind::Lifetime(re1), GenericArgKind::Lifetime(re2))
|
||||
if re1.is_erased() && re2.is_erased() =>
|
||||
{
|
||||
// no action needed
|
||||
}
|
||||
(GenericArgKind::Lifetime(v1), GenericArgKind::Lifetime(v2)) => {
|
||||
|
|
|
@ -915,7 +915,7 @@ impl<'tcx> TypeRelation<'tcx> for ConstInferUnifier<'_, 'tcx> {
|
|||
debug_assert_eq!(r, _r);
|
||||
debug!("ConstInferUnifier: r={:?}", r);
|
||||
|
||||
match r {
|
||||
match *r {
|
||||
// Never make variables for regions bound within the type itself,
|
||||
// nor for erased regions.
|
||||
ty::ReLateBound(..) | ty::ReErased => {
|
||||
|
|
|
@ -239,7 +239,7 @@ pub fn unexpected_hidden_region_diagnostic<'tcx>(
|
|||
);
|
||||
|
||||
// Explain the region we are capturing.
|
||||
match hidden_region {
|
||||
match *hidden_region {
|
||||
ty::ReEmpty(ty::UniverseIndex::ROOT) => {
|
||||
// All lifetimes shorter than the function body are `empty` in
|
||||
// lexical region resolution. The default explanation of "an empty
|
||||
|
@ -1114,7 +1114,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
|||
}
|
||||
|
||||
fn push_ty_ref<'tcx>(
|
||||
region: &ty::Region<'tcx>,
|
||||
region: ty::Region<'tcx>,
|
||||
ty: Ty<'tcx>,
|
||||
mutbl: hir::Mutability,
|
||||
s: &mut DiagnosticStyledString,
|
||||
|
@ -1335,14 +1335,14 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
|||
// When finding T != &T, highlight only the borrow
|
||||
(&ty::Ref(r1, ref_ty1, mutbl1), _) if equals(ref_ty1, t2) => {
|
||||
let mut values = (DiagnosticStyledString::new(), DiagnosticStyledString::new());
|
||||
push_ty_ref(&r1, ref_ty1, mutbl1, &mut values.0);
|
||||
push_ty_ref(r1, ref_ty1, mutbl1, &mut values.0);
|
||||
values.1.push_normal(t2.to_string());
|
||||
values
|
||||
}
|
||||
(_, &ty::Ref(r2, ref_ty2, mutbl2)) if equals(t1, ref_ty2) => {
|
||||
let mut values = (DiagnosticStyledString::new(), DiagnosticStyledString::new());
|
||||
values.0.push_normal(t1.to_string());
|
||||
push_ty_ref(&r2, ref_ty2, mutbl2, &mut values.1);
|
||||
push_ty_ref(r2, ref_ty2, mutbl2, &mut values.1);
|
||||
values
|
||||
}
|
||||
|
||||
|
@ -1351,8 +1351,8 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
|||
if equals(ref_ty1, ref_ty2) =>
|
||||
{
|
||||
let mut values = (DiagnosticStyledString::new(), DiagnosticStyledString::new());
|
||||
push_ty_ref(&r1, ref_ty1, mutbl1, &mut values.0);
|
||||
push_ty_ref(&r2, ref_ty2, mutbl2, &mut values.1);
|
||||
push_ty_ref(r1, ref_ty1, mutbl1, &mut values.0);
|
||||
push_ty_ref(r2, ref_ty2, mutbl2, &mut values.1);
|
||||
values
|
||||
}
|
||||
|
||||
|
|
|
@ -369,7 +369,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
|||
pub fn extract_inference_diagnostics_data(
|
||||
&self,
|
||||
arg: GenericArg<'tcx>,
|
||||
highlight: Option<ty::print::RegionHighlightMode>,
|
||||
highlight: Option<ty::print::RegionHighlightMode<'tcx>>,
|
||||
) -> InferenceDiagnosticsData {
|
||||
match arg.unpack() {
|
||||
GenericArgKind::Type(ty) => {
|
||||
|
|
|
@ -10,7 +10,7 @@ use rustc_data_structures::stable_set::FxHashSet;
|
|||
use rustc_errors::{Applicability, ErrorReported};
|
||||
use rustc_hir as hir;
|
||||
use rustc_hir::intravisit::Visitor;
|
||||
use rustc_middle::ty::{self, TypeVisitor};
|
||||
use rustc_middle::ty::TypeVisitor;
|
||||
use rustc_span::MultiSpan;
|
||||
|
||||
impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
||||
|
@ -22,7 +22,7 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
RegionResolutionError::ConcreteFailure(origin, sub, sup) => (origin, sub, sup),
|
||||
_ => return None,
|
||||
};
|
||||
if *sub != ty::RegionKind::ReStatic {
|
||||
if !sub.is_static() {
|
||||
return None;
|
||||
}
|
||||
let cause = match origin {
|
||||
|
|
|
@ -66,9 +66,9 @@ impl<'cx, 'tcx> NiceRegionError<'cx, 'tcx> {
|
|||
|
||||
pub fn regions(&self) -> Option<(Span, ty::Region<'tcx>, ty::Region<'tcx>)> {
|
||||
match (&self.error, self.regions) {
|
||||
(Some(ConcreteFailure(origin, sub, sup)), None) => Some((origin.span(), sub, sup)),
|
||||
(Some(ConcreteFailure(origin, sub, sup)), None) => Some((origin.span(), *sub, *sup)),
|
||||
(Some(SubSupConflict(_, _, origin, sub, _, sup, _)), None) => {
|
||||
Some((origin.span(), sub, sup))
|
||||
Some((origin.span(), *sub, *sup))
|
||||
}
|
||||
(None, Some((span, sub, sup))) => Some((span, sub, sup)),
|
||||
_ => None,
|
||||
|
|
|
@ -48,7 +48,7 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
|
||||
// Suggesting to add a `'static` lifetime to a parameter is nearly always incorrect,
|
||||
// and can steer users down the wrong path.
|
||||
if *named == ty::ReStatic {
|
||||
if named.is_static() {
|
||||
return None;
|
||||
}
|
||||
|
||||
|
|
|
@ -3,13 +3,14 @@ use crate::infer::lexical_region_resolve::RegionResolutionError;
|
|||
use crate::infer::ValuePairs;
|
||||
use crate::infer::{SubregionOrigin, TypeTrace};
|
||||
use crate::traits::{ObligationCause, ObligationCauseCode};
|
||||
use rustc_data_structures::intern::Interned;
|
||||
use rustc_errors::DiagnosticBuilder;
|
||||
use rustc_hir::def::Namespace;
|
||||
use rustc_hir::def_id::DefId;
|
||||
use rustc_middle::ty::error::ExpectedFound;
|
||||
use rustc_middle::ty::print::{FmtPrinter, Print, RegionHighlightMode};
|
||||
use rustc_middle::ty::subst::SubstsRef;
|
||||
use rustc_middle::ty::{self, TyCtxt};
|
||||
use rustc_middle::ty::{self, RePlaceholder, ReVar, Region, TyCtxt};
|
||||
|
||||
use std::fmt::{self, Write};
|
||||
|
||||
|
@ -31,15 +32,15 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
vid,
|
||||
_,
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sub_placeholder @ ty::RePlaceholder(_),
|
||||
sub_placeholder @ Region(Interned(RePlaceholder(_), _)),
|
||||
_,
|
||||
sup_placeholder @ ty::RePlaceholder(_),
|
||||
sup_placeholder @ Region(Interned(RePlaceholder(_), _)),
|
||||
_,
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
Some(self.tcx().mk_region(ty::ReVar(*vid))),
|
||||
Some(self.tcx().mk_region(ReVar(*vid))),
|
||||
cause,
|
||||
Some(sub_placeholder),
|
||||
Some(sup_placeholder),
|
||||
Some(*sub_placeholder),
|
||||
Some(*sup_placeholder),
|
||||
values,
|
||||
),
|
||||
|
||||
|
@ -47,14 +48,14 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
vid,
|
||||
_,
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sub_placeholder @ ty::RePlaceholder(_),
|
||||
sub_placeholder @ Region(Interned(RePlaceholder(_), _)),
|
||||
_,
|
||||
_,
|
||||
_,
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
Some(self.tcx().mk_region(ty::ReVar(*vid))),
|
||||
Some(self.tcx().mk_region(ReVar(*vid))),
|
||||
cause,
|
||||
Some(sub_placeholder),
|
||||
Some(*sub_placeholder),
|
||||
None,
|
||||
values,
|
||||
),
|
||||
|
@ -65,10 +66,10 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
_,
|
||||
_,
|
||||
sup_placeholder @ ty::RePlaceholder(_),
|
||||
sup_placeholder @ Region(Interned(RePlaceholder(_), _)),
|
||||
_,
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
Some(self.tcx().mk_region(ty::ReVar(*vid))),
|
||||
Some(self.tcx().mk_region(ReVar(*vid))),
|
||||
cause,
|
||||
None,
|
||||
Some(*sup_placeholder),
|
||||
|
@ -81,10 +82,10 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
_,
|
||||
_,
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sup_placeholder @ ty::RePlaceholder(_),
|
||||
sup_placeholder @ Region(Interned(RePlaceholder(_), _)),
|
||||
_,
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
Some(self.tcx().mk_region(ty::ReVar(*vid))),
|
||||
Some(self.tcx().mk_region(ReVar(*vid))),
|
||||
cause,
|
||||
None,
|
||||
Some(*sup_placeholder),
|
||||
|
@ -96,9 +97,9 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
_,
|
||||
_,
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sup_placeholder @ ty::RePlaceholder(_),
|
||||
sup_placeholder @ Region(Interned(RePlaceholder(_), _)),
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
Some(self.tcx().mk_region(ty::ReVar(*vid))),
|
||||
Some(self.tcx().mk_region(ReVar(*vid))),
|
||||
cause,
|
||||
None,
|
||||
Some(*sup_placeholder),
|
||||
|
@ -107,8 +108,8 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
|
||||
Some(RegionResolutionError::ConcreteFailure(
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sub_region @ ty::RePlaceholder(_),
|
||||
sup_region @ ty::RePlaceholder(_),
|
||||
sub_region @ Region(Interned(RePlaceholder(_), _)),
|
||||
sup_region @ Region(Interned(RePlaceholder(_), _)),
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
None,
|
||||
cause,
|
||||
|
@ -119,12 +120,12 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
|
||||
Some(RegionResolutionError::ConcreteFailure(
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sub_region @ ty::RePlaceholder(_),
|
||||
sub_region @ Region(Interned(RePlaceholder(_), _)),
|
||||
sup_region,
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
(!sup_region.has_name()).then_some(sup_region),
|
||||
(!sup_region.has_name()).then_some(*sup_region),
|
||||
cause,
|
||||
Some(sub_region),
|
||||
Some(*sub_region),
|
||||
None,
|
||||
values,
|
||||
),
|
||||
|
@ -132,12 +133,12 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
Some(RegionResolutionError::ConcreteFailure(
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, values }),
|
||||
sub_region,
|
||||
sup_region @ ty::RePlaceholder(_),
|
||||
sup_region @ Region(Interned(RePlaceholder(_), _)),
|
||||
)) => self.try_report_trait_placeholder_mismatch(
|
||||
(!sub_region.has_name()).then_some(sub_region),
|
||||
(!sub_region.has_name()).then_some(*sub_region),
|
||||
cause,
|
||||
None,
|
||||
Some(sup_region),
|
||||
Some(*sup_region),
|
||||
values,
|
||||
),
|
||||
|
||||
|
@ -147,10 +148,10 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
|
||||
fn try_report_trait_placeholder_mismatch(
|
||||
&self,
|
||||
vid: Option<ty::Region<'tcx>>,
|
||||
vid: Option<Region<'tcx>>,
|
||||
cause: &ObligationCause<'tcx>,
|
||||
sub_placeholder: Option<ty::Region<'tcx>>,
|
||||
sup_placeholder: Option<ty::Region<'tcx>>,
|
||||
sub_placeholder: Option<Region<'tcx>>,
|
||||
sup_placeholder: Option<Region<'tcx>>,
|
||||
value_pairs: &ValuePairs<'tcx>,
|
||||
) -> Option<DiagnosticBuilder<'tcx>> {
|
||||
let (expected_substs, found_substs, trait_def_id) = match value_pairs {
|
||||
|
@ -193,10 +194,10 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
#[instrument(level = "debug", skip(self))]
|
||||
fn report_trait_placeholder_mismatch(
|
||||
&self,
|
||||
vid: Option<ty::Region<'tcx>>,
|
||||
vid: Option<Region<'tcx>>,
|
||||
cause: &ObligationCause<'tcx>,
|
||||
sub_placeholder: Option<ty::Region<'tcx>>,
|
||||
sup_placeholder: Option<ty::Region<'tcx>>,
|
||||
sub_placeholder: Option<Region<'tcx>>,
|
||||
sup_placeholder: Option<Region<'tcx>>,
|
||||
trait_def_id: DefId,
|
||||
expected_substs: SubstsRef<'tcx>,
|
||||
actual_substs: SubstsRef<'tcx>,
|
||||
|
@ -306,13 +307,13 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
fn explain_actual_impl_that_was_found(
|
||||
&self,
|
||||
err: &mut DiagnosticBuilder<'_>,
|
||||
sub_placeholder: Option<ty::Region<'tcx>>,
|
||||
sup_placeholder: Option<ty::Region<'tcx>>,
|
||||
sub_placeholder: Option<Region<'tcx>>,
|
||||
sup_placeholder: Option<Region<'tcx>>,
|
||||
has_sub: Option<usize>,
|
||||
has_sup: Option<usize>,
|
||||
expected_trait_ref: ty::TraitRef<'tcx>,
|
||||
actual_trait_ref: ty::TraitRef<'tcx>,
|
||||
vid: Option<ty::Region<'tcx>>,
|
||||
vid: Option<Region<'tcx>>,
|
||||
expected_has_vid: Option<usize>,
|
||||
actual_has_vid: Option<usize>,
|
||||
any_self_ty_has_vid: bool,
|
||||
|
@ -322,7 +323,7 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
#[derive(Copy, Clone)]
|
||||
struct Highlighted<'tcx, T> {
|
||||
tcx: TyCtxt<'tcx>,
|
||||
highlight: RegionHighlightMode,
|
||||
highlight: RegionHighlightMode<'tcx>,
|
||||
value: T,
|
||||
}
|
||||
|
||||
|
@ -366,7 +367,7 @@ impl<'tcx> NiceRegionError<'_, 'tcx> {
|
|||
|
||||
let highlight_trait_ref = |trait_ref| Highlighted {
|
||||
tcx: self.tcx(),
|
||||
highlight: RegionHighlightMode::default(),
|
||||
highlight: RegionHighlightMode::new(self.tcx()),
|
||||
value: trait_ref,
|
||||
};
|
||||
|
||||
|
|
|
@ -10,8 +10,7 @@ use rustc_hir::def_id::DefId;
|
|||
use rustc_hir::intravisit::{walk_ty, Visitor};
|
||||
use rustc_hir::{self as hir, GenericBound, Item, ItemKind, Lifetime, LifetimeName, Node, TyKind};
|
||||
use rustc_middle::ty::{
|
||||
self, AssocItemContainer, RegionKind, StaticLifetimeVisitor, Ty, TyCtxt, TypeFoldable,
|
||||
TypeVisitor,
|
||||
self, AssocItemContainer, StaticLifetimeVisitor, Ty, TyCtxt, TypeFoldable, TypeVisitor,
|
||||
};
|
||||
use rustc_span::symbol::Ident;
|
||||
use rustc_span::{MultiSpan, Span};
|
||||
|
@ -33,25 +32,23 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
sup_origin,
|
||||
sup_r,
|
||||
spans,
|
||||
) if **sub_r == RegionKind::ReStatic => {
|
||||
(var_origin, sub_origin, sub_r, sup_origin, sup_r, spans)
|
||||
}
|
||||
) if sub_r.is_static() => (var_origin, sub_origin, sub_r, sup_origin, sup_r, spans),
|
||||
RegionResolutionError::ConcreteFailure(
|
||||
SubregionOrigin::Subtype(box TypeTrace { cause, .. }),
|
||||
sub_r,
|
||||
sup_r,
|
||||
) if **sub_r == RegionKind::ReStatic => {
|
||||
) if sub_r.is_static() => {
|
||||
// This is for an implicit `'static` requirement coming from `impl dyn Trait {}`.
|
||||
if let ObligationCauseCode::UnifyReceiver(ctxt) = cause.code() {
|
||||
// This may have a closure and it would cause ICE
|
||||
// through `find_param_with_region` (#78262).
|
||||
let anon_reg_sup = tcx.is_suitable_region(sup_r)?;
|
||||
let anon_reg_sup = tcx.is_suitable_region(*sup_r)?;
|
||||
let fn_returns = tcx.return_type_impl_or_dyn_traits(anon_reg_sup.def_id);
|
||||
if fn_returns.is_empty() {
|
||||
return None;
|
||||
}
|
||||
|
||||
let param = self.find_param_with_region(sup_r, sub_r)?;
|
||||
let param = self.find_param_with_region(*sup_r, *sub_r)?;
|
||||
let lifetime = if sup_r.has_name() {
|
||||
format!("lifetime `{}`", sup_r)
|
||||
} else {
|
||||
|
@ -101,11 +98,11 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
"try_report_static_impl_trait(var={:?}, sub={:?} {:?} sup={:?} {:?})",
|
||||
var_origin, sub_origin, sub_r, sup_origin, sup_r
|
||||
);
|
||||
let anon_reg_sup = tcx.is_suitable_region(sup_r)?;
|
||||
let anon_reg_sup = tcx.is_suitable_region(*sup_r)?;
|
||||
debug!("try_report_static_impl_trait: anon_reg_sup={:?}", anon_reg_sup);
|
||||
let sp = var_origin.span();
|
||||
let return_sp = sub_origin.span();
|
||||
let param = self.find_param_with_region(sup_r, sub_r)?;
|
||||
let param = self.find_param_with_region(*sup_r, *sub_r)?;
|
||||
let (lifetime_name, lifetime) = if sup_r.has_name() {
|
||||
(sup_r.to_string(), format!("lifetime `{}`", sup_r))
|
||||
} else {
|
||||
|
@ -560,7 +557,7 @@ pub(super) struct TraitObjectVisitor(pub(super) FxHashSet<DefId>);
|
|||
impl<'tcx> TypeVisitor<'tcx> for TraitObjectVisitor {
|
||||
fn visit_ty(&mut self, t: Ty<'tcx>) -> ControlFlow<Self::BreakTy> {
|
||||
match t.kind() {
|
||||
ty::Dynamic(preds, RegionKind::ReStatic) => {
|
||||
ty::Dynamic(preds, re) if re.is_static() => {
|
||||
if let Some(def_id) = preds.principal_def_id() {
|
||||
self.0.insert(def_id);
|
||||
}
|
||||
|
|
|
@ -81,21 +81,21 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
|
||||
// Mark all unnamed regions in the type with a number.
|
||||
// This diagnostic is called in response to lifetime errors, so be informative.
|
||||
struct HighlightBuilder {
|
||||
highlight: RegionHighlightMode,
|
||||
struct HighlightBuilder<'tcx> {
|
||||
highlight: RegionHighlightMode<'tcx>,
|
||||
counter: usize,
|
||||
}
|
||||
|
||||
impl HighlightBuilder {
|
||||
fn build(ty: Ty<'_>) -> RegionHighlightMode {
|
||||
impl<'tcx> HighlightBuilder<'tcx> {
|
||||
fn build(tcx: TyCtxt<'tcx>, ty: Ty<'tcx>) -> RegionHighlightMode<'tcx> {
|
||||
let mut builder =
|
||||
HighlightBuilder { highlight: RegionHighlightMode::default(), counter: 1 };
|
||||
HighlightBuilder { highlight: RegionHighlightMode::new(tcx), counter: 1 };
|
||||
builder.visit_ty(ty);
|
||||
builder.highlight
|
||||
}
|
||||
}
|
||||
|
||||
impl<'tcx> ty::fold::TypeVisitor<'tcx> for HighlightBuilder {
|
||||
impl<'tcx> ty::fold::TypeVisitor<'tcx> for HighlightBuilder<'tcx> {
|
||||
fn visit_region(&mut self, r: ty::Region<'tcx>) -> ControlFlow<Self::BreakTy> {
|
||||
if !r.has_name() && self.counter <= 3 {
|
||||
self.highlight.highlighting_region(r, self.counter);
|
||||
|
@ -105,12 +105,12 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
}
|
||||
}
|
||||
|
||||
let expected_highlight = HighlightBuilder::build(expected);
|
||||
let expected_highlight = HighlightBuilder::build(self.tcx(), expected);
|
||||
let expected = self
|
||||
.infcx
|
||||
.extract_inference_diagnostics_data(expected.into(), Some(expected_highlight))
|
||||
.name;
|
||||
let found_highlight = HighlightBuilder::build(found);
|
||||
let found_highlight = HighlightBuilder::build(self.tcx(), found);
|
||||
let found =
|
||||
self.infcx.extract_inference_diagnostics_data(found.into(), Some(found_highlight)).name;
|
||||
|
||||
|
|
|
@ -70,7 +70,7 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
|
|||
let ty = fn_sig.inputs()[index];
|
||||
let mut found_anon_region = false;
|
||||
let new_param_ty = self.tcx().fold_regions(ty, &mut false, |r, _| {
|
||||
if *r == *anon_region {
|
||||
if r == anon_region {
|
||||
found_anon_region = true;
|
||||
replace_region
|
||||
} else {
|
||||
|
|
|
@ -115,7 +115,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
|||
infer::Subtype(box trace) => {
|
||||
let terr = TypeError::RegionsDoesNotOutlive(sup, sub);
|
||||
let mut err = self.report_and_explain_type_error(trace, &terr);
|
||||
match (sub, sup) {
|
||||
match (*sub, *sup) {
|
||||
(ty::RePlaceholder(_), ty::RePlaceholder(_)) => {}
|
||||
(ty::RePlaceholder(_), _) => {
|
||||
note_and_explain_region(
|
||||
|
|
|
@ -41,8 +41,8 @@ pub struct FreeRegionMap<'tcx> {
|
|||
}
|
||||
|
||||
impl<'tcx> FreeRegionMap<'tcx> {
|
||||
pub fn elements(&self) -> impl Iterator<Item = &Region<'tcx>> {
|
||||
self.relation.elements()
|
||||
pub fn elements(&self) -> impl Iterator<Item = Region<'tcx>> + '_ {
|
||||
self.relation.elements().copied()
|
||||
}
|
||||
|
||||
pub fn is_empty(&self) -> bool {
|
||||
|
@ -91,7 +91,7 @@ impl<'tcx> FreeRegionMap<'tcx> {
|
|||
|
||||
/// True for free regions other than `'static`.
|
||||
pub fn is_free(&self, r: Region<'_>) -> bool {
|
||||
matches!(r, ty::ReEarlyBound(_) | ty::ReFree(_))
|
||||
matches!(*r, ty::ReEarlyBound(_) | ty::ReFree(_))
|
||||
}
|
||||
|
||||
/// True if `r` is a free region or static of the sort that this
|
||||
|
|
|
@ -13,6 +13,7 @@ use rustc_data_structures::fx::FxHashSet;
|
|||
use rustc_data_structures::graph::implementation::{
|
||||
Direction, Graph, NodeIndex, INCOMING, OUTGOING,
|
||||
};
|
||||
use rustc_data_structures::intern::Interned;
|
||||
use rustc_index::vec::{Idx, IndexVec};
|
||||
use rustc_middle::ty::fold::TypeFoldable;
|
||||
use rustc_middle::ty::{self, Ty, TyCtxt};
|
||||
|
@ -250,8 +251,8 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
changes.push(b_vid);
|
||||
}
|
||||
if let Some(a_vid) = a_vid {
|
||||
match *b_data {
|
||||
VarValue::Value(ReStatic) | VarValue::ErrorValue => (),
|
||||
match b_data {
|
||||
VarValue::Value(Region(Interned(ReStatic, _))) | VarValue::ErrorValue => (),
|
||||
_ => {
|
||||
constraints[a_vid].push((a_vid, b_vid));
|
||||
constraints[b_vid].push((a_vid, b_vid));
|
||||
|
@ -270,7 +271,10 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
if self.expand_node(a_region, b_vid, b_data) {
|
||||
changes.push(b_vid);
|
||||
}
|
||||
!matches!(b_data, VarValue::Value(ReStatic) | VarValue::ErrorValue)
|
||||
!matches!(
|
||||
b_data,
|
||||
VarValue::Value(Region(Interned(ReStatic, _))) | VarValue::ErrorValue
|
||||
)
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -301,8 +305,8 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
// check below for a common case, here purely as an
|
||||
// optimization.
|
||||
let b_universe = self.var_infos[b_vid].universe;
|
||||
if let ReEmpty(a_universe) = a_region {
|
||||
if *a_universe == b_universe {
|
||||
if let ReEmpty(a_universe) = *a_region {
|
||||
if a_universe == b_universe {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -321,7 +325,7 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
// tighter bound than `'static`.
|
||||
//
|
||||
// (This might e.g. arise from being asked to prove `for<'a> { 'b: 'a }`.)
|
||||
if let ty::RePlaceholder(p) = lub {
|
||||
if let ty::RePlaceholder(p) = *lub {
|
||||
if b_universe.cannot_name(p.universe) {
|
||||
lub = self.tcx().lifetimes.re_static;
|
||||
}
|
||||
|
@ -372,12 +376,12 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
/// term "concrete regions").
|
||||
#[instrument(level = "trace", skip(self))]
|
||||
fn lub_concrete_regions(&self, a: Region<'tcx>, b: Region<'tcx>) -> Region<'tcx> {
|
||||
let r = match (a, b) {
|
||||
(&ReLateBound(..), _) | (_, &ReLateBound(..)) | (&ReErased, _) | (_, &ReErased) => {
|
||||
let r = match (*a, *b) {
|
||||
(ReLateBound(..), _) | (_, ReLateBound(..)) | (ReErased, _) | (_, ReErased) => {
|
||||
bug!("cannot relate region: LUB({:?}, {:?})", a, b);
|
||||
}
|
||||
|
||||
(&ReVar(v_id), _) | (_, &ReVar(v_id)) => {
|
||||
(ReVar(v_id), _) | (_, ReVar(v_id)) => {
|
||||
span_bug!(
|
||||
self.var_infos[v_id].origin.span(),
|
||||
"lub_concrete_regions invoked with non-concrete \
|
||||
|
@ -387,27 +391,32 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
);
|
||||
}
|
||||
|
||||
(&ReStatic, _) | (_, &ReStatic) => {
|
||||
(ReStatic, _) | (_, ReStatic) => {
|
||||
// nothing lives longer than `'static`
|
||||
self.tcx().lifetimes.re_static
|
||||
}
|
||||
|
||||
(&ReEmpty(_), r @ (ReEarlyBound(_) | ReFree(_)))
|
||||
| (r @ (ReEarlyBound(_) | ReFree(_)), &ReEmpty(_)) => {
|
||||
(ReEmpty(_), ReEarlyBound(_) | ReFree(_)) => {
|
||||
// All empty regions are less than early-bound, free,
|
||||
// and scope regions.
|
||||
r
|
||||
b
|
||||
}
|
||||
|
||||
(&ReEmpty(a_ui), &ReEmpty(b_ui)) => {
|
||||
(ReEarlyBound(_) | ReFree(_), ReEmpty(_)) => {
|
||||
// All empty regions are less than early-bound, free,
|
||||
// and scope regions.
|
||||
a
|
||||
}
|
||||
|
||||
(ReEmpty(a_ui), ReEmpty(b_ui)) => {
|
||||
// Empty regions are ordered according to the universe
|
||||
// they are associated with.
|
||||
let ui = a_ui.min(b_ui);
|
||||
self.tcx().mk_region(ReEmpty(ui))
|
||||
}
|
||||
|
||||
(&ReEmpty(empty_ui), &RePlaceholder(placeholder))
|
||||
| (&RePlaceholder(placeholder), &ReEmpty(empty_ui)) => {
|
||||
(ReEmpty(empty_ui), RePlaceholder(placeholder))
|
||||
| (RePlaceholder(placeholder), ReEmpty(empty_ui)) => {
|
||||
// If this empty region is from a universe that can
|
||||
// name the placeholder, then the placeholder is
|
||||
// larger; otherwise, the only ancestor is `'static`.
|
||||
|
@ -418,13 +427,13 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
}
|
||||
}
|
||||
|
||||
(&ReEarlyBound(_) | &ReFree(_), &ReEarlyBound(_) | &ReFree(_)) => {
|
||||
(ReEarlyBound(_) | ReFree(_), ReEarlyBound(_) | ReFree(_)) => {
|
||||
self.region_rels.lub_free_regions(a, b)
|
||||
}
|
||||
|
||||
// For these types, we cannot define any additional
|
||||
// relationship:
|
||||
(&RePlaceholder(..), _) | (_, &RePlaceholder(..)) => {
|
||||
(RePlaceholder(..), _) | (_, RePlaceholder(..)) => {
|
||||
if a == b {
|
||||
a
|
||||
} else {
|
||||
|
@ -676,7 +685,7 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
let node_universe = self.var_infos[node_idx].universe;
|
||||
|
||||
for lower_bound in &lower_bounds {
|
||||
let effective_lower_bound = if let ty::RePlaceholder(p) = lower_bound.region {
|
||||
let effective_lower_bound = if let ty::RePlaceholder(p) = *lower_bound.region {
|
||||
if node_universe.cannot_name(p.universe) {
|
||||
self.tcx().lifetimes.re_static
|
||||
} else {
|
||||
|
@ -721,7 +730,7 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
.expect("lower_vid_bounds should at least include `node_idx`");
|
||||
|
||||
for upper_bound in &upper_bounds {
|
||||
if let ty::RePlaceholder(p) = upper_bound.region {
|
||||
if let ty::RePlaceholder(p) = *upper_bound.region {
|
||||
if min_universe.cannot_name(p.universe) {
|
||||
let origin = self.var_infos[node_idx].origin;
|
||||
errors.push(RegionResolutionError::UpperBoundUniverseConflict(
|
||||
|
@ -855,11 +864,11 @@ impl<'cx, 'tcx> LexicalResolver<'cx, 'tcx> {
|
|||
}
|
||||
|
||||
VerifyBound::OutlivedBy(r) => {
|
||||
self.sub_concrete_regions(min, var_values.normalize(self.tcx(), r))
|
||||
self.sub_concrete_regions(min, var_values.normalize(self.tcx(), *r))
|
||||
}
|
||||
|
||||
VerifyBound::IsEmpty => {
|
||||
matches!(min, ty::ReEmpty(_))
|
||||
matches!(*min, ty::ReEmpty(_))
|
||||
}
|
||||
|
||||
VerifyBound::AnyBound(bs) => {
|
||||
|
@ -884,8 +893,8 @@ impl<'tcx> LexicalRegionResolutions<'tcx> {
|
|||
where
|
||||
T: TypeFoldable<'tcx>,
|
||||
{
|
||||
tcx.fold_regions(value, &mut false, |r, _db| match r {
|
||||
ty::ReVar(rid) => self.resolve_var(*rid),
|
||||
tcx.fold_regions(value, &mut false, |r, _db| match *r {
|
||||
ty::ReVar(rid) => self.resolve_var(rid),
|
||||
_ => r,
|
||||
})
|
||||
}
|
||||
|
|
|
@ -244,8 +244,8 @@ where
|
|||
scopes: &[BoundRegionScope<'tcx>],
|
||||
) -> ty::Region<'tcx> {
|
||||
debug!("replace_bound_regions(scopes={:?})", scopes);
|
||||
if let ty::ReLateBound(debruijn, br) = r {
|
||||
Self::lookup_bound_region(*debruijn, br, first_free_index, scopes)
|
||||
if let ty::ReLateBound(debruijn, br) = *r {
|
||||
Self::lookup_bound_region(debruijn, &br, first_free_index, scopes)
|
||||
} else {
|
||||
r
|
||||
}
|
||||
|
@ -779,9 +779,9 @@ impl<'me, 'tcx> TypeVisitor<'tcx> for ScopeInstantiator<'me, 'tcx> {
|
|||
fn visit_region(&mut self, r: ty::Region<'tcx>) -> ControlFlow<Self::BreakTy> {
|
||||
let ScopeInstantiator { bound_region_scope, next_region, .. } = self;
|
||||
|
||||
match r {
|
||||
ty::ReLateBound(debruijn, br) if *debruijn == self.target_index => {
|
||||
bound_region_scope.map.entry(*br).or_insert_with(|| next_region(*br));
|
||||
match *r {
|
||||
ty::ReLateBound(debruijn, br) if debruijn == self.target_index => {
|
||||
bound_region_scope.map.entry(br).or_insert_with(|| next_region(br));
|
||||
}
|
||||
|
||||
_ => {}
|
||||
|
@ -963,8 +963,8 @@ where
|
|||
) -> RelateResult<'tcx, ty::Region<'tcx>> {
|
||||
debug!("TypeGeneralizer::regions(a={:?})", a);
|
||||
|
||||
if let ty::ReLateBound(debruijn, _) = a {
|
||||
if *debruijn < self.first_free_index {
|
||||
if let ty::ReLateBound(debruijn, _) = *a {
|
||||
if debruijn < self.first_free_index {
|
||||
return Ok(a);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,8 +2,9 @@ use crate::infer::free_regions::FreeRegionMap;
|
|||
use crate::infer::{GenericKind, InferCtxt};
|
||||
use crate::traits::query::OutlivesBound;
|
||||
use rustc_data_structures::fx::FxHashMap;
|
||||
use rustc_data_structures::intern::Interned;
|
||||
use rustc_hir as hir;
|
||||
use rustc_middle::ty;
|
||||
use rustc_middle::ty::{self, ReEarlyBound, ReFree, ReVar, Region};
|
||||
|
||||
use super::explicit_outlives_bounds;
|
||||
|
||||
|
@ -66,7 +67,7 @@ pub struct OutlivesEnvironment<'tcx> {
|
|||
/// "Region-bound pairs" tracks outlives relations that are known to
|
||||
/// be true, either because of explicit where-clauses like `T: 'a` or
|
||||
/// because of implied bounds.
|
||||
pub type RegionBoundPairs<'tcx> = Vec<(ty::Region<'tcx>, GenericKind<'tcx>)>;
|
||||
pub type RegionBoundPairs<'tcx> = Vec<(Region<'tcx>, GenericKind<'tcx>)>;
|
||||
|
||||
impl<'a, 'tcx> OutlivesEnvironment<'tcx> {
|
||||
pub fn new(param_env: ty::ParamEnv<'tcx>) -> Self {
|
||||
|
@ -164,10 +165,10 @@ impl<'a, 'tcx> OutlivesEnvironment<'tcx> {
|
|||
debug!("add_outlives_bounds: outlives_bound={:?}", outlives_bound);
|
||||
match outlives_bound {
|
||||
OutlivesBound::RegionSubRegion(
|
||||
r_a @ (&ty::ReEarlyBound(_) | &ty::ReFree(_)),
|
||||
&ty::ReVar(vid_b),
|
||||
r_a @ (Region(Interned(ReEarlyBound(_), _)) | Region(Interned(ReFree(_), _))),
|
||||
Region(Interned(ReVar(vid_b), _)),
|
||||
) => {
|
||||
infcx.expect("no infcx provided but region vars found").add_given(r_a, vid_b);
|
||||
infcx.expect("no infcx provided but region vars found").add_given(r_a, *vid_b);
|
||||
}
|
||||
OutlivesBound::RegionSubParam(r_a, param_b) => {
|
||||
self.region_bound_pairs_accum.push((r_a, GenericKind::Param(param_b)));
|
||||
|
|
|
@ -285,7 +285,7 @@ where
|
|||
let origin = origin.clone();
|
||||
match component {
|
||||
Component::Region(region1) => {
|
||||
self.delegate.push_sub_region_constraint(origin, region, region1);
|
||||
self.delegate.push_sub_region_constraint(origin, region, *region1);
|
||||
}
|
||||
Component::Param(param_ty) => {
|
||||
self.param_ty_must_outlive(origin, region, *param_ty);
|
||||
|
|
|
@ -154,17 +154,17 @@ impl<'me, 'tcx> LeakCheck<'me, 'tcx> {
|
|||
let scc = self.mini_graph.sccs.scc(*leak_check_node);
|
||||
|
||||
// Set the universe of each SCC to be the minimum of its constituent universes
|
||||
let universe = self.rcc.universe(region);
|
||||
let universe = self.rcc.universe(*region);
|
||||
debug!(
|
||||
"assign_placeholder_values: scc={:?} universe={:?} region={:?}",
|
||||
scc, universe, region
|
||||
);
|
||||
self.scc_universes[scc].take_min(universe, region);
|
||||
self.scc_universes[scc].take_min(universe, *region);
|
||||
|
||||
// Detect those SCCs that directly contain a placeholder
|
||||
if let ty::RePlaceholder(placeholder) = region {
|
||||
if let ty::RePlaceholder(placeholder) = **region {
|
||||
if self.universe_at_start_of_snapshot.cannot_name(placeholder.universe) {
|
||||
self.assign_scc_value(scc, *placeholder)?;
|
||||
self.assign_scc_value(scc, placeholder)?;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,6 +8,7 @@ use super::{
|
|||
};
|
||||
|
||||
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
|
||||
use rustc_data_structures::intern::Interned;
|
||||
use rustc_data_structures::sync::Lrc;
|
||||
use rustc_data_structures::undo_log::UndoLogs;
|
||||
use rustc_data_structures::unify as ut;
|
||||
|
@ -502,14 +503,15 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
|
|||
self.make_subregion(origin, sup, sub);
|
||||
|
||||
match (sub, sup) {
|
||||
(&ty::ReVar(sub), &ty::ReVar(sup)) => {
|
||||
(Region(Interned(ReVar(sub), _)), Region(Interned(ReVar(sup), _))) => {
|
||||
debug!("make_eqregion: unifying {:?} with {:?}", sub, sup);
|
||||
self.unification_table().union(sub, sup);
|
||||
self.unification_table().union(*sub, *sup);
|
||||
self.any_unifications = true;
|
||||
}
|
||||
(&ty::ReVar(vid), value) | (value, &ty::ReVar(vid)) => {
|
||||
(Region(Interned(ReVar(vid), _)), value)
|
||||
| (value, Region(Interned(ReVar(vid), _))) => {
|
||||
debug!("make_eqregion: unifying {:?} with {:?}", vid, value);
|
||||
self.unification_table().union_value(vid, UnifiedRegion(Some(value)));
|
||||
self.unification_table().union_value(*vid, UnifiedRegion(Some(value)));
|
||||
self.any_unifications = true;
|
||||
}
|
||||
(_, _) => {}
|
||||
|
@ -550,20 +552,20 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
|
|||
// cannot add constraints once regions are resolved
|
||||
debug!("origin = {:#?}", origin);
|
||||
|
||||
match (sub, sup) {
|
||||
(&ReLateBound(..), _) | (_, &ReLateBound(..)) => {
|
||||
match (*sub, *sup) {
|
||||
(ReLateBound(..), _) | (_, ReLateBound(..)) => {
|
||||
span_bug!(origin.span(), "cannot relate bound region: {:?} <= {:?}", sub, sup);
|
||||
}
|
||||
(_, &ReStatic) => {
|
||||
(_, ReStatic) => {
|
||||
// all regions are subregions of static, so we can ignore this
|
||||
}
|
||||
(&ReVar(sub_id), &ReVar(sup_id)) => {
|
||||
(ReVar(sub_id), ReVar(sup_id)) => {
|
||||
self.add_constraint(Constraint::VarSubVar(sub_id, sup_id), origin);
|
||||
}
|
||||
(_, &ReVar(sup_id)) => {
|
||||
(_, ReVar(sup_id)) => {
|
||||
self.add_constraint(Constraint::RegSubVar(sub, sup_id), origin);
|
||||
}
|
||||
(&ReVar(sub_id), _) => {
|
||||
(ReVar(sub_id), _) => {
|
||||
self.add_constraint(Constraint::VarSubReg(sub_id, sup), origin);
|
||||
}
|
||||
_ => {
|
||||
|
@ -591,16 +593,12 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
|
|||
) -> Region<'tcx> {
|
||||
// cannot add constraints once regions are resolved
|
||||
debug!("RegionConstraintCollector: lub_regions({:?}, {:?})", a, b);
|
||||
match (a, b) {
|
||||
(r @ &ReStatic, _) | (_, r @ &ReStatic) => {
|
||||
r // nothing lives longer than static
|
||||
}
|
||||
|
||||
_ if a == b => {
|
||||
a // LUB(a,a) = a
|
||||
}
|
||||
|
||||
_ => self.combine_vars(tcx, Lub, a, b, origin),
|
||||
if a.is_static() || b.is_static() {
|
||||
a // nothing lives longer than static
|
||||
} else if a == b {
|
||||
a // LUB(a,a) = a
|
||||
} else {
|
||||
self.combine_vars(tcx, Lub, a, b, origin)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -613,16 +611,14 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
|
|||
) -> Region<'tcx> {
|
||||
// cannot add constraints once regions are resolved
|
||||
debug!("RegionConstraintCollector: glb_regions({:?}, {:?})", a, b);
|
||||
match (a, b) {
|
||||
(&ReStatic, r) | (r, &ReStatic) => {
|
||||
r // static lives longer than everything else
|
||||
}
|
||||
|
||||
_ if a == b => {
|
||||
a // GLB(a,a) = a
|
||||
}
|
||||
|
||||
_ => self.combine_vars(tcx, Glb, a, b, origin),
|
||||
if a.is_static() {
|
||||
b // static lives longer than everything else
|
||||
} else if b.is_static() {
|
||||
a // static lives longer than everything else
|
||||
} else if a == b {
|
||||
a // GLB(a,a) = a
|
||||
} else {
|
||||
self.combine_vars(tcx, Glb, a, b, origin)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -639,11 +635,11 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
|
|||
tcx: TyCtxt<'tcx>,
|
||||
region: ty::Region<'tcx>,
|
||||
) -> ty::Region<'tcx> {
|
||||
match region {
|
||||
match *region {
|
||||
ty::ReVar(rid) => {
|
||||
let unified_region = self.unification_table().probe_value(*rid);
|
||||
let unified_region = self.unification_table().probe_value(rid);
|
||||
unified_region.0.unwrap_or_else(|| {
|
||||
let root = self.unification_table().find(*rid).vid;
|
||||
let root = self.unification_table().find(rid).vid;
|
||||
tcx.reuse_or_mk_region(region, ty::ReVar(root))
|
||||
})
|
||||
}
|
||||
|
@ -767,8 +763,7 @@ impl<'tcx> VerifyBound<'tcx> {
|
|||
pub fn must_hold(&self) -> bool {
|
||||
match self {
|
||||
VerifyBound::IfEq(..) => false,
|
||||
VerifyBound::OutlivedBy(ty::ReStatic) => true,
|
||||
VerifyBound::OutlivedBy(_) => false,
|
||||
VerifyBound::OutlivedBy(re) => re.is_static(),
|
||||
VerifyBound::IsEmpty => false,
|
||||
VerifyBound::AnyBound(bs) => bs.iter().any(|b| b.must_hold()),
|
||||
VerifyBound::AllBounds(bs) => bs.iter().all(|b| b.must_hold()),
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue