@@ -35,16 +35,59 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
3535 let parent_node_id = tcx. parent_hir_id ( hir_id) ;
3636 let parent_node = tcx. hir_node ( parent_node_id) ;
3737
38+ match parent_node {
39+ // Anon consts "inside" the type system.
40+ Node :: ConstArg ( & ConstArg {
41+ hir_id : arg_hir_id,
42+ kind : ConstArgKind :: Anon ( & AnonConst { hir_id : anon_hir_id, .. } ) ,
43+ ..
44+ } ) if anon_hir_id == hir_id => const_arg_anon_type_of ( tcx, arg_hir_id, def_id, span) ,
45+
46+ // Anon consts outside the type system.
47+ Node :: Expr ( & Expr { kind : ExprKind :: InlineAsm ( asm) , .. } )
48+ | Node :: Item ( & Item { kind : ItemKind :: GlobalAsm ( asm) , .. } )
49+ if asm. operands . iter ( ) . any ( |( op, _op_sp) | match op {
50+ hir:: InlineAsmOperand :: Const { anon_const }
51+ | hir:: InlineAsmOperand :: SymFn { anon_const } => anon_const. hir_id == hir_id,
52+ _ => false ,
53+ } ) =>
54+ {
55+ tcx. typeck ( def_id) . node_type ( hir_id)
56+ }
57+ Node :: Variant ( Variant { disr_expr : Some ( ref e) , .. } ) if e. hir_id == hir_id => {
58+ tcx. adt_def ( tcx. hir ( ) . get_parent_item ( hir_id) ) . repr ( ) . discr_type ( ) . to_ty ( tcx)
59+ }
60+
61+ _ => Ty :: new_error_with_message (
62+ tcx,
63+ span,
64+ format ! ( "unexpected anon const parent in type_of(): {parent_node:?}" ) ,
65+ ) ,
66+ }
67+ }
68+
69+ fn const_arg_anon_type_of < ' tcx > (
70+ tcx : TyCtxt < ' tcx > ,
71+ arg_hir_id : HirId ,
72+ anon_def_id : LocalDefId ,
73+ span : Span ,
74+ ) -> Ty < ' tcx > {
75+ use hir:: * ;
76+ use rustc_middle:: ty:: Ty ;
77+
78+ let parent_node_id = tcx. parent_hir_id ( arg_hir_id) ;
79+ let parent_node = tcx. hir_node ( parent_node_id) ;
80+
3881 let ( generics, arg_idx) = match parent_node {
3982 // Easy case: arrays repeat expressions.
4083 Node :: Ty ( & hir:: Ty { kind : TyKind :: Array ( _, ref constant) , .. } )
4184 | Node :: Expr ( & Expr { kind : ExprKind :: Repeat ( _, ref constant) , .. } )
42- if constant. hir_id ( ) == hir_id =>
85+ if constant. hir_id ( ) == arg_hir_id =>
4386 {
4487 return tcx. types . usize ;
4588 }
46- Node :: Ty ( & hir:: Ty { kind : TyKind :: Typeof ( ref e) , span, .. } ) if e. hir_id == hir_id => {
47- let ty = tcx. typeck ( def_id ) . node_type ( e . hir_id ) ;
89+ Node :: Ty ( & hir:: Ty { kind : TyKind :: Typeof ( ref e) , span, .. } ) if e. hir_id == arg_hir_id => {
90+ let ty = tcx. typeck ( anon_def_id ) . node_type ( tcx . local_def_id_to_hir_id ( anon_def_id ) ) ;
4891 let ty = tcx. fold_regions ( ty, |r, _| {
4992 if r. is_erased ( ) { ty:: Region :: new_error_misc ( tcx) } else { r }
5093 } ) ;
@@ -56,24 +99,11 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
5699 tcx. dcx ( ) . emit_err ( TypeofReservedKeywordUsed { span, ty, opt_sugg } ) ;
57100 return ty;
58101 }
59- Node :: Expr ( & Expr { kind : ExprKind :: InlineAsm ( asm) , .. } )
60- | Node :: Item ( & Item { kind : ItemKind :: GlobalAsm ( asm) , .. } )
61- if asm. operands . iter ( ) . any ( |( op, _op_sp) | match op {
62- hir:: InlineAsmOperand :: Const { anon_const }
63- | hir:: InlineAsmOperand :: SymFn { anon_const } => anon_const. hir_id == hir_id,
64- _ => false ,
65- } ) =>
66- {
67- return tcx. typeck ( def_id) . node_type ( hir_id) ;
68- }
69- Node :: Variant ( Variant { disr_expr : Some ( ref e) , .. } ) if e. hir_id == hir_id => {
70- return tcx. adt_def ( tcx. hir ( ) . get_parent_item ( hir_id) ) . repr ( ) . discr_type ( ) . to_ty ( tcx) ;
71- }
72102 Node :: GenericParam ( & GenericParam {
73103 def_id : param_def_id,
74104 kind : GenericParamKind :: Const { default : Some ( ct) , .. } ,
75105 ..
76- } ) if ct. hir_id == hir_id => {
106+ } ) if ct. hir_id == arg_hir_id => {
77107 return tcx
78108 . type_of ( param_def_id)
79109 . no_bound_vars ( )
@@ -104,7 +134,7 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
104134 // to a ty::Alias(ty::Projection, `<Self as Foo>::Assoc<3>`).
105135 let item_def_id = tcx
106136 . hir ( )
107- . parent_owner_iter ( hir_id )
137+ . parent_owner_iter ( arg_hir_id )
108138 . find ( |( _, node) | matches ! ( node, OwnerNode :: Item ( _) ) )
109139 . unwrap ( )
110140 . 0
@@ -124,7 +154,7 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
124154 args. args
125155 . iter ( )
126156 . filter ( |arg| arg. is_ty_or_const ( ) )
127- . position ( |arg| arg. hir_id ( ) == hir_id )
157+ . position ( |arg| arg. hir_id ( ) == arg_hir_id )
128158 } )
129159 . unwrap_or_else ( || {
130160 bug ! ( "no arg matching AnonConst in segment" ) ;
@@ -145,7 +175,7 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
145175 ExprKind :: MethodCall ( segment, ..) | ExprKind :: Path ( QPath :: TypeRelative ( _, segment) ) ,
146176 ..
147177 } ) => {
148- let body_owner = tcx. hir ( ) . enclosing_body_owner ( hir_id ) ;
178+ let body_owner = tcx. hir ( ) . enclosing_body_owner ( arg_hir_id ) ;
149179 let tables = tcx. typeck ( body_owner) ;
150180 // This may fail in case the method/path does not actually exist.
151181 // As there is no relevant param for `def_id`, we simply return
@@ -163,10 +193,10 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
163193 args. args
164194 . iter ( )
165195 . filter ( |arg| arg. is_ty_or_const ( ) )
166- . position ( |arg| arg. hir_id ( ) == hir_id )
196+ . position ( |arg| arg. hir_id ( ) == arg_hir_id )
167197 } )
168198 . unwrap_or_else ( || {
169- bug ! ( "no arg matching AnonConst in segment" ) ;
199+ bug ! ( "no arg matching ConstArg in segment" ) ;
170200 } ) ;
171201
172202 ( tcx. generics_of ( type_dependent_def) , idx)
@@ -185,18 +215,18 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
185215 | ExprKind :: Struct ( & QPath :: Resolved ( _, path) , ..) ,
186216 ..
187217 } ) => {
188- let body_owner = tcx. hir ( ) . enclosing_body_owner ( hir_id ) ;
218+ let body_owner = tcx. hir ( ) . enclosing_body_owner ( arg_hir_id ) ;
189219 let _tables = tcx. typeck ( body_owner) ;
190220 & * path
191221 }
192222 Node :: Pat ( pat) => {
193- if let Some ( path) = get_path_containing_arg_in_pat ( pat, hir_id ) {
223+ if let Some ( path) = get_path_containing_arg_in_pat ( pat, arg_hir_id ) {
194224 path
195225 } else {
196226 return Ty :: new_error_with_message (
197227 tcx,
198228 span,
199- format ! ( "unable to find const parent for {hir_id } in pat {pat:?}" ) ,
229+ format ! ( "unable to find const parent for {arg_hir_id } in pat {pat:?}" ) ,
200230 ) ;
201231 }
202232 }
@@ -217,14 +247,14 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
217247 args. args
218248 . iter ( )
219249 . filter ( |arg| arg. is_ty_or_const ( ) )
220- . position ( |arg| arg. hir_id ( ) == hir_id )
250+ . position ( |arg| arg. hir_id ( ) == arg_hir_id )
221251 . map ( |index| ( index, seg) )
222252 . or_else ( || {
223253 args. constraints
224254 . iter ( )
225255 . copied ( )
226256 . filter_map ( AssocItemConstraint :: ct)
227- . position ( |ct| ct. hir_id == hir_id )
257+ . position ( |ct| ct. hir_id == arg_hir_id )
228258 . map ( |idx| ( idx, seg) )
229259 } )
230260 } ) else {
@@ -249,7 +279,7 @@ fn anon_const_type_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Ty<'tcx> {
249279 return Ty :: new_error_with_message (
250280 tcx,
251281 span,
252- format ! ( "unexpected const parent in type_of(): {parent_node:?}" ) ,
282+ format ! ( "unexpected const arg parent in type_of(): {parent_node:?}" ) ,
253283 ) ;
254284 }
255285 } ;
0 commit comments