@@ -11,9 +11,9 @@ use rustc_data_structures::fx::{FxHashMap, FxHashSet};
1111use rustc_data_structures:: sync:: Lrc ;
1212use rustc_data_structures:: undo_log:: UndoLogs ;
1313use rustc_data_structures:: unify as ut;
14- use rustc_data_structures:: unify:: UnifyKey ;
1514use rustc_hir:: def_id:: DefId ;
1615use rustc_index:: vec:: IndexVec ;
16+ use rustc_middle:: infer:: unify_key:: { RegionVidKey , UnifiedRegion } ;
1717use rustc_middle:: ty:: ReStatic ;
1818use rustc_middle:: ty:: { self , Ty , TyCtxt } ;
1919use rustc_middle:: ty:: { ReLateBound , ReVar } ;
@@ -47,13 +47,13 @@ pub struct RegionConstraintStorage<'tcx> {
4747
4848 /// When we add a R1 == R2 constriant, we currently add (a) edges
4949 /// R1 <= R2 and R2 <= R1 and (b) we unify the two regions in this
50- /// table. You can then call `opportunistic_resolve_var ` early
50+ /// table. You can then call `opportunistic_resolve_region ` early
5151 /// which will map R1 and R2 to some common region (i.e., either
5252 /// R1 or R2). This is important when fulfillment, dropck and other such
5353 /// code is iterating to a fixed point, because otherwise we sometimes
5454 /// would wind up with a fresh stream of region variables that have been
5555 /// equated but appear distinct.
56- pub ( super ) unification_table : ut:: UnificationTableStorage < ty :: RegionVid > ,
56+ pub ( super ) unification_table : ut:: UnificationTableStorage < RegionVidKey < ' tcx > > ,
5757
5858 /// a flag set to true when we perform any unifications; this is used
5959 /// to micro-optimize `take_and_reset_data`
@@ -406,8 +406,7 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
406406 // `RegionConstraintData` contains the relationship here.
407407 if * any_unifications {
408408 * any_unifications = false ;
409- self . unification_table ( )
410- . reset_unifications ( |_| ( ) ) ;
409+ self . unification_table ( ) . reset_unifications ( |_| UnifiedRegion ( None ) ) ;
411410 }
412411
413412 data
@@ -434,8 +433,8 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
434433 ) -> RegionVid {
435434 let vid = self . var_infos . push ( RegionVariableInfo { origin, universe } ) ;
436435
437- let u_vid = self . unification_table ( ) . new_key ( ( ) ) ;
438- assert_eq ! ( vid, u_vid) ;
436+ let u_vid = self . unification_table ( ) . new_key ( UnifiedRegion ( None ) ) ;
437+ assert_eq ! ( vid, u_vid. vid ) ;
439438 self . undo_log . push ( AddVar ( vid) ) ;
440439 debug ! ( "created new region variable {:?} in {:?} with origin {:?}" , vid, universe, origin) ;
441440 vid
@@ -497,10 +496,18 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
497496 self . make_subregion ( origin. clone ( ) , sub, sup) ;
498497 self . make_subregion ( origin, sup, sub) ;
499498
500- if let ( ty:: ReVar ( sub) , ty:: ReVar ( sup) ) = ( * sub, * sup) {
501- debug ! ( "make_eqregion: uniying {:?} with {:?}" , sub, sup) ;
502- self . unification_table ( ) . union ( sub, sup) ;
503- self . any_unifications = true ;
499+ match ( sub, sup) {
500+ ( & ty:: ReVar ( sub) , & ty:: ReVar ( sup) ) => {
501+ debug ! ( "make_eqregion: unifying {:?} with {:?}" , sub, sup) ;
502+ self . unification_table ( ) . union ( sub, sup) ;
503+ self . any_unifications = true ;
504+ }
505+ ( & ty:: ReVar ( vid) , value) | ( value, & ty:: ReVar ( vid) ) => {
506+ debug ! ( "make_eqregion: unifying {:?} with {:?}" , vid, value) ;
507+ self . unification_table ( ) . union_value ( vid, UnifiedRegion ( Some ( value) ) ) ;
508+ self . any_unifications = true ;
509+ }
510+ ( _, _) => { }
504511 }
505512 }
506513 }
@@ -616,8 +623,21 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
616623 }
617624 }
618625
619- pub fn opportunistic_resolve_var ( & mut self , rid : RegionVid ) -> ty:: RegionVid {
620- self . unification_table ( ) . find ( rid)
626+ pub fn opportunistic_resolve_region (
627+ & mut self ,
628+ tcx : TyCtxt < ' tcx > ,
629+ region : ty:: Region < ' tcx > ,
630+ ) -> ty:: Region < ' tcx > {
631+ match region {
632+ ty:: ReVar ( rid) => {
633+ let unified_region = self . unification_table ( ) . probe_value ( * rid) ;
634+ unified_region. 0 . unwrap_or_else ( || {
635+ let root = self . unification_table ( ) . find ( * rid) . vid ;
636+ tcx. reuse_or_mk_region ( region, ty:: ReVar ( root) )
637+ } )
638+ }
639+ _ => region,
640+ }
621641 }
622642
623643 fn combine_map ( & mut self , t : CombineMapType ) -> & mut CombineMap < ' tcx > {
@@ -672,8 +692,8 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
672692 & self ,
673693 value_count : usize ,
674694 ) -> ( Range < RegionVid > , Vec < RegionVariableOrigin > ) {
675- let range = RegionVid :: from_index ( value_count as u32 )
676- ..RegionVid :: from_index ( self . unification_table . len ( ) as u32 ) ;
695+ let range = RegionVid :: from ( value_count as u32 )
696+ ..RegionVid :: from ( self . unification_table . len ( ) as u32 ) ;
677697 (
678698 range. clone ( ) ,
679699 ( range. start . index ( ) ..range. end . index ( ) )
@@ -695,7 +715,7 @@ impl<'tcx> RegionConstraintCollector<'_, 'tcx> {
695715 }
696716
697717 #[ inline]
698- fn unification_table ( & mut self ) -> super :: UnificationTable < ' _ , ' tcx , ty :: RegionVid > {
718+ fn unification_table ( & mut self ) -> super :: UnificationTable < ' _ , ' tcx , RegionVidKey < ' tcx > > {
699719 ut:: UnificationTable :: with_log ( & mut self . storage . unification_table , self . undo_log )
700720 }
701721}
0 commit comments