@@ -68,6 +68,7 @@ use crate::infer::{
68
68
} ;
69
69
use crate :: traits:: { ObligationCause , ObligationCauseCode } ;
70
70
use rustc_data_structures:: undo_log:: UndoLogs ;
71
+ use rustc_hir:: def_id:: DefId ;
71
72
use rustc_hir:: def_id:: LocalDefId ;
72
73
use rustc_middle:: mir:: ConstraintCategory ;
73
74
use rustc_middle:: ty:: subst:: GenericArgKind ;
@@ -324,6 +325,29 @@ where
324
325
origin : infer:: SubregionOrigin < ' tcx > ,
325
326
region : ty:: Region < ' tcx > ,
326
327
projection_ty : ty:: ProjectionTy < ' tcx > ,
328
+ ) {
329
+ self . generic_must_outlive (
330
+ origin,
331
+ region,
332
+ GenericKind :: Projection ( projection_ty) ,
333
+ projection_ty. item_def_id ,
334
+ projection_ty. substs ,
335
+ |ty| match ty. kind ( ) {
336
+ ty:: Projection ( projection_ty) => ( projection_ty. item_def_id , projection_ty. substs ) ,
337
+ _ => bug ! ( "expected only projection types from env, not {:?}" , ty) ,
338
+ } ,
339
+ ) ;
340
+ }
341
+
342
+ #[ instrument( level = "debug" , skip( self , filter) ) ]
343
+ fn generic_must_outlive (
344
+ & mut self ,
345
+ origin : infer:: SubregionOrigin < ' tcx > ,
346
+ region : ty:: Region < ' tcx > ,
347
+ generic : GenericKind < ' tcx > ,
348
+ def_id : DefId ,
349
+ substs : SubstsRef < ' tcx > ,
350
+ filter : impl Fn ( Ty < ' tcx > ) -> ( DefId , SubstsRef < ' tcx > ) ,
327
351
) {
328
352
// This case is thorny for inference. The fundamental problem is
329
353
// that there are many cases where we have choice, and inference
@@ -342,13 +366,10 @@ where
342
366
// Compute the bounds we can derive from the trait definition.
343
367
// These are guaranteed to apply, no matter the inference
344
368
// results.
345
- let trait_bounds: Vec < _ > =
346
- self . verify_bound . bounds ( projection_ty. item_def_id , projection_ty. substs ) . collect ( ) ;
369
+ let trait_bounds: Vec < _ > = self . verify_bound . bounds ( def_id, substs) . collect ( ) ;
347
370
348
371
debug ! ( ?trait_bounds) ;
349
372
350
- let generic = GenericKind :: Projection ( projection_ty) ;
351
-
352
373
// Compute the bounds we can derive from the environment. This
353
374
// is an "approximate" match -- in some cases, these bounds
354
375
// may not apply.
@@ -367,14 +388,8 @@ where
367
388
// If the declaration is `trait Trait<'b> { type Item: 'b; }`, then `projection_declared_bounds_from_trait`
368
389
// will be invoked with `['b => ^1]` and so we will get `^1` returned.
369
390
let bound = bound_outlives. skip_binder ( ) ;
370
- match * bound. 0 . kind ( ) {
371
- ty:: Projection ( projection_ty) => self
372
- . verify_bound
373
- . bounds ( projection_ty. item_def_id , projection_ty. substs )
374
- . all ( |r| r != bound. 1 ) ,
375
-
376
- _ => panic ! ( "expected only projection types from env, not {:?}" , bound. 0 ) ,
377
- }
391
+ let ( def_id, substs) = filter ( bound. 0 ) ;
392
+ self . verify_bound . bounds ( def_id, substs) . all ( |r| r != bound. 1 )
378
393
} ) ;
379
394
380
395
// If declared bounds list is empty, the only applicable rule is
@@ -391,11 +406,11 @@ where
391
406
// the problem is to add `T: 'r`, which isn't true. So, if there are no
392
407
// inference variables, we use a verify constraint instead of adding
393
408
// edges, which winds up enforcing the same condition.
394
- let needs_infer = projection_ty . needs_infer ( ) ;
409
+ let needs_infer = substs . needs_infer ( ) ;
395
410
if approx_env_bounds. is_empty ( ) && trait_bounds. is_empty ( ) && needs_infer {
396
411
debug ! ( "no declared bounds" ) ;
397
412
398
- self . substs_must_outlive ( projection_ty . substs , origin, region) ;
413
+ self . substs_must_outlive ( substs, origin, region) ;
399
414
400
415
return ;
401
416
}
0 commit comments