about summary refs log tree commit diff
diff options
context:
space:
mode:
authorSantiago Pastorino <spastorino@gmail.com>2022-08-02 11:03:29 -0300
committerSantiago Pastorino <spastorino@gmail.com>2022-08-04 11:26:54 -0300
commit1802d45b1238409d2c29cf7e8f25a96b94874fe2 (patch)
tree2edfdea9f2bba81026966bca964e181da793a584
parent81c4d2371aab4636c56ac5d61d391ae195d8bb0a (diff)
downloadrust-1802d45b1238409d2c29cf7e8f25a96b94874fe2.tar.gz
rust-1802d45b1238409d2c29cf7e8f25a96b94874fe2.zip
Record RPITs elided lifetimes in path segments
-rw-r--r--compiler/rustc_ast_lowering/src/lib.rs2
-rw-r--r--compiler/rustc_ast_lowering/src/lifetime_collector.rs51
2 files changed, 35 insertions, 18 deletions
diff --git a/compiler/rustc_ast_lowering/src/lib.rs b/compiler/rustc_ast_lowering/src/lib.rs
index c21afa26f4f..6cf938a242e 100644
--- a/compiler/rustc_ast_lowering/src/lib.rs
+++ b/compiler/rustc_ast_lowering/src/lib.rs
@@ -1446,7 +1446,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
         hir::OwnerNode::Item(self.arena.alloc(opaque_ty_item))
     }
 
-    fn create_and_capture_lifetime_defs(&mut self, lifetimes_in_bounds: &[&Lifetime]) {
+    fn create_and_capture_lifetime_defs(&mut self, lifetimes_in_bounds: &[Lifetime]) {
         for lifetime in lifetimes_in_bounds {
             let ident = lifetime.ident;
             let span = ident.span;
diff --git a/compiler/rustc_ast_lowering/src/lifetime_collector.rs b/compiler/rustc_ast_lowering/src/lifetime_collector.rs
index 586436240f1..51fa7075d34 100644
--- a/compiler/rustc_ast_lowering/src/lifetime_collector.rs
+++ b/compiler/rustc_ast_lowering/src/lifetime_collector.rs
@@ -1,25 +1,26 @@
 use super::ResolverAstLoweringExt;
 use rustc_ast::visit::{self, BoundKind, LifetimeCtxt, Visitor};
 use rustc_ast::{
-    FnRetTy, GenericBounds, Lifetime, NodeId, PolyTraitRef, TraitBoundModifier, Ty, TyKind,
+    FnRetTy, GenericBounds, Lifetime, NodeId, PathSegment, PolyTraitRef, TraitBoundModifier, Ty,
+    TyKind,
 };
 use rustc_hir::def::LifetimeRes;
 use rustc_middle::ty::ResolverAstLowering;
+use rustc_span::symbol::{kw, Ident};
+use rustc_span::Span;
 
-struct LifetimeCollectVisitor<'this, 'ast: 'this> {
-    resolver: &'this ResolverAstLowering,
+struct LifetimeCollectVisitor<'ast> {
+    resolver: &'ast ResolverAstLowering,
     current_binders: Vec<NodeId>,
-    collected_lifetimes: Vec<&'ast Lifetime>,
+    collected_lifetimes: Vec<Lifetime>,
 }
 
-impl<'this, 'ast: 'this> LifetimeCollectVisitor<'this, 'ast> {
-    fn new(resolver: &'this ResolverAstLowering) -> Self {
+impl<'ast> LifetimeCollectVisitor<'ast> {
+    fn new(resolver: &'ast ResolverAstLowering) -> Self {
         Self { resolver, current_binders: Vec::new(), collected_lifetimes: Vec::new() }
     }
-}
 
-impl<'this, 'ast: 'this> Visitor<'ast> for LifetimeCollectVisitor<'this, 'ast> {
-    fn visit_lifetime(&mut self, lifetime: &'ast Lifetime, _: LifetimeCtxt) {
+    fn record_lifetime_use(&mut self, lifetime: Lifetime) {
         let res = self.resolver.get_lifetime_res(lifetime.id).unwrap_or(LifetimeRes::Error);
 
         if res.binder().map_or(true, |b| !self.current_binders.contains(&b)) {
@@ -28,6 +29,25 @@ impl<'this, 'ast: 'this> Visitor<'ast> for LifetimeCollectVisitor<'this, 'ast> {
             }
         }
     }
+}
+
+impl<'ast> Visitor<'ast> for LifetimeCollectVisitor<'ast> {
+    fn visit_lifetime(&mut self, lifetime: &'ast Lifetime, _: LifetimeCtxt) {
+        self.record_lifetime_use(*lifetime);
+    }
+
+    fn visit_path_segment(&mut self, path_span: Span, path_segment: &'ast PathSegment) {
+        if let Some(LifetimeRes::ElidedAnchor { start, end }) =
+            self.resolver.get_lifetime_res(path_segment.id)
+        {
+            for i in start..end {
+                let lifetime =
+                    Lifetime { id: i, ident: Ident::new(kw::UnderscoreLifetime, path_span) };
+                self.record_lifetime_use(lifetime);
+            }
+        }
+        visit::walk_path_segment(self, path_span, path_segment);
+    }
 
     fn visit_poly_trait_ref(&mut self, t: &'ast PolyTraitRef, m: &'ast TraitBoundModifier) {
         self.current_binders.push(t.trait_ref.ref_id);
@@ -51,19 +71,16 @@ impl<'this, 'ast: 'this> Visitor<'ast> for LifetimeCollectVisitor<'this, 'ast> {
     }
 }
 
-pub fn lifetimes_in_ret_ty<'this, 'ast: 'this>(
-    resolver: &'this ResolverAstLowering,
-    ret_ty: &'ast FnRetTy,
-) -> Vec<&'ast Lifetime> {
+pub fn lifetimes_in_ret_ty(resolver: &ResolverAstLowering, ret_ty: &FnRetTy) -> Vec<Lifetime> {
     let mut visitor = LifetimeCollectVisitor::new(resolver);
     visitor.visit_fn_ret_ty(ret_ty);
     visitor.collected_lifetimes
 }
 
-pub fn lifetimes_in_bounds<'this, 'ast: 'this>(
-    resolver: &'this ResolverAstLowering,
-    bounds: &'ast GenericBounds,
-) -> Vec<&'ast Lifetime> {
+pub fn lifetimes_in_bounds(
+    resolver: &ResolverAstLowering,
+    bounds: &GenericBounds,
+) -> Vec<Lifetime> {
     let mut visitor = LifetimeCollectVisitor::new(resolver);
     for bound in bounds {
         visitor.visit_param_bound(bound, BoundKind::Bound);