@@ -8,7 +8,7 @@ use rustc_errors::ErrorGuaranteed;
8
8
use rustc_hir as hir;
9
9
use rustc_hir:: def_id:: { DefId , LocalDefId } ;
10
10
use rustc_index:: bit_set:: BitMatrix ;
11
- use rustc_index:: vec:: IndexVec ;
11
+ use rustc_index:: vec:: { Idx , IndexVec } ;
12
12
use rustc_span:: Span ;
13
13
use rustc_target:: abi:: VariantIdx ;
14
14
use smallvec:: SmallVec ;
@@ -289,13 +289,6 @@ pub struct ConstQualifs {
289
289
/// instance of the closure is created, the corresponding free regions
290
290
/// can be extracted from its type and constrained to have the given
291
291
/// outlives relationship.
292
- ///
293
- /// In some cases, we have to record outlives requirements between types and
294
- /// regions as well. In that case, if those types include any regions, those
295
- /// regions are recorded using their external names (`ReStatic`,
296
- /// `ReEarlyBound`, `ReFree`). We use these because in a query response we
297
- /// cannot use `ReVar` (which is what we use internally within the rest of the
298
- /// NLL code).
299
292
#[ derive( Clone , Debug , TyEncodable , TyDecodable , HashStable ) ]
300
293
pub struct ClosureRegionRequirements < ' tcx > {
301
294
/// The number of external regions defined on the closure. In our
@@ -392,16 +385,56 @@ pub enum ClosureOutlivesSubject<'tcx> {
392
385
/// Subject is a type, typically a type parameter, but could also
393
386
/// be a projection. Indicates a requirement like `T: 'a` being
394
387
/// passed to the caller, where the type here is `T`.
395
- ///
396
- /// The type here is guaranteed not to contain any free regions at
397
- /// present.
398
- Ty ( Ty < ' tcx > ) ,
388
+ Ty ( ClosureOutlivesSubjectTy < ' tcx > ) ,
399
389
400
390
/// Subject is a free region from the closure. Indicates a requirement
401
391
/// like `'a: 'b` being passed to the caller; the region here is `'a`.
402
392
Region ( ty:: RegionVid ) ,
403
393
}
404
394
395
+ /// Represents a `ty::Ty` for use in [`ClosureOutlivesSubject`].
396
+ ///
397
+ /// This indirection is necessary because the type may include `ReVar` regions,
398
+ /// which is what we use internally within NLL code,
399
+ /// and we can't use `ReVar`s in a query response.
400
+ #[ derive( Copy , Clone , Debug , TyEncodable , TyDecodable , HashStable ) ]
401
+ pub struct ClosureOutlivesSubjectTy < ' tcx > {
402
+ inner : Ty < ' tcx > ,
403
+ }
404
+
405
+ impl < ' tcx > ClosureOutlivesSubjectTy < ' tcx > {
406
+ // All regions of `ty` must be of kind `ReVar`
407
+ // and must point to an early-bound region in the closure's signature.
408
+ pub fn new ( tcx : TyCtxt < ' tcx > , ty : Ty < ' tcx > ) -> Self {
409
+ let inner = tcx. fold_regions ( ty, |r, depth| match r. kind ( ) {
410
+ ty:: ReVar ( vid) => {
411
+ let br = ty:: BoundRegion {
412
+ var : ty:: BoundVar :: new ( vid. index ( ) ) ,
413
+ kind : ty:: BrAnon ( 0u32 , None ) ,
414
+ } ;
415
+ tcx. mk_re_late_bound ( depth, br)
416
+ }
417
+ _ => bug ! ( "unexpected region in ClosureOutlivesSubjectTy: {r:?}" ) ,
418
+ } ) ;
419
+
420
+ Self { inner }
421
+ }
422
+
423
+ pub fn instantiate (
424
+ self ,
425
+ tcx : TyCtxt < ' tcx > ,
426
+ mut map : impl FnMut ( ty:: RegionVid ) -> ty:: Region < ' tcx > ,
427
+ ) -> Ty < ' tcx > {
428
+ tcx. fold_regions ( self . inner , |r, depth| match r. kind ( ) {
429
+ ty:: ReLateBound ( debruijn, br) => {
430
+ debug_assert_eq ! ( debruijn, depth) ;
431
+ map ( ty:: RegionVid :: new ( br. var . index ( ) ) )
432
+ }
433
+ _ => bug ! ( "unexpected region {r:?}" ) ,
434
+ } )
435
+ }
436
+ }
437
+
405
438
/// The constituent parts of a mir constant of kind ADT or array.
406
439
#[ derive( Copy , Clone , Debug , HashStable ) ]
407
440
pub struct DestructuredConstant < ' tcx > {
0 commit comments