@@ -142,6 +142,8 @@ struct LoweringContext<'a, 'hir> {
142142 /// defined on the TAIT, so we have type Foo<'a1> = ... and we establish a mapping in this
143143 /// field from the original parameter 'a to the new parameter 'a1.
144144 generics_def_id_map : Vec < FxHashMap < LocalDefId , LocalDefId > > ,
145+
146+ host_param_id : Option < LocalDefId > ,
145147}
146148
147149trait ResolverAstLoweringExt {
@@ -1262,6 +1264,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
12621264 span : t. span
12631265 } ,
12641266 itctx,
1267+ ast:: Const :: No ,
12651268 ) ;
12661269 let bounds = this. arena . alloc_from_iter ( [ bound] ) ;
12671270 let lifetime_bound = this. elided_dyn_bound ( t. span ) ;
@@ -1272,7 +1275,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
12721275 }
12731276
12741277 let id = self . lower_node_id ( t. id ) ;
1275- let qpath = self . lower_qpath ( t. id , qself, path, param_mode, itctx) ;
1278+ let qpath = self . lower_qpath ( t. id , qself, path, param_mode, itctx, None ) ;
12761279 self . ty_path ( id, t. span , qpath)
12771280 }
12781281
@@ -1356,10 +1359,12 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
13561359 this. arena . alloc_from_iter ( bounds. iter ( ) . filter_map ( |bound| match bound {
13571360 GenericBound :: Trait (
13581361 ty,
1359- TraitBoundModifier :: None
1362+ modifier @ ( TraitBoundModifier :: None
13601363 | TraitBoundModifier :: MaybeConst
1361- | TraitBoundModifier :: Negative ,
1362- ) => Some ( this. lower_poly_trait_ref ( ty, itctx) ) ,
1364+ | TraitBoundModifier :: Negative ) ,
1365+ ) => {
1366+ Some ( this. lower_poly_trait_ref ( ty, itctx, modifier. to_constness ( ) ) )
1367+ }
13631368 // `~const ?Bound` will cause an error during AST validation
13641369 // anyways, so treat it like `?Bound` as compilation proceeds.
13651370 GenericBound :: Trait (
@@ -1952,7 +1957,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
19521957 ) -> hir:: GenericBound < ' hir > {
19531958 match tpb {
19541959 GenericBound :: Trait ( p, modifier) => hir:: GenericBound :: Trait (
1955- self . lower_poly_trait_ref ( p, itctx) ,
1960+ self . lower_poly_trait_ref ( p, itctx, modifier . to_constness ( ) ) ,
19561961 self . lower_trait_bound_modifier ( * modifier) ,
19571962 ) ,
19581963 GenericBound :: Outlives ( lifetime) => {
@@ -2095,8 +2100,20 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
20952100 }
20962101 }
20972102
2098- fn lower_trait_ref ( & mut self , p : & TraitRef , itctx : & ImplTraitContext ) -> hir:: TraitRef < ' hir > {
2099- let path = match self . lower_qpath ( p. ref_id , & None , & p. path , ParamMode :: Explicit , itctx) {
2103+ fn lower_trait_ref (
2104+ & mut self ,
2105+ constness : ast:: Const ,
2106+ p : & TraitRef ,
2107+ itctx : & ImplTraitContext ,
2108+ ) -> hir:: TraitRef < ' hir > {
2109+ let path = match self . lower_qpath (
2110+ p. ref_id ,
2111+ & None ,
2112+ & p. path ,
2113+ ParamMode :: Explicit ,
2114+ itctx,
2115+ Some ( constness) ,
2116+ ) {
21002117 hir:: QPath :: Resolved ( None , path) => path,
21012118 qpath => panic ! ( "lower_trait_ref: unexpected QPath `{qpath:?}`" ) ,
21022119 } ;
@@ -2108,10 +2125,11 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
21082125 & mut self ,
21092126 p : & PolyTraitRef ,
21102127 itctx : & ImplTraitContext ,
2128+ constness : ast:: Const ,
21112129 ) -> hir:: PolyTraitRef < ' hir > {
21122130 let bound_generic_params =
21132131 self . lower_lifetime_binder ( p. trait_ref . ref_id , & p. bound_generic_params ) ;
2114- let trait_ref = self . lower_trait_ref ( & p. trait_ref , itctx) ;
2132+ let trait_ref = self . lower_trait_ref ( constness , & p. trait_ref , itctx) ;
21152133 hir:: PolyTraitRef { bound_generic_params, trait_ref, span : self . lower_span ( p. span ) }
21162134 }
21172135
@@ -2465,6 +2483,67 @@ struct GenericArgsCtor<'hir> {
24652483}
24662484
24672485impl < ' hir > GenericArgsCtor < ' hir > {
2486+ fn push_constness ( & mut self , lcx : & mut LoweringContext < ' _ , ' hir > , constness : ast:: Const ) {
2487+ if !lcx. tcx . features ( ) . effects {
2488+ return ;
2489+ }
2490+
2491+ // if bound is non-const, don't add host effect param
2492+ let ast:: Const :: Yes ( span) = constness else { return } ;
2493+
2494+ let span = lcx. lower_span ( span) ;
2495+
2496+ let id = lcx. next_node_id ( ) ;
2497+ let hir_id = lcx. next_id ( ) ;
2498+ let body = lcx. lower_body ( |lcx| {
2499+ (
2500+ & [ ] ,
2501+ match constness {
2502+ ast:: Const :: Yes ( _) => {
2503+ let hir_id = lcx. next_id ( ) ;
2504+ let res =
2505+ Res :: Def ( DefKind :: ConstParam , lcx. host_param_id . unwrap ( ) . to_def_id ( ) ) ;
2506+ let expr_kind = hir:: ExprKind :: Path ( hir:: QPath :: Resolved (
2507+ None ,
2508+ lcx. arena . alloc ( hir:: Path {
2509+ span,
2510+ res,
2511+ segments : arena_vec ! [ lcx; hir:: PathSegment :: new( Ident {
2512+ name: sym:: host,
2513+ span,
2514+ } , hir_id, res) ] ,
2515+ } ) ,
2516+ ) ) ;
2517+ lcx. expr ( span, expr_kind)
2518+ }
2519+ ast:: Const :: No => lcx. expr (
2520+ span,
2521+ hir:: ExprKind :: Lit (
2522+ lcx. arena . alloc ( hir:: Lit { span, node : ast:: LitKind :: Bool ( true ) } ) ,
2523+ ) ,
2524+ ) ,
2525+ } ,
2526+ )
2527+ } ) ;
2528+
2529+ let attr_id = lcx. tcx . sess . parse_sess . attr_id_generator . mk_attr_id ( ) ;
2530+ let attr = lcx. arena . alloc ( Attribute {
2531+ kind : AttrKind :: Normal ( P ( NormalAttr :: from_ident ( Ident :: new ( sym:: rustc_host, span) ) ) ) ,
2532+ span,
2533+ id : attr_id,
2534+ style : AttrStyle :: Outer ,
2535+ } ) ;
2536+ lcx. attrs . insert ( hir_id. local_id , std:: slice:: from_ref ( attr) ) ;
2537+
2538+ let def_id =
2539+ lcx. create_def ( lcx. current_hir_id_owner . def_id , id, DefPathData :: AnonConst , span) ;
2540+ lcx. children . push ( ( def_id, hir:: MaybeOwner :: NonOwner ( hir_id) ) ) ;
2541+ self . args . push ( hir:: GenericArg :: Const ( hir:: ConstArg {
2542+ value : hir:: AnonConst { def_id, hir_id, body } ,
2543+ span,
2544+ } ) )
2545+ }
2546+
24682547 fn is_empty ( & self ) -> bool {
24692548 self . args . is_empty ( )
24702549 && self . bindings . is_empty ( )
0 commit comments