@@ -669,30 +669,11 @@ fn project<'cx, 'tcx>(
669669
670670    match  candidates { 
671671        ProjectionCandidateSet :: Single ( candidate)  => { 
672-             Ok ( Projected :: Progress ( confirm_candidate ( selcx,  obligation,  candidate) ) ) 
672+             confirm_candidate ( selcx,  obligation,  candidate) 
673673        } 
674674        ProjectionCandidateSet :: None  => { 
675675            let  tcx = selcx. tcx ( ) ; 
676-             let  term = match  tcx. def_kind ( obligation. predicate . def_id )  { 
677-                 DefKind :: AssocTy  => Ty :: new_projection_from_args ( 
678-                     tcx, 
679-                     obligation. predicate . def_id , 
680-                     obligation. predicate . args , 
681-                 ) 
682-                 . into ( ) , 
683-                 DefKind :: AssocConst  => ty:: Const :: new_unevaluated ( 
684-                     tcx, 
685-                     ty:: UnevaluatedConst :: new ( 
686-                         obligation. predicate . def_id , 
687-                         obligation. predicate . args , 
688-                     ) , 
689-                 ) 
690-                 . into ( ) , 
691-                 kind => { 
692-                     bug ! ( "unknown projection def-id: {}" ,  kind. descr( obligation. predicate. def_id) ) 
693-                 } 
694-             } ; 
695- 
676+             let  term = obligation. predicate . to_term ( tcx) ; 
696677            Ok ( Projected :: NoProgress ( term) ) 
697678        } 
698679        // Error occurred while trying to processing impls. 
@@ -1244,18 +1225,16 @@ fn confirm_candidate<'cx, 'tcx>(
12441225    selcx :  & mut  SelectionContext < ' cx ,  ' tcx > , 
12451226    obligation :  & ProjectionTermObligation < ' tcx > , 
12461227    candidate :  ProjectionCandidate < ' tcx > , 
1247- )  -> Progress < ' tcx >  { 
1228+ )  -> Result < Projected < ' tcx > ,   ProjectionError < ' tcx > >  { 
12481229    debug ! ( ?obligation,  ?candidate,  "confirm_candidate" ) ; 
1249-     let  mut  progress  = match  candidate { 
1230+     let  mut  result  = match  candidate { 
12501231        ProjectionCandidate :: ParamEnv ( poly_projection) 
1251-         | ProjectionCandidate :: Object ( poly_projection)  => { 
1252-             confirm_param_env_candidate ( selcx,  obligation,  poly_projection,  false ) 
1253-         } 
1254- 
1255-         ProjectionCandidate :: TraitDef ( poly_projection)  => { 
1256-             confirm_param_env_candidate ( selcx,  obligation,  poly_projection,  true ) 
1257-         } 
1258- 
1232+         | ProjectionCandidate :: Object ( poly_projection)  => Ok ( Projected :: Progress ( 
1233+             confirm_param_env_candidate ( selcx,  obligation,  poly_projection,  false ) , 
1234+         ) ) , 
1235+         ProjectionCandidate :: TraitDef ( poly_projection)  => Ok ( Projected :: Progress ( 
1236+             confirm_param_env_candidate ( selcx,  obligation,  poly_projection,  true ) , 
1237+         ) ) , 
12591238        ProjectionCandidate :: Select ( impl_source)  => { 
12601239            confirm_select_candidate ( selcx,  obligation,  impl_source) 
12611240        } 
@@ -1266,23 +1245,26 @@ fn confirm_candidate<'cx, 'tcx>(
12661245    // with new region variables, we need to resolve them to existing variables 
12671246    // when possible for this to work. See `auto-trait-projection-recursion.rs` 
12681247    // for a case where this matters. 
1269-     if  progress. term . has_infer_regions ( )  { 
1248+     if  let  Ok ( Projected :: Progress ( progress) )  = & mut  result
1249+         && progress. term . has_infer_regions ( ) 
1250+     { 
12701251        progress. term  = progress. term . fold_with ( & mut  OpportunisticRegionResolver :: new ( selcx. infcx ) ) ; 
12711252    } 
1272-     progress
1253+ 
1254+     result
12731255} 
12741256
12751257fn  confirm_select_candidate < ' cx ,  ' tcx > ( 
12761258    selcx :  & mut  SelectionContext < ' cx ,  ' tcx > , 
12771259    obligation :  & ProjectionTermObligation < ' tcx > , 
12781260    impl_source :  Selection < ' tcx > , 
1279- )  -> Progress < ' tcx >  { 
1261+ )  -> Result < Projected < ' tcx > ,   ProjectionError < ' tcx > >  { 
12801262    match  impl_source { 
12811263        ImplSource :: UserDefined ( data)  => confirm_impl_candidate ( selcx,  obligation,  data) , 
12821264        ImplSource :: Builtin ( BuiltinImplSource :: Misc  | BuiltinImplSource :: Trivial ,  data)  => { 
12831265            let  tcx = selcx. tcx ( ) ; 
12841266            let  trait_def_id = obligation. predicate . trait_def_id ( tcx) ; 
1285-             if  tcx. is_lang_item ( trait_def_id,  LangItem :: Coroutine )  { 
1267+             let  progress =  if  tcx. is_lang_item ( trait_def_id,  LangItem :: Coroutine )  { 
12861268                confirm_coroutine_candidate ( selcx,  obligation,  data) 
12871269            }  else  if  tcx. is_lang_item ( trait_def_id,  LangItem :: Future )  { 
12881270                confirm_future_candidate ( selcx,  obligation,  data) 
@@ -1304,7 +1286,8 @@ fn confirm_select_candidate<'cx, 'tcx>(
13041286                confirm_async_fn_kind_helper_candidate ( selcx,  obligation,  data) 
13051287            }  else  { 
13061288                confirm_builtin_candidate ( selcx,  obligation,  data) 
1307-             } 
1289+             } ; 
1290+             Ok ( Projected :: Progress ( progress) ) 
13081291        } 
13091292        ImplSource :: Builtin ( BuiltinImplSource :: Object  {  .. } ,  _) 
13101293        | ImplSource :: Param ( ..) 
@@ -2000,7 +1983,7 @@ fn confirm_impl_candidate<'cx, 'tcx>(
20001983    selcx :  & mut  SelectionContext < ' cx ,  ' tcx > , 
20011984    obligation :  & ProjectionTermObligation < ' tcx > , 
20021985    impl_impl_source :  ImplSourceUserDefinedData < ' tcx ,  PredicateObligation < ' tcx > > , 
2003- )  -> Progress < ' tcx >  { 
1986+ )  -> Result < Projected < ' tcx > ,   ProjectionError < ' tcx > >  { 
20041987    let  tcx = selcx. tcx ( ) ; 
20051988
20061989    let  ImplSourceUserDefinedData  {  impl_def_id,  args,  mut  nested }  = impl_impl_source; 
@@ -2011,19 +1994,33 @@ fn confirm_impl_candidate<'cx, 'tcx>(
20111994    let  param_env = obligation. param_env ; 
20121995    let  assoc_ty = match  specialization_graph:: assoc_def ( tcx,  impl_def_id,  assoc_item_id)  { 
20131996        Ok ( assoc_ty)  => assoc_ty, 
2014-         Err ( guar)  => return  Progress :: error ( tcx,  guar) , 
1997+         Err ( guar)  => return  Ok ( Projected :: Progress ( Progress :: error ( tcx,  guar) ) ) , 
20151998    } ; 
1999+ 
2000+     // This means that the impl is missing a definition for the 
2001+     // associated type. This is either because the associate item 
2002+     // has impossible-to-satisfy predicates (since those were 
2003+     // allowed in <https://github.com/rust-lang/rust/pull/135480>), 
2004+     // or because the impl is literally missing the definition. 
20162005    if  !assoc_ty. item . defaultness ( tcx) . has_value ( )  { 
2017-         // This means that the impl is missing a definition for the 
2018-         // associated type. This error will be reported by the type 
2019-         // checker method `check_impl_items_against_trait`, so here we 
2020-         // just return Error. 
20212006        debug ! ( 
20222007            "confirm_impl_candidate: no associated type {:?} for {:?}" , 
20232008            assoc_ty. item. name,  obligation. predicate
20242009        ) ; 
2025-         return  Progress  {  term :  Ty :: new_misc_error ( tcx) . into ( ) ,  obligations :  nested } ; 
2010+         if  tcx. impl_self_is_guaranteed_unsized ( impl_def_id)  { 
2011+             // We treat this projection as rigid here, which is represented via 
2012+             // `Projected::NoProgress`. This will ensure that the projection is 
2013+             // checked for well-formedness, and it's either satisfied by a trivial 
2014+             // where clause in its env or it results in an error. 
2015+             return  Ok ( Projected :: NoProgress ( obligation. predicate . to_term ( tcx) ) ) ; 
2016+         }  else  { 
2017+             return  Ok ( Projected :: Progress ( Progress  { 
2018+                 term :  Ty :: new_misc_error ( tcx) . into ( ) , 
2019+                 obligations :  nested, 
2020+             } ) ) ; 
2021+         } 
20262022    } 
2023+ 
20272024    // If we're trying to normalize `<Vec<u32> as X>::A<S>` using 
20282025    //`impl<T> X for Vec<T> { type A<Y> = Box<Y>; }`, then: 
20292026    // 
@@ -2033,6 +2030,7 @@ fn confirm_impl_candidate<'cx, 'tcx>(
20332030    let  args = obligation. predicate . args . rebase_onto ( tcx,  trait_def_id,  args) ; 
20342031    let  args = translate_args ( selcx. infcx ,  param_env,  impl_def_id,  args,  assoc_ty. defining_node ) ; 
20352032    let  is_const = matches ! ( tcx. def_kind( assoc_ty. item. def_id) ,  DefKind :: AssocConst ) ; 
2033+ 
20362034    let  term:  ty:: EarlyBinder < ' tcx ,  ty:: Term < ' tcx > >  = if  is_const { 
20372035        let  did = assoc_ty. item . def_id ; 
20382036        let  identity_args = crate :: traits:: GenericArgs :: identity_for_item ( tcx,  did) ; 
@@ -2041,7 +2039,8 @@ fn confirm_impl_candidate<'cx, 'tcx>(
20412039    }  else  { 
20422040        tcx. type_of ( assoc_ty. item . def_id ) . map_bound ( |ty| ty. into ( ) ) 
20432041    } ; 
2044-     if  !tcx. check_args_compatible ( assoc_ty. item . def_id ,  args)  { 
2042+ 
2043+     let  progress = if  !tcx. check_args_compatible ( assoc_ty. item . def_id ,  args)  { 
20452044        let  err = Ty :: new_error_with_message ( 
20462045            tcx, 
20472046            obligation. cause . span , 
@@ -2051,7 +2050,8 @@ fn confirm_impl_candidate<'cx, 'tcx>(
20512050    }  else  { 
20522051        assoc_ty_own_obligations ( selcx,  obligation,  & mut  nested) ; 
20532052        Progress  {  term :  term. instantiate ( tcx,  args) ,  obligations :  nested } 
2054-     } 
2053+     } ; 
2054+     Ok ( Projected :: Progress ( progress) ) 
20552055} 
20562056
20572057// Get obligations corresponding to the predicates from the where-clause of the 
0 commit comments