Skip to content

Commit 8cfaf1b

Browse files
committed
Trait item lifetime resolution for GATs
1 parent 442b7bd commit 8cfaf1b

File tree

1 file changed

+67
-20
lines changed

1 file changed

+67
-20
lines changed

src/librustc/middle/resolve_lifetime.rs

+67-20
Original file line numberDiff line numberDiff line change
@@ -624,30 +624,77 @@ impl<'a, 'tcx> Visitor<'tcx> for LifetimeContext<'a, 'tcx> {
624624
}
625625

626626
fn visit_trait_item(&mut self, trait_item: &'tcx hir::TraitItem) {
627-
let tcx = self.tcx;
628-
if let hir::TraitItemKind::Method(ref sig, _) = trait_item.node {
629-
self.visit_early_late(
630-
Some(tcx.hir.get_parent(trait_item.id)),
631-
&sig.decl,
632-
&trait_item.generics,
633-
|this| intravisit::walk_trait_item(this, trait_item),
634-
)
635-
} else {
636-
intravisit::walk_trait_item(self, trait_item);
627+
use self::hir::TraitItemKind::*;
628+
match trait_item.node {
629+
Method(ref sig, _) => {
630+
let tcx = self.tcx;
631+
self.visit_early_late(
632+
Some(tcx.hir.get_parent(trait_item.id)),
633+
&sig.decl,
634+
&trait_item.generics,
635+
|this| intravisit::walk_trait_item(this, trait_item),
636+
);
637+
},
638+
Type(ref bounds, ref ty) => {
639+
let generics = &trait_item.generics;
640+
let mut index = self.next_early_index();
641+
debug!("visit_ty: index = {}", index);
642+
let lifetimes = generics.lifetimes.iter()
643+
.map(|lt_def| Region::early(&self.tcx.hir, &mut index, lt_def))
644+
.collect();
645+
646+
let next_early_index = index + generics.ty_params.len() as u32;
647+
let scope = Scope::Binder { lifetimes, next_early_index, s: self.scope };
648+
self.with(scope, |_old_scope, this| {
649+
this.visit_generics(generics);
650+
for bound in bounds {
651+
this.visit_ty_param_bound(bound);
652+
}
653+
if let Some(ty) = ty {
654+
this.visit_ty(ty);
655+
}
656+
});
657+
},
658+
Const(_, _) => {
659+
// Only methods and types support generics.
660+
assert!(!trait_item.generics.is_parameterized());
661+
intravisit::walk_trait_item(self, trait_item);
662+
},
637663
}
638664
}
639665

640666
fn visit_impl_item(&mut self, impl_item: &'tcx hir::ImplItem) {
641-
let tcx = self.tcx;
642-
if let hir::ImplItemKind::Method(ref sig, _) = impl_item.node {
643-
self.visit_early_late(
644-
Some(tcx.hir.get_parent(impl_item.id)),
645-
&sig.decl,
646-
&impl_item.generics,
647-
|this| intravisit::walk_impl_item(this, impl_item),
648-
)
649-
} else {
650-
intravisit::walk_impl_item(self, impl_item);
667+
use self::hir::ImplItemKind::*;
668+
match impl_item.node {
669+
Method(ref sig, _) => {
670+
let tcx = self.tcx;
671+
self.visit_early_late(
672+
Some(tcx.hir.get_parent(impl_item.id)),
673+
&sig.decl,
674+
&impl_item.generics,
675+
|this| intravisit::walk_impl_item(this, impl_item),
676+
)
677+
},
678+
Type(ref ty) => {
679+
let generics = &impl_item.generics;
680+
let mut index = self.next_early_index();
681+
debug!("visit_ty: index = {}", index);
682+
let lifetimes = generics.lifetimes.iter()
683+
.map(|lt_def| Region::early(&self.tcx.hir, &mut index, lt_def))
684+
.collect();
685+
686+
let next_early_index = index + generics.ty_params.len() as u32;
687+
let scope = Scope::Binder { lifetimes, next_early_index, s: self.scope };
688+
self.with(scope, |_old_scope, this| {
689+
this.visit_generics(generics);
690+
this.visit_ty(ty);
691+
});
692+
},
693+
Const(_, _) => {
694+
// Only methods and types support generics.
695+
assert!(!impl_item.generics.is_parameterized());
696+
intravisit::walk_impl_item(self, impl_item);
697+
},
651698
}
652699
}
653700

0 commit comments

Comments
 (0)