@@ -28,7 +28,7 @@ use crate::traits::{
2828    BuiltinDerivedObligation ,  ImplDerivedObligation ,  ImplDerivedObligationCause ,  ImplSource , 
2929    ImplSourceUserDefinedData ,  Normalized ,  Obligation ,  ObligationCause ,  PolyTraitObligation , 
3030    PredicateObligation ,  Selection ,  SelectionError ,  SignatureMismatch ,  TraitNotObjectSafe , 
31-     Unimplemented , 
31+     TraitObligation ,   Unimplemented , 
3232} ; 
3333
3434use  super :: BuiltinImplConditions ; 
@@ -678,17 +678,10 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
678678        fn_host_effect :  ty:: Const < ' tcx > , 
679679    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
680680        debug ! ( ?obligation,  "confirm_fn_pointer_candidate" ) ; 
681+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
682+         let  self_ty = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
681683
682684        let  tcx = self . tcx ( ) ; 
683- 
684-         let  Some ( self_ty)  = self . infcx . shallow_resolve ( obligation. self_ty ( ) . no_bound_vars ( ) )  else  { 
685-             // FIXME: Ideally we'd support `for<'a> fn(&'a ()): Fn(&'a ())`, 
686-             // but we do not currently. Luckily, such a bound is not 
687-             // particularly useful, so we don't expect users to write 
688-             // them often. 
689-             return  Err ( SelectionError :: Unimplemented ) ; 
690-         } ; 
691- 
692685        let  sig = self_ty. fn_sig ( tcx) ; 
693686        let  trait_ref = closure_trait_ref_and_return_type ( 
694687            tcx, 
@@ -700,7 +693,8 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
700693        ) 
701694        . map_bound ( |( trait_ref,  _) | trait_ref) ; 
702695
703-         let  mut  nested = self . confirm_poly_trait_refs ( obligation,  trait_ref) ?; 
696+         let  mut  nested =
697+             self . equate_trait_refs ( obligation. with ( tcx,  placeholder_predicate) ,  trait_ref) ?; 
704698        let  cause = obligation. derived_cause ( BuiltinDerivedObligation ) ; 
705699
706700        // Confirm the `type Output: Sized;` bound that is present on `FnOnce` 
@@ -748,10 +742,8 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
748742        & mut  self , 
749743        obligation :  & PolyTraitObligation < ' tcx > , 
750744    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
751-         // Okay to skip binder because the args on coroutine types never 
752-         // touch bound regions, they just capture the in-scope 
753-         // type/region parameters. 
754-         let  self_ty = self . infcx . shallow_resolve ( obligation. self_ty ( ) . skip_binder ( ) ) ; 
745+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
746+         let  self_ty = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
755747        let  ty:: Coroutine ( coroutine_def_id,  args)  = * self_ty. kind ( )  else  { 
756748            bug ! ( "closure candidate for non-closure {:?}" ,  obligation) ; 
757749        } ; 
@@ -760,23 +752,17 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
760752
761753        let  coroutine_sig = args. as_coroutine ( ) . sig ( ) ; 
762754
763-         // NOTE: The self-type is a coroutine type and hence is 
764-         // in fact unparameterized (or at least does not reference any 
765-         // regions bound in the obligation). 
766-         let  self_ty = obligation
767-             . predicate 
768-             . self_ty ( ) 
769-             . no_bound_vars ( ) 
770-             . expect ( "unboxed closure type should not capture bound vars from the predicate" ) ; 
771- 
772755        let  ( trait_ref,  _,  _)  = super :: util:: coroutine_trait_ref_and_outputs ( 
773756            self . tcx ( ) , 
774757            obligation. predicate . def_id ( ) , 
775758            self_ty, 
776759            coroutine_sig, 
777760        ) ; 
778761
779-         let  nested = self . confirm_poly_trait_refs ( obligation,  ty:: Binder :: dummy ( trait_ref) ) ?; 
762+         let  nested = self . equate_trait_refs ( 
763+             obligation. with ( self . tcx ( ) ,  placeholder_predicate) , 
764+             ty:: Binder :: dummy ( trait_ref) , 
765+         ) ?; 
780766        debug ! ( ?trait_ref,  ?nested,  "coroutine candidate obligations" ) ; 
781767
782768        Ok ( nested) 
@@ -786,10 +772,8 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
786772        & mut  self , 
787773        obligation :  & PolyTraitObligation < ' tcx > , 
788774    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
789-         // Okay to skip binder because the args on coroutine types never 
790-         // touch bound regions, they just capture the in-scope 
791-         // type/region parameters. 
792-         let  self_ty = self . infcx . shallow_resolve ( obligation. self_ty ( ) . skip_binder ( ) ) ; 
775+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
776+         let  self_ty = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
793777        let  ty:: Coroutine ( coroutine_def_id,  args)  = * self_ty. kind ( )  else  { 
794778            bug ! ( "closure candidate for non-closure {:?}" ,  obligation) ; 
795779        } ; 
@@ -801,11 +785,14 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
801785        let  ( trait_ref,  _)  = super :: util:: future_trait_ref_and_outputs ( 
802786            self . tcx ( ) , 
803787            obligation. predicate . def_id ( ) , 
804-             obligation . predicate . no_bound_vars ( ) . expect ( "future has no bound vars" ) . self_ty ( ) , 
788+             self_ty, 
805789            coroutine_sig, 
806790        ) ; 
807791
808-         let  nested = self . confirm_poly_trait_refs ( obligation,  ty:: Binder :: dummy ( trait_ref) ) ?; 
792+         let  nested = self . equate_trait_refs ( 
793+             obligation. with ( self . tcx ( ) ,  placeholder_predicate) , 
794+             ty:: Binder :: dummy ( trait_ref) , 
795+         ) ?; 
809796        debug ! ( ?trait_ref,  ?nested,  "future candidate obligations" ) ; 
810797
811798        Ok ( nested) 
@@ -815,10 +802,8 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
815802        & mut  self , 
816803        obligation :  & PolyTraitObligation < ' tcx > , 
817804    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
818-         // Okay to skip binder because the args on coroutine types never 
819-         // touch bound regions, they just capture the in-scope 
820-         // type/region parameters. 
821-         let  self_ty = self . infcx . shallow_resolve ( obligation. self_ty ( ) . skip_binder ( ) ) ; 
805+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
806+         let  self_ty = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
822807        let  ty:: Coroutine ( coroutine_def_id,  args)  = * self_ty. kind ( )  else  { 
823808            bug ! ( "closure candidate for non-closure {:?}" ,  obligation) ; 
824809        } ; 
@@ -830,11 +815,14 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
830815        let  ( trait_ref,  _)  = super :: util:: iterator_trait_ref_and_outputs ( 
831816            self . tcx ( ) , 
832817            obligation. predicate . def_id ( ) , 
833-             obligation . predicate . no_bound_vars ( ) . expect ( "iterator has no bound vars" ) . self_ty ( ) , 
818+             self_ty, 
834819            gen_sig, 
835820        ) ; 
836821
837-         let  nested = self . confirm_poly_trait_refs ( obligation,  ty:: Binder :: dummy ( trait_ref) ) ?; 
822+         let  nested = self . equate_trait_refs ( 
823+             obligation. with ( self . tcx ( ) ,  placeholder_predicate) , 
824+             ty:: Binder :: dummy ( trait_ref) , 
825+         ) ?; 
838826        debug ! ( ?trait_ref,  ?nested,  "iterator candidate obligations" ) ; 
839827
840828        Ok ( nested) 
@@ -844,10 +832,8 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
844832        & mut  self , 
845833        obligation :  & PolyTraitObligation < ' tcx > , 
846834    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
847-         // Okay to skip binder because the args on coroutine types never 
848-         // touch bound regions, they just capture the in-scope 
849-         // type/region parameters. 
850-         let  self_ty = self . infcx . shallow_resolve ( obligation. self_ty ( ) . skip_binder ( ) ) ; 
835+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
836+         let  self_ty = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
851837        let  ty:: Coroutine ( coroutine_def_id,  args)  = * self_ty. kind ( )  else  { 
852838            bug ! ( "closure candidate for non-closure {:?}" ,  obligation) ; 
853839        } ; 
@@ -859,11 +845,14 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
859845        let  ( trait_ref,  _)  = super :: util:: async_iterator_trait_ref_and_outputs ( 
860846            self . tcx ( ) , 
861847            obligation. predicate . def_id ( ) , 
862-             obligation . predicate . no_bound_vars ( ) . expect ( "iterator has no bound vars" ) . self_ty ( ) , 
848+             self_ty, 
863849            gen_sig, 
864850        ) ; 
865851
866-         let  nested = self . confirm_poly_trait_refs ( obligation,  ty:: Binder :: dummy ( trait_ref) ) ?; 
852+         let  nested = self . equate_trait_refs ( 
853+             obligation. with ( self . tcx ( ) ,  placeholder_predicate) , 
854+             ty:: Binder :: dummy ( trait_ref) , 
855+         ) ?; 
867856        debug ! ( ?trait_ref,  ?nested,  "iterator candidate obligations" ) ; 
868857
869858        Ok ( nested) 
@@ -874,14 +863,15 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
874863        & mut  self , 
875864        obligation :  & PolyTraitObligation < ' tcx > , 
876865    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
877-         // Okay to skip binder because the args on closure types never 
878-         // touch bound regions, they just capture the in-scope 
879-         // type/region parameters. 
880-         let  self_ty = self . infcx . shallow_resolve ( obligation. self_ty ( ) . skip_binder ( ) ) ; 
866+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
867+         let  self_ty:  Ty < ' _ >  = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
868+ 
881869        let  trait_ref = match  * self_ty. kind ( )  { 
882-             ty:: Closure ( _,  args)  => { 
883-                 self . closure_trait_ref_unnormalized ( obligation,  args,  self . tcx ( ) . consts . true_ ) 
884-             } 
870+             ty:: Closure ( ..)  => self . closure_trait_ref_unnormalized ( 
871+                 self_ty, 
872+                 obligation. predicate . def_id ( ) , 
873+                 self . tcx ( ) . consts . true_ , 
874+             ) , 
885875            ty:: CoroutineClosure ( _,  args)  => { 
886876                args. as_coroutine_closure ( ) . coroutine_closure_sig ( ) . map_bound ( |sig| { 
887877                    ty:: TraitRef :: new ( 
@@ -896,16 +886,18 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
896886            } 
897887        } ; 
898888
899-         self . confirm_poly_trait_refs ( obligation,  trait_ref) 
889+         self . equate_trait_refs ( obligation. with ( self . tcx ( ) ,  placeholder_predicate ) ,  trait_ref) 
900890    } 
901891
902892    #[ instrument( skip( self ) ,  level = "debug" ) ]  
903893    fn  confirm_async_closure_candidate ( 
904894        & mut  self , 
905895        obligation :  & PolyTraitObligation < ' tcx > , 
906896    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
897+         let  placeholder_predicate = self . infcx . enter_forall_and_leak_universe ( obligation. predicate ) ; 
898+         let  self_ty = self . infcx . shallow_resolve ( placeholder_predicate. self_ty ( ) ) ; 
899+ 
907900        let  tcx = self . tcx ( ) ; 
908-         let  self_ty = self . infcx . shallow_resolve ( obligation. self_ty ( ) . skip_binder ( ) ) ; 
909901
910902        let  mut  nested = vec ! [ ] ; 
911903        let  ( trait_ref,  kind_ty)  = match  * self_ty. kind ( )  { 
@@ -972,7 +964,9 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
972964            _ => bug ! ( "expected callable type for AsyncFn candidate" ) , 
973965        } ; 
974966
975-         nested. extend ( self . confirm_poly_trait_refs ( obligation,  trait_ref) ?) ; 
967+         nested. extend ( 
968+             self . equate_trait_refs ( obligation. with ( tcx,  placeholder_predicate) ,  trait_ref) ?, 
969+         ) ; 
976970
977971        let  goal_kind =
978972            self . tcx ( ) . async_fn_trait_kind_from_def_id ( obligation. predicate . def_id ( ) ) . unwrap ( ) ; 
@@ -1025,42 +1019,40 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
10251019     /// selection of the impl. Therefore, if there is a mismatch, we 
10261020     /// report an error to the user. 
10271021     #[ instrument( skip( self ) ,  level = "trace" ) ]  
1028-     fn  confirm_poly_trait_refs ( 
1022+     fn  equate_trait_refs ( 
10291023        & mut  self , 
1030-         obligation :  & PolyTraitObligation < ' tcx > , 
1031-         self_ty_trait_ref :  ty:: PolyTraitRef < ' tcx > , 
1024+         obligation :  TraitObligation < ' tcx > , 
1025+         found_trait_ref :  ty:: PolyTraitRef < ' tcx > , 
10321026    )  -> Result < Vec < PredicateObligation < ' tcx > > ,  SelectionError < ' tcx > >  { 
1033-         let  obligation_trait_ref =
1034-             self . infcx . enter_forall_and_leak_universe ( obligation. predicate . to_poly_trait_ref ( ) ) ; 
1035-         let  self_ty_trait_ref = self . infcx . instantiate_binder_with_fresh_vars ( 
1027+         let  found_trait_ref = self . infcx . instantiate_binder_with_fresh_vars ( 
10361028            obligation. cause . span , 
10371029            HigherRankedType , 
1038-             self_ty_trait_ref , 
1030+             found_trait_ref , 
10391031        ) ; 
10401032        // Normalize the obligation and expected trait refs together, because why not 
1041-         let  Normalized  {  obligations :  nested,  value :  ( obligation_trait_ref,  expected_trait_ref )  }  =
1033+         let  Normalized  {  obligations :  nested,  value :  ( obligation_trait_ref,  found_trait_ref )  }  =
10421034            ensure_sufficient_stack ( || { 
10431035                normalize_with_depth ( 
10441036                    self , 
10451037                    obligation. param_env , 
10461038                    obligation. cause . clone ( ) , 
10471039                    obligation. recursion_depth  + 1 , 
1048-                     ( obligation_trait_ref ,  self_ty_trait_ref ) , 
1040+                     ( obligation . predicate . trait_ref ,  found_trait_ref ) , 
10491041                ) 
10501042            } ) ; 
10511043
10521044        // needed to define opaque types for tests/ui/type-alias-impl-trait/assoc-projection-ice.rs 
10531045        self . infcx 
10541046            . at ( & obligation. cause ,  obligation. param_env ) 
1055-             . eq ( DefineOpaqueTypes :: Yes ,  obligation_trait_ref,  expected_trait_ref ) 
1047+             . eq ( DefineOpaqueTypes :: Yes ,  obligation_trait_ref,  found_trait_ref ) 
10561048            . map ( |InferOk  {  mut  obligations,  .. } | { 
10571049                obligations. extend ( nested) ; 
10581050                obligations
10591051            } ) 
10601052            . map_err ( |terr| { 
10611053                SignatureMismatch ( Box :: new ( SignatureMismatchData  { 
10621054                    expected_trait_ref :  ty:: Binder :: dummy ( obligation_trait_ref) , 
1063-                     found_trait_ref :  ty:: Binder :: dummy ( expected_trait_ref ) , 
1055+                     found_trait_ref :  ty:: Binder :: dummy ( found_trait_ref ) , 
10641056                    terr, 
10651057                } ) ) 
10661058            } ) 
0 commit comments