@@ -21,7 +21,7 @@ use crate::{
2121 keys,
2222 src:: HasChildSource ,
2323 src:: HasSource ,
24- type_ref:: { TypeBound , TypeRef } ,
24+ type_ref:: { LifetimeRef , TypeBound , TypeRef } ,
2525 AdtId , GenericDefId , LocalTypeParamId , Lookup , TypeParamId ,
2626} ;
2727
@@ -33,6 +33,12 @@ pub struct TypeParamData {
3333 pub provenance : TypeParamProvenance ,
3434}
3535
36+ /// Data about a generic parameter (to a function, struct, impl, ...).
37+ #[ derive( Clone , PartialEq , Eq , Debug ) ]
38+ pub struct LifetimeParamData {
39+ pub name : Name ,
40+ }
41+
3642#[ derive( Copy , Clone , PartialEq , Eq , Debug ) ]
3743pub enum TypeParamProvenance {
3844 TypeParamList ,
@@ -44,7 +50,7 @@ pub enum TypeParamProvenance {
4450#[ derive( Clone , PartialEq , Eq , Debug , Default ) ]
4551pub struct GenericParams {
4652 pub types : Arena < TypeParamData > ,
47- // lifetimes: Arena<LocalLifetimeParamId, LifetimeParamData>,
53+ pub lifetimes : Arena < LifetimeParamData > ,
4854 pub where_predicates : Vec < WherePredicate > ,
4955}
5056
@@ -53,16 +59,17 @@ pub struct GenericParams {
5359/// It might still result in multiple actual predicates though, because of
5460/// associated type bindings like `Iterator<Item = u32>`.
5561#[ derive( Clone , PartialEq , Eq , Debug ) ]
56- pub struct WherePredicate {
57- pub target : WherePredicateTarget ,
58- pub bound : TypeBound ,
62+ pub enum WherePredicate {
63+ TypeBound { target : WherePredicateTypeTarget , bound : TypeBound } ,
64+ Lifetime { target : LifetimeRef , bound : LifetimeRef } ,
5965}
6066
6167#[ derive( Clone , PartialEq , Eq , Debug ) ]
62- pub enum WherePredicateTarget {
68+ pub enum WherePredicateTypeTarget {
6369 TypeRef ( TypeRef ) ,
6470 /// For desugared where predicates that can directly refer to a type param.
6571 TypeParam ( LocalTypeParamId ) ,
72+ // FIXME: ForLifetime(Vec<LifetimeParamId>, TypeRef)
6673}
6774
6875type SourceMap = ArenaMap < LocalTypeParamId , Either < ast:: Trait , ast:: TypeParam > > ;
@@ -123,7 +130,7 @@ impl GenericParams {
123130 }
124131
125132 fn new ( db : & dyn DefDatabase , def : GenericDefId ) -> ( GenericParams , InFile < SourceMap > ) {
126- let mut generics = GenericParams { types : Arena :: default ( ) , where_predicates : Vec :: new ( ) } ;
133+ let mut generics = GenericParams :: default ( ) ;
127134 let mut sm = ArenaMap :: default ( ) ;
128135
129136 // FIXME: add `: Sized` bound for everything except for `Self` in traits
@@ -171,7 +178,7 @@ impl GenericParams {
171178 // add super traits as bounds on Self
172179 // i.e., trait Foo: Bar is equivalent to trait Foo where Self: Bar
173180 let self_param = TypeRef :: Path ( name ! [ Self ] . into ( ) ) ;
174- generics. fill_bounds ( & lower_ctx, & src. value , self_param) ;
181+ generics. fill_bounds ( & lower_ctx, & src. value , Either :: Left ( self_param) ) ;
175182
176183 generics. fill ( & lower_ctx, & mut sm, & src. value ) ;
177184 src. file_id
@@ -218,12 +225,12 @@ impl GenericParams {
218225 & mut self ,
219226 lower_ctx : & LowerCtx ,
220227 node : & dyn ast:: TypeBoundsOwner ,
221- type_ref : TypeRef ,
228+ target : Either < TypeRef , LifetimeRef > ,
222229 ) {
223230 for bound in
224231 node. type_bound_list ( ) . iter ( ) . flat_map ( |type_bound_list| type_bound_list. bounds ( ) )
225232 {
226- self . add_where_predicate_from_bound ( lower_ctx, bound, type_ref . clone ( ) ) ;
233+ self . add_where_predicate_from_bound ( lower_ctx, bound, target . clone ( ) ) ;
227234 }
228235 }
229236
@@ -246,19 +253,30 @@ impl GenericParams {
246253 sm. insert ( param_id, Either :: Right ( type_param. clone ( ) ) ) ;
247254
248255 let type_ref = TypeRef :: Path ( name. into ( ) ) ;
249- self . fill_bounds ( & lower_ctx, & type_param, type_ref) ;
256+ self . fill_bounds ( & lower_ctx, & type_param, Either :: Left ( type_ref) ) ;
257+ }
258+ for lifetime_param in params. lifetime_params ( ) {
259+ let name = lifetime_param
260+ . lifetime_token ( )
261+ . map_or_else ( Name :: missing, |tok| Name :: new_lifetime ( & tok) ) ;
262+ let param = LifetimeParamData { name : name. clone ( ) } ;
263+ let _param_id = self . lifetimes . alloc ( param) ;
264+ let lifetime_ref = LifetimeRef :: new_name ( name) ;
265+ self . fill_bounds ( & lower_ctx, & lifetime_param, Either :: Right ( lifetime_ref) ) ;
250266 }
251267 }
252268
253269 fn fill_where_predicates ( & mut self , lower_ctx : & LowerCtx , where_clause : ast:: WhereClause ) {
254270 for pred in where_clause. predicates ( ) {
255- let type_ref = match pred. ty ( ) {
256- Some ( type_ref) => type_ref,
257- None => continue ,
271+ let target = if let Some ( type_ref) = pred. ty ( ) {
272+ Either :: Left ( TypeRef :: from_ast ( lower_ctx, type_ref) )
273+ } else if let Some ( lifetime_tok) = pred. lifetime_token ( ) {
274+ Either :: Right ( LifetimeRef :: from_token ( lifetime_tok) )
275+ } else {
276+ continue ;
258277 } ;
259- let type_ref = TypeRef :: from_ast ( lower_ctx, type_ref) ;
260278 for bound in pred. type_bound_list ( ) . iter ( ) . flat_map ( |l| l. bounds ( ) ) {
261- self . add_where_predicate_from_bound ( lower_ctx, bound, type_ref . clone ( ) ) ;
279+ self . add_where_predicate_from_bound ( lower_ctx, bound, target . clone ( ) ) ;
262280 }
263281 }
264282 }
@@ -267,15 +285,24 @@ impl GenericParams {
267285 & mut self ,
268286 lower_ctx : & LowerCtx ,
269287 bound : ast:: TypeBound ,
270- type_ref : TypeRef ,
288+ target : Either < TypeRef , LifetimeRef > ,
271289 ) {
272290 if bound. question_mark_token ( ) . is_some ( ) {
273291 // FIXME: remove this bound
274292 return ;
275293 }
276294 let bound = TypeBound :: from_ast ( lower_ctx, bound) ;
277- self . where_predicates
278- . push ( WherePredicate { target : WherePredicateTarget :: TypeRef ( type_ref) , bound } ) ;
295+ let predicate = match ( target, bound) {
296+ ( Either :: Left ( type_ref) , bound) => WherePredicate :: TypeBound {
297+ target : WherePredicateTypeTarget :: TypeRef ( type_ref) ,
298+ bound,
299+ } ,
300+ ( Either :: Right ( lifetime) , TypeBound :: Lifetime ( bound) ) => {
301+ WherePredicate :: Lifetime { target : lifetime, bound }
302+ }
303+ _ => return ,
304+ } ;
305+ self . where_predicates . push ( predicate) ;
279306 }
280307
281308 pub ( crate ) fn fill_implicit_impl_trait_args ( & mut self , type_ref : & TypeRef ) {
@@ -288,8 +315,8 @@ impl GenericParams {
288315 } ;
289316 let param_id = self . types . alloc ( param) ;
290317 for bound in bounds {
291- self . where_predicates . push ( WherePredicate {
292- target : WherePredicateTarget :: TypeParam ( param_id) ,
318+ self . where_predicates . push ( WherePredicate :: TypeBound {
319+ target : WherePredicateTypeTarget :: TypeParam ( param_id) ,
293320 bound : bound. clone ( ) ,
294321 } ) ;
295322 }
0 commit comments