From: Niko Matsakis Date: Thu, 20 Apr 2017 08:45:53 +0000 (-0400) Subject: intern CodeExtents X-Git-Url: https://git.lizzy.rs/?a=commitdiff_plain;h=c7dc39dbf095f04839b57a1e34afc6ab29d905d3;p=rust.git intern CodeExtents Make a `CodeExtent<'tcx>` be something allocated in an arena instead of an index into the `RegionMaps`. --- diff --git a/src/librustc/cfg/construct.rs b/src/librustc/cfg/construct.rs index 8471d2ae4e3..7b7c204a0ee 100644 --- a/src/librustc/cfg/construct.rs +++ b/src/librustc/cfg/construct.rs @@ -583,10 +583,10 @@ fn add_exiting_edge(&mut self, scope_id: ast::NodeId, to_index: CFGIndex) { let mut data = CFGEdgeData { exiting_scopes: vec![] }; - let mut scope = self.tcx.region_maps().node_extent(from_expr.id); - let target_scope = self.tcx.region_maps().node_extent(scope_id); + let mut scope = self.tcx.node_extent(from_expr.id); + let target_scope = self.tcx.node_extent(scope_id); while scope != target_scope { - data.exiting_scopes.push(scope.node_id(&self.tcx.region_maps())); + data.exiting_scopes.push(scope.node_id()); scope = self.tcx.region_maps().encl_scope(scope); } self.graph.add_edge(from_index, to_index, data); diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index d68a62e5030..52bdb5d0240 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -39,7 +39,7 @@ fn hash_stable(&self, } } -impl<'a, 'tcx> HashStable> for ty::Region { +impl<'a, 'tcx> HashStable> for ty::RegionKind<'tcx> { fn hash_stable(&self, hcx: &mut StableHashingContext<'a, 'tcx>, hasher: &mut StableHasher) { @@ -432,17 +432,6 @@ fn hash_stable(&self, FnPtrAddrCast }); -impl<'a, 'tcx> HashStable> for ::middle::region::CodeExtent -{ - fn hash_stable(&self, - hcx: &mut StableHashingContext<'a, 'tcx>, - hasher: &mut StableHasher) { - hcx.with_node_id_hashing_mode(NodeIdHashingMode::HashDefPath, |hcx| { - hcx.tcx().region_maps().code_extent_data(*self).hash_stable(hcx, hasher); - }); - } -} - impl<'a, 'tcx> HashStable> for ::middle::region::CodeExtentData { fn hash_stable(&self, @@ -477,7 +466,7 @@ fn hash_stable(&self, custom_kind }); -impl_stable_hash_for!(struct ty::FreeRegion { +impl_stable_hash_for!(struct ty::FreeRegion<'tcx> { scope, bound_region }); diff --git a/src/librustc/infer/combine.rs b/src/librustc/infer/combine.rs index b73079b02bd..1bac512e209 100644 --- a/src/librustc/infer/combine.rs +++ b/src/librustc/infer/combine.rs @@ -315,7 +315,7 @@ fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> { } } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { // Never make variables for regions bound within the type itself, // nor for erased regions. diff --git a/src/librustc/infer/equate.rs b/src/librustc/infer/equate.rs index f620965ced8..f0b179fa2e4 100644 --- a/src/librustc/infer/equate.rs +++ b/src/librustc/infer/equate.rs @@ -78,8 +78,8 @@ fn tys(&mut self, a: Ty<'tcx>, b: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> { } } - fn regions(&mut self, a: &'tcx ty::Region, b: &'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region> { + fn regions(&mut self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>> { debug!("{}.regions({:?}, {:?})", self.tag(), a, diff --git a/src/librustc/infer/error_reporting/mod.rs b/src/librustc/infer/error_reporting/mod.rs index 10712f5ec70..8f2bdd4e85c 100644 --- a/src/librustc/infer/error_reporting/mod.rs +++ b/src/librustc/infer/error_reporting/mod.rs @@ -79,7 +79,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { pub fn note_and_explain_region(self, err: &mut DiagnosticBuilder, prefix: &str, - region: &'tcx ty::Region, + region: ty::Region<'tcx>, suffix: &str) { fn item_scope_tag(item: &hir::Item) -> &'static str { match item.node { @@ -124,14 +124,14 @@ fn explain_span<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, format!("{}unknown scope: {:?}{}. Please report a bug.", prefix, scope, suffix) }; - let span = match scope.span(&self.region_maps(), &self.hir) { + let span = match scope.span(&self.hir) { Some(s) => s, None => { err.note(&unknown_scope()); return; } }; - let tag = match self.hir.find(scope.node_id(&self.region_maps())) { + let tag = match self.hir.find(scope.node_id()) { Some(hir_map::NodeBlock(_)) => "block", Some(hir_map::NodeExpr(expr)) => match expr.node { hir::ExprCall(..) => "call", @@ -151,7 +151,7 @@ fn explain_span<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, return; } }; - let scope_decorated_tag = match self.region_maps().code_extent_data(scope) { + let scope_decorated_tag = match *scope { region::CodeExtentData::Misc(_) => tag, region::CodeExtentData::CallSiteScope { .. } => { "scope of call-site for function" @@ -184,7 +184,7 @@ fn explain_span<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, } }; - let node = fr.scope.map(|s| s.node_id(&self.region_maps())) + let node = fr.scope.map(|s| s.node_id()) .unwrap_or(DUMMY_NODE_ID); let unknown; let tag = match self.hir.find(node) { @@ -517,7 +517,7 @@ fn cmp(&self, t1: ty::Ty<'tcx>, t2: ty::Ty<'tcx>) values.1.push_normal("<"); } - fn lifetime_display(lifetime: &Region) -> String { + fn lifetime_display(lifetime: Region) -> String { let s = format!("{}", lifetime); if s.is_empty() { "'_".to_string() @@ -769,7 +769,7 @@ fn expected_found_str>( fn report_generic_bound_failure(&self, origin: SubregionOrigin<'tcx>, bound_kind: GenericKind<'tcx>, - sub: &'tcx Region) + sub: Region<'tcx>) { // FIXME: it would be better to report the first error message // with the span of the parameter itself, rather than the span @@ -848,9 +848,9 @@ fn report_generic_bound_failure(&self, fn report_sub_sup_conflict(&self, var_origin: RegionVariableOrigin, sub_origin: SubregionOrigin<'tcx>, - sub_region: &'tcx Region, + sub_region: Region<'tcx>, sup_origin: SubregionOrigin<'tcx>, - sup_region: &'tcx Region) { + sup_region: Region<'tcx>) { let mut err = self.report_inference_failure(var_origin); self.tcx.note_and_explain_region(&mut err, diff --git a/src/librustc/infer/error_reporting/note.rs b/src/librustc/infer/error_reporting/note.rs index 8b753e0d22b..49952d81cbb 100644 --- a/src/librustc/infer/error_reporting/note.rs +++ b/src/librustc/infer/error_reporting/note.rs @@ -146,8 +146,8 @@ pub(super) fn note_region_origin(&self, pub(super) fn report_concrete_failure(&self, origin: SubregionOrigin<'tcx>, - sub: &'tcx Region, - sup: &'tcx Region) + sub: Region<'tcx>, + sup: Region<'tcx>) -> DiagnosticBuilder<'tcx> { match origin { infer::Subtype(trace) => { diff --git a/src/librustc/infer/freshen.rs b/src/librustc/infer/freshen.rs index 922842136dc..ad67ef9a127 100644 --- a/src/librustc/infer/freshen.rs +++ b/src/librustc/infer/freshen.rs @@ -83,7 +83,7 @@ fn tcx<'b>(&'b self) -> TyCtxt<'b, 'gcx, 'tcx> { self.infcx.tcx } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { ty::ReEarlyBound(..) | ty::ReLateBound(..) => { diff --git a/src/librustc/infer/fudge.rs b/src/librustc/infer/fudge.rs index 72b23a3bc18..a8bc33f772d 100644 --- a/src/librustc/infer/fudge.rs +++ b/src/librustc/infer/fudge.rs @@ -147,7 +147,7 @@ fn fold_ty(&mut self, ty: Ty<'tcx>) -> Ty<'tcx> { } } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { ty::ReVar(v) if self.region_vars.contains(&v) => { self.infcx.next_region_var(self.origin.clone()) diff --git a/src/librustc/infer/glb.rs b/src/librustc/infer/glb.rs index a6dd18c113f..d7afeba7dc9 100644 --- a/src/librustc/infer/glb.rs +++ b/src/librustc/infer/glb.rs @@ -59,8 +59,8 @@ fn tys(&mut self, a: Ty<'tcx>, b: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> { lattice::super_lattice_tys(self, a, b) } - fn regions(&mut self, a: &'tcx ty::Region, b: &'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region> { + fn regions(&mut self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>> { debug!("{}.regions({:?}, {:?})", self.tag(), a, diff --git a/src/librustc/infer/higher_ranked/mod.rs b/src/librustc/infer/higher_ranked/mod.rs index e3ffc99c0e9..09f909ef399 100644 --- a/src/librustc/infer/higher_ranked/mod.rs +++ b/src/librustc/infer/higher_ranked/mod.rs @@ -269,9 +269,9 @@ fn generalize_region<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, snapshot: &CombinedSnapshot, debruijn: ty::DebruijnIndex, new_vars: &[ty::RegionVid], - a_map: &FxHashMap, - r0: &'tcx ty::Region) - -> &'tcx ty::Region { + a_map: &FxHashMap>, + r0: ty::Region<'tcx>) + -> ty::Region<'tcx> { // Regions that pre-dated the LUB computation stay as they are. if !is_var_in_set(new_vars, r0) { assert!(!r0.is_bound()); @@ -284,7 +284,7 @@ fn generalize_region<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, // Variables created during LUB computation which are // *related* to regions that pre-date the LUB computation // stay as they are. - if !tainted.iter().all(|r| is_var_in_set(new_vars, *r)) { + if !tainted.iter().all(|&r| is_var_in_set(new_vars, r)) { debug!("generalize_region(r0={:?}): \ non-new-variables found in {:?}", r0, tainted); @@ -365,11 +365,11 @@ fn generalize_region<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, snapshot: &CombinedSnapshot, debruijn: ty::DebruijnIndex, new_vars: &[ty::RegionVid], - a_map: &FxHashMap, + a_map: &FxHashMap>, a_vars: &[ty::RegionVid], b_vars: &[ty::RegionVid], - r0: &'tcx ty::Region) - -> &'tcx ty::Region { + r0: ty::Region<'tcx>) + -> ty::Region<'tcx> { if !is_var_in_set(new_vars, r0) { assert!(!r0.is_bound()); return r0; @@ -434,8 +434,8 @@ fn generalize_region<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, fn rev_lookup<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, span: Span, - a_map: &FxHashMap, - r: &'tcx ty::Region) -> &'tcx ty::Region + a_map: &FxHashMap>, + r: ty::Region<'tcx>) -> ty::Region<'tcx> { for (a_br, a_r) in a_map { if *a_r == r { @@ -450,14 +450,14 @@ fn rev_lookup<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, fn fresh_bound_variable<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, debruijn: ty::DebruijnIndex) - -> &'tcx ty::Region { + -> ty::Region<'tcx> { infcx.region_vars.new_bound(debruijn) } } } fn var_ids<'a, 'gcx, 'tcx>(fields: &CombineFields<'a, 'gcx, 'tcx>, - map: &FxHashMap) + map: &FxHashMap>) -> Vec { map.iter() .map(|(_, &r)| match *r { @@ -472,7 +472,7 @@ fn var_ids<'a, 'gcx, 'tcx>(fields: &CombineFields<'a, 'gcx, 'tcx>, .collect() } -fn is_var_in_set(new_vars: &[ty::RegionVid], r: &ty::Region) -> bool { +fn is_var_in_set(new_vars: &[ty::RegionVid], r: ty::Region) -> bool { match *r { ty::ReVar(ref v) => new_vars.iter().any(|x| x == v), _ => false @@ -484,7 +484,7 @@ fn fold_regions_in<'a, 'gcx, 'tcx, T, F>(tcx: TyCtxt<'a, 'gcx, 'tcx>, mut fldr: F) -> T where T: TypeFoldable<'tcx>, - F: FnMut(&'tcx ty::Region, ty::DebruijnIndex) -> &'tcx ty::Region, + F: FnMut(ty::Region<'tcx>, ty::DebruijnIndex) -> ty::Region<'tcx>, { tcx.fold_regions(unbound_value, &mut false, |region, current_depth| { // we should only be encountering "escaping" late-bound regions here, @@ -502,9 +502,9 @@ fn fold_regions_in<'a, 'gcx, 'tcx, T, F>(tcx: TyCtxt<'a, 'gcx, 'tcx>, impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { fn tainted_regions(&self, snapshot: &CombinedSnapshot, - r: &'tcx ty::Region, + r: ty::Region<'tcx>, directions: TaintDirections) - -> FxHashSet<&'tcx ty::Region> { + -> FxHashSet> { self.region_vars.tainted(&snapshot.region_vars_snapshot, r, directions) } @@ -731,7 +731,7 @@ pub fn plug_leaks(&self, // region back to the `ty::BoundRegion` that it originally // represented. Because `leak_check` passed, we know that // these taint sets are mutually disjoint. - let inv_skol_map: FxHashMap<&'tcx ty::Region, ty::BoundRegion> = + let inv_skol_map: FxHashMap, ty::BoundRegion> = skol_map .iter() .flat_map(|(&skol_br, &skol)| { diff --git a/src/librustc/infer/lub.rs b/src/librustc/infer/lub.rs index d7e5c92b6e1..04b470b29fc 100644 --- a/src/librustc/infer/lub.rs +++ b/src/librustc/infer/lub.rs @@ -59,8 +59,8 @@ fn tys(&mut self, a: Ty<'tcx>, b: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> { lattice::super_lattice_tys(self, a, b) } - fn regions(&mut self, a: &'tcx ty::Region, b: &'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region> { + fn regions(&mut self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>> { debug!("{}.regions({:?}, {:?})", self.tag(), a, diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index e75513e924e..a0451c5fe0b 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -205,7 +205,7 @@ pub struct InferCtxt<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { /// A map returned by `skolemize_late_bound_regions()` indicating the skolemized /// region that each late-bound region was replaced with. -pub type SkolemizationMap<'tcx> = FxHashMap; +pub type SkolemizationMap<'tcx> = FxHashMap>; /// See `error_reporting` module for more details #[derive(Clone, Debug)] @@ -1008,7 +1008,7 @@ pub fn probe(&self, f: F) -> R where } pub fn add_given(&self, - sub: ty::FreeRegion, + sub: ty::FreeRegion<'tcx>, sup: ty::RegionVid) { self.region_vars.add_given(sub, sup); @@ -1107,8 +1107,8 @@ pub fn sub_poly_trait_refs(&self, pub fn sub_regions(&self, origin: SubregionOrigin<'tcx>, - a: &'tcx ty::Region, - b: &'tcx ty::Region) { + a: ty::Region<'tcx>, + b: ty::Region<'tcx>) { debug!("sub_regions({:?} <: {:?})", a, b); self.region_vars.make_subregion(origin, a, b); } @@ -1210,7 +1210,7 @@ pub fn next_float_var_id(&self) -> FloatVid { } pub fn next_region_var(&self, origin: RegionVariableOrigin) - -> &'tcx ty::Region { + -> ty::Region<'tcx> { self.tcx.mk_region(ty::ReVar(self.region_vars.new_region_var(origin))) } @@ -1219,7 +1219,7 @@ pub fn next_region_var(&self, origin: RegionVariableOrigin) pub fn region_var_for_def(&self, span: Span, def: &ty::RegionParameterDef) - -> &'tcx ty::Region { + -> ty::Region<'tcx> { self.next_region_var(EarlyBoundRegion(span, def.name, def.issue_32330)) } @@ -1270,7 +1270,7 @@ pub fn fresh_substs_for_item(&self, }) } - pub fn fresh_bound_region(&self, debruijn: ty::DebruijnIndex) -> &'tcx ty::Region { + pub fn fresh_bound_region(&self, debruijn: ty::DebruijnIndex) -> ty::Region<'tcx> { self.region_vars.new_bound(debruijn) } @@ -1322,7 +1322,7 @@ pub fn expr_ty(&self, ex: &hir::Expr) -> Ty<'tcx> { } pub fn resolve_regions_and_report_errors(&self, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, subject_node_id: ast::NodeId) { let errors = self.region_vars.resolve_regions(free_regions, subject_node_id); if !self.is_tainted_by_errors() { @@ -1531,7 +1531,7 @@ pub fn replace_late_bound_regions_with_fresh_var( span: Span, lbrct: LateBoundRegionConversionTime, value: &ty::Binder) - -> (T, FxHashMap) + -> (T, FxHashMap>) where T : TypeFoldable<'tcx> { self.tcx.replace_late_bound_regions( @@ -1577,7 +1577,7 @@ pub fn match_poly_projection_predicate(&self, pub fn verify_generic_bound(&self, origin: SubregionOrigin<'tcx>, kind: GenericKind<'tcx>, - a: &'tcx ty::Region, + a: ty::Region<'tcx>, bound: VerifyBound<'tcx>) { debug!("verify_generic_bound({:?}, {:?} <: {:?})", kind, diff --git a/src/librustc/infer/region_inference/graphviz.rs b/src/librustc/infer/region_inference/graphviz.rs index f8d188fcaed..7de81e14d77 100644 --- a/src/librustc/infer/region_inference/graphviz.rs +++ b/src/librustc/infer/region_inference/graphviz.rs @@ -123,20 +123,20 @@ struct ConstraintGraph<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { tcx: TyCtxt<'a, 'gcx, 'tcx>, graph_name: String, map: &'a FxHashMap, SubregionOrigin<'tcx>>, - node_ids: FxHashMap, + node_ids: FxHashMap, usize>, } #[derive(Clone, Hash, PartialEq, Eq, Debug, Copy)] -enum Node { +enum Node<'tcx> { RegionVid(ty::RegionVid), - Region(ty::Region), + Region(ty::RegionKind<'tcx>), } // type Edge = Constraint; #[derive(Clone, PartialEq, Eq, Debug, Copy)] enum Edge<'tcx> { Constraint(Constraint<'tcx>), - EnclScope(CodeExtent, CodeExtent), + EnclScope(CodeExtent<'tcx>, CodeExtent<'tcx>), } impl<'a, 'gcx, 'tcx> ConstraintGraph<'a, 'gcx, 'tcx> { @@ -160,8 +160,8 @@ fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>, } tcx.region_maps().each_encl_scope(|sub, sup| { - add_node(Node::Region(ty::ReScope(*sub))); - add_node(Node::Region(ty::ReScope(*sup))); + add_node(Node::Region(ty::ReScope(sub))); + add_node(Node::Region(ty::ReScope(sup))); }); } @@ -175,7 +175,7 @@ fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>, } impl<'a, 'gcx, 'tcx> dot::Labeller<'a> for ConstraintGraph<'a, 'gcx, 'tcx> { - type Node = Node; + type Node = Node<'tcx>; type Edge = Edge<'tcx>; fn graph_id(&self) -> dot::Id { dot::Id::new(&*self.graph_name).unwrap() @@ -208,7 +208,7 @@ fn edge_label(&self, e: &Edge) -> dot::LabelText { } } -fn constraint_to_nodes(c: &Constraint) -> (Node, Node) { +fn constraint_to_nodes<'tcx>(c: &Constraint<'tcx>) -> (Node<'tcx>, Node<'tcx>) { match *c { Constraint::ConstrainVarSubVar(rv_1, rv_2) => (Node::RegionVid(rv_1), Node::RegionVid(rv_2)), @@ -221,7 +221,7 @@ fn constraint_to_nodes(c: &Constraint) -> (Node, Node) { } } -fn edge_to_nodes(e: &Edge) -> (Node, Node) { +fn edge_to_nodes<'tcx>(e: &Edge<'tcx>) -> (Node<'tcx>, Node<'tcx>) { match *e { Edge::Constraint(ref c) => constraint_to_nodes(c), Edge::EnclScope(sub, sup) => { @@ -232,9 +232,9 @@ fn edge_to_nodes(e: &Edge) -> (Node, Node) { } impl<'a, 'gcx, 'tcx> dot::GraphWalk<'a> for ConstraintGraph<'a, 'gcx, 'tcx> { - type Node = Node; + type Node = Node<'tcx>; type Edge = Edge<'tcx>; - fn nodes(&self) -> dot::Nodes { + fn nodes(&self) -> dot::Nodes> { let mut set = FxHashSet(); for node in self.node_ids.keys() { set.insert(*node); @@ -245,16 +245,16 @@ fn nodes(&self) -> dot::Nodes { fn edges(&self) -> dot::Edges> { debug!("constraint graph has {} edges", self.map.len()); let mut v: Vec<_> = self.map.keys().map(|e| Edge::Constraint(*e)).collect(); - self.tcx.region_maps().each_encl_scope(|sub, sup| v.push(Edge::EnclScope(*sub, *sup))); + self.tcx.region_maps().each_encl_scope(|sub, sup| v.push(Edge::EnclScope(sub, sup))); debug!("region graph has {} edges", v.len()); Cow::Owned(v) } - fn source(&self, edge: &Edge<'tcx>) -> Node { + fn source(&self, edge: &Edge<'tcx>) -> Node<'tcx> { let (n1, _) = edge_to_nodes(edge); debug!("edge {:?} has source {:?}", edge, n1); n1 } - fn target(&self, edge: &Edge<'tcx>) -> Node { + fn target(&self, edge: &Edge<'tcx>) -> Node<'tcx> { let (_, n2) = edge_to_nodes(edge); debug!("edge {:?} has target {:?}", edge, n2); n2 diff --git a/src/librustc/infer/region_inference/mod.rs b/src/librustc/infer/region_inference/mod.rs index f9aab59acaf..33754b738a0 100644 --- a/src/librustc/infer/region_inference/mod.rs +++ b/src/librustc/infer/region_inference/mod.rs @@ -44,17 +44,17 @@ pub enum Constraint<'tcx> { ConstrainVarSubVar(RegionVid, RegionVid), // Concrete region is subregion of region variable - ConstrainRegSubVar(&'tcx Region, RegionVid), + ConstrainRegSubVar(Region<'tcx>, RegionVid), // Region variable is subregion of concrete region. This does not // directly affect inference, but instead is checked after // inference is complete. - ConstrainVarSubReg(RegionVid, &'tcx Region), + ConstrainVarSubReg(RegionVid, Region<'tcx>), // A constraint where neither side is a variable. This does not // directly affect inference, but instead is checked after // inference is complete. - ConstrainRegSubReg(&'tcx Region, &'tcx Region), + ConstrainRegSubReg(Region<'tcx>, Region<'tcx>), } // VerifyGenericBound(T, _, R, RS): The parameter type `T` (or @@ -66,7 +66,7 @@ pub enum Constraint<'tcx> { pub struct Verify<'tcx> { kind: GenericKind<'tcx>, origin: SubregionOrigin<'tcx>, - region: &'tcx Region, + region: Region<'tcx>, bound: VerifyBound<'tcx>, } @@ -86,14 +86,14 @@ pub enum VerifyBound<'tcx> { // Put another way, the subject value is known to outlive all // regions in {R}, so if any of those outlives 'min, then the // bound is met. - AnyRegion(Vec<&'tcx Region>), + AnyRegion(Vec>), // B = forall {R} --> all 'r in {R} must outlive 'min // // Put another way, the subject value is known to outlive some // region in {R}, so if all of those outlives 'min, then the bound // is met. - AllRegions(Vec<&'tcx Region>), + AllRegions(Vec>), // B = exists {B} --> 'min must meet some bound b in {B} AnyBound(Vec>), @@ -104,8 +104,8 @@ pub enum VerifyBound<'tcx> { #[derive(Copy, Clone, PartialEq, Eq, Hash)] pub struct TwoRegions<'tcx> { - a: &'tcx Region, - b: &'tcx Region, + a: Region<'tcx>, + b: Region<'tcx>, } #[derive(Copy, Clone, PartialEq)] @@ -128,7 +128,7 @@ pub enum UndoLogEntry<'tcx> { AddVerify(usize), /// We added the given `given` - AddGiven(ty::FreeRegion, ty::RegionVid), + AddGiven(ty::FreeRegion<'tcx>, ty::RegionVid), /// We added a GLB/LUB "combinaton variable" AddCombination(CombineMapType, TwoRegions<'tcx>), @@ -153,13 +153,13 @@ pub enum RegionResolutionError<'tcx> { /// `ConcreteFailure(o, a, b)`: /// /// `o` requires that `a <= b`, but this does not hold - ConcreteFailure(SubregionOrigin<'tcx>, &'tcx Region, &'tcx Region), + ConcreteFailure(SubregionOrigin<'tcx>, Region<'tcx>, Region<'tcx>), /// `GenericBoundFailure(p, s, a) /// /// The parameter/associated-type `p` must be known to outlive the lifetime /// `a` (but none of the known bounds are sufficient). - GenericBoundFailure(SubregionOrigin<'tcx>, GenericKind<'tcx>, &'tcx Region), + GenericBoundFailure(SubregionOrigin<'tcx>, GenericKind<'tcx>, Region<'tcx>), /// `SubSupConflict(v, sub_origin, sub_r, sup_origin, sup_r)`: /// @@ -168,14 +168,14 @@ pub enum RegionResolutionError<'tcx> { /// `sub_r <= sup_r` does not hold. SubSupConflict(RegionVariableOrigin, SubregionOrigin<'tcx>, - &'tcx Region, + Region<'tcx>, SubregionOrigin<'tcx>, - &'tcx Region), + Region<'tcx>), } #[derive(Clone, Debug)] pub enum ProcessedErrorOrigin<'tcx> { - ConcreteFailure(SubregionOrigin<'tcx>, &'tcx Region, &'tcx Region), + ConcreteFailure(SubregionOrigin<'tcx>, Region<'tcx>, Region<'tcx>), VariableFailure(RegionVariableOrigin), } @@ -214,7 +214,7 @@ pub struct RegionVarBindings<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { // record the fact that `'a <= 'b` is implied by the fn signature, // and then ignore the constraint when solving equations. This is // a bit of a hack but seems to work. - givens: RefCell>, + givens: RefCell, ty::RegionVid)>>, lubs: RefCell>, glbs: RefCell>, @@ -271,12 +271,12 @@ pub fn both() -> Self { struct TaintSet<'tcx> { directions: TaintDirections, - regions: FxHashSet<&'tcx ty::Region> + regions: FxHashSet> } impl<'a, 'gcx, 'tcx> TaintSet<'tcx> { fn new(directions: TaintDirections, - initial_region: &'tcx ty::Region) + initial_region: ty::Region<'tcx>) -> Self { let mut regions = FxHashSet(); regions.insert(initial_region); @@ -328,7 +328,7 @@ fn fixed_point(&mut self, } } - fn into_set(self) -> FxHashSet<&'tcx ty::Region> { + fn into_set(self) -> FxHashSet> { self.regions } @@ -337,8 +337,8 @@ fn len(&self) -> usize { } fn add_edge(&mut self, - source: &'tcx ty::Region, - target: &'tcx ty::Region) { + source: ty::Region<'tcx>, + target: ty::Region<'tcx>) { if self.directions.incoming { if self.regions.contains(&target) { self.regions.insert(source); @@ -499,7 +499,7 @@ pub fn var_origin(&self, vid: RegionVid) -> RegionVariableOrigin { /// it's just there to make it explicit which snapshot bounds the /// skolemized region that results. It should always be the top-most snapshot. pub fn push_skolemized(&self, br: ty::BoundRegion, snapshot: &RegionSnapshot) - -> &'tcx Region { + -> Region<'tcx> { assert!(self.in_snapshot()); assert!(self.undo_log.borrow()[snapshot.length] == OpenSnapshot); @@ -513,7 +513,7 @@ pub fn push_skolemized(&self, br: ty::BoundRegion, snapshot: &RegionSnapshot) /// completes to remove all trace of the skolemized regions /// created in that time. pub fn pop_skolemized(&self, - skols: &FxHashSet<&'tcx ty::Region>, + skols: &FxHashSet>, snapshot: &RegionSnapshot) { debug!("pop_skolemized_regions(skols={:?})", skols); @@ -567,7 +567,7 @@ pub fn pop_skolemized(&self, self.skolemization_count.set(snapshot.skolemization_count); return; - fn kill_constraint<'tcx>(skols: &FxHashSet<&'tcx ty::Region>, + fn kill_constraint<'tcx>(skols: &FxHashSet>, undo_entry: &UndoLogEntry<'tcx>) -> bool { match undo_entry { @@ -596,7 +596,7 @@ fn kill_constraint<'tcx>(skols: &FxHashSet<&'tcx ty::Region>, } - pub fn new_bound(&self, debruijn: ty::DebruijnIndex) -> &'tcx Region { + pub fn new_bound(&self, debruijn: ty::DebruijnIndex) -> Region<'tcx> { // Creates a fresh bound variable for use in GLB computations. // See discussion of GLB computation in the large comment at // the top of this file for more details. @@ -662,7 +662,7 @@ fn add_verify(&self, verify: Verify<'tcx>) { } } - pub fn add_given(&self, sub: ty::FreeRegion, sup: ty::RegionVid) { + pub fn add_given(&self, sub: ty::FreeRegion<'tcx>, sup: ty::RegionVid) { // cannot add givens once regions are resolved assert!(self.values_are_none()); @@ -676,8 +676,8 @@ pub fn add_given(&self, sub: ty::FreeRegion, sup: ty::RegionVid) { pub fn make_eqregion(&self, origin: SubregionOrigin<'tcx>, - sub: &'tcx Region, - sup: &'tcx Region) { + sub: Region<'tcx>, + sup: Region<'tcx>) { if sub != sup { // Eventually, it would be nice to add direct support for // equating regions. @@ -692,8 +692,8 @@ pub fn make_eqregion(&self, pub fn make_subregion(&self, origin: SubregionOrigin<'tcx>, - sub: &'tcx Region, - sup: &'tcx Region) { + sub: Region<'tcx>, + sup: Region<'tcx>) { // cannot add constraints once regions are resolved assert!(self.values_are_none()); @@ -734,7 +734,7 @@ pub fn make_subregion(&self, pub fn verify_generic_bound(&self, origin: SubregionOrigin<'tcx>, kind: GenericKind<'tcx>, - sub: &'tcx Region, + sub: Region<'tcx>, bound: VerifyBound<'tcx>) { self.add_verify(Verify { kind: kind, @@ -746,9 +746,9 @@ pub fn verify_generic_bound(&self, pub fn lub_regions(&self, origin: SubregionOrigin<'tcx>, - a: &'tcx Region, - b: &'tcx Region) - -> &'tcx Region { + a: Region<'tcx>, + b: Region<'tcx>) + -> Region<'tcx> { // cannot add constraints once regions are resolved assert!(self.values_are_none()); @@ -772,9 +772,9 @@ pub fn lub_regions(&self, pub fn glb_regions(&self, origin: SubregionOrigin<'tcx>, - a: &'tcx Region, - b: &'tcx Region) - -> &'tcx Region { + a: Region<'tcx>, + b: Region<'tcx>) + -> Region<'tcx> { // cannot add constraints once regions are resolved assert!(self.values_are_none()); @@ -796,7 +796,7 @@ pub fn glb_regions(&self, } } - pub fn resolve_var(&self, rid: RegionVid) -> &'tcx ty::Region { + pub fn resolve_var(&self, rid: RegionVid) -> ty::Region<'tcx> { match *self.values.borrow() { None => { span_bug!((*self.var_origins.borrow())[rid.index as usize].span(), @@ -811,7 +811,7 @@ pub fn resolve_var(&self, rid: RegionVid) -> &'tcx ty::Region { } } - pub fn opportunistic_resolve_var(&self, rid: RegionVid) -> &'tcx ty::Region { + pub fn opportunistic_resolve_var(&self, rid: RegionVid) -> ty::Region<'tcx> { let vid = self.unification_table.borrow_mut().find_value(rid).min_vid; self.tcx.mk_region(ty::ReVar(vid)) } @@ -825,12 +825,12 @@ fn combine_map(&self, t: CombineMapType) -> &RefCell> { pub fn combine_vars(&self, t: CombineMapType, - a: &'tcx Region, - b: &'tcx Region, + a: Region<'tcx>, + b: Region<'tcx>, origin: SubregionOrigin<'tcx>, mut relate: F) - -> &'tcx Region - where F: FnMut(&RegionVarBindings<'a, 'gcx, 'tcx>, &'tcx Region, &'tcx Region) + -> Region<'tcx> + where F: FnMut(&RegionVarBindings<'a, 'gcx, 'tcx>, Region<'tcx>, Region<'tcx>) { let vars = TwoRegions { a: a, b: b }; if let Some(&c) = self.combine_map(t).borrow().get(&vars) { @@ -869,9 +869,9 @@ pub fn vars_created_since_snapshot(&self, mark: &RegionSnapshot) -> Vec, directions: TaintDirections) - -> FxHashSet<&'tcx ty::Region> { + -> FxHashSet> { debug!("tainted(mark={:?}, r0={:?}, directions={:?})", mark, r0, directions); @@ -892,7 +892,7 @@ pub fn tainted(&self, /// constraints, assuming such values can be found; if they cannot, /// errors are reported. pub fn resolve_regions(&self, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, subject_node: ast::NodeId) -> Vec> { debug!("RegionVarBindings: resolve_regions()"); @@ -903,10 +903,10 @@ pub fn resolve_regions(&self, } fn lub_concrete_regions(&self, - free_regions: &FreeRegionMap, - a: &'tcx Region, - b: &'tcx Region) - -> &'tcx Region { + free_regions: &FreeRegionMap<'tcx>, + a: Region<'tcx>, + b: Region<'tcx>) + -> Region<'tcx> { match (a, b) { (&ReLateBound(..), _) | (_, &ReLateBound(..)) | @@ -961,8 +961,8 @@ fn lub_concrete_regions(&self, self.tcx.region_maps().nearest_common_ancestor(a_id, b_id))) } - (&ReFree(a_fr), &ReFree(b_fr)) => { - self.tcx.mk_region(free_regions.lub_free_regions(a_fr, b_fr)) + (&ReFree(_), &ReFree(_)) => { + free_regions.lub_free_regions(self.tcx, a, b) } // For these types, we cannot define any additional @@ -983,12 +983,12 @@ fn lub_concrete_regions(&self, #[derive(Copy, Clone, Debug)] pub enum VarValue<'tcx> { - Value(&'tcx Region), + Value(Region<'tcx>), ErrorValue, } struct RegionAndOrigin<'tcx> { - region: &'tcx Region, + region: Region<'tcx>, origin: SubregionOrigin<'tcx>, } @@ -996,7 +996,7 @@ struct RegionAndOrigin<'tcx> { impl<'a, 'gcx, 'tcx> RegionVarBindings<'a, 'gcx, 'tcx> { fn infer_variable_values(&self, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, errors: &mut Vec>, subject: ast::NodeId) -> Vec> { @@ -1056,7 +1056,7 @@ fn expand_givens(&self, graph: &RegionGraph) { } } - fn expansion(&self, free_regions: &FreeRegionMap, var_values: &mut [VarValue<'tcx>]) { + fn expansion(&self, free_regions: &FreeRegionMap<'tcx>, var_values: &mut [VarValue<'tcx>]) { self.iterate_until_fixed_point("Expansion", |constraint, origin| { debug!("expansion: constraint={:?} origin={:?}", constraint, origin); @@ -1085,8 +1085,8 @@ fn expansion(&self, free_regions: &FreeRegionMap, var_values: &mut [VarValue<'tc } fn expand_node(&self, - free_regions: &FreeRegionMap, - a_region: &'tcx Region, + free_regions: &FreeRegionMap<'tcx>, + a_region: Region<'tcx>, b_vid: RegionVid, b_data: &mut VarValue<'tcx>) -> bool { @@ -1132,7 +1132,7 @@ fn expand_node(&self, /// cases where the region cannot grow larger than a fixed point) /// and check that they are satisfied. fn collect_errors(&self, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, var_data: &mut Vec>, errors: &mut Vec>) { let constraints = self.constraints.borrow(); @@ -1209,7 +1209,7 @@ fn collect_errors(&self, /// Go over the variables that were declared to be error variables /// and create a `RegionResolutionError` for each of them. fn collect_var_errors(&self, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, var_data: &[VarValue<'tcx>], graph: &RegionGraph<'tcx>, errors: &mut Vec>) { @@ -1311,7 +1311,7 @@ fn construct_graph(&self) -> RegionGraph<'tcx> { } fn collect_error_for_expanding_node(&self, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, graph: &RegionGraph<'tcx>, dup_vec: &mut [u32], node_idx: RegionVid, @@ -1480,8 +1480,8 @@ fn iterate_until_fixed_point(&self, tag: &str, mut body: F) fn normalize<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, values: &Vec>, - r: &'tcx ty::Region) - -> &'tcx ty::Region { + r: ty::Region<'tcx>) + -> ty::Region<'tcx> { match *r { ty::ReVar(rid) => lookup(tcx, values, rid), _ => r, @@ -1491,7 +1491,7 @@ fn normalize<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, fn lookup<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, values: &Vec>, rid: ty::RegionVid) - -> &'tcx ty::Region { + -> ty::Region<'tcx> { match values[rid.index as usize] { Value(r) => r, ErrorValue => tcx.types.re_static, // Previously reported error. @@ -1539,7 +1539,7 @@ pub fn to_ty(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> Ty<'tcx> { } impl<'a, 'gcx, 'tcx> VerifyBound<'tcx> { - fn for_each_region(&self, f: &mut FnMut(&'tcx ty::Region)) { + fn for_each_region(&self, f: &mut FnMut(ty::Region<'tcx>)) { match self { &VerifyBound::AnyRegion(ref rs) | &VerifyBound::AllRegions(ref rs) => for &r in rs { @@ -1592,9 +1592,9 @@ pub fn and(self, vb: VerifyBound<'tcx>) -> VerifyBound<'tcx> { } fn is_met(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, - free_regions: &FreeRegionMap, + free_regions: &FreeRegionMap<'tcx>, var_values: &Vec>, - min: &'tcx ty::Region) + min: ty::Region<'tcx>) -> bool { match self { &VerifyBound::AnyRegion(ref rs) => diff --git a/src/librustc/infer/resolve.rs b/src/librustc/infer/resolve.rs index 357a03a2ffd..2e8b843d07b 100644 --- a/src/librustc/infer/resolve.rs +++ b/src/librustc/infer/resolve.rs @@ -72,7 +72,7 @@ fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> { } } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { ty::ReVar(rid) => self.infcx.region_vars.opportunistic_resolve_var(rid), _ => r, @@ -138,7 +138,7 @@ fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> { } } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { ty::ReVar(rid) => self.infcx.region_vars.resolve_var(rid), _ => r, diff --git a/src/librustc/infer/sub.rs b/src/librustc/infer/sub.rs index 2a7dbbc026b..487195fdfae 100644 --- a/src/librustc/infer/sub.rs +++ b/src/librustc/infer/sub.rs @@ -127,8 +127,8 @@ fn tys(&mut self, a: Ty<'tcx>, b: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>> { } } - fn regions(&mut self, a: &'tcx ty::Region, b: &'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region> { + fn regions(&mut self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>> { debug!("{}.regions({:?}, {:?}) self.cause={:?}", self.tag(), a, b, self.fields.cause); diff --git a/src/librustc/middle/expr_use_visitor.rs b/src/librustc/middle/expr_use_visitor.rs index 82e7d972c57..9be05313439 100644 --- a/src/librustc/middle/expr_use_visitor.rs +++ b/src/librustc/middle/expr_use_visitor.rs @@ -75,7 +75,7 @@ fn borrow(&mut self, borrow_id: ast::NodeId, borrow_span: Span, cmt: mc::cmt<'tcx>, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, bk: ty::BorrowKind, loan_cause: LoanCause); @@ -347,7 +347,7 @@ fn mutate_expr(&mut self, fn borrow_expr(&mut self, expr: &hir::Expr, - r: &'tcx ty::Region, + r: ty::Region<'tcx>, bk: ty::BorrowKind, cause: LoanCause) { debug!("borrow_expr(expr={:?}, r={:?}, bk={:?})", diff --git a/src/librustc/middle/free_region.rs b/src/librustc/middle/free_region.rs index 9701595a9d8..1dc633c6d00 100644 --- a/src/librustc/middle/free_region.rs +++ b/src/librustc/middle/free_region.rs @@ -15,18 +15,21 @@ //! `TransitiveRelation` type and use that to decide when one free //! region outlives another and so forth. -use ty::{self, TyCtxt, FreeRegion, Region}; +use ty::{self, Lift, TyCtxt, Region}; use ty::wf::ImpliedBound; use rustc_data_structures::transitive_relation::TransitiveRelation; #[derive(Clone, RustcEncodable, RustcDecodable)] -pub struct FreeRegionMap { +pub struct FreeRegionMap<'tcx> { // Stores the relation `a < b`, where `a` and `b` are regions. - relation: TransitiveRelation + // + // Invariant: only free regions like `'x` or `'static` are stored + // in this relation, not scopes. + relation: TransitiveRelation> } -impl FreeRegionMap { - pub fn new() -> FreeRegionMap { +impl<'tcx> FreeRegionMap<'tcx> { + pub fn new() -> Self { FreeRegionMap { relation: TransitiveRelation::new() } } @@ -34,15 +37,16 @@ pub fn is_empty(&self) -> bool { self.relation.is_empty() } - pub fn relate_free_regions_from_implied_bounds<'tcx>(&mut self, - implied_bounds: &[ImpliedBound<'tcx>]) + pub fn relate_free_regions_from_implied_bounds(&mut self, + implied_bounds: &[ImpliedBound<'tcx>]) { debug!("relate_free_regions_from_implied_bounds()"); for implied_bound in implied_bounds { debug!("implied bound: {:?}", implied_bound); match *implied_bound { - ImpliedBound::RegionSubRegion(&ty::ReFree(free_a), &ty::ReFree(free_b)) => { - self.relate_free_regions(free_a, free_b); + ImpliedBound::RegionSubRegion(a @ &ty::ReFree(_), b @ &ty::ReFree(_)) | + ImpliedBound::RegionSubRegion(a @ &ty::ReStatic, b @ &ty::ReFree(_)) => { + self.relate_regions(a, b); } ImpliedBound::RegionSubRegion(..) | ImpliedBound::RegionSubParam(..) | @@ -53,7 +57,7 @@ pub fn relate_free_regions_from_implied_bounds<'tcx>(&mut self, } pub fn relate_free_regions_from_predicates(&mut self, - predicates: &[ty::Predicate]) { + predicates: &[ty::Predicate<'tcx>]) { debug!("relate_free_regions_from_predicates(predicates={:?})", predicates); for predicate in predicates { match *predicate { @@ -69,12 +73,15 @@ pub fn relate_free_regions_from_predicates(&mut self, } ty::Predicate::RegionOutlives(ty::Binder(ty::OutlivesPredicate(r_a, r_b))) => { match (r_a, r_b) { + // `'static: 'x` is not notable (&ty::ReStatic, &ty::ReFree(_)) => {}, - (&ty::ReFree(fr_a), &ty::ReStatic) => self.relate_to_static(fr_a), - (&ty::ReFree(fr_a), &ty::ReFree(fr_b)) => { + + (&ty::ReFree(_), &ty::ReStatic) | + (&ty::ReFree(_), &ty::ReFree(_)) => { // Record that `'a:'b`. Or, put another way, `'b <= 'a`. - self.relate_free_regions(fr_b, fr_a); + self.relate_regions(r_b, r_a); } + _ => { // All named regions are instantiated with free regions. bug!("record_region_bounds: non free region: {:?} / {:?}", @@ -87,48 +94,36 @@ pub fn relate_free_regions_from_predicates(&mut self, } } - fn relate_to_static(&mut self, sup: FreeRegion) { - self.relation.add(ty::ReStatic, ty::ReFree(sup)); - } - - fn relate_free_regions(&mut self, sub: FreeRegion, sup: FreeRegion) { - self.relation.add(ty::ReFree(sub), ty::ReFree(sup)) - } - - /// Determines whether two free regions have a subregion relationship - /// by walking the graph encoded in `map`. Note that - /// it is possible that `sub != sup` and `sub <= sup` and `sup <= sub` - /// (that is, the user can give two different names to the same lifetime). - pub fn sub_free_region(&self, sub: FreeRegion, sup: FreeRegion) -> bool { - let result = sub == sup || { - let sub = ty::ReFree(sub); - let sup = ty::ReFree(sup); - self.relation.contains(&sub, &sup) || self.relation.contains(&ty::ReStatic, &sup) - }; - debug!("sub_free_region(sub={:?}, sup={:?}) = {:?}", sub, sup, result); - result + fn relate_regions(&mut self, sub: Region<'tcx>, sup: Region<'tcx>) { + assert!(match *sub { ty::ReFree(_) | ty::ReStatic => true, _ => false }); + assert!(match *sup { ty::ReFree(_) | ty::ReStatic => true, _ => false }); + self.relation.add(sub, sup) } - pub fn lub_free_regions(&self, fr_a: FreeRegion, fr_b: FreeRegion) -> Region { - let r_a = ty::ReFree(fr_a); - let r_b = ty::ReFree(fr_b); - let result = if fr_a == fr_b { r_a } else { + pub fn lub_free_regions<'a, 'gcx>(&self, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + r_a: Region<'tcx>, + r_b: Region<'tcx>) + -> Region<'tcx> { + assert!(match *r_a { ty::ReFree(_) => true, _ => false }); + assert!(match *r_b { ty::ReFree(_) => true, _ => false }); + let result = if r_a == r_b { r_a } else { match self.relation.postdom_upper_bound(&r_a, &r_b) { - None => ty::ReStatic, + None => tcx.mk_region(ty::ReStatic), Some(r) => *r, } }; - debug!("lub_free_regions(fr_a={:?}, fr_b={:?}) = {:?}", fr_a, fr_b, result); + debug!("lub_free_regions(r_a={:?}, r_b={:?}) = {:?}", r_a, r_b, result); result } /// Determines whether one region is a subregion of another. This is intended to run *after /// inference* and sadly the logic is somewhat duplicated with the code in infer.rs. - pub fn is_subregion_of(&self, - tcx: TyCtxt, - sub_region: &ty::Region, - super_region: &ty::Region) - -> bool { + pub fn is_subregion_of<'a, 'gcx>(&self, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + sub_region: ty::Region<'tcx>, + super_region: ty::Region<'tcx>) + -> bool { let result = sub_region == super_region || { match (sub_region, super_region) { (&ty::ReEmpty, _) | @@ -141,17 +136,18 @@ pub fn is_subregion_of(&self, (&ty::ReScope(sub_scope), &ty::ReFree(fr)) => { // 1. It is safe to unwrap `fr.scope` because we // should only ever wind up comparing against - // `ReScope` in the context of a method or fn + // `ReScope` in the context of a method or // body, where `fr.scope` should be `Some`. tcx.region_maps().is_subscope_of(sub_scope, fr.scope.unwrap() /*1*/) || - self.is_static(fr) + self.is_static(tcx, super_region) } - (&ty::ReFree(sub_fr), &ty::ReFree(super_fr)) => - self.sub_free_region(sub_fr, super_fr), + (&ty::ReFree(_), &ty::ReFree(_)) => + self.relation.contains(&sub_region, &super_region) || + self.is_static(tcx, super_region), - (&ty::ReStatic, &ty::ReFree(sup_fr)) => - self.is_static(sup_fr), + (&ty::ReStatic, &ty::ReFree(_)) => + self.is_static(tcx, super_region), _ => false, @@ -163,28 +159,28 @@ pub fn is_subregion_of(&self, } /// Determines whether this free-region is required to be 'static - pub fn is_static(&self, super_region: ty::FreeRegion) -> bool { + fn is_static<'a, 'gcx>(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, super_region: ty::Region<'tcx>) + -> bool { debug!("is_static(super_region={:?})", super_region); - self.relation.contains(&ty::ReStatic, &ty::ReFree(super_region)) + match *super_region { + ty::ReStatic => true, + ty::ReFree(_) => { + let re_static = tcx.mk_region(ty::ReStatic); + self.relation.contains(&re_static, &super_region) + } + _ => bug!("only free regions should be given to `is_static`") + } } } -#[cfg(test)] -fn free_region(index: u32) -> FreeRegion { - FreeRegion { scope: None, bound_region: ty::BoundRegion::BrAnon(index) } -} - -#[test] -fn lub() { - // a very VERY basic test, but see the tests in - // TransitiveRelation, which are much more thorough. - let frs: Vec<_> = (0..3).map(|i| free_region(i)).collect(); - let mut map = FreeRegionMap::new(); - map.relate_free_regions(frs[0], frs[2]); - map.relate_free_regions(frs[1], frs[2]); - assert_eq!(map.lub_free_regions(frs[0], frs[1]), ty::ReFree(frs[2])); -} - -impl_stable_hash_for!(struct FreeRegionMap { +impl_stable_hash_for!(struct FreeRegionMap<'tcx> { relation }); + +impl<'a, 'tcx> Lift<'tcx> for FreeRegionMap<'a> { + type Lifted = FreeRegionMap<'tcx>; + fn lift_to_tcx<'b, 'gcx>(&self, tcx: TyCtxt<'b, 'gcx, 'tcx>) -> Option> { + self.relation.maybe_map(|&fr| fr.lift_to_tcx(tcx)) + .map(|relation| FreeRegionMap { relation }) + } +} diff --git a/src/librustc/middle/liveness.rs b/src/librustc/middle/liveness.rs index 508dfe9cfcd..1ea87cc0a45 100644 --- a/src/librustc/middle/liveness.rs +++ b/src/librustc/middle/liveness.rs @@ -1441,7 +1441,7 @@ fn check_ret(&self, // and must outlive the *call-site* of the function. let fn_ret = self.ir.tcx.liberate_late_bound_regions( - Some(self.ir.tcx.region_maps().call_site_extent(id, body.value.id)), + Some(self.ir.tcx.call_site_extent(id, body.value.id)), &fn_ret); if !fn_ret.is_never() && self.live_on_entry(entry_ln, self.s.no_ret_var).is_some() { diff --git a/src/librustc/middle/mem_categorization.rs b/src/librustc/middle/mem_categorization.rs index 92777bb1604..3b1a9552ece 100644 --- a/src/librustc/middle/mem_categorization.rs +++ b/src/librustc/middle/mem_categorization.rs @@ -89,7 +89,7 @@ #[derive(Clone, PartialEq)] pub enum Categorization<'tcx> { // temporary val, argument is its scope - Rvalue(&'tcx ty::Region, &'tcx ty::Region), + Rvalue(ty::Region<'tcx>, ty::Region<'tcx>), StaticItem, Upvar(Upvar), // upvar referenced by closure env Local(ast::NodeId), // local variable @@ -114,13 +114,13 @@ pub enum PointerKind<'tcx> { Unique, /// `&T` - BorrowedPtr(ty::BorrowKind, &'tcx ty::Region), + BorrowedPtr(ty::BorrowKind, ty::Region<'tcx>), /// `*T` UnsafePtr(hir::Mutability), /// Implicit deref of the `&T` that results from an overloaded index `[]`. - Implicit(ty::BorrowKind, &'tcx ty::Region), + Implicit(ty::BorrowKind, ty::Region<'tcx>), } // We use the term "interior" to mean "something reachable from the @@ -796,7 +796,7 @@ fn env_deref(&self, // The environment of a closure is guaranteed to // outlive any bindings introduced in the body of the // closure itself. - scope: Some(self.tcx().region_maps().item_extent(fn_body_id)), + scope: Some(self.tcx().item_extent(fn_body_id)), bound_region: ty::BrEnv })); @@ -842,10 +842,10 @@ fn env_deref(&self, /// Returns the lifetime of a temporary created by expr with id `id`. /// This could be `'static` if `id` is part of a constant expression. - pub fn temporary_scope(&self, id: ast::NodeId) -> (&'tcx ty::Region, &'tcx ty::Region) + pub fn temporary_scope(&self, id: ast::NodeId) -> (ty::Region<'tcx>, ty::Region<'tcx>) { let (scope, old_scope) = - self.tcx().region_maps().old_and_new_temporary_scope(id); + self.tcx().region_maps().old_and_new_temporary_scope(self.tcx(), id); (self.tcx().mk_region(match scope { Some(scope) => ty::ReScope(scope), None => ty::ReStatic @@ -887,8 +887,8 @@ pub fn cat_rvalue_node(&self, pub fn cat_rvalue(&self, cmt_id: ast::NodeId, span: Span, - temp_scope: &'tcx ty::Region, - old_temp_scope: &'tcx ty::Region, + temp_scope: ty::Region<'tcx>, + old_temp_scope: ty::Region<'tcx>, expr_ty: Ty<'tcx>) -> cmt<'tcx> { let ret = Rc::new(cmt_ { id:cmt_id, diff --git a/src/librustc/middle/region.rs b/src/librustc/middle/region.rs index e381a904478..062432e27e5 100644 --- a/src/librustc/middle/region.rs +++ b/src/librustc/middle/region.rs @@ -17,14 +17,12 @@ //! `middle/infer/region_inference/README.md` use hir::map as hir_map; -use session::Session; use util::nodemap::{FxHashMap, NodeMap, NodeSet}; use ty; -use std::collections::hash_map::Entry; -use std::fmt; use std::mem; use std::rc::Rc; +use serialize; use syntax::codemap; use syntax::ast::{self, NodeId}; use syntax_pos::Span; @@ -34,33 +32,12 @@ use hir; use hir::def_id::{CrateNum, LOCAL_CRATE}; use hir::intravisit::{self, Visitor, FnKind, NestedVisitorMap}; -use hir::{Body, Block, Item, FnDecl, Arm, Pat, PatKind, Stmt, Expr, Local}; +use hir::{Block, Item, FnDecl, Arm, Pat, PatKind, Stmt, Expr, Local}; -#[derive(Clone, PartialEq, PartialOrd, Eq, Ord, Hash, RustcEncodable, - RustcDecodable, Copy)] -pub struct CodeExtent(u32); - -impl fmt::Debug for CodeExtent { - fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!(f, "CodeExtent({:?}", self.0)?; - - ty::tls::with_opt(|opt_tcx| { - if let Some(tcx) = opt_tcx { - let region_maps = tcx.region_maps(); - { - let code_extents = ®ion_maps.code_extents; - if let Some(data) = code_extents.get(self.0 as usize) { - write!(f, "/{:?}", data)?; - } - mem::drop(code_extents); // FIXME why is this necessary? - } - } - Ok(()) - })?; +pub type CodeExtent<'tcx> = &'tcx CodeExtentData; - write!(f, ")") - } -} +impl<'tcx> serialize::UseSpecializedEncodable for CodeExtent<'tcx> {} +impl<'tcx> serialize::UseSpecializedDecodable for CodeExtent<'tcx> {} /// CodeExtent represents a statically-describable extent that can be /// used to bound the lifetime/region for values. @@ -123,7 +100,7 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { /// placate the same deriving in `ty::FreeRegion`, but we may want to /// actually attach a more meaningful ordering to scopes than the one /// generated via deriving here. -#[derive(Clone, PartialEq, PartialOrd, Eq, Ord, Hash, Debug, Copy)] +#[derive(Clone, PartialEq, PartialOrd, Eq, Ord, Hash, Debug, Copy, RustcEncodable, RustcDecodable)] pub enum CodeExtentData { Misc(ast::NodeId), @@ -150,8 +127,8 @@ pub struct CallSiteScopeData { } impl CallSiteScopeData { - pub fn to_code_extent(&self, region_maps: &RegionMaps) -> CodeExtent { - region_maps.lookup_code_extent( + pub fn to_code_extent<'a, 'tcx, 'gcx>(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> CodeExtent<'tcx> { + tcx.intern_code_extent( match *self { CallSiteScopeData { fn_id, body_id } => CodeExtentData::CallSiteScope { fn_id: fn_id, body_id: body_id }, @@ -200,20 +177,14 @@ pub fn node_id(&self) -> ast::NodeId { CodeExtentData::ParameterScope { fn_id: _, body_id } => body_id, } } -} - -impl CodeExtent { - pub fn node_id(&self, region_maps: &RegionMaps) -> ast::NodeId { - region_maps.code_extent_data(*self).node_id() - } /// Returns the span of this CodeExtent. Note that in general the /// returned span may not correspond to the span of any node id in /// the AST. - pub fn span(&self, region_maps: &RegionMaps, hir_map: &hir_map::Map) -> Option { - match hir_map.find(self.node_id(region_maps)) { + pub fn span(&self, hir_map: &hir_map::Map) -> Option { + match hir_map.find(self.node_id()) { Some(hir_map::NodeBlock(ref blk)) => { - match region_maps.code_extent_data(*self) { + match *self { CodeExtentData::CallSiteScope { .. } | CodeExtentData::ParameterScope { .. } | CodeExtentData::Misc(_) | @@ -242,20 +213,18 @@ pub fn span(&self, region_maps: &RegionMaps, hir_map: &hir_map::Map) -> Option, - code_extent_interner: FxHashMap, +pub struct RegionMaps<'tcx> { /// `scope_map` maps from a scope id to the enclosing scope id; /// this is usually corresponding to the lexical nesting, though /// in the case of closures the parent scope is the innermost /// conditional expression or repeating block. (Note that the /// enclosing scope id for the block associated with a closure is /// the closure itself.) - scope_map: Vec>, + scope_map: FxHashMap, CodeExtent<'tcx>>, /// `var_map` maps from a variable or binding id to the block in /// which that variable is declared. - var_map: NodeMap, + var_map: NodeMap>, /// `rvalue_scopes` includes entries for those expressions whose cleanup scope is /// larger than the default. The map goes from the expression id @@ -263,14 +232,14 @@ pub struct RegionMaps { /// table, the appropriate cleanup scope is the innermost /// enclosing statement, conditional expression, or repeating /// block (see `terminating_scopes`). - rvalue_scopes: NodeMap, + rvalue_scopes: NodeMap>, /// Records the value of rvalue scopes before they were shrunk by /// #36082, for error reporting. /// /// FIXME: this should be temporary. Remove this by 1.18.0 or /// so. - shrunk_rvalue_scopes: NodeMap, + shrunk_rvalue_scopes: NodeMap>, /// Encodes the hierarchy of fn bodies. Every fn body (including /// closures) forms its own distinct region hierarchy, rooted in @@ -286,7 +255,7 @@ pub struct RegionMaps { } #[derive(Debug, Copy, Clone)] -pub struct Context { +pub struct Context<'tcx> { /// the root of the current region tree. This is typically the id /// of the innermost fn body. Each fn forms its own disjoint tree /// in the region hierarchy. These fn bodies are themselves @@ -296,21 +265,21 @@ pub struct Context { root_id: Option, /// the scope that contains any new variables declared - var_parent: Option, + var_parent: Option>, /// region parent of expressions etc - parent: Option, + parent: Option>, } -struct RegionResolutionVisitor<'hir: 'a, 'a> { - sess: &'a Session, +struct RegionResolutionVisitor<'a, 'tcx: 'a> { + tcx: TyCtxt<'a, 'tcx, 'tcx>, // Generated maps: - region_maps: &'a mut RegionMaps, + region_maps: &'a mut RegionMaps<'tcx>, - cx: Context, + cx: Context<'tcx>, - map: &'a hir_map::Map<'hir>, + map: &'a hir_map::Map<'tcx>, /// `terminating_scopes` is a set containing the ids of each /// statement, or conditional/repeating expression. These scopes @@ -336,64 +305,13 @@ struct RegionResolutionVisitor<'hir: 'a, 'a> { } -impl RegionMaps { - pub fn lookup_code_extent(&self, e: CodeExtentData) -> CodeExtent { - match self.code_extent_interner.get(&e) { - Some(&d) => d, - None => bug!("unknown code extent {:?}", e) - } - } - pub fn node_extent(&self, n: ast::NodeId) -> CodeExtent { - self.lookup_code_extent(CodeExtentData::Misc(n)) - } - // Returns the code extent for an item - the destruction scope. - pub fn item_extent(&self, n: ast::NodeId) -> CodeExtent { - self.lookup_code_extent(CodeExtentData::DestructionScope(n)) - } - pub fn call_site_extent(&self, fn_id: ast::NodeId, body_id: ast::NodeId) -> CodeExtent { - assert!(fn_id != body_id); - self.lookup_code_extent(CodeExtentData::CallSiteScope { fn_id: fn_id, body_id: body_id }) - } - pub fn opt_destruction_extent(&self, n: ast::NodeId) -> Option { - self.code_extent_interner.get(&CodeExtentData::DestructionScope(n)).cloned() - } - pub fn intern_code_extent(&mut self, - e: CodeExtentData, - parent: Option) -> CodeExtent { - match self.code_extent_interner.entry(e) { - Entry::Occupied(_) => { - bug!("intern_code_extent: already exists") - } - Entry::Vacant(v) => { - if self.code_extents.len() > 0xffffffffusize { - bug!() // should pass a sess, - // but this isn't the only place - } - let idx = CodeExtent(self.code_extents.len() as u32); - debug!("CodeExtent({:?}) = {:?} [parent={:?}]", idx, e, parent); - self.code_extents.push(e); - self.scope_map.push(parent); - *v.insert(idx) - } - } - } - pub fn intern_node(&mut self, - n: ast::NodeId, - parent: Option) -> CodeExtent { - self.intern_code_extent(CodeExtentData::Misc(n), parent) - } - pub fn code_extent_data(&self, e: CodeExtent) -> CodeExtentData { - self.code_extents[e.0 as usize] - } - pub fn each_encl_scope(&self, mut e:E) where E: FnMut(&CodeExtent, &CodeExtent) { - for child_id in 1..self.code_extents.len() { - let child = CodeExtent(child_id as u32); - if let Some(parent) = self.opt_encl_scope(child) { - e(&child, &parent) - } +impl<'tcx> RegionMaps<'tcx> { + pub fn each_encl_scope(&self, mut e:E) where E: FnMut(CodeExtent<'tcx>, CodeExtent<'tcx>) { + for (&child, &parent) in &self.scope_map { + e(child, parent) } } - pub fn each_var_scope(&self, mut e:E) where E: FnMut(&ast::NodeId, &CodeExtent) { + pub fn each_var_scope(&self, mut e:E) where E: FnMut(&ast::NodeId, CodeExtent<'tcx>) { for (child, parent) in self.var_map.iter() { e(child, parent) } @@ -419,45 +337,48 @@ fn fn_is_enclosed_by(&self, mut sub_fn: ast::NodeId, sup_fn: ast::NodeId) -> boo } } - fn record_var_scope(&mut self, var: ast::NodeId, lifetime: CodeExtent) { + fn record_var_scope(&mut self, var: ast::NodeId, lifetime: CodeExtent<'tcx>) { debug!("record_var_scope(sub={:?}, sup={:?})", var, lifetime); - assert!(var != lifetime.node_id(self)); + assert!(var != lifetime.node_id()); self.var_map.insert(var, lifetime); } - fn record_rvalue_scope(&mut self, var: ast::NodeId, lifetime: CodeExtent) { + fn record_rvalue_scope(&mut self, var: ast::NodeId, lifetime: CodeExtent<'tcx>) { debug!("record_rvalue_scope(sub={:?}, sup={:?})", var, lifetime); - assert!(var != lifetime.node_id(self)); + assert!(var != lifetime.node_id()); self.rvalue_scopes.insert(var, lifetime); } - fn record_shrunk_rvalue_scope(&mut self, var: ast::NodeId, lifetime: CodeExtent) { + fn record_shrunk_rvalue_scope(&mut self, var: ast::NodeId, lifetime: CodeExtent<'tcx>) { debug!("record_rvalue_scope(sub={:?}, sup={:?})", var, lifetime); - assert!(var != lifetime.node_id(self)); + assert!(var != lifetime.node_id()); self.shrunk_rvalue_scopes.insert(var, lifetime); } - pub fn opt_encl_scope(&self, id: CodeExtent) -> Option { + pub fn opt_encl_scope(&self, id: CodeExtent<'tcx>) -> Option> { //! Returns the narrowest scope that encloses `id`, if any. - self.scope_map[id.0 as usize] + self.scope_map.get(&id).cloned() } #[allow(dead_code)] // used in cfg - pub fn encl_scope(&self, id: CodeExtent) -> CodeExtent { + pub fn encl_scope(&self, id: CodeExtent<'tcx>) -> CodeExtent<'tcx> { //! Returns the narrowest scope that encloses `id`, if any. self.opt_encl_scope(id).unwrap() } /// Returns the lifetime of the local variable `var_id` - pub fn var_scope(&self, var_id: ast::NodeId) -> CodeExtent { + pub fn var_scope(&self, var_id: ast::NodeId) -> CodeExtent<'tcx> { match self.var_map.get(&var_id) { Some(&r) => r, None => { bug!("no enclosing scope for id {:?}", var_id); } } } - pub fn temporary_scope2(&self, expr_id: ast::NodeId) -> (Option, bool) { - let temporary_scope = self.temporary_scope(expr_id); + pub fn temporary_scope2<'a, 'gcx: 'tcx>(&self, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + expr_id: ast::NodeId) + -> (Option>, bool) { + let temporary_scope = self.temporary_scope(tcx, expr_id); let was_shrunk = match self.shrunk_rvalue_scopes.get(&expr_id) { Some(&s) => { info!("temporary_scope2({:?}, scope={:?}, shrunk={:?})", @@ -470,17 +391,23 @@ pub fn temporary_scope2(&self, expr_id: ast::NodeId) -> (Option, boo (temporary_scope, was_shrunk) } - pub fn old_and_new_temporary_scope(&self, expr_id: ast::NodeId) -> - (Option, Option) + pub fn old_and_new_temporary_scope<'a, 'gcx: 'tcx>(&self, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + expr_id: ast::NodeId) + -> (Option>, + Option>) { - let temporary_scope = self.temporary_scope(expr_id); + let temporary_scope = self.temporary_scope(tcx, expr_id); (temporary_scope, self.shrunk_rvalue_scopes .get(&expr_id).cloned() .or(temporary_scope)) } - pub fn temporary_scope(&self, expr_id: ast::NodeId) -> Option { + pub fn temporary_scope<'a, 'gcx: 'tcx>(&self, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + expr_id: ast::NodeId) + -> Option> { //! Returns the scope when temp created by expr_id will be cleaned up // check for a designated rvalue scope @@ -489,17 +416,14 @@ pub fn temporary_scope(&self, expr_id: ast::NodeId) -> Option { return Some(s); } - let scope_map : &[Option] = &self.scope_map; - let code_extents: &[CodeExtentData] = &self.code_extents; - // else, locate the innermost terminating scope // if there's one. Static items, for instance, won't // have an enclosing scope, hence no scope will be // returned. - let mut id = self.node_extent(expr_id); + let mut id = tcx.node_extent(expr_id); - while let Some(p) = scope_map[id.0 as usize] { - match code_extents[p.0 as usize] { + while let Some(&p) = self.scope_map.get(id) { + match *p { CodeExtentData::DestructionScope(..) => { debug!("temporary_scope({:?}) = {:?} [enclosing]", expr_id, id); @@ -513,7 +437,7 @@ pub fn temporary_scope(&self, expr_id: ast::NodeId) -> Option { return None; } - pub fn var_region(&self, id: ast::NodeId) -> ty::Region { + pub fn var_region(&self, id: ast::NodeId) -> ty::RegionKind<'tcx> { //! Returns the lifetime of the variable `id`. let scope = ty::ReScope(self.var_scope(id)); @@ -555,9 +479,9 @@ pub fn is_subscope_of(&self, /// Finds the nearest common ancestor (if any) of two scopes. That is, finds the smallest /// scope which is greater than or equal to both `scope_a` and `scope_b`. pub fn nearest_common_ancestor(&self, - scope_a: CodeExtent, - scope_b: CodeExtent) - -> CodeExtent { + scope_a: CodeExtent<'tcx>, + scope_b: CodeExtent<'tcx>) + -> CodeExtent<'tcx> { if scope_a == scope_b { return scope_a; } /// [1] The initial values for `a_buf` and `b_buf` are not used. @@ -565,10 +489,10 @@ pub fn nearest_common_ancestor(&self, /// is re-initialized with new values (or else fallback to a /// heap-allocated vector). let mut a_buf: [CodeExtent; 32] = [scope_a /* [1] */; 32]; - let mut a_vec: Vec = vec![]; + let mut a_vec: Vec> = vec![]; let mut b_buf: [CodeExtent; 32] = [scope_b /* [1] */; 32]; - let mut b_vec: Vec = vec![]; - let scope_map : &[Option] = &self.scope_map; + let mut b_vec: Vec> = vec![]; + let scope_map = &self.scope_map; let a_ancestors = ancestors_of(scope_map, scope_a, &mut a_buf, &mut a_vec); let b_ancestors = ancestors_of(scope_map, scope_b, &mut b_buf, &mut b_vec); let mut a_index = a_ancestors.len() - 1; @@ -588,11 +512,11 @@ pub fn nearest_common_ancestor(&self, // nesting. The reasoning behind this is subtle. See the // "Modeling closures" section of the README in // infer::region_inference for more details. - let a_root_scope = self.code_extent_data(a_ancestors[a_index]); - let b_root_scope = self.code_extent_data(a_ancestors[a_index]); + let a_root_scope = a_ancestors[a_index]; + let b_root_scope = a_ancestors[a_index]; return match (a_root_scope, b_root_scope) { - (CodeExtentData::DestructionScope(a_root_id), - CodeExtentData::DestructionScope(b_root_id)) => { + (&CodeExtentData::DestructionScope(a_root_id), + &CodeExtentData::DestructionScope(b_root_id)) => { if self.fn_is_enclosed_by(a_root_id, b_root_id) { // `a` is enclosed by `b`, hence `b` is the ancestor of everything in `a` scope_b @@ -623,18 +547,18 @@ pub fn nearest_common_ancestor(&self, } } - fn ancestors_of<'a>(scope_map: &[Option], - scope: CodeExtent, - buf: &'a mut [CodeExtent; 32], - vec: &'a mut Vec) - -> &'a [CodeExtent] { + fn ancestors_of<'a, 'tcx>(scope_map: &FxHashMap, CodeExtent<'tcx>>, + scope: CodeExtent<'tcx>, + buf: &'a mut [CodeExtent<'tcx>; 32], + vec: &'a mut Vec>) + -> &'a [CodeExtent<'tcx>] { // debug!("ancestors_of(scope={:?})", scope); let mut scope = scope; let mut i = 0; while i < 32 { buf[i] = scope; - match scope_map[scope.0 as usize] { + match scope_map.get(&scope) { Some(superscope) => scope = superscope, _ => return &buf[..i+1] } @@ -645,7 +569,7 @@ fn ancestors_of<'a>(scope_map: &[Option], vec.extend_from_slice(buf); loop { vec.push(scope); - match scope_map[scope.0 as usize] { + match scope_map.get(&scope) { Some(superscope) => scope = superscope, _ => return &*vec } @@ -669,7 +593,7 @@ fn record_var_lifetime(visitor: &mut RegionResolutionVisitor, } } -fn resolve_block<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, blk: &'tcx hir::Block) { +fn resolve_block<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, blk: &'tcx hir::Block) { debug!("resolve_block(blk.id={:?})", blk.id); let prev_cx = visitor.cx; @@ -740,7 +664,7 @@ fn resolve_block<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, blk: visitor.cx = prev_cx; } -fn resolve_arm<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, arm: &'tcx hir::Arm) { +fn resolve_arm<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, arm: &'tcx hir::Arm) { visitor.terminating_scopes.insert(arm.body.id); if let Some(ref expr) = arm.guard { @@ -750,7 +674,7 @@ fn resolve_arm<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, arm: & intravisit::walk_arm(visitor, arm); } -fn resolve_pat<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, pat: &'tcx hir::Pat) { +fn resolve_pat<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, pat: &'tcx hir::Pat) { visitor.new_node_extent(pat.id); // If this is a binding then record the lifetime of that binding. @@ -761,7 +685,7 @@ fn resolve_pat<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, pat: & intravisit::walk_pat(visitor, pat); } -fn resolve_stmt<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, stmt: &'tcx hir::Stmt) { +fn resolve_stmt<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, stmt: &'tcx hir::Stmt) { let stmt_id = stmt.node.id(); debug!("resolve_stmt(stmt.id={:?})", stmt_id); @@ -779,7 +703,7 @@ fn resolve_stmt<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, stmt: visitor.cx.parent = prev_parent; } -fn resolve_expr<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, expr: &'tcx hir::Expr) { +fn resolve_expr<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, expr: &'tcx hir::Expr) { debug!("resolve_expr(expr.id={:?})", expr.id); let expr_extent = visitor.new_node_extent_with_dtor(expr.id); @@ -857,7 +781,7 @@ fn resolve_expr<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, expr: visitor.cx = prev_cx; } -fn resolve_local<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, +fn resolve_local<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, local: &'tcx hir::Local) { debug!("resolve_local(local.id={:?},local.init={:?})", local.id,local.init.is_some()); @@ -998,9 +922,11 @@ fn is_borrowed_ty(ty: &hir::Ty) -> bool { /// | box E& /// | E& as ... /// | ( E& ) - fn record_rvalue_scope_if_borrow_expr(visitor: &mut RegionResolutionVisitor, - expr: &hir::Expr, - blk_id: CodeExtent) { + fn record_rvalue_scope_if_borrow_expr<'a, 'tcx>( + visitor: &mut RegionResolutionVisitor<'a, 'tcx>, + expr: &hir::Expr, + blk_id: CodeExtent<'tcx>) + { match expr.node { hir::ExprAddrOf(_, ref subexpr) => { record_rvalue_scope_if_borrow_expr(visitor, &subexpr, blk_id); @@ -1047,10 +973,10 @@ fn record_rvalue_scope_if_borrow_expr(visitor: &mut RegionResolutionVisitor, /// | /// /// Note: ET is intended to match "rvalues or lvalues based on rvalues". - fn record_rvalue_scope<'a>(visitor: &mut RegionResolutionVisitor, - expr: &'a hir::Expr, - blk_scope: CodeExtent, - is_shrunk: bool) { + fn record_rvalue_scope<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, + expr: &hir::Expr, + blk_scope: CodeExtent<'tcx>, + is_shrunk: bool) { let mut expr = expr; loop { // Note: give all the expressions matching `ET` with the @@ -1081,10 +1007,8 @@ fn record_rvalue_scope<'a>(visitor: &mut RegionResolutionVisitor, } } -fn resolve_item_like<'a, 'tcx, F>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, - id: ast::NodeId, - walk: F) - where F: FnOnce(&mut RegionResolutionVisitor<'tcx, 'a>) +fn resolve_item_like<'a, 'tcx, F>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, walk: F) + where F: FnOnce(&mut RegionResolutionVisitor<'a, 'tcx>) { // Items create a new outer block scope as far as we're concerned. let prev_cx = visitor.cx; @@ -1095,12 +1019,11 @@ fn resolve_item_like<'a, 'tcx, F>(visitor: &mut RegionResolutionVisitor<'tcx, 'a parent: None, }; walk(visitor); - visitor.create_item_scope_if_needed(id); visitor.cx = prev_cx; visitor.terminating_scopes = prev_ts; } -fn resolve_fn<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, +fn resolve_fn<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, kind: FnKind<'tcx>, decl: &'tcx hir::FnDecl, body_id: hir::BodyId, @@ -1111,7 +1034,7 @@ fn resolve_fn<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, body.id={:?}, \ cx.parent={:?})", id, - visitor.sess.codemap().span_to_string(sp), + visitor.tcx.sess.codemap().span_to_string(sp), body_id, visitor.cx.parent); @@ -1152,17 +1075,37 @@ fn resolve_fn<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'tcx, 'a>, visitor.terminating_scopes = outer_ts; } -impl<'hir, 'a> RegionResolutionVisitor<'hir, 'a> { +impl<'a, 'tcx> RegionResolutionVisitor<'a, 'tcx> { + pub fn intern_code_extent(&mut self, + data: CodeExtentData, + parent: Option>) + -> CodeExtent<'tcx> { + let code_extent = self.tcx.intern_code_extent(data); + debug!("{:?}.parent = {:?}", code_extent, parent); + if let Some(p) = parent { + let prev = self.region_maps.scope_map.insert(code_extent, p); + assert!(prev.is_none()); + } + code_extent + } + + pub fn intern_node(&mut self, + n: ast::NodeId, + parent: Option>) -> CodeExtent<'tcx> { + self.intern_code_extent(CodeExtentData::Misc(n), parent) + } + /// Records the current parent (if any) as the parent of `child_scope`. - fn new_code_extent(&mut self, child_scope: CodeExtentData) -> CodeExtent { - self.region_maps.intern_code_extent(child_scope, self.cx.parent) + fn new_code_extent(&mut self, child_scope: CodeExtentData) -> CodeExtent<'tcx> { + let parent = self.cx.parent; + self.intern_code_extent(child_scope, parent) } - fn new_node_extent(&mut self, child_scope: ast::NodeId) -> CodeExtent { + fn new_node_extent(&mut self, child_scope: ast::NodeId) -> CodeExtent<'tcx> { self.new_code_extent(CodeExtentData::Misc(child_scope)) } - fn new_node_extent_with_dtor(&mut self, id: ast::NodeId) -> CodeExtent { + fn new_node_extent_with_dtor(&mut self, id: ast::NodeId) -> CodeExtent<'tcx> { // If node was previously marked as a terminating scope during the // recursive visit of its parent node in the AST, then we need to // account for the destruction scope representing the extent of @@ -1170,101 +1113,79 @@ fn new_node_extent_with_dtor(&mut self, id: ast::NodeId) -> CodeExtent { if self.terminating_scopes.contains(&id) { let ds = self.new_code_extent( CodeExtentData::DestructionScope(id)); - self.region_maps.intern_node(id, Some(ds)) + self.intern_node(id, Some(ds)) } else { self.new_node_extent(id) } } - - fn create_item_scope_if_needed(&mut self, id: ast::NodeId) { - // create a region for the destruction scope - this is needed - // for constructing parameter environments based on the item. - // functions put their destruction scopes *inside* their parameter - // scopes. - let scope = CodeExtentData::DestructionScope(id); - if !self.region_maps.code_extent_interner.contains_key(&scope) { - self.region_maps.intern_code_extent(scope, None); - } - } } -impl<'hir, 'a> Visitor<'hir> for RegionResolutionVisitor<'hir, 'a> { - fn nested_visit_map<'this>(&'this mut self) -> NestedVisitorMap<'this, 'hir> { +impl<'a, 'tcx> Visitor<'tcx> for RegionResolutionVisitor<'a, 'tcx> { + fn nested_visit_map<'this>(&'this mut self) -> NestedVisitorMap<'this, 'tcx> { NestedVisitorMap::OnlyBodies(&self.map) } - fn visit_body(&mut self, b: &'hir Body) { - // make sure that every body owner has an item scope, since - // MIR construction wants that - let owner = self.map.body_owner(b.id()); - self.create_item_scope_if_needed(owner); - - intravisit::walk_body(self, b); - } - - fn visit_block(&mut self, b: &'hir Block) { + fn visit_block(&mut self, b: &'tcx Block) { resolve_block(self, b); } - fn visit_item(&mut self, i: &'hir Item) { - resolve_item_like(self, i.id, |this| intravisit::walk_item(this, i)); + fn visit_item(&mut self, i: &'tcx Item) { + resolve_item_like(self, |this| intravisit::walk_item(this, i)); } - fn visit_impl_item(&mut self, ii: &'hir hir::ImplItem) { - resolve_item_like(self, ii.id, |this| intravisit::walk_impl_item(this, ii)); + fn visit_impl_item(&mut self, ii: &'tcx hir::ImplItem) { + resolve_item_like(self, |this| intravisit::walk_impl_item(this, ii)); } - fn visit_trait_item(&mut self, ti: &'hir hir::TraitItem) { - resolve_item_like(self, ti.id, |this| intravisit::walk_trait_item(this, ti)); + fn visit_trait_item(&mut self, ti: &'tcx hir::TraitItem) { + resolve_item_like(self, |this| intravisit::walk_trait_item(this, ti)); } - fn visit_fn(&mut self, fk: FnKind<'hir>, fd: &'hir FnDecl, + fn visit_fn(&mut self, fk: FnKind<'tcx>, fd: &'tcx FnDecl, b: hir::BodyId, s: Span, n: NodeId) { resolve_fn(self, fk, fd, b, s, n); } - fn visit_arm(&mut self, a: &'hir Arm) { + fn visit_arm(&mut self, a: &'tcx Arm) { resolve_arm(self, a); } - fn visit_pat(&mut self, p: &'hir Pat) { + fn visit_pat(&mut self, p: &'tcx Pat) { resolve_pat(self, p); } - fn visit_stmt(&mut self, s: &'hir Stmt) { + fn visit_stmt(&mut self, s: &'tcx Stmt) { resolve_stmt(self, s); } - fn visit_expr(&mut self, ex: &'hir Expr) { + fn visit_expr(&mut self, ex: &'tcx Expr) { resolve_expr(self, ex); } - fn visit_local(&mut self, l: &'hir Local) { + fn visit_local(&mut self, l: &'tcx Local) { resolve_local(self, l); } } -pub fn resolve_crate<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Rc { +pub fn resolve_crate<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Rc> { tcx.region_resolve_crate(LOCAL_CRATE) } fn region_resolve_crate<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, crate_num: CrateNum) - -> Rc + -> Rc> { debug_assert!(crate_num == LOCAL_CRATE); - let sess = &tcx.sess; let hir_map = &tcx.hir; let krate = hir_map.krate(); let mut maps = RegionMaps { - code_extents: vec![], - code_extent_interner: FxHashMap(), - scope_map: vec![], + scope_map: FxHashMap(), var_map: NodeMap(), rvalue_scopes: NodeMap(), shrunk_rvalue_scopes: NodeMap(), fn_tree: NodeMap(), }; + { let mut visitor = RegionResolutionVisitor { - sess: sess, + tcx: tcx, region_maps: &mut maps, map: hir_map, cx: Context { diff --git a/src/librustc/mir/mod.rs b/src/librustc/mir/mod.rs index 724d4f457de..8f8af8b1036 100644 --- a/src/librustc/mir/mod.rs +++ b/src/librustc/mir/mod.rs @@ -1034,7 +1034,7 @@ pub enum Rvalue<'tcx> { Repeat(Operand<'tcx>, ConstUsize), /// &x or &mut x - Ref(&'tcx Region, BorrowKind, Lvalue<'tcx>), + Ref(Region<'tcx>, BorrowKind, Lvalue<'tcx>), /// length of a [X] or [X;n] value Len(Lvalue<'tcx>), diff --git a/src/librustc/mir/visit.rs b/src/librustc/mir/visit.rs index 83963de8b00..31bdd99ef32 100644 --- a/src/librustc/mir/visit.rs +++ b/src/librustc/mir/visit.rs @@ -747,7 +747,7 @@ pub enum LvalueContext<'tcx> { Inspect, // Being borrowed - Borrow { region: &'tcx Region, kind: BorrowKind }, + Borrow { region: Region<'tcx>, kind: BorrowKind }, // Used as base for another lvalue, e.g. `x` in `x.y`. // diff --git a/src/librustc/traits/fulfill.rs b/src/librustc/traits/fulfill.rs index 908bb337fa1..e8baaa7ffb2 100644 --- a/src/librustc/traits/fulfill.rs +++ b/src/librustc/traits/fulfill.rs @@ -84,7 +84,7 @@ pub struct FulfillmentContext<'tcx> { #[derive(Clone)] pub struct RegionObligation<'tcx> { - pub sub_region: &'tcx ty::Region, + pub sub_region: ty::Region<'tcx>, pub sup_type: Ty<'tcx>, pub cause: ObligationCause<'tcx>, } @@ -155,7 +155,7 @@ pub fn register_bound(&mut self, pub fn register_region_obligation(&mut self, t_a: Ty<'tcx>, - r_b: &'tcx ty::Region, + r_b: ty::Region<'tcx>, cause: ObligationCause<'tcx>) { register_region_obligation(t_a, r_b, cause, &mut self.region_obligations); @@ -566,7 +566,7 @@ fn coinductive_obligation<'a,'gcx,'tcx>(selcx: &SelectionContext<'a,'gcx,'tcx>, } fn register_region_obligation<'tcx>(t_a: Ty<'tcx>, - r_b: &'tcx ty::Region, + r_b: ty::Region<'tcx>, cause: ObligationCause<'tcx>, region_obligations: &mut NodeMap>>) { diff --git a/src/librustc/traits/mod.rs b/src/librustc/traits/mod.rs index a7f9cc74c4f..5ac79a8e72a 100644 --- a/src/librustc/traits/mod.rs +++ b/src/librustc/traits/mod.rs @@ -112,7 +112,7 @@ pub enum ObligationCauseCode<'tcx> { ReferenceOutlivesReferent(Ty<'tcx>), /// A type like `Box + 'b>` is WF only if `'b: 'a`. - ObjectTypeBound(Ty<'tcx>, &'tcx ty::Region), + ObjectTypeBound(Ty<'tcx>, ty::Region<'tcx>), /// Obligation incurred due to an object cast. ObjectCastObligation(/* Object type */ Ty<'tcx>), diff --git a/src/librustc/ty/_match.rs b/src/librustc/ty/_match.rs index b1846e03941..f86c1cf0dd6 100644 --- a/src/librustc/ty/_match.rs +++ b/src/librustc/ty/_match.rs @@ -52,8 +52,8 @@ fn relate_with_variance>(&mut self, self.relate(a, b) } - fn regions(&mut self, a: &'tcx ty::Region, b: &'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region> { + fn regions(&mut self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>> { debug!("{}.regions({:?}, {:?})", self.tag(), a, diff --git a/src/librustc/ty/adjustment.rs b/src/librustc/ty/adjustment.rs index 1d7100a7a4e..385591e10f7 100644 --- a/src/librustc/ty/adjustment.rs +++ b/src/librustc/ty/adjustment.rs @@ -133,7 +133,7 @@ pub fn is_identity(&self) -> bool { #[derive(Copy, Clone, PartialEq, Debug, RustcEncodable, RustcDecodable)] pub enum AutoBorrow<'tcx> { /// Convert from T to &T. - Ref(&'tcx ty::Region, hir::Mutability), + Ref(ty::Region<'tcx>, hir::Mutability), /// Convert from T to *T. RawPtr(hir::Mutability), diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index c6e9822da89..3c6f833c4ef 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -21,7 +21,7 @@ use hir::map::DisambiguatedDefPathData; use middle::free_region::FreeRegionMap; use middle::lang_items; -use middle::region::RegionMaps; +use middle::region::{CodeExtent, CodeExtentData, RegionMaps}; use middle::resolve_lifetime; use middle::stability; use mir::Mir; @@ -33,6 +33,7 @@ use ty::{AdtKind, AdtDef, ClosureSubsts, Region}; use hir::FreevarMap; use ty::{PolyFnSig, InferTy, ParamTy, ProjectionTy, ExistentialPredicate}; +use ty::RegionKind; use ty::{TyVar, TyVid, IntVar, IntVid, FloatVar, FloatVid}; use ty::TypeVariants::*; use ty::layout::{Layout, TargetDataLayout}; @@ -94,7 +95,7 @@ pub struct CtxtInterners<'tcx> { type_: RefCell>>>, type_list: RefCell>>>>, substs: RefCell>>>, - region: RefCell>>, + region: RefCell>>>, existential_predicates: RefCell>>>>, } @@ -192,9 +193,9 @@ pub struct CommonTypes<'tcx> { pub never: Ty<'tcx>, pub err: Ty<'tcx>, - pub re_empty: &'tcx Region, - pub re_static: &'tcx Region, - pub re_erased: &'tcx Region, + pub re_empty: Region<'tcx>, + pub re_static: Region<'tcx>, + pub re_erased: Region<'tcx>, } #[derive(RustcEncodable, RustcDecodable)] @@ -257,7 +258,7 @@ pub struct TypeckTables<'tcx> { /// Stores the free-region relationships that were deduced from /// its where clauses and parameter types. These are then /// read-again by borrowck. - pub free_region_map: FreeRegionMap, + pub free_region_map: FreeRegionMap<'tcx>, } impl<'tcx> TypeckTables<'tcx> { @@ -393,9 +394,9 @@ fn new(interners: &CtxtInterners<'tcx>) -> CommonTypes<'tcx> { f32: mk(TyFloat(ast::FloatTy::F32)), f64: mk(TyFloat(ast::FloatTy::F64)), - re_empty: mk_region(Region::ReEmpty), - re_static: mk_region(Region::ReStatic), - re_erased: mk_region(Region::ReErased), + re_empty: mk_region(RegionKind::ReEmpty), + re_static: mk_region(RegionKind::ReStatic), + re_erased: mk_region(RegionKind::ReErased), } } } @@ -549,6 +550,8 @@ pub struct GlobalCtxt<'tcx> { layout_interner: RefCell>, + code_extent_interner: RefCell>>, + /// A vector of every trait accessible in the whole crate /// (i.e. including those from subcrates). This is used only for /// error reporting, and so is lazily initialised and generally @@ -649,6 +652,38 @@ pub fn intern_stability(self, stab: attr::Stability) -> &'gcx attr::Stability { interned } + pub fn node_extent(self, n: ast::NodeId) -> CodeExtent<'gcx> { + self.intern_code_extent(CodeExtentData::Misc(n)) + } + + // TODO this is revealing side-effects of query, bad + pub fn opt_destruction_extent(self, n: ast::NodeId) -> Option> { + let s = CodeExtentData::DestructionScope(n); + self.code_extent_interner.borrow().get(&s).cloned() + } + + // Returns the code extent for an item - the destruction scope. + pub fn item_extent(self, n: ast::NodeId) -> CodeExtent<'gcx> { + self.intern_code_extent(CodeExtentData::DestructionScope(n)) + } + + pub fn call_site_extent(self, fn_id: ast::NodeId, body_id: ast::NodeId) -> CodeExtent<'gcx> { + assert!(fn_id != body_id); + self.intern_code_extent(CodeExtentData::CallSiteScope { fn_id: fn_id, body_id: body_id }) + } + + pub fn intern_code_extent(self, data: CodeExtentData) -> CodeExtent<'gcx> { + if let Some(st) = self.code_extent_interner.borrow().get(&data) { + return st; + } + + let interned = self.global_interners.arena.alloc(data); + if let Some(prev) = self.code_extent_interner.borrow_mut().replace(interned) { + bug!("Tried to overwrite interned code-extent: {:?}", prev) + } + interned + } + pub fn intern_layout(self, layout: Layout) -> &'gcx Layout { if let Some(layout) = self.layout_interner.borrow().get(&layout) { return layout; @@ -677,7 +712,7 @@ fn is_global(self) -> bool { local as usize == global as usize } - pub fn region_maps(self) -> Rc { + pub fn region_maps(self) -> Rc> { self.region_resolve_crate(LOCAL_CRATE) } @@ -741,6 +776,7 @@ pub fn create_and_enter(s: &'tcx Session, data_layout: data_layout, layout_cache: RefCell::new(FxHashMap()), layout_interner: RefCell::new(FxHashSet()), + code_extent_interner: RefCell::new(FxHashSet()), layout_depth: Cell::new(0), derive_macros: RefCell::new(NodeMap()), stability_interner: RefCell::new(FxHashSet()), @@ -820,9 +856,18 @@ fn lift_to_tcx<'b, 'gcx>(&self, tcx: TyCtxt<'b, 'gcx, 'tcx>) -> Option<&'tcx Sub } } -impl<'a, 'tcx> Lift<'tcx> for &'a Region { - type Lifted = &'tcx Region; - fn lift_to_tcx<'b, 'gcx>(&self, tcx: TyCtxt<'b, 'gcx, 'tcx>) -> Option<&'tcx Region> { +impl<'a, 'tcx> Lift<'tcx> for ty::FreeRegion<'a> { + type Lifted = ty::FreeRegion<'tcx>; + fn lift_to_tcx<'b, 'gcx>(&self, tcx: TyCtxt<'b, 'gcx, 'tcx>) -> Option { + let scope = self.scope.map(|code_extent| tcx.intern_code_extent(*code_extent)); + let bound_region = self.bound_region; + Some(ty::FreeRegion { scope, bound_region }) + } +} + +impl<'a, 'tcx> Lift<'tcx> for Region<'a> { + type Lifted = Region<'tcx>; + fn lift_to_tcx<'b, 'gcx>(&self, tcx: TyCtxt<'b, 'gcx, 'tcx>) -> Option> { if tcx.interners.arena.in_arena(*self as *const _) { return Some(unsafe { mem::transmute(*self) }); } @@ -1083,9 +1128,9 @@ fn borrow<'a>(&'a self) -> &'a [Kind<'lcx>] { } } -impl<'tcx> Borrow for Interned<'tcx, Region> { - fn borrow<'a>(&'a self) -> &'a Region { - self.0 +impl<'tcx> Borrow> for Interned<'tcx, RegionKind<'tcx>> { + fn borrow<'a>(&'a self) -> &'a RegionKind<'tcx> { + &self.0 } } @@ -1176,7 +1221,7 @@ fn keep_local<'tcx, T: ty::TypeFoldable<'tcx>>(x: &T) -> bool { &ty::ReVar(_) | &ty::ReSkolemized(..) => true, _ => false } - }) -> Region + }) -> RegionKind<'tcx> ); macro_rules! slice_interners { @@ -1268,15 +1313,15 @@ pub fn mk_ptr(self, tm: TypeAndMut<'tcx>) -> Ty<'tcx> { self.mk_ty(TyRawPtr(tm)) } - pub fn mk_ref(self, r: &'tcx Region, tm: TypeAndMut<'tcx>) -> Ty<'tcx> { + pub fn mk_ref(self, r: Region<'tcx>, tm: TypeAndMut<'tcx>) -> Ty<'tcx> { self.mk_ty(TyRef(r, tm)) } - pub fn mk_mut_ref(self, r: &'tcx Region, ty: Ty<'tcx>) -> Ty<'tcx> { + pub fn mk_mut_ref(self, r: Region<'tcx>, ty: Ty<'tcx>) -> Ty<'tcx> { self.mk_ref(r, TypeAndMut {ty: ty, mutbl: hir::MutMutable}) } - pub fn mk_imm_ref(self, r: &'tcx Region, ty: Ty<'tcx>) -> Ty<'tcx> { + pub fn mk_imm_ref(self, r: Region<'tcx>, ty: Ty<'tcx>) -> Ty<'tcx> { self.mk_ref(r, TypeAndMut {ty: ty, mutbl: hir::MutImmutable}) } @@ -1338,7 +1383,7 @@ pub fn mk_fn_ptr(self, fty: PolyFnSig<'tcx>) -> Ty<'tcx> { pub fn mk_dynamic( self, obj: ty::Binder<&'tcx Slice>>, - reg: &'tcx ty::Region + reg: ty::Region<'tcx> ) -> Ty<'tcx> { self.mk_ty(TyDynamic(obj, reg)) } diff --git a/src/librustc/ty/error.rs b/src/librustc/ty/error.rs index 73d9c8b00ae..cec52b10736 100644 --- a/src/librustc/ty/error.rs +++ b/src/librustc/ty/error.rs @@ -36,11 +36,11 @@ pub enum TypeError<'tcx> { TupleSize(ExpectedFound), FixedArraySize(ExpectedFound), ArgCount, - RegionsDoesNotOutlive(&'tcx Region, &'tcx Region), - RegionsNotSame(&'tcx Region, &'tcx Region), - RegionsNoOverlap(&'tcx Region, &'tcx Region), - RegionsInsufficientlyPolymorphic(BoundRegion, &'tcx Region, Option>), - RegionsOverlyPolymorphic(BoundRegion, &'tcx Region, Option>), + RegionsDoesNotOutlive(Region<'tcx>, Region<'tcx>), + RegionsNotSame(Region<'tcx>, Region<'tcx>), + RegionsNoOverlap(Region<'tcx>, Region<'tcx>), + RegionsInsufficientlyPolymorphic(BoundRegion, Region<'tcx>, Option>), + RegionsOverlyPolymorphic(BoundRegion, Region<'tcx>, Option>), Sorts(ExpectedFound>), IntMismatch(ExpectedFound), FloatMismatch(ExpectedFound), diff --git a/src/librustc/ty/flags.rs b/src/librustc/ty/flags.rs index 384f99ceb4e..686b99ba680 100644 --- a/src/librustc/ty/flags.rs +++ b/src/librustc/ty/flags.rs @@ -186,7 +186,7 @@ fn add_fn_sig(&mut self, fn_sig: ty::PolyFnSig) { self.add_bound_computation(&computation); } - fn add_region(&mut self, r: &ty::Region) { + fn add_region(&mut self, r: ty::Region) { self.add_flags(r.type_flags()); if let ty::ReLateBound(debruijn, _) = *r { self.add_depth(debruijn.depth); diff --git a/src/librustc/ty/fold.rs b/src/librustc/ty/fold.rs index 1cf6c3f334f..21ccf6f987b 100644 --- a/src/librustc/ty/fold.rs +++ b/src/librustc/ty/fold.rs @@ -159,7 +159,7 @@ fn fold_fn_sig(&mut self, sig.super_fold_with(self) } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { r.super_fold_with(self) } @@ -182,7 +182,7 @@ fn visit_trait_ref(&mut self, trait_ref: ty::TraitRef<'tcx>) -> bool { trait_ref.super_visit_with(self) } - fn visit_region(&mut self, r: &'tcx ty::Region) -> bool { + fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool { r.super_visit_with(self) } } @@ -216,7 +216,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { /// whether any late-bound regions were skipped pub fn collect_regions(self, value: &T, - region_set: &mut FxHashSet<&'tcx ty::Region>) + region_set: &mut FxHashSet>) -> bool where T : TypeFoldable<'tcx> { @@ -236,7 +236,7 @@ pub fn fold_regions(self, skipped_regions: &mut bool, mut f: F) -> T - where F : FnMut(&'tcx ty::Region, u32) -> &'tcx ty::Region, + where F : FnMut(ty::Region<'tcx>, u32) -> ty::Region<'tcx>, T : TypeFoldable<'tcx>, { value.fold_with(&mut RegionFolder::new(self, skipped_regions, &mut f)) @@ -256,14 +256,14 @@ pub struct RegionFolder<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { tcx: TyCtxt<'a, 'gcx, 'tcx>, skipped_regions: &'a mut bool, current_depth: u32, - fld_r: &'a mut (FnMut(&'tcx ty::Region, u32) -> &'tcx ty::Region + 'a), + fld_r: &'a mut (FnMut(ty::Region<'tcx>, u32) -> ty::Region<'tcx> + 'a), } impl<'a, 'gcx, 'tcx> RegionFolder<'a, 'gcx, 'tcx> { pub fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>, skipped_regions: &'a mut bool, fld_r: &'a mut F) -> RegionFolder<'a, 'gcx, 'tcx> - where F : FnMut(&'tcx ty::Region, u32) -> &'tcx ty::Region + where F : FnMut(ty::Region<'tcx>, u32) -> ty::Region<'tcx> { RegionFolder { tcx: tcx, @@ -284,7 +284,7 @@ fn fold_binder>(&mut self, t: &ty::Binder) -> ty::Binde t } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { ty::ReLateBound(debruijn, _) if debruijn.depth < self.current_depth => { debug!("RegionFolder.fold_region({:?}) skipped bound region (current depth={})", @@ -309,16 +309,16 @@ fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { struct RegionReplacer<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { tcx: TyCtxt<'a, 'gcx, 'tcx>, current_depth: u32, - fld_r: &'a mut (FnMut(ty::BoundRegion) -> &'tcx ty::Region + 'a), - map: FxHashMap + fld_r: &'a mut (FnMut(ty::BoundRegion) -> ty::Region<'tcx> + 'a), + map: FxHashMap> } impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { pub fn replace_late_bound_regions(self, value: &Binder, mut f: F) - -> (T, FxHashMap) - where F : FnMut(ty::BoundRegion) -> &'tcx ty::Region, + -> (T, FxHashMap>) + where F : FnMut(ty::BoundRegion) -> ty::Region<'tcx>, T : TypeFoldable<'tcx>, { let mut replacer = RegionReplacer::new(self, &mut f); @@ -330,7 +330,7 @@ pub fn replace_late_bound_regions(self, /// Replace any late-bound regions bound in `value` with free variants attached to scope-id /// `scope_id`. pub fn liberate_late_bound_regions(self, - all_outlive_scope: Option, + all_outlive_scope: Option>, value: &Binder) -> T where T : TypeFoldable<'tcx> @@ -435,7 +435,7 @@ pub fn anonymize_late_bound_regions(self, sig: &Binder) -> Binder impl<'a, 'gcx, 'tcx> RegionReplacer<'a, 'gcx, 'tcx> { fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>, fld_r: &'a mut F) -> RegionReplacer<'a, 'gcx, 'tcx> - where F : FnMut(ty::BoundRegion) -> &'tcx ty::Region + where F : FnMut(ty::BoundRegion) -> ty::Region<'tcx> { RegionReplacer { tcx: tcx, @@ -464,7 +464,7 @@ fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> { t.super_fold_with(self) } - fn fold_region(&mut self, r:&'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match *r { ty::ReLateBound(debruijn, br) if debruijn.depth == self.current_depth => { let fld_r = &mut self.fld_r; @@ -527,7 +527,7 @@ fn fold_binder(&mut self, t: &ty::Binder) -> ty::Binder u.super_fold_with(self) } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { // because late-bound regions affect subtyping, we can't // erase the bound/free distinction, but we can replace // all free regions with 'erased. @@ -554,7 +554,7 @@ fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { // regions. See comment on `shift_regions_through_binders` method in // `subst.rs` for more details. -pub fn shift_region(region: ty::Region, amount: u32) -> ty::Region { +pub fn shift_region<'tcx>(region: ty::RegionKind<'tcx>, amount: u32) -> ty::RegionKind<'tcx> { match region { ty::ReLateBound(debruijn, br) => { ty::ReLateBound(debruijn.shifted(amount), br) @@ -567,9 +567,9 @@ pub fn shift_region(region: ty::Region, amount: u32) -> ty::Region { pub fn shift_region_ref<'a, 'gcx, 'tcx>( tcx: TyCtxt<'a, 'gcx, 'tcx>, - region: &'tcx ty::Region, + region: ty::Region<'tcx>, amount: u32) - -> &'tcx ty::Region + -> ty::Region<'tcx> { match region { &ty::ReLateBound(debruijn, br) if amount > 0 => { @@ -582,7 +582,8 @@ pub fn shift_region_ref<'a, 'gcx, 'tcx>( } pub fn shift_regions<'a, 'gcx, 'tcx, T>(tcx: TyCtxt<'a, 'gcx, 'tcx>, - amount: u32, value: &T) -> T + amount: u32, + value: &T) -> T where T: TypeFoldable<'tcx> { debug!("shift_regions(value={:?}, amount={})", @@ -631,7 +632,7 @@ fn visit_ty(&mut self, t: Ty<'tcx>) -> bool { t.region_depth > self.depth } - fn visit_region(&mut self, r: &'tcx ty::Region) -> bool { + fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool { r.escapes_depth(self.depth) } } @@ -647,7 +648,7 @@ fn visit_ty(&mut self, t: Ty) -> bool { flags.intersects(self.flags) } - fn visit_region(&mut self, r: &'tcx ty::Region) -> bool { + fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool { let flags = r.type_flags(); debug!("HasTypeFlagsVisitor: r={:?} r.flags={:?} self.flags={:?}", r, flags, self.flags); flags.intersects(self.flags) @@ -693,7 +694,7 @@ fn visit_ty(&mut self, t: Ty<'tcx>) -> bool { t.super_visit_with(self) } - fn visit_region(&mut self, r: &'tcx ty::Region) -> bool { + fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool { match *r { ty::ReLateBound(debruijn, br) if debruijn.depth == self.current_depth => { self.regions.insert(br); diff --git a/src/librustc/ty/maps.rs b/src/librustc/ty/maps.rs index abee0ae4ad6..4a780b9178e 100644 --- a/src/librustc/ty/maps.rs +++ b/src/librustc/ty/maps.rs @@ -578,7 +578,7 @@ fn default() -> Self { [] reachable_set: reachability_dep_node(CrateNum) -> Rc, - [] region_resolve_crate: region_resolve_crate_dep_node(CrateNum) -> Rc, + [] region_resolve_crate: region_resolve_crate_dep_node(CrateNum) -> Rc>, [] mir_shims: mir_shim_dep_node(ty::InstanceDef<'tcx>) -> &'tcx RefCell>, diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index fd0b1308c95..e6a8459e001 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -67,11 +67,12 @@ pub use self::sty::{ExistentialTraitRef, PolyExistentialTraitRef}; pub use self::sty::{ExistentialProjection, PolyExistentialProjection}; pub use self::sty::{BoundRegion, EarlyBoundRegion, FreeRegion, Region}; +pub use self::sty::RegionKind; pub use self::sty::Issue32330; pub use self::sty::{TyVid, IntVid, FloatVid, RegionVid, SkolemizedRegionVid}; pub use self::sty::BoundRegion::*; pub use self::sty::InferTy::*; -pub use self::sty::Region::*; +pub use self::sty::RegionKind::*; pub use self::sty::TypeVariants::*; pub use self::context::{TyCtxt, GlobalArenas, tls}; @@ -601,7 +602,7 @@ pub struct UpvarBorrow<'tcx> { pub kind: BorrowKind, /// Region of the resulting reference. - pub region: &'tcx ty::Region, + pub region: ty::Region<'tcx>, } pub type UpvarCaptureMap<'tcx> = FxHashMap>; @@ -934,9 +935,9 @@ pub fn dep_node(&self) -> DepNode { #[derive(Clone, PartialEq, Eq, Hash, Debug, RustcEncodable, RustcDecodable)] pub struct OutlivesPredicate(pub A, pub B); // `A : B` pub type PolyOutlivesPredicate = ty::Binder>; -pub type PolyRegionOutlivesPredicate<'tcx> = PolyOutlivesPredicate<&'tcx ty::Region, - &'tcx ty::Region>; -pub type PolyTypeOutlivesPredicate<'tcx> = PolyOutlivesPredicate, &'tcx ty::Region>; +pub type PolyRegionOutlivesPredicate<'tcx> = PolyOutlivesPredicate, + ty::Region<'tcx>>; +pub type PolyTypeOutlivesPredicate<'tcx> = PolyOutlivesPredicate, ty::Region<'tcx>>; #[derive(Clone, PartialEq, Eq, Hash, Debug, RustcEncodable, RustcDecodable)] pub struct SubtypePredicate<'tcx> { @@ -1167,7 +1168,7 @@ pub struct ParameterEnvironment<'tcx> { /// region of the callee. If it is `None`, then the parameter /// environment is for an item or something where the "callee" is /// not clear. - pub implicit_region_bound: Option<&'tcx ty::Region>, + pub implicit_region_bound: Option>, /// Obligations that the caller must satisfy. This is basically /// the set of bounds on the in-scope type parameters, translated @@ -1181,7 +1182,7 @@ pub struct ParameterEnvironment<'tcx> { /// FIXME(#3696). It would be nice to refactor so that free /// regions don't have this implicit scope and instead introduce /// relationships in the environment. - pub free_id_outlive: Option, + pub free_id_outlive: Option>, /// A cache for `moves_by_default`. pub is_copy_cache: RefCell, bool>>, @@ -1222,13 +1223,13 @@ pub fn for_item(tcx: TyCtxt<'a, 'tcx, 'tcx>, id: NodeId) let impl_def_id = tcx.hir.local_def_id(impl_id); tcx.construct_parameter_environment(impl_item.span, impl_def_id, - Some(tcx.region_maps().item_extent(id))) + Some(tcx.item_extent(id))) } hir::ImplItemKind::Method(_, ref body) => { tcx.construct_parameter_environment( impl_item.span, tcx.hir.local_def_id(id), - Some(tcx.region_maps().call_site_extent(id, body.node_id))) + Some(tcx.call_site_extent(id, body.node_id))) } } } @@ -1241,7 +1242,7 @@ pub fn for_item(tcx: TyCtxt<'a, 'tcx, 'tcx>, id: NodeId) let trait_def_id = tcx.hir.local_def_id(trait_id); tcx.construct_parameter_environment(trait_item.span, trait_def_id, - Some(tcx.region_maps().item_extent(id))) + Some(tcx.item_extent(id))) } hir::TraitItemKind::Method(_, ref body) => { // Use call-site for extent (unless this is a @@ -1249,10 +1250,10 @@ pub fn for_item(tcx: TyCtxt<'a, 'tcx, 'tcx>, id: NodeId) // to the method id). let extent = if let hir::TraitMethod::Provided(body_id) = *body { // default impl: use call_site extent as free_id_outlive bound. - tcx.region_maps().call_site_extent(id, body_id.node_id) + tcx.call_site_extent(id, body_id.node_id) } else { // no default impl: use item extent as free_id_outlive bound. - tcx.region_maps().item_extent(id) + tcx.item_extent(id) }; tcx.construct_parameter_environment( trait_item.span, @@ -1270,7 +1271,7 @@ pub fn for_item(tcx: TyCtxt<'a, 'tcx, 'tcx>, id: NodeId) tcx.construct_parameter_environment( item.span, fn_def_id, - Some(tcx.region_maps().call_site_extent(id, body_id.node_id))) + Some(tcx.call_site_extent(id, body_id.node_id))) } hir::ItemEnum(..) | hir::ItemStruct(..) | @@ -1282,13 +1283,13 @@ pub fn for_item(tcx: TyCtxt<'a, 'tcx, 'tcx>, id: NodeId) let def_id = tcx.hir.local_def_id(id); tcx.construct_parameter_environment(item.span, def_id, - Some(tcx.region_maps().item_extent(id))) + Some(tcx.item_extent(id))) } hir::ItemTrait(..) => { let def_id = tcx.hir.local_def_id(id); tcx.construct_parameter_environment(item.span, def_id, - Some(tcx.region_maps().item_extent(id))) + Some(tcx.item_extent(id))) } _ => { span_bug!(item.span, @@ -1306,7 +1307,7 @@ pub fn for_item(tcx: TyCtxt<'a, 'tcx, 'tcx>, id: NodeId) tcx.construct_parameter_environment( expr.span, base_def_id, - Some(tcx.region_maps().call_site_extent(id, body.node_id))) + Some(tcx.call_site_extent(id, body.node_id))) } else { tcx.empty_parameter_environment() } @@ -2454,8 +2455,9 @@ pub fn empty_parameter_environment(self) -> ParameterEnvironment<'tcx> { /// In general, this means converting from bound parameters to /// free parameters. Since we currently represent bound/free type /// parameters in the same way, this only has an effect on regions. - pub fn construct_free_substs(self, def_id: DefId, - free_id_outlive: Option) + pub fn construct_free_substs(self, + def_id: DefId, + free_id_outlive: Option>) -> &'gcx Substs<'gcx> { let substs = Substs::for_item(self.global_tcx(), def_id, |def, _| { @@ -2479,7 +2481,7 @@ pub fn construct_free_substs(self, def_id: DefId, pub fn construct_parameter_environment(self, span: Span, def_id: DefId, - free_id_outlive: Option) + free_id_outlive: Option>) -> ParameterEnvironment<'gcx> { // @@ -2521,14 +2523,14 @@ pub fn construct_parameter_environment(self, is_freeze_cache: RefCell::new(FxHashMap()), }; - let body_id = free_id_outlive.map(|f| f.node_id(&self.region_maps())) + let body_id = free_id_outlive.map(|f| f.node_id()) .unwrap_or(DUMMY_NODE_ID); let cause = traits::ObligationCause::misc(span, body_id); traits::normalize_param_env_or_error(tcx, unnormalized_env, cause) } - pub fn node_scope_region(self, id: NodeId) -> &'tcx Region { - self.mk_region(ty::ReScope(self.region_maps().node_extent(id))) + pub fn node_scope_region(self, id: NodeId) -> Region<'tcx> { + self.mk_region(ty::ReScope(self.node_extent(id))) } pub fn visit_all_item_likes_in_krate(self, diff --git a/src/librustc/ty/outlives.rs b/src/librustc/ty/outlives.rs index bc30f1fb717..a544b2dd399 100644 --- a/src/librustc/ty/outlives.rs +++ b/src/librustc/ty/outlives.rs @@ -16,7 +16,7 @@ #[derive(Debug)] pub enum Component<'tcx> { - Region(&'tcx ty::Region), + Region(ty::Region<'tcx>), Param(ty::ParamTy), UnresolvedInferenceVariable(ty::InferTy), @@ -202,7 +202,7 @@ fn capture_components(&self, ty: Ty<'tcx>) -> Vec> { } } -fn push_region_constraints<'tcx>(out: &mut Vec>, regions: Vec<&'tcx ty::Region>) { +fn push_region_constraints<'tcx>(out: &mut Vec>, regions: Vec>) { for r in regions { if !r.is_bound() { out.push(Component::Region(r)); diff --git a/src/librustc/ty/relate.rs b/src/librustc/ty/relate.rs index 58ebc843da1..ac434c01c6a 100644 --- a/src/librustc/ty/relate.rs +++ b/src/librustc/ty/relate.rs @@ -67,8 +67,8 @@ fn relate_with_variance>(&mut self, fn tys(&mut self, a: Ty<'tcx>, b: Ty<'tcx>) -> RelateResult<'tcx, Ty<'tcx>>; - fn regions(&mut self, a: &'tcx ty::Region, b: &'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region>; + fn regions(&mut self, a: ty::Region<'tcx>, b: ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>>; fn binders(&mut self, a: &ty::Binder, b: &ty::Binder) -> RelateResult<'tcx, ty::Binder> @@ -529,11 +529,11 @@ fn relate<'a, 'gcx, R>(relation: &mut R, } } -impl<'tcx> Relate<'tcx> for &'tcx ty::Region { +impl<'tcx> Relate<'tcx> for ty::Region<'tcx> { fn relate<'a, 'gcx, R>(relation: &mut R, - a: &&'tcx ty::Region, - b: &&'tcx ty::Region) - -> RelateResult<'tcx, &'tcx ty::Region> + a: &ty::Region<'tcx>, + b: &ty::Region<'tcx>) + -> RelateResult<'tcx, ty::Region<'tcx>> where R: TypeRelation<'a, 'gcx, 'tcx>, 'gcx: 'a+'tcx, 'tcx: 'a { relation.regions(*a, *b) diff --git a/src/librustc/ty/structural_impls.rs b/src/librustc/ty/structural_impls.rs index a4466d7d840..53d516e581b 100644 --- a/src/librustc/ty/structural_impls.rs +++ b/src/librustc/ty/structural_impls.rs @@ -624,7 +624,7 @@ fn super_visit_with>(&self, visitor: &mut V) -> bool { } } -impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::Region { +impl<'tcx> TypeFoldable<'tcx> for ty::Region<'tcx> { fn super_fold_with<'gcx: 'tcx, F: TypeFolder<'gcx, 'tcx>>(&self, _folder: &mut F) -> Self { *self } diff --git a/src/librustc/ty/sty.rs b/src/librustc/ty/sty.rs index 02c4bad8e4e..1ec8fd572a4 100644 --- a/src/librustc/ty/sty.rs +++ b/src/librustc/ty/sty.rs @@ -47,8 +47,8 @@ pub struct TypeAndMut<'tcx> { /// If `fr.scope` is None, then this is in some context (e.g., an /// impl) where lifetimes are more abstract and the notion of the /// caller/callee stack frames are not applicable. -pub struct FreeRegion { - pub scope: Option, +pub struct FreeRegion<'tcx> { + pub scope: Option>, pub bound_region: BoundRegion, } @@ -128,7 +128,7 @@ pub enum TypeVariants<'tcx> { /// A reference; a pointer with an associated lifetime. Written as /// `&'a mut T` or `&'a T`. - TyRef(&'tcx Region, TypeAndMut<'tcx>), + TyRef(Region<'tcx>, TypeAndMut<'tcx>), /// The anonymous type of a function declaration/definition. Each /// function has a unique type. @@ -140,7 +140,7 @@ pub enum TypeVariants<'tcx> { TyFnPtr(PolyFnSig<'tcx>), /// A trait, defined with `trait`. - TyDynamic(Binder<&'tcx Slice>>, &'tcx ty::Region), + TyDynamic(Binder<&'tcx Slice>>, ty::Region<'tcx>), /// The anonymous type of a closure. Used to represent the type of /// `|a| a`. @@ -679,6 +679,8 @@ pub struct DebruijnIndex { pub depth: u32, } +pub type Region<'tcx> = &'tcx RegionKind<'tcx>; + /// Representation of regions. /// /// Unlike types, most region variants are "fictitious", not concrete, @@ -736,7 +738,7 @@ pub struct DebruijnIndex { /// [1] http://smallcultfollowing.com/babysteps/blog/2013/10/29/intermingled-parameter-lists/ /// [2] http://smallcultfollowing.com/babysteps/blog/2013/11/04/intermingled-parameter-lists/ #[derive(Clone, PartialEq, Eq, Hash, Copy, RustcEncodable, RustcDecodable)] -pub enum Region { +pub enum RegionKind<'tcx> { // Region bound in a type or fn declaration which will be // substituted 'early' -- that is, at the same time when type // parameters are substituted. @@ -749,12 +751,12 @@ pub enum Region { /// When checking a function body, the types of all arguments and so forth /// that refer to bound region parameters are modified to refer to free /// region parameters. - ReFree(FreeRegion), + ReFree(FreeRegion<'tcx>), /// A concrete region naming some statically determined extent /// (e.g. an expression or sequence of statements) within the /// current function. - ReScope(region::CodeExtent), + ReScope(region::CodeExtent<'tcx>), /// Static data that has an "infinite" lifetime. Top in the region lattice. ReStatic, @@ -779,7 +781,7 @@ pub enum Region { ReErased, } -impl<'tcx> serialize::UseSpecializedDecodable for &'tcx Region {} +impl<'tcx> serialize::UseSpecializedDecodable for Region<'tcx> {} #[derive(Copy, Clone, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, Debug)] pub struct EarlyBoundRegion { @@ -898,7 +900,7 @@ pub fn shifted(&self, amount: u32) -> DebruijnIndex { } // Region utilities -impl Region { +impl<'tcx> RegionKind<'tcx> { pub fn is_bound(&self) -> bool { match *self { ty::ReEarlyBound(..) => true, @@ -922,7 +924,7 @@ pub fn escapes_depth(&self, depth: u32) -> bool { } /// Returns the depth of `self` from the (1-based) binding level `depth` - pub fn from_depth(&self, depth: u32) -> Region { + pub fn from_depth(&self, depth: u32) -> RegionKind<'tcx> { match *self { ty::ReLateBound(debruijn, r) => ty::ReLateBound(DebruijnIndex { depth: debruijn.depth - (depth - 1) @@ -1334,7 +1336,7 @@ pub fn ty_adt_def(&self) -> Option<&'tcx AdtDef> { /// Returns the regions directly referenced from this type (but /// not types reachable from this type via `walk_tys`). This /// ignores late-bound regions binders. - pub fn regions(&self) -> Vec<&'tcx ty::Region> { + pub fn regions(&self) -> Vec> { match self.sty { TyRef(region, _) => { vec![region] diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 961140d5eac..c591845dd63 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -11,7 +11,7 @@ // Type substitutions. use hir::def_id::DefId; -use ty::{self, Slice, Ty, TyCtxt}; +use ty::{self, Slice, Region, Ty, TyCtxt}; use ty::fold::{TypeFoldable, TypeFolder, TypeVisitor}; use serialize::{self, Encodable, Encoder, Decodable, Decoder}; @@ -32,7 +32,7 @@ #[derive(Copy, Clone, PartialEq, Eq, Hash)] pub struct Kind<'tcx> { ptr: NonZero, - marker: PhantomData<(Ty<'tcx>, &'tcx ty::Region)> + marker: PhantomData<(Ty<'tcx>, ty::Region<'tcx>)> } const TAG_MASK: usize = 0b11; @@ -54,8 +54,8 @@ fn from(ty: Ty<'tcx>) -> Kind<'tcx> { } } -impl<'tcx> From<&'tcx ty::Region> for Kind<'tcx> { - fn from(r: &'tcx ty::Region) -> Kind<'tcx> { +impl<'tcx> From> for Kind<'tcx> { + fn from(r: ty::Region<'tcx>) -> Kind<'tcx> { // Ensure we can use the tag bits. assert_eq!(mem::align_of_val(r) & TAG_MASK, 0); @@ -88,7 +88,7 @@ pub fn as_type(self) -> Option> { } #[inline] - pub fn as_region(self) -> Option<&'tcx ty::Region> { + pub fn as_region(self) -> Option> { unsafe { self.downcast(REGION_TAG) } @@ -153,7 +153,7 @@ fn decode(d: &mut D) -> Result, D::Error> { d.read_enum_variant(&["Ty", "Region"], |d, tag| { match tag { TYPE_TAG => Ty::decode(d).map(Kind::from), - REGION_TAG => <&ty::Region>::decode(d).map(Kind::from), + REGION_TAG => Region::decode(d).map(Kind::from), _ => Err(d.error("invalid Kind tag")) } }) @@ -183,7 +183,7 @@ pub fn for_item(tcx: TyCtxt<'a, 'gcx, 'tcx>, mut mk_region: FR, mut mk_type: FT) -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> &'tcx ty::Region, + where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { let defs = tcx.generics_of(def_id); let mut substs = Vec::with_capacity(defs.count()); @@ -197,7 +197,7 @@ pub fn extend_to(&self, mut mk_region: FR, mut mk_type: FT) -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> &'tcx ty::Region, + where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { let defs = tcx.generics_of(def_id); @@ -212,7 +212,7 @@ fn fill_item(substs: &mut Vec>, defs: &ty::Generics, mk_region: &mut FR, mk_type: &mut FT) - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> &'tcx ty::Region, + where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { if let Some(def_id) = defs.parent { @@ -226,7 +226,7 @@ fn fill_single(substs: &mut Vec>, defs: &ty::Generics, mk_region: &mut FR, mk_type: &mut FT) - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> &'tcx ty::Region, + where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { // Handle Self first, before all regions. let mut types = defs.types.iter(); @@ -260,7 +260,7 @@ pub fn types(&'a self) -> impl DoubleEndedIterator> + 'a { } #[inline] - pub fn regions(&'a self) -> impl DoubleEndedIterator + 'a { + pub fn regions(&'a self) -> impl DoubleEndedIterator> + 'a { self.iter().filter_map(|k| k.as_region()) } @@ -272,7 +272,7 @@ pub fn type_at(&self, i: usize) -> Ty<'tcx> { } #[inline] - pub fn region_at(&self, i: usize) -> &'tcx ty::Region { + pub fn region_at(&self, i: usize) -> ty::Region<'tcx> { self[i].as_region().unwrap_or_else(|| { bug!("expected region for param #{} in {:?}", i, self); }) @@ -284,7 +284,7 @@ pub fn type_for_def(&self, ty_param_def: &ty::TypeParameterDef) -> Ty<'tcx> { } #[inline] - pub fn region_for_def(&self, def: &ty::RegionParameterDef) -> &'tcx ty::Region { + pub fn region_for_def(&self, def: &ty::RegionParameterDef) -> ty::Region<'tcx> { self.region_at(def.index as usize) } @@ -396,7 +396,7 @@ fn fold_binder>(&mut self, t: &ty::Binder) -> ty::Binde t } - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { // Note: This routine only handles regions that are bound on // type declarations and other outer declarations, not those // bound in *fn types*. Region substitution of the bound @@ -538,7 +538,7 @@ fn shift_regions_through_binders(&self, ty: Ty<'tcx>) -> Ty<'tcx> { result } - fn shift_region_through_binders(&self, region: &'tcx ty::Region) -> &'tcx ty::Region { + fn shift_region_through_binders(&self, region: ty::Region<'tcx>) -> ty::Region<'tcx> { if self.region_binders_passed == 0 || !region.has_escaping_regions() { return region; } diff --git a/src/librustc/ty/util.rs b/src/librustc/ty/util.rs index 87921c80502..befc4e6c5fd 100644 --- a/src/librustc/ty/util.rs +++ b/src/librustc/ty/util.rs @@ -316,7 +316,7 @@ pub fn struct_lockstep_tails(self, pub fn required_region_bounds(self, erased_self_ty: Ty<'tcx>, predicates: Vec>) - -> Vec<&'tcx ty::Region> { + -> Vec> { debug!("required_region_bounds(erased_self_ty={:?}, predicates={:?})", erased_self_ty, predicates); @@ -457,7 +457,7 @@ pub fn destructor_constraints(self, def: &'tcx ty::AdtDef) let result = item_substs.iter().zip(impl_substs.iter()) .filter(|&(_, &k)| { - if let Some(&ty::Region::ReEarlyBound(ref ebr)) = k.as_region() { + if let Some(&ty::RegionKind::ReEarlyBound(ref ebr)) = k.as_region() { !impl_generics.region_param(ebr).pure_wrt_drop } else if let Some(&ty::TyS { sty: ty::TypeVariants::TyParam(ref pt), .. @@ -673,7 +673,7 @@ fn visit_ty(&mut self, ty: Ty<'tcx>) -> bool { ty.super_visit_with(self) } - fn visit_region(&mut self, r: &'tcx ty::Region) -> bool { + fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool { self.hash_discriminant_u8(r); match *r { ty::ReErased | diff --git a/src/librustc/ty/wf.rs b/src/librustc/ty/wf.rs index 6c7073de70b..d0cbbaf2c10 100644 --- a/src/librustc/ty/wf.rs +++ b/src/librustc/ty/wf.rs @@ -116,9 +116,9 @@ pub fn predicate_obligations<'a, 'gcx, 'tcx>(infcx: &InferCtxt<'a, 'gcx, 'tcx>, /// For `&'a T` to be WF, `T: 'a` must hold. So we can assume `T: 'a`. #[derive(Debug)] pub enum ImpliedBound<'tcx> { - RegionSubRegion(&'tcx ty::Region, &'tcx ty::Region), - RegionSubParam(&'tcx ty::Region, ty::ParamTy), - RegionSubProjection(&'tcx ty::Region, ty::ProjectionTy<'tcx>), + RegionSubRegion(ty::Region<'tcx>, ty::Region<'tcx>), + RegionSubParam(ty::Region<'tcx>, ty::ParamTy), + RegionSubProjection(ty::Region<'tcx>, ty::ProjectionTy<'tcx>), } /// Compute the implied bounds that a callee/impl can assume based on @@ -198,7 +198,7 @@ pub fn implied_bounds<'a, 'gcx, 'tcx>( /// this down to determine what relationships would have to hold for /// `T: 'a` to hold. We get to assume that the caller has validated /// those relationships. -fn implied_bounds_from_components<'tcx>(sub_region: &'tcx ty::Region, +fn implied_bounds_from_components<'tcx>(sub_region: ty::Region<'tcx>, sup_components: Vec>) -> Vec> { @@ -455,7 +455,7 @@ fn nominal_obligations(&mut self, fn from_object_ty(&mut self, ty: Ty<'tcx>, data: ty::Binder<&'tcx ty::Slice>>, - region: &'tcx ty::Region) { + region: ty::Region<'tcx>) { // Imagine a type like this: // // trait Foo { } @@ -512,7 +512,7 @@ fn from_object_ty(&mut self, ty: Ty<'tcx>, pub fn object_region_bounds<'a, 'gcx, 'tcx>( tcx: TyCtxt<'a, 'gcx, 'tcx>, existential_predicates: ty::Binder<&'tcx ty::Slice>>) - -> Vec<&'tcx ty::Region> + -> Vec> { // Since we don't actually *know* the self type for an object, // this "open(err)" serves as a kind of dummy standin -- basically diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index df5a2731c89..d773bb2da08 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -177,12 +177,12 @@ pub fn parameterized(f: &mut fmt::Formatter, let print_regions = |f: &mut fmt::Formatter, start: &str, skip, count| { // Don't print any regions if they're all erased. let regions = || substs.regions().skip(skip).take(count); - if regions().all(|r: &ty::Region| *r == ty::ReErased) { + if regions().all(|r: ty::Region| *r == ty::ReErased) { return Ok(()); } for region in regions() { - let region: &ty::Region = region; + let region: ty::Region = region; start_or_continue(f, start, ", ")?; if verbose { write!(f, "{:?}", region)?; @@ -458,7 +458,7 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { } } -impl fmt::Debug for ty::Region { +impl<'tcx> fmt::Debug for ty::RegionKind<'tcx> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { match *self { ty::ReEarlyBound(ref data) => { @@ -516,7 +516,7 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { } } -impl fmt::Display for ty::Region { +impl<'tcx> fmt::Display for ty::RegionKind<'tcx> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { if verbose() { return write!(f, "{:?}", *self); @@ -544,7 +544,7 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { } } -impl fmt::Debug for ty::FreeRegion { +impl<'tcx> fmt::Debug for ty::FreeRegion<'tcx> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { write!(f, "ReFree({:?}, {:?})", self.scope, self.bound_region) @@ -689,14 +689,14 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { } } -impl<'tcx> fmt::Display for ty::Binder, &'tcx ty::Region>> { +impl<'tcx> fmt::Display for ty::Binder, ty::Region<'tcx>>> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self))) } } -impl<'tcx> fmt::Display for ty::Binder> { +impl<'tcx> fmt::Display for ty::Binder, + ty::Region<'tcx>>> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self))) } diff --git a/src/librustc_borrowck/borrowck/check_loans.rs b/src/librustc_borrowck/borrowck/check_loans.rs index 97cf9253038..96753d63af2 100644 --- a/src/librustc_borrowck/borrowck/check_loans.rs +++ b/src/librustc_borrowck/borrowck/check_loans.rs @@ -126,7 +126,7 @@ fn borrow(&mut self, borrow_id: ast::NodeId, borrow_span: Span, cmt: mc::cmt<'tcx>, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, bk: ty::BorrowKind, loan_cause: euv::LoanCause) { @@ -232,14 +232,14 @@ pub fn each_issued_loan(&self, node: ast::NodeId, mut op: F) -> bool where }) } - pub fn each_in_scope_loan(&self, scope: region::CodeExtent, mut op: F) -> bool where + pub fn each_in_scope_loan(&self, scope: region::CodeExtent<'tcx>, mut op: F) -> bool where F: FnMut(&Loan<'tcx>) -> bool, { //! Like `each_issued_loan()`, but only considers loans that are //! currently in scope. let tcx = self.tcx(); - self.each_issued_loan(scope.node_id(&tcx.region_maps()), |loan| { + self.each_issued_loan(scope.node_id(), |loan| { if tcx.region_maps().is_subscope_of(scope, loan.kill_scope) { op(loan) } else { @@ -249,7 +249,7 @@ pub fn each_in_scope_loan(&self, scope: region::CodeExtent, mut op: F) -> boo } fn each_in_scope_loan_affecting_path(&self, - scope: region::CodeExtent, + scope: region::CodeExtent<'tcx>, loan_path: &LoanPath<'tcx>, mut op: F) -> bool where @@ -460,8 +460,7 @@ pub fn report_error_if_loan_conflicts_with_restriction(&self, // 3. Where does old loan expire. let previous_end_span = - self.tcx().hir.span(old_loan.kill_scope.node_id(&self.tcx().region_maps())) - .end_point(); + self.tcx().hir.span(old_loan.kill_scope.node_id()).end_point(); let mut err = match (new_loan.kind, old_loan.kind) { (ty::MutBorrow, ty::MutBorrow) => { @@ -710,7 +709,7 @@ pub fn analyze_restrictions_on_use(&self, let mut ret = UseOk; self.each_in_scope_loan_affecting_path( - self.tcx().region_maps().node_extent(expr_id), use_path, |loan| { + self.tcx().node_extent(expr_id), use_path, |loan| { if !compatible_borrow_kinds(loan.kind, borrow_kind) { ret = UseWhileBorrowed(loan.loan_path.clone(), loan.span); false @@ -824,7 +823,7 @@ fn check_assignment(&self, // Check that we don't invalidate any outstanding loans if let Some(loan_path) = opt_loan_path(&assignee_cmt) { - let scope = self.tcx().region_maps().node_extent(assignment_id); + let scope = self.tcx().node_extent(assignment_id); self.each_in_scope_loan_affecting_path(scope, &loan_path, |loan| { self.report_illegal_mutation(assignment_span, &loan_path, loan); false diff --git a/src/librustc_borrowck/borrowck/gather_loans/lifetime.rs b/src/librustc_borrowck/borrowck/gather_loans/lifetime.rs index 2dfb4f1dd82..9f8ffd86f54 100644 --- a/src/librustc_borrowck/borrowck/gather_loans/lifetime.rs +++ b/src/librustc_borrowck/borrowck/gather_loans/lifetime.rs @@ -24,11 +24,11 @@ type R = Result<(),()>; pub fn guarantee_lifetime<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>, - item_scope: region::CodeExtent, + item_scope: region::CodeExtent<'tcx>, span: Span, cause: euv::LoanCause, cmt: mc::cmt<'tcx>, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, _: ty::BorrowKind) -> Result<(),()> { //! Reports error if `loan_region` is larger than S @@ -52,11 +52,11 @@ struct GuaranteeLifetimeContext<'a, 'tcx: 'a> { bccx: &'a BorrowckCtxt<'a, 'tcx>, // the scope of the function body for the enclosing item - item_scope: region::CodeExtent, + item_scope: region::CodeExtent<'tcx>, span: Span, cause: euv::LoanCause, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, cmt_original: mc::cmt<'tcx> } @@ -92,7 +92,7 @@ fn check(&self, cmt: &mc::cmt<'tcx>, discr_scope: Option) -> R { } } - fn check_scope(&self, max_scope: &'tcx ty::Region) -> R { + fn check_scope(&self, max_scope: ty::Region<'tcx>) -> R { //! Reports an error if `loan_region` is larger than `max_scope` if !self.bccx.is_subregion_of(self.loan_region, max_scope) { @@ -102,7 +102,7 @@ fn check_scope(&self, max_scope: &'tcx ty::Region) -> R { } } - fn scope(&self, cmt: &mc::cmt<'tcx>) -> &'tcx ty::Region { + fn scope(&self, cmt: &mc::cmt<'tcx>) -> ty::Region<'tcx> { //! Returns the maximal region scope for the which the //! lvalue `cmt` is guaranteed to be valid without any //! rooting etc, and presuming `cmt` is not mutated. diff --git a/src/librustc_borrowck/borrowck/gather_loans/mod.rs b/src/librustc_borrowck/borrowck/gather_loans/mod.rs index f5cdd40714c..09ed515939d 100644 --- a/src/librustc_borrowck/borrowck/gather_loans/mod.rs +++ b/src/librustc_borrowck/borrowck/gather_loans/mod.rs @@ -45,7 +45,7 @@ pub fn gather_loans_in_fn<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>, bccx: bccx, infcx: &infcx, all_loans: Vec::new(), - item_ub: bccx.tcx.region_maps().node_extent(body.node_id), + item_ub: bccx.tcx.node_extent(body.node_id), move_data: MoveData::new(), move_error_collector: move_error::MoveErrorCollector::new(), }; @@ -66,7 +66,7 @@ struct GatherLoanCtxt<'a, 'tcx: 'a> { all_loans: Vec>, /// `item_ub` is used as an upper-bound on the lifetime whenever we /// ask for the scope of an expression categorized as an upvar. - item_ub: region::CodeExtent, + item_ub: region::CodeExtent<'tcx>, } impl<'a, 'tcx> euv::Delegate<'tcx> for GatherLoanCtxt<'a, 'tcx> { @@ -127,7 +127,7 @@ fn borrow(&mut self, borrow_id: ast::NodeId, borrow_span: Span, cmt: mc::cmt<'tcx>, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, bk: ty::BorrowKind, loan_cause: euv::LoanCause) { @@ -299,7 +299,7 @@ fn guarantee_valid(&mut self, borrow_span: Span, cmt: mc::cmt<'tcx>, req_kind: ty::BorrowKind, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, cause: euv::LoanCause) { debug!("guarantee_valid(borrow_id={}, cmt={:?}, \ req_mutbl={:?}, loan_region={:?})", @@ -371,7 +371,7 @@ fn guarantee_valid(&mut self, }; debug!("loan_scope = {:?}", loan_scope); - let borrow_scope = self.tcx().region_maps().node_extent(borrow_id); + let borrow_scope = self.tcx().node_extent(borrow_id); let gen_scope = self.compute_gen_scope(borrow_scope, loan_scope); debug!("gen_scope = {:?}", gen_scope); @@ -450,9 +450,9 @@ pub fn mark_loan_path_as_mutated(&self, loan_path: &LoanPath) { } pub fn compute_gen_scope(&self, - borrow_scope: region::CodeExtent, - loan_scope: region::CodeExtent) - -> region::CodeExtent { + borrow_scope: region::CodeExtent<'tcx>, + loan_scope: region::CodeExtent<'tcx>) + -> region::CodeExtent<'tcx> { //! Determine when to introduce the loan. Typically the loan //! is introduced at the point of the borrow, but in some cases, //! notably method arguments, the loan may be introduced only @@ -465,8 +465,8 @@ pub fn compute_gen_scope(&self, } } - pub fn compute_kill_scope(&self, loan_scope: region::CodeExtent, lp: &LoanPath<'tcx>) - -> region::CodeExtent { + pub fn compute_kill_scope(&self, loan_scope: region::CodeExtent<'tcx>, lp: &LoanPath<'tcx>) + -> region::CodeExtent<'tcx> { //! Determine when the loan restrictions go out of scope. //! This is either when the lifetime expires or when the //! local variable which roots the loan-path goes out of scope, diff --git a/src/librustc_borrowck/borrowck/gather_loans/restrictions.rs b/src/librustc_borrowck/borrowck/gather_loans/restrictions.rs index fdcefdc0d43..7f90a8b19d4 100644 --- a/src/librustc_borrowck/borrowck/gather_loans/restrictions.rs +++ b/src/librustc_borrowck/borrowck/gather_loans/restrictions.rs @@ -31,7 +31,7 @@ pub fn compute_restrictions<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>, span: Span, cause: euv::LoanCause, cmt: mc::cmt<'tcx>, - loan_region: &'tcx ty::Region) + loan_region: ty::Region<'tcx>) -> RestrictionResult<'tcx> { let ctxt = RestrictionsContext { bccx: bccx, @@ -49,7 +49,7 @@ pub fn compute_restrictions<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>, struct RestrictionsContext<'a, 'tcx: 'a> { bccx: &'a BorrowckCtxt<'a, 'tcx>, span: Span, - loan_region: &'tcx ty::Region, + loan_region: ty::Region<'tcx>, cause: euv::LoanCause, } diff --git a/src/librustc_borrowck/borrowck/mod.rs b/src/librustc_borrowck/borrowck/mod.rs index 2baec7418eb..1a7c700e239 100644 --- a/src/librustc_borrowck/borrowck/mod.rs +++ b/src/librustc_borrowck/borrowck/mod.rs @@ -141,9 +141,9 @@ fn build_borrowck_dataflow_data<'a, 'tcx>(this: &mut BorrowckCtxt<'a, 'tcx>, id_range, all_loans.len()); for (loan_idx, loan) in all_loans.iter().enumerate() { - loan_dfcx.add_gen(loan.gen_scope.node_id(&tcx.region_maps()), loan_idx); + loan_dfcx.add_gen(loan.gen_scope.node_id(), loan_idx); loan_dfcx.add_kill(KillFrom::ScopeEnd, - loan.kill_scope.node_id(&tcx.region_maps()), loan_idx); + loan.kill_scope.node_id(), loan_idx); } loan_dfcx.add_kills_from_flow_exits(cfg); loan_dfcx.propagate(cfg, body); @@ -206,13 +206,13 @@ pub struct Loan<'tcx> { /// cases, notably method arguments, the loan may be introduced /// only later, once it comes into scope. See also /// `GatherLoanCtxt::compute_gen_scope`. - gen_scope: region::CodeExtent, + gen_scope: region::CodeExtent<'tcx>, /// kill_scope indicates when the loan goes out of scope. This is /// either when the lifetime expires or when the local variable /// which roots the loan-path goes out of scope, whichever happens /// faster. See also `GatherLoanCtxt::compute_kill_scope`. - kill_scope: region::CodeExtent, + kill_scope: region::CodeExtent<'tcx>, span: Span, cause: euv::LoanCause, } @@ -312,12 +312,12 @@ pub fn closure_to_block(closure_id: ast::NodeId, } impl<'a, 'tcx> LoanPath<'tcx> { - pub fn kill_scope(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>) -> region::CodeExtent { + pub fn kill_scope(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>) -> region::CodeExtent<'tcx> { match self.kind { LpVar(local_id) => tcx.region_maps().var_scope(local_id), LpUpvar(upvar_id) => { let block_id = closure_to_block(upvar_id.closure_expr_id, tcx); - tcx.region_maps().node_extent(block_id) + tcx.node_extent(block_id) } LpDowncast(ref base, _) | LpExtend(ref base, ..) => base.kill_scope(tcx), @@ -444,8 +444,8 @@ pub fn opt_loan_path<'tcx>(cmt: &mc::cmt<'tcx>) -> Option>> { pub enum bckerr_code<'tcx> { err_mutbl, /// superscope, subscope, loan cause - err_out_of_scope(&'tcx ty::Region, &'tcx ty::Region, euv::LoanCause), - err_borrowed_pointer_too_short(&'tcx ty::Region, &'tcx ty::Region), // loan, ptr + err_out_of_scope(ty::Region<'tcx>, ty::Region<'tcx>, euv::LoanCause), + err_borrowed_pointer_too_short(ty::Region<'tcx>, ty::Region<'tcx>), // loan, ptr } // Combination of an error code and the categorization of the expression @@ -475,8 +475,8 @@ pub enum MovedValueUseKind { impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> { pub fn is_subregion_of(&self, - r_sub: &'tcx ty::Region, - r_sup: &'tcx ty::Region) + r_sub: ty::Region<'tcx>, + r_sup: ty::Region<'tcx>) -> bool { self.tables.free_region_map.is_subregion_of(self.tcx, r_sub, r_sup) @@ -963,10 +963,10 @@ fn report_out_of_scope_escaping_closure_capture(&self, .emit(); } - fn region_end_span(&self, region: &'tcx ty::Region) -> Option { + fn region_end_span(&self, region: ty::Region<'tcx>) -> Option { match *region { ty::ReScope(scope) => { - match scope.span(&self.tcx.region_maps(), &self.tcx.hir) { + match scope.span(&self.tcx.hir) { Some(s) => { Some(s.end_point()) } @@ -1244,10 +1244,10 @@ pub fn cmt_to_path_or_string(&self, cmt: &mc::cmt<'tcx>) -> String { } } -fn statement_scope_span(tcx: TyCtxt, region: &ty::Region) -> Option { +fn statement_scope_span(tcx: TyCtxt, region: ty::Region) -> Option { match *region { ty::ReScope(scope) => { - match tcx.hir.find(scope.node_id(&tcx.region_maps())) { + match tcx.hir.find(scope.node_id()) { Some(hir_map::NodeStmt(stmt)) => Some(stmt.span), _ => None } diff --git a/src/librustc_borrowck/borrowck/move_data.rs b/src/librustc_borrowck/borrowck/move_data.rs index 60d0ab5ff82..3d7df7f0372 100644 --- a/src/librustc_borrowck/borrowck/move_data.rs +++ b/src/librustc_borrowck/borrowck/move_data.rs @@ -548,7 +548,7 @@ fn add_gen_kills(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, LpVar(..) | LpUpvar(..) | LpDowncast(..) => { let kill_scope = path.loan_path.kill_scope(tcx); let path = *self.path_map.borrow().get(&path.loan_path).unwrap(); - self.kill_moves(path, kill_scope.node_id(&tcx.region_maps()), + self.kill_moves(path, kill_scope.node_id(), KillFrom::ScopeEnd, dfcx_moves); } LpExtend(..) => {} @@ -563,7 +563,7 @@ fn add_gen_kills(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, LpVar(..) | LpUpvar(..) | LpDowncast(..) => { let kill_scope = lp.kill_scope(tcx); dfcx_assign.add_kill(KillFrom::ScopeEnd, - kill_scope.node_id(&tcx.region_maps()), + kill_scope.node_id(), assignment_index); } LpExtend(..) => { diff --git a/src/librustc_const_eval/check_match.rs b/src/librustc_const_eval/check_match.rs index 2e0afe789c6..5a2fc9adc2f 100644 --- a/src/librustc_const_eval/check_match.rs +++ b/src/librustc_const_eval/check_match.rs @@ -533,7 +533,7 @@ fn borrow(&mut self, _: ast::NodeId, span: Span, _: cmt, - _: &'tcx ty::Region, + _: ty::Region<'tcx>, kind:ty:: BorrowKind, _: LoanCause) { match kind { diff --git a/src/librustc_const_eval/pattern.rs b/src/librustc_const_eval/pattern.rs index aea40b85535..e15d63a63c2 100644 --- a/src/librustc_const_eval/pattern.rs +++ b/src/librustc_const_eval/pattern.rs @@ -35,7 +35,7 @@ pub enum PatternError<'tcx> { #[derive(Copy, Clone, Debug)] pub enum BindingMode<'tcx> { ByValue, - ByRef(&'tcx Region, BorrowKind), + ByRef(Region<'tcx>, BorrowKind), } #[derive(Clone, Debug)] @@ -811,7 +811,7 @@ fn super_fold_with>(&self, _: &mut F) -> Self { } CloneImpls!{ <'tcx> - Span, Field, Mutability, ast::Name, ast::NodeId, usize, ConstVal<'tcx>, Region, + Span, Field, Mutability, ast::Name, ast::NodeId, usize, ConstVal<'tcx>, Region<'tcx>, Ty<'tcx>, BindingMode<'tcx>, &'tcx AdtDef, &'tcx Substs<'tcx>, &'tcx Kind<'tcx> } diff --git a/src/librustc_data_structures/transitive_relation.rs b/src/librustc_data_structures/transitive_relation.rs index 2631108aeb5..b0fca5c0ff3 100644 --- a/src/librustc_data_structures/transitive_relation.rs +++ b/src/librustc_data_structures/transitive_relation.rs @@ -80,6 +80,27 @@ fn add_index(&mut self, a: T) -> Index { } } + /// Applies the (partial) function to each edge and returns a new + /// relation. If `f` returns `None` for any end-point, returns + /// `None`. + pub fn maybe_map(&self, mut f: F) -> Option> + where F: FnMut(&T) -> Option, + U: Debug + PartialEq, + { + let mut result = TransitiveRelation::new(); + for edge in &self.edges { + let r = f(&self.elements[edge.source.0]).and_then(|source| { + f(&self.elements[edge.target.0]).and_then(|target| { + Some(result.add(source, target)) + }) + }); + if r.is_none() { + return None; + } + } + Some(result) + } + /// Indicate that `a < b` (where `<` is this relation) pub fn add(&mut self, a: T, b: T) { let a = self.add_index(a); diff --git a/src/librustc_driver/test.rs b/src/librustc_driver/test.rs index a19bc4aea2c..38f98548571 100644 --- a/src/librustc_driver/test.rs +++ b/src/librustc_driver/test.rs @@ -293,7 +293,7 @@ pub fn t_param(&self, index: u32) -> Ty<'tcx> { self.infcx.tcx.mk_param(index, Symbol::intern(&name)) } - pub fn re_early_bound(&self, index: u32, name: &'static str) -> &'tcx ty::Region { + pub fn re_early_bound(&self, index: u32, name: &'static str) -> ty::Region<'tcx> { let name = Symbol::intern(name); self.infcx.tcx.mk_region(ty::ReEarlyBound(ty::EarlyBoundRegion { index: index, @@ -304,11 +304,11 @@ pub fn re_early_bound(&self, index: u32, name: &'static str) -> &'tcx ty::Region pub fn re_late_bound_with_debruijn(&self, id: u32, debruijn: ty::DebruijnIndex) - -> &'tcx ty::Region { + -> ty::Region<'tcx> { self.infcx.tcx.mk_region(ty::ReLateBound(debruijn, ty::BrAnon(id))) } - pub fn t_rptr(&self, r: &'tcx ty::Region) -> Ty<'tcx> { + pub fn t_rptr(&self, r: ty::Region<'tcx>) -> Ty<'tcx> { self.infcx.tcx.mk_imm_ref(r, self.tcx().types.isize) } @@ -330,7 +330,7 @@ pub fn t_rptr_scope(&self, id: u32) -> Ty<'tcx> { self.infcx.tcx.mk_imm_ref(self.infcx.tcx.mk_region(r), self.tcx().types.isize) } - pub fn re_free(&self, nid: ast::NodeId, id: u32) -> &'tcx ty::Region { + pub fn re_free(&self, nid: ast::NodeId, id: u32) -> ty::Region<'tcx> { self.infcx.tcx.mk_region(ty::ReFree(ty::FreeRegion { scope: self.tcx().region_maps.item_extent(nid), bound_region: ty::BrAnon(id), diff --git a/src/librustc_metadata/decoder.rs b/src/librustc_metadata/decoder.rs index 28fea2eec60..9f4625c2ce3 100644 --- a/src/librustc_metadata/decoder.rs +++ b/src/librustc_metadata/decoder.rs @@ -20,6 +20,7 @@ use rustc::hir::def::{self, Def, CtorKind}; use rustc::hir::def_id::{CrateNum, DefId, DefIndex, CRATE_DEF_INDEX, LOCAL_CRATE}; use rustc::middle::lang_items; +use rustc::middle::region; use rustc::session::Session; use rustc::ty::{self, Ty, TyCtxt}; use rustc::ty::subst::Substs; @@ -352,12 +353,18 @@ fn specialized_decode(&mut self) -> Result<&'tcx Substs<'tcx>, Self::Error> { } } -impl<'a, 'tcx> SpecializedDecoder<&'tcx ty::Region> for DecodeContext<'a, 'tcx> { - fn specialized_decode(&mut self) -> Result<&'tcx ty::Region, Self::Error> { +impl<'a, 'tcx> SpecializedDecoder> for DecodeContext<'a, 'tcx> { + fn specialized_decode(&mut self) -> Result, Self::Error> { Ok(self.tcx().mk_region(Decodable::decode(self)?)) } } +impl<'a, 'tcx> SpecializedDecoder> for DecodeContext<'a, 'tcx> { + fn specialized_decode(&mut self) -> Result, Self::Error> { + Ok(self.tcx().intern_code_extent(Decodable::decode(self)?)) + } +} + impl<'a, 'tcx> SpecializedDecoder<&'tcx ty::Slice>> for DecodeContext<'a, 'tcx> { fn specialized_decode(&mut self) -> Result<&'tcx ty::Slice>, Self::Error> { Ok(self.tcx().mk_type_list((0..self.read_usize()?).map(|_| Decodable::decode(self)))?) diff --git a/src/librustc_mir/build/block.rs b/src/librustc_mir/build/block.rs index f99f41c633e..d81de954dbf 100644 --- a/src/librustc_mir/build/block.rs +++ b/src/librustc_mir/build/block.rs @@ -83,7 +83,7 @@ fn ast_block_stmts(&mut self, let_extent_stack.push(remainder_scope); // Declare the bindings, which may create a visibility scope. - let remainder_span = remainder_scope.span(&tcx.region_maps(), &tcx.hir); + let remainder_span = remainder_scope.span(&tcx.hir); let remainder_span = remainder_span.unwrap_or(span); let scope = this.declare_bindings(None, remainder_span, &pattern); diff --git a/src/librustc_mir/build/expr/as_operand.rs b/src/librustc_mir/build/expr/as_operand.rs index 8d79e755685..22a36bb21d8 100644 --- a/src/librustc_mir/build/expr/as_operand.rs +++ b/src/librustc_mir/build/expr/as_operand.rs @@ -39,7 +39,7 @@ pub fn as_local_operand(&mut self, block: BasicBlock, expr: M) /// The operand is known to be live until the end of `scope`. pub fn as_operand(&mut self, block: BasicBlock, - scope: Option, + scope: Option>, expr: M) -> BlockAnd> where M: Mirror<'tcx, Output = Expr<'tcx>> { @@ -49,7 +49,7 @@ pub fn as_operand(&mut self, fn expr_as_operand(&mut self, mut block: BasicBlock, - scope: Option, + scope: Option>, expr: Expr<'tcx>) -> BlockAnd> { debug!("expr_as_operand(block={:?}, expr={:?})", block, expr); diff --git a/src/librustc_mir/build/expr/as_rvalue.rs b/src/librustc_mir/build/expr/as_rvalue.rs index fb547332c5f..8dc7745cd9e 100644 --- a/src/librustc_mir/build/expr/as_rvalue.rs +++ b/src/librustc_mir/build/expr/as_rvalue.rs @@ -38,7 +38,7 @@ pub fn as_local_rvalue(&mut self, block: BasicBlock, expr: M) } /// Compile `expr`, yielding an rvalue. - pub fn as_rvalue(&mut self, block: BasicBlock, scope: Option, expr: M) + pub fn as_rvalue(&mut self, block: BasicBlock, scope: Option>, expr: M) -> BlockAnd> where M: Mirror<'tcx, Output = Expr<'tcx>> { @@ -48,7 +48,7 @@ pub fn as_rvalue(&mut self, block: BasicBlock, scope: Option, exp fn expr_as_rvalue(&mut self, mut block: BasicBlock, - scope: Option, + scope: Option>, expr: Expr<'tcx>) -> BlockAnd> { debug!("expr_as_rvalue(block={:?}, expr={:?})", block, expr); diff --git a/src/librustc_mir/build/expr/as_temp.rs b/src/librustc_mir/build/expr/as_temp.rs index a334923546f..db4561af734 100644 --- a/src/librustc_mir/build/expr/as_temp.rs +++ b/src/librustc_mir/build/expr/as_temp.rs @@ -21,7 +21,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { /// up rvalues so as to freeze the value that will be consumed. pub fn as_temp(&mut self, block: BasicBlock, - temp_lifetime: Option, + temp_lifetime: Option>, expr: M) -> BlockAnd> where M: Mirror<'tcx, Output = Expr<'tcx>> @@ -32,7 +32,7 @@ pub fn as_temp(&mut self, fn expr_as_temp(&mut self, mut block: BasicBlock, - temp_lifetime: Option, + temp_lifetime: Option>, expr: Expr<'tcx>) -> BlockAnd> { debug!("expr_as_temp(block={:?}, expr={:?})", block, expr); diff --git a/src/librustc_mir/build/mod.rs b/src/librustc_mir/build/mod.rs index f3a258a8ca5..6c01e4315f3 100644 --- a/src/librustc_mir/build/mod.rs +++ b/src/librustc_mir/build/mod.rs @@ -137,10 +137,10 @@ pub fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>, let mut builder = Builder::new(hir, span, arguments.len(), return_ty); let call_site_extent = - tcx.region_maps().lookup_code_extent( + tcx.intern_code_extent( CodeExtentData::CallSiteScope { fn_id: fn_id, body_id: body.value.id }); let arg_extent = - tcx.region_maps().lookup_code_extent( + tcx.intern_code_extent( CodeExtentData::ParameterScope { fn_id: fn_id, body_id: body.value.id }); let mut block = START_BLOCK; unpack!(block = builder.in_scope(call_site_extent, block, |builder| { @@ -205,8 +205,8 @@ pub fn construct_const<'a, 'gcx, 'tcx>(hir: Cx<'a, 'gcx, 'tcx>, let mut builder = Builder::new(hir, span, 0, ty); let region_maps = tcx.region_maps(); - let extent = region_maps.temporary_scope(ast_expr.id) - .unwrap_or(region_maps.item_extent(owner_id)); + let extent = region_maps.temporary_scope(tcx, ast_expr.id) + .unwrap_or(tcx.item_extent(owner_id)); let mut block = START_BLOCK; let _ = builder.in_scope(extent, block, |builder| { let expr = builder.hir.mirror(ast_expr); @@ -290,7 +290,7 @@ fn finish(self, fn args_and_body(&mut self, mut block: BasicBlock, arguments: &[(Ty<'gcx>, Option<&'gcx hir::Pat>)], - argument_extent: CodeExtent, + argument_extent: CodeExtent<'tcx>, ast_body: &'gcx hir::Expr) -> BlockAnd<()> { diff --git a/src/librustc_mir/build/scope.rs b/src/librustc_mir/build/scope.rs index 2a024454ecb..fcd06835d98 100644 --- a/src/librustc_mir/build/scope.rs +++ b/src/librustc_mir/build/scope.rs @@ -102,7 +102,7 @@ pub struct Scope<'tcx> { visibility_scope: VisibilityScope, /// the extent of this scope within source code. - extent: CodeExtent, + extent: CodeExtent<'tcx>, /// Whether there's anything to do for the cleanup path, that is, /// when unwinding through this scope. This includes destructors, @@ -137,7 +137,7 @@ pub struct Scope<'tcx> { free: Option>, /// The cache for drop chain on “normal” exit into a particular BasicBlock. - cached_exits: FxHashMap<(BasicBlock, CodeExtent), BasicBlock>, + cached_exits: FxHashMap<(BasicBlock, CodeExtent<'tcx>), BasicBlock>, } struct DropData<'tcx> { @@ -180,7 +180,7 @@ struct FreeData<'tcx> { #[derive(Clone, Debug)] pub struct BreakableScope<'tcx> { /// Extent of the loop - pub extent: CodeExtent, + pub extent: CodeExtent<'tcx>, /// Where the body of the loop begins. `None` if block pub continue_block: Option, /// Block to branch into when the loop or block terminates (either by being `break`-en out @@ -248,10 +248,10 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { /// /// Returns the might_break attribute of the BreakableScope used. pub fn in_breakable_scope(&mut self, - loop_block: Option, - break_block: BasicBlock, - break_destination: Lvalue<'tcx>, - f: F) -> R + loop_block: Option, + break_block: BasicBlock, + break_destination: Lvalue<'tcx>, + f: F) -> R where F: FnOnce(&mut Builder<'a, 'gcx, 'tcx>) -> R { let extent = self.topmost_scope(); @@ -270,7 +270,7 @@ pub fn in_breakable_scope(&mut self, /// Convenience wrapper that pushes a scope and then executes `f` /// to build its contents, popping the scope afterwards. - pub fn in_scope(&mut self, extent: CodeExtent, mut block: BasicBlock, f: F) -> BlockAnd + pub fn in_scope(&mut self, extent: CodeExtent<'tcx>, mut block: BasicBlock, f: F) -> BlockAnd where F: FnOnce(&mut Builder<'a, 'gcx, 'tcx>) -> BlockAnd { debug!("in_scope(extent={:?}, block={:?})", extent, block); @@ -285,7 +285,7 @@ pub fn in_scope(&mut self, extent: CodeExtent, mut block: BasicBlock, f: F /// scope and call `pop_scope` afterwards. Note that these two /// calls must be paired; using `in_scope` as a convenience /// wrapper maybe preferable. - pub fn push_scope(&mut self, extent: CodeExtent) { + pub fn push_scope(&mut self, extent: CodeExtent<'tcx>) { debug!("push_scope({:?})", extent); let vis_scope = self.visibility_scope; self.scopes.push(Scope { @@ -302,7 +302,7 @@ pub fn push_scope(&mut self, extent: CodeExtent) { /// drops onto the end of `block` that are needed. This must /// match 1-to-1 with `push_scope`. pub fn pop_scope(&mut self, - extent: CodeExtent, + extent: CodeExtent<'tcx>, mut block: BasicBlock) -> BlockAnd<()> { debug!("pop_scope({:?}, {:?})", extent, block); @@ -326,7 +326,7 @@ pub fn pop_scope(&mut self, /// module comment for details. pub fn exit_scope(&mut self, span: Span, - extent: CodeExtent, + extent: CodeExtent<'tcx>, mut block: BasicBlock, target: BasicBlock) { debug!("exit_scope(extent={:?}, block={:?}, target={:?})", extent, block, target); @@ -387,7 +387,7 @@ pub fn new_visibility_scope(&mut self, span: Span) -> VisibilityScope { /// resolving `break` and `continue`. pub fn find_breakable_scope(&mut self, span: Span, - label: CodeExtent) + label: CodeExtent<'tcx>) -> &mut BreakableScope<'tcx> { // find the loop-scope with the correct id self.breakable_scopes.iter_mut() @@ -407,11 +407,11 @@ pub fn source_info(&self, span: Span) -> SourceInfo { /// Returns the extent of the scope which should be exited by a /// return. - pub fn extent_of_return_scope(&self) -> CodeExtent { + pub fn extent_of_return_scope(&self) -> CodeExtent<'tcx> { // The outermost scope (`scopes[0]`) will be the `CallSiteScope`. // We want `scopes[1]`, which is the `ParameterScope`. assert!(self.scopes.len() >= 2); - assert!(match self.hir.tcx().region_maps().code_extent_data(self.scopes[1].extent) { + assert!(match *self.scopes[1].extent { CodeExtentData::ParameterScope { .. } => true, _ => false, }); @@ -420,7 +420,7 @@ pub fn extent_of_return_scope(&self) -> CodeExtent { /// Returns the topmost active scope, which is known to be alive until /// the next scope expression. - pub fn topmost_scope(&self) -> CodeExtent { + pub fn topmost_scope(&self) -> CodeExtent<'tcx> { self.scopes.last().expect("topmost_scope: no scopes present").extent } @@ -430,7 +430,7 @@ pub fn topmost_scope(&self) -> CodeExtent { /// `extent`. pub fn schedule_drop(&mut self, span: Span, - extent: CodeExtent, + extent: CodeExtent<'tcx>, lvalue: &Lvalue<'tcx>, lvalue_ty: Ty<'tcx>) { let needs_drop = self.hir.needs_drop(lvalue_ty); @@ -499,7 +499,7 @@ pub fn schedule_drop(&mut self, scope.needs_cleanup = true; } let tcx = self.hir.tcx(); - let extent_span = extent.span(&tcx.region_maps(), &tcx.hir).unwrap(); + let extent_span = extent.span(&tcx.hir).unwrap(); // Attribute scope exit drops to scope's closing brace let scope_end = Span { lo: extent_span.hi, .. extent_span}; scope.drops.push(DropData { @@ -520,7 +520,7 @@ pub fn schedule_drop(&mut self, /// There may only be one “free” scheduled in any given scope. pub fn schedule_box_free(&mut self, span: Span, - extent: CodeExtent, + extent: CodeExtent<'tcx>, value: &Lvalue<'tcx>, item_ty: Ty<'tcx>) { for scope in self.scopes.iter_mut().rev() { diff --git a/src/librustc_mir/hair/cx/block.rs b/src/librustc_mir/hair/cx/block.rs index 1be07fba2b0..15c2df55cf3 100644 --- a/src/librustc_mir/hair/cx/block.rs +++ b/src/librustc_mir/hair/cx/block.rs @@ -24,7 +24,7 @@ fn make_mirror<'a, 'gcx>(self, cx: &mut Cx<'a, 'gcx, 'tcx>) -> Block<'tcx> { let stmts = mirror_stmts(cx, self.id, &*self.stmts); Block { targeted_by_break: self.targeted_by_break, - extent: cx.tcx.region_maps().node_extent(self.id), + extent: cx.tcx.node_extent(self.id), span: self.span, stmts: stmts, expr: self.expr.to_ref(), @@ -44,7 +44,7 @@ fn mirror_stmts<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, result.push(StmtRef::Mirror(Box::new(Stmt { span: stmt.span, kind: StmtKind::Expr { - scope: cx.tcx.region_maps().node_extent(id), + scope: cx.tcx.node_extent(id), expr: expr.to_ref(), }, }))) @@ -60,14 +60,14 @@ fn mirror_stmts<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, first_statement_index: index as u32, }); let remainder_extent = - cx.tcx.region_maps().lookup_code_extent(remainder_extent); + cx.tcx.intern_code_extent(remainder_extent); let pattern = Pattern::from_hir(cx.tcx, cx.tables(), &local.pat); result.push(StmtRef::Mirror(Box::new(Stmt { span: stmt.span, kind: StmtKind::Let { remainder_scope: remainder_extent, - init_scope: cx.tcx.region_maps().node_extent(id), + init_scope: cx.tcx.node_extent(id), pattern: pattern, initializer: local.init.to_ref(), }, @@ -84,7 +84,7 @@ pub fn to_expr_ref<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, block: &'tcx hir::Block) -> ExprRef<'tcx> { let block_ty = cx.tables().node_id_to_type(block.id); - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(block.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, block.id); let expr = Expr { ty: block_ty, temp_lifetime: temp_lifetime, diff --git a/src/librustc_mir/hair/cx/expr.rs b/src/librustc_mir/hair/cx/expr.rs index ad51530b191..e37df8822c8 100644 --- a/src/librustc_mir/hair/cx/expr.rs +++ b/src/librustc_mir/hair/cx/expr.rs @@ -26,8 +26,8 @@ impl<'tcx> Mirror<'tcx> for &'tcx hir::Expr { type Output = Expr<'tcx>; fn make_mirror<'a, 'gcx>(self, cx: &mut Cx<'a, 'gcx, 'tcx>) -> Expr<'tcx> { - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(self.id); - let expr_extent = cx.tcx.region_maps().node_extent(self.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, self.id); + let expr_extent = cx.tcx.node_extent(self.id); debug!("Expr::make_mirror(): id={}, span={:?}", self.id, self.span); @@ -216,7 +216,7 @@ fn make_mirror<'a, 'gcx>(self, cx: &mut Cx<'a, 'gcx, 'tcx>) -> Expr<'tcx> { }; // Finally, create a destruction scope, if any. - if let Some(extent) = cx.tcx.region_maps().opt_destruction_extent(self.id) { + if let Some(extent) = cx.tcx.opt_destruction_extent(self.id) { expr = Expr { temp_lifetime: temp_lifetime, temp_lifetime_was_shrunk: was_shrunk, @@ -238,7 +238,7 @@ fn make_mirror_unadjusted<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, expr: &'tcx hir::Expr) -> Expr<'tcx> { let expr_ty = cx.tables().expr_ty(expr); - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(expr.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, expr.id); let kind = match expr.node { // Here comes the interesting stuff: @@ -610,7 +610,7 @@ fn make_mirror_unadjusted<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, match dest.target_id { hir::ScopeTarget::Block(target_id) | hir::ScopeTarget::Loop(hir::LoopIdResult::Ok(target_id)) => ExprKind::Break { - label: cx.tcx.region_maps().node_extent(target_id), + label: cx.tcx.node_extent(target_id), value: value.to_ref(), }, hir::ScopeTarget::Loop(hir::LoopIdResult::Err(err)) => @@ -621,7 +621,7 @@ fn make_mirror_unadjusted<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, match dest.target_id { hir::ScopeTarget::Block(_) => bug!("cannot continue to blocks"), hir::ScopeTarget::Loop(hir::LoopIdResult::Ok(loop_id)) => ExprKind::Continue { - label: cx.tcx.region_maps().node_extent(loop_id), + label: cx.tcx.node_extent(loop_id), }, hir::ScopeTarget::Loop(hir::LoopIdResult::Err(err)) => bug!("invalid loop id for continue: {}", err) @@ -686,7 +686,7 @@ fn make_mirror_unadjusted<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, hir::ExprBox(ref value) => { ExprKind::Box { value: value.to_ref(), - value_extents: cx.tcx.region_maps().node_extent(value.id), + value_extents: cx.tcx.node_extent(value.id), } } hir::ExprArray(ref fields) => ExprKind::Array { fields: fields.to_ref() }, @@ -707,7 +707,7 @@ fn method_callee<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, method_call: ty::MethodCall) -> Expr<'tcx> { let callee = cx.tables().method_map[&method_call]; - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(expr.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, expr.id); Expr { temp_lifetime: temp_lifetime, temp_lifetime_was_shrunk: was_shrunk, @@ -791,7 +791,7 @@ fn convert_var<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, expr: &'tcx hir::Expr, def: Def) -> ExprKind<'tcx> { - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(expr.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, expr.id); match def { Def::Local(def_id) => { @@ -827,8 +827,8 @@ fn convert_var<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, // FIXME we're just hard-coding the idea that the // signature will be &self or &mut self and hence will // have a bound region with number 0 - let region = ty::Region::ReFree(ty::FreeRegion { - scope: Some(cx.tcx.region_maps().node_extent(body_id)), + let region = ty::ReFree(ty::FreeRegion { + scope: Some(cx.tcx.node_extent(body_id)), bound_region: ty::BoundRegion::BrAnon(0), }); let region = cx.tcx.mk_region(region); @@ -979,7 +979,7 @@ fn overloaded_operator<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, PassArgs::ByRef => { let region = cx.tcx.node_scope_region(expr.id); let (temp_lifetime, was_shrunk) = - cx.tcx.region_maps().temporary_scope2(expr.id); + cx.tcx.region_maps().temporary_scope2(cx.tcx, expr.id); argrefs.extend(args.iter() .map(|arg| { let arg_ty = cx.tables().expr_ty_adjusted(arg); @@ -1031,7 +1031,7 @@ fn overloaded_lvalue<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, // construct the complete expression `foo()` for the overloaded call, // which will yield the &T type - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(expr.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, expr.id); let ref_kind = overloaded_operator(cx, expr, method_call, pass_args, receiver, args); let ref_expr = Expr { temp_lifetime: temp_lifetime, @@ -1056,7 +1056,7 @@ fn capture_freevar<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, closure_expr_id: closure_expr.id, }; let upvar_capture = cx.tables().upvar_capture(upvar_id).unwrap(); - let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(closure_expr.id); + let (temp_lifetime, was_shrunk) = cx.tcx.region_maps().temporary_scope2(cx.tcx, closure_expr.id); let var_ty = cx.tables().node_id_to_type(id_var); let captured_var = Expr { temp_lifetime: temp_lifetime, diff --git a/src/librustc_mir/hair/mod.rs b/src/librustc_mir/hair/mod.rs index a3982efd2d6..0e8992e62ea 100644 --- a/src/librustc_mir/hair/mod.rs +++ b/src/librustc_mir/hair/mod.rs @@ -32,7 +32,7 @@ #[derive(Clone, Debug)] pub struct Block<'tcx> { pub targeted_by_break: bool, - pub extent: CodeExtent, + pub extent: CodeExtent<'tcx>, pub span: Span, pub stmts: Vec>, pub expr: Option>, @@ -53,7 +53,7 @@ pub struct Stmt<'tcx> { pub enum StmtKind<'tcx> { Expr { /// scope for this statement; may be used as lifetime of temporaries - scope: CodeExtent, + scope: CodeExtent<'tcx>, /// expression being evaluated in this statement expr: ExprRef<'tcx>, @@ -62,11 +62,11 @@ pub enum StmtKind<'tcx> { Let { /// scope for variables bound in this let; covers this and /// remaining statements in block - remainder_scope: CodeExtent, + remainder_scope: CodeExtent<'tcx>, /// scope for the initialization itself; might be used as /// lifetime of temporaries - init_scope: CodeExtent, + init_scope: CodeExtent<'tcx>, /// let = ... pattern: Pattern<'tcx>, @@ -97,7 +97,7 @@ pub struct Expr<'tcx> { /// lifetime of this expression if it should be spilled into a /// temporary; should be None only if in a constant context - pub temp_lifetime: Option, + pub temp_lifetime: Option>, /// whether this temp lifetime was shrunk by #36082. pub temp_lifetime_was_shrunk: bool, @@ -112,12 +112,12 @@ pub struct Expr<'tcx> { #[derive(Clone, Debug)] pub enum ExprKind<'tcx> { Scope { - extent: CodeExtent, + extent: CodeExtent<'tcx>, value: ExprRef<'tcx>, }, Box { value: ExprRef<'tcx>, - value_extents: CodeExtent, + value_extents: CodeExtent<'tcx>, }, Call { ty: ty::Ty<'tcx>, @@ -205,16 +205,16 @@ pub enum ExprKind<'tcx> { id: DefId, }, Borrow { - region: &'tcx Region, + region: Region<'tcx>, borrow_kind: BorrowKind, arg: ExprRef<'tcx>, }, Break { - label: CodeExtent, + label: CodeExtent<'tcx>, value: Option>, }, Continue { - label: CodeExtent, + label: CodeExtent<'tcx>, }, Return { value: Option>, diff --git a/src/librustc_mir/mir_map.rs b/src/librustc_mir/mir_map.rs index cbd88733e82..1abae515ae6 100644 --- a/src/librustc_mir/mir_map.rs +++ b/src/librustc_mir/mir_map.rs @@ -252,8 +252,8 @@ fn closure_self_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, -> Ty<'tcx> { let closure_ty = tcx.body_tables(body_id).node_id_to_type(closure_expr_id); - let region = ty::Region::ReFree(ty::FreeRegion { - scope: Some(tcx.region_maps().item_extent(body_id.node_id)), + let region = ty::ReFree(ty::FreeRegion { + scope: Some(tcx.item_extent(body_id.node_id)), bound_region: ty::BoundRegion::BrEnv, }); let region = tcx.mk_region(region); diff --git a/src/librustc_passes/consts.rs b/src/librustc_passes/consts.rs index f275b4cafaf..cb0625ceccf 100644 --- a/src/librustc_passes/consts.rs +++ b/src/librustc_passes/consts.rs @@ -480,7 +480,7 @@ fn borrow(&mut self, borrow_id: ast::NodeId, _borrow_span: Span, cmt: mc::cmt<'tcx>, - _loan_region: &'tcx ty::Region, + _loan_region: ty::Region<'tcx>, bk: ty::BorrowKind, loan_cause: euv::LoanCause) { // Kind of hacky, but we allow Unsafe coercions in constants. diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index d672637649e..c89e3ca8b68 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -53,7 +53,7 @@ fn get_type_parameter_bounds(&self, span: Span, def_id: DefId) /// What lifetime should we use when a lifetime is omitted (and not elided)? fn re_infer(&self, span: Span, _def: Option<&ty::RegionParameterDef>) - -> Option<&'tcx ty::Region>; + -> Option>; /// What type should we use when a type is omitted? fn ty_infer(&self, span: Span) -> Ty<'tcx>; @@ -104,7 +104,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { pub fn ast_region_to_region(&self, lifetime: &hir::Lifetime, def: Option<&ty::RegionParameterDef>) - -> &'tcx ty::Region + -> ty::Region<'tcx> { let tcx = self.tcx(); let r = match tcx.named_region_map.defs.get(&lifetime.id) { @@ -133,7 +133,7 @@ pub fn ast_region_to_region(&self, Some(&rl::Region::Free(scope, id)) => { let name = tcx.hir.name(id); tcx.mk_region(ty::ReFree(ty::FreeRegion { - scope: Some(scope.to_code_extent(&tcx.region_maps())), + scope: Some(scope.to_code_extent(tcx)), bound_region: ty::BrNamed(tcx.hir.local_def_id(id), name) })) @@ -1342,7 +1342,7 @@ pub fn ty_of_closure(&self, fn compute_object_lifetime_bound(&self, span: Span, existential_predicates: ty::Binder<&'tcx ty::Slice>>) - -> Option<&'tcx ty::Region> // if None, use the default + -> Option> // if None, use the default { let tcx = self.tcx(); @@ -1489,7 +1489,7 @@ fn report_lifetime_number_error(tcx: TyCtxt, span: Span, number: usize, expected // and return from functions in multiple places. #[derive(PartialEq, Eq, Clone, Debug)] pub struct Bounds<'tcx> { - pub region_bounds: Vec<&'tcx ty::Region>, + pub region_bounds: Vec>, pub implicitly_sized: bool, pub trait_bounds: Vec>, pub projection_bounds: Vec>, @@ -1533,7 +1533,7 @@ pub fn predicates(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, param_ty: Ty<'tcx>) pub enum ExplicitSelf<'tcx> { ByValue, - ByReference(&'tcx ty::Region, hir::Mutability), + ByReference(ty::Region<'tcx>, hir::Mutability), ByBox } diff --git a/src/librustc_typeck/check/closure.rs b/src/librustc_typeck/check/closure.rs index 5d24df136ff..45b0a571bd0 100644 --- a/src/librustc_typeck/check/closure.rs +++ b/src/librustc_typeck/check/closure.rs @@ -73,7 +73,7 @@ fn check_closure(&self, debug!("check_closure: expr.id={:?} closure_type={:?}", expr.id, closure_type); - let extent = self.tcx.region_maps().call_site_extent(expr.id, body.value.id); + let extent = self.tcx.call_site_extent(expr.id, body.value.id); let fn_sig = self.tcx.liberate_late_bound_regions(Some(extent), &sig); let fn_sig = self.inh.normalize_associated_types_in(body.value.span, body.value.id, &fn_sig); diff --git a/src/librustc_typeck/check/coercion.rs b/src/librustc_typeck/check/coercion.rs index d21b5f739bd..d42532a714e 100644 --- a/src/librustc_typeck/check/coercion.rs +++ b/src/librustc_typeck/check/coercion.rs @@ -250,7 +250,7 @@ fn coerce_borrowed_pointer(&self, exprs: &[E], a: Ty<'tcx>, b: Ty<'tcx>, - r_b: &'tcx ty::Region, + r_b: ty::Region<'tcx>, mt_b: TypeAndMut<'tcx>) -> CoerceResult<'tcx> where E: AsCoercionSite diff --git a/src/librustc_typeck/check/dropck.rs b/src/librustc_typeck/check/dropck.rs index 4c9874cfa5a..e4408413ee6 100644 --- a/src/librustc_typeck/check/dropck.rs +++ b/src/librustc_typeck/check/dropck.rs @@ -271,7 +271,7 @@ pub fn check_safety_of_destructor_if_necessary<'a, 'gcx, 'tcx>( rcx: &mut RegionCtxt<'a, 'gcx, 'tcx>, ty: ty::Ty<'tcx>, span: Span, - scope: region::CodeExtent) + scope: region::CodeExtent<'tcx>) -> Result<(), ErrorReported> { debug!("check_safety_of_destructor_if_necessary typ: {:?} scope: {:?}", diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 8b366fd5a27..729d25aaef5 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -781,7 +781,7 @@ fn typeck_tables_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, check_abi(tcx, span, fn_sig.abi()); // Compute the fty from point of view of inside fn. - let fn_scope = inh.tcx.region_maps().call_site_extent(id, body_id.node_id); + let fn_scope = inh.tcx.call_site_extent(id, body_id.node_id); let fn_sig = fn_sig.subst(inh.tcx, &inh.parameter_environment.free_substs); let fn_sig = @@ -1549,7 +1549,7 @@ fn get_type_parameter_bounds(&self, _: Span, def_id: DefId) } fn re_infer(&self, span: Span, def: Option<&ty::RegionParameterDef>) - -> Option<&'tcx ty::Region> { + -> Option> { let v = match def { Some(def) => infer::EarlyBoundRegion(span, def.name, def.issue_32330), None => infer::MiscVariable(span) @@ -1963,7 +1963,7 @@ pub fn opt_node_ty_substs(&self, /// outlive the region `r`. pub fn register_region_obligation(&self, ty: Ty<'tcx>, - region: &'tcx ty::Region, + region: ty::Region<'tcx>, cause: traits::ObligationCause<'tcx>) { let mut fulfillment_cx = self.fulfillment_cx.borrow_mut(); diff --git a/src/librustc_typeck/check/regionck.rs b/src/librustc_typeck/check/regionck.rs index a6f72898a54..9a978934dda 100644 --- a/src/librustc_typeck/check/regionck.rs +++ b/src/librustc_typeck/check/regionck.rs @@ -171,15 +171,15 @@ pub fn regionck_fn(&self, pub struct RegionCtxt<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { pub fcx: &'a FnCtxt<'a, 'gcx, 'tcx>, - region_bound_pairs: Vec<(&'tcx ty::Region, GenericKind<'tcx>)>, + region_bound_pairs: Vec<(ty::Region<'tcx>, GenericKind<'tcx>)>, - free_region_map: FreeRegionMap, + free_region_map: FreeRegionMap<'tcx>, // id of innermost fn body id body_id: ast::NodeId, // call_site scope of innermost fn - call_site_scope: Option, + call_site_scope: Option>, // id of innermost fn or loop repeating_scope: ast::NodeId, @@ -215,7 +215,8 @@ pub fn new(fcx: &'a FnCtxt<'a, 'gcx, 'tcx>, } } - fn set_call_site_scope(&mut self, call_site_scope: Option) -> Option { + fn set_call_site_scope(&mut self, call_site_scope: Option>) + -> Option> { mem::replace(&mut self.call_site_scope, call_site_scope) } @@ -276,7 +277,7 @@ fn visit_fn_body(&mut self, let body_id = body.id(); - let call_site = self.tcx.region_maps().lookup_code_extent( + let call_site = self.tcx.intern_code_extent( region::CodeExtentData::CallSiteScope { fn_id: id, body_id: body_id.node_id }); let old_call_site_scope = self.set_call_site_scope(Some(call_site)); @@ -302,7 +303,7 @@ fn visit_fn_body(&mut self, let old_body_id = self.set_body_id(body_id.node_id); self.relate_free_regions(&fn_sig_tys[..], body_id.node_id, span); - self.link_fn_args(self.tcx.region_maps().node_extent(body_id.node_id), &body.arguments); + self.link_fn_args(self.tcx.node_extent(body_id.node_id), &body.arguments); self.visit_body(body); self.visit_region_obligations(body_id.node_id); @@ -868,7 +869,7 @@ fn constrain_call<'b, I: Iterator>(&mut self, // call occurs. // // FIXME(#6268) to support nested method calls, should be callee_id - let callee_scope = self.tcx.region_maps().node_extent(call_expr.id); + let callee_scope = self.tcx.node_extent(call_expr.id); let callee_region = self.tcx.mk_region(ty::ReScope(callee_scope)); debug!("callee_region={:?}", callee_region); @@ -982,8 +983,8 @@ fn constrain_autoderefs(&mut self, pub fn mk_subregion_due_to_dereference(&mut self, deref_span: Span, - minimum_lifetime: &'tcx ty::Region, - maximum_lifetime: &'tcx ty::Region) { + minimum_lifetime: ty::Region<'tcx>, + maximum_lifetime: ty::Region<'tcx>) { self.sub_regions(infer::DerefPointer(deref_span), minimum_lifetime, maximum_lifetime) } @@ -1021,7 +1022,7 @@ fn constrain_index(&mut self, debug!("constrain_index(index_expr=?, indexed_ty={}", self.ty_to_string(indexed_ty)); - let r_index_expr = ty::ReScope(self.tcx.region_maps().node_extent(index_expr.id)); + let r_index_expr = ty::ReScope(self.tcx.node_extent(index_expr.id)); if let ty::TyRef(r_ptr, mt) = indexed_ty.sty { match mt.ty.sty { ty::TySlice(_) | ty::TyStr => { @@ -1038,7 +1039,7 @@ fn constrain_index(&mut self, fn type_of_node_must_outlive(&mut self, origin: infer::SubregionOrigin<'tcx>, id: ast::NodeId, - minimum_lifetime: &'tcx ty::Region) + minimum_lifetime: ty::Region<'tcx>) { // Try to resolve the type. If we encounter an error, then typeck // is going to fail anyway, so just stop here and let typeck @@ -1101,7 +1102,7 @@ fn link_match(&self, discr: &hir::Expr, arms: &[hir::Arm]) { /// Computes the guarantors for any ref bindings in a match and /// then ensures that the lifetime of the resulting pointer is /// linked to the lifetime of its guarantor (if any). - fn link_fn_args(&self, body_scope: CodeExtent, args: &[hir::Arg]) { + fn link_fn_args(&self, body_scope: CodeExtent<'tcx>, args: &[hir::Arg]) { debug!("regionck::link_fn_args(body_scope={:?})", body_scope); let mc = mc::MemCategorizationContext::new(self); for arg in args { @@ -1167,7 +1168,7 @@ fn link_autoref(&self, /// must outlive `callee_scope`. fn link_by_ref(&self, expr: &hir::Expr, - callee_scope: CodeExtent) { + callee_scope: CodeExtent<'tcx>) { debug!("link_by_ref(expr={:?}, callee_scope={:?})", expr, callee_scope); let mc = mc::MemCategorizationContext::new(self); @@ -1200,7 +1201,7 @@ fn link_region_from_node_type(&self, /// between regions, as explained in `link_reborrowed_region()`. fn link_region(&self, span: Span, - borrow_region: &'tcx ty::Region, + borrow_region: ty::Region<'tcx>, borrow_kind: ty::BorrowKind, borrow_cmt: mc::cmt<'tcx>) { let mut borrow_cmt = borrow_cmt; @@ -1297,10 +1298,10 @@ fn link_region(&self, /// recurse and process `ref_cmt` (see case 2 above). fn link_reborrowed_region(&self, span: Span, - borrow_region: &'tcx ty::Region, + borrow_region: ty::Region<'tcx>, borrow_kind: ty::BorrowKind, ref_cmt: mc::cmt<'tcx>, - ref_region: &'tcx ty::Region, + ref_region: ty::Region<'tcx>, mut ref_kind: ty::BorrowKind, note: mc::Note) -> Option<(mc::cmt<'tcx>, ty::BorrowKind)> @@ -1411,7 +1412,7 @@ fn substs_wf_in_scope(&mut self, origin: infer::ParameterOrigin, substs: &Substs<'tcx>, expr_span: Span, - expr_region: &'tcx ty::Region) { + expr_region: ty::Region<'tcx>) { debug!("substs_wf_in_scope(substs={:?}, \ expr_region={:?}, \ origin={:?}, \ @@ -1436,7 +1437,7 @@ fn substs_wf_in_scope(&mut self, pub fn type_must_outlive(&self, origin: infer::SubregionOrigin<'tcx>, ty: Ty<'tcx>, - region: &'tcx ty::Region) + region: ty::Region<'tcx>) { let ty = self.resolve_type(ty); @@ -1454,7 +1455,7 @@ pub fn type_must_outlive(&self, fn components_must_outlive(&self, origin: infer::SubregionOrigin<'tcx>, components: Vec>, - region: &'tcx ty::Region) + region: ty::Region<'tcx>) { for component in components { let origin = origin.clone(); @@ -1485,7 +1486,7 @@ fn components_must_outlive(&self, fn param_ty_must_outlive(&self, origin: infer::SubregionOrigin<'tcx>, - region: &'tcx ty::Region, + region: ty::Region<'tcx>, param_ty: ty::ParamTy) { debug!("param_ty_must_outlive(region={:?}, param_ty={:?}, origin={:?})", region, param_ty, origin); @@ -1497,7 +1498,7 @@ fn param_ty_must_outlive(&self, fn projection_must_outlive(&self, origin: infer::SubregionOrigin<'tcx>, - region: &'tcx ty::Region, + region: ty::Region<'tcx>, projection_ty: ty::ProjectionTy<'tcx>) { debug!("projection_must_outlive(region={:?}, projection_ty={:?}, origin={:?})", @@ -1622,7 +1623,7 @@ fn param_bound(&self, param_ty: ty::ParamTy) -> VerifyBound<'tcx> { fn projection_declared_bounds(&self, span: Span, projection_ty: ty::ProjectionTy<'tcx>) - -> Vec<&'tcx ty::Region> + -> Vec> { // First assemble bounds from where clauses and traits. @@ -1637,7 +1638,7 @@ fn projection_declared_bounds(&self, fn projection_bound(&self, span: Span, - declared_bounds: Vec<&'tcx ty::Region>, + declared_bounds: Vec>, projection_ty: ty::ProjectionTy<'tcx>) -> VerifyBound<'tcx> { debug!("projection_bound(declared_bounds={:?}, projection_ty={:?})", @@ -1673,7 +1674,7 @@ fn recursive_type_bound(&self, span: Span, ty: Ty<'tcx>) -> VerifyBound<'tcx> { } fn declared_generic_bounds_from_env(&self, generic: GenericKind<'tcx>) - -> Vec<&'tcx ty::Region> + -> Vec> { let param_env = &self.parameter_environment; @@ -1707,7 +1708,7 @@ fn declared_generic_bounds_from_env(&self, generic: GenericKind<'tcx>) fn declared_projection_bounds_from_trait(&self, span: Span, projection_ty: ty::ProjectionTy<'tcx>) - -> Vec<&'tcx ty::Region> + -> Vec> { debug!("projection_bounds(projection_ty={:?})", projection_ty); diff --git a/src/librustc_typeck/check/upvar.rs b/src/librustc_typeck/check/upvar.rs index 7b146842671..a2c9b7876aa 100644 --- a/src/librustc_typeck/check/upvar.rs +++ b/src/librustc_typeck/check/upvar.rs @@ -536,7 +536,7 @@ fn borrow(&mut self, borrow_id: ast::NodeId, _borrow_span: Span, cmt: mc::cmt<'tcx>, - _loan_region: &'tcx ty::Region, + _loan_region: ty::Region<'tcx>, bk: ty::BorrowKind, _loan_cause: euv::LoanCause) { diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index f306d5dd70f..1887eaef360 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -341,7 +341,7 @@ fn check_item_fn(&mut self, let predicates = fcx.instantiate_bounds(item.span, def_id, free_substs); let mut implied_bounds = vec![]; - let free_id_outlive = fcx.tcx.region_maps().call_site_extent(item.id, body_id.node_id); + let free_id_outlive = fcx.tcx.call_site_extent(item.id, body_id.node_id); this.check_fn_or_method(fcx, item.span, sig, &predicates, Some(free_id_outlive), &mut implied_bounds); implied_bounds @@ -429,7 +429,7 @@ fn check_fn_or_method<'fcx, 'tcx>(&mut self, span: Span, sig: ty::PolyFnSig<'tcx>, predicates: &ty::InstantiatedPredicates<'tcx>, - free_id_outlive: Option, + free_id_outlive: Option>, implied_bounds: &mut Vec>) { let free_substs = &fcx.parameter_environment.free_substs; @@ -453,7 +453,7 @@ fn check_method_receiver<'fcx, 'tcx>(&mut self, fcx: &FnCtxt<'fcx, 'gcx, 'tcx>, method_sig: &hir::MethodSig, method: &ty::AssociatedItem, - free_id_outlive: Option, + free_id_outlive: Option>, self_ty: ty::Ty<'tcx>) { // check that the type of the method's receiver matches the diff --git a/src/librustc_typeck/check/writeback.rs b/src/librustc_typeck/check/writeback.rs index 35b2e8f8afc..ab2151544fc 100644 --- a/src/librustc_typeck/check/writeback.rs +++ b/src/librustc_typeck/check/writeback.rs @@ -76,7 +76,7 @@ struct WritebackCx<'cx, 'gcx: 'cx+'tcx, 'tcx: 'cx> { // early-bound versions of them, visible from the // outside of the function. This is needed by, and // only populated if there are any `impl Trait`. - free_to_bound_regions: DefIdMap<&'gcx ty::Region>, + free_to_bound_regions: DefIdMap>, body: &'gcx hir::Body, } @@ -275,7 +275,9 @@ fn visit_lints(&mut self) { } fn visit_free_region_map(&mut self) { - self.tables.free_region_map = self.fcx.tables.borrow().free_region_map.clone(); + let free_region_map = self.tcx().lift_to_global(&self.fcx.tables.borrow().free_region_map); + let free_region_map = free_region_map.expect("all regions in free-region-map are global"); + self.tables.free_region_map = free_region_map; } fn visit_anon_types(&mut self) { @@ -522,7 +524,7 @@ fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> { // FIXME This should be carefully checked // We could use `self.report_error` but it doesn't accept a ty::Region, right now. - fn fold_region(&mut self, r: &'tcx ty::Region) -> &'tcx ty::Region { + fn fold_region(&mut self, r: ty::Region<'tcx>) -> ty::Region<'tcx> { match self.infcx.fully_resolve(&r) { Ok(r) => r, Err(_) => { diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 3cd8b8bd489..0d75a1ecf3d 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -215,7 +215,7 @@ fn get_free_substs(&self) -> Option<&Substs<'tcx>> { } fn re_infer(&self, _span: Span, _def: Option<&ty::RegionParameterDef>) - -> Option<&'tcx ty::Region> { + -> Option> { None } diff --git a/src/librustc_typeck/constrained_type_params.rs b/src/librustc_typeck/constrained_type_params.rs index 22be4491273..ee11b774cf2 100644 --- a/src/librustc_typeck/constrained_type_params.rs +++ b/src/librustc_typeck/constrained_type_params.rs @@ -75,7 +75,7 @@ fn visit_ty(&mut self, t: Ty<'tcx>) -> bool { t.super_visit_with(self) } - fn visit_region(&mut self, r: &'tcx ty::Region) -> bool { + fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool { match *r { ty::ReEarlyBound(data) => { self.parameters.push(Parameter::from(data)); diff --git a/src/librustc_typeck/variance/constraints.rs b/src/librustc_typeck/variance/constraints.rs index 5bbc285c3d5..529b2700679 100644 --- a/src/librustc_typeck/variance/constraints.rs +++ b/src/librustc_typeck/variance/constraints.rs @@ -479,7 +479,7 @@ fn add_constraints_from_sig(&mut self, /// context with ambient variance `variance` fn add_constraints_from_region(&mut self, generics: &ty::Generics, - region: &'tcx ty::Region, + region: ty::Region<'tcx>, variance: VarianceTermPtr<'a>) { match *region { ty::ReEarlyBound(ref data) => { diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index a25eb60d2a2..5899ce90611 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -726,7 +726,7 @@ fn clean(&self, cx: &DocContext) -> TyParamBound { if let ty::TyTuple(ts, _) = ty_s.sty { for &ty_s in ts { if let ty::TyRef(ref reg, _) = ty_s.sty { - if let &ty::Region::ReLateBound(..) = *reg { + if let &ty::RegionKind::ReLateBound(..) = *reg { debug!(" hit an ReLateBound {:?}", reg); if let Some(lt) = reg.clean(cx) { late_bounds.push(lt); @@ -819,7 +819,7 @@ fn clean(&self, _: &DocContext) -> Lifetime { } } -impl Clean> for ty::Region { +impl<'tcx> Clean> for ty::RegionKind<'tcx> { fn clean(&self, cx: &DocContext) -> Option { match *self { ty::ReStatic => Some(Lifetime::statik()), @@ -915,7 +915,7 @@ fn clean(&self, _cx: &DocContext) -> WherePredicate { } } -impl<'tcx> Clean for ty::OutlivesPredicate<&'tcx ty::Region, &'tcx ty::Region> { +impl<'tcx> Clean for ty::OutlivesPredicate, ty::Region<'tcx>> { fn clean(&self, cx: &DocContext) -> WherePredicate { let ty::OutlivesPredicate(ref a, ref b) = *self; WherePredicate::RegionPredicate { @@ -925,7 +925,7 @@ fn clean(&self, cx: &DocContext) -> WherePredicate { } } -impl<'tcx> Clean for ty::OutlivesPredicate, &'tcx ty::Region> { +impl<'tcx> Clean for ty::OutlivesPredicate, ty::Region<'tcx>> { fn clean(&self, cx: &DocContext) -> WherePredicate { let ty::OutlivesPredicate(ref ty, ref lt) = *self; diff --git a/src/test/run-pass/kindck-implicit-close-over-mut-var.rs b/src/test/run-pass/kindck-implicit-close-over-mut-var.rs index a81c0846a27..d1f957bf6b9 100644 --- a/src/test/run-pass/kindck-implicit-close-over-mut-var.rs +++ b/src/test/run-pass/kindck-implicit-close-over-mut-var.rs @@ -1,4 +1,4 @@ -// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT +s// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT // file at the top-level directory of this distribution and at // http://rust-lang.org/COPYRIGHT. //