Skip to content

Commit 0404753

Browse files
committed
wip on using ConstArg for const item bodies
1 parent 54b9a85 commit 0404753

File tree

11 files changed

+152
-83
lines changed

11 files changed

+152
-83
lines changed

compiler/rustc_ast_lowering/src/item.rs

Lines changed: 34 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -193,18 +193,20 @@ impl<'hir> LoweringContext<'_, 'hir> {
193193
..
194194
}) => {
195195
let ident = self.lower_ident(*ident);
196-
let (generics, (ty, body_id)) = self.lower_generics(
196+
let (generics, (ty, body)) = self.lower_generics(
197197
generics,
198198
id,
199199
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
200200
|this| {
201201
let ty = this
202202
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
203-
(ty, this.lower_const_item(span, body_id.zip(expr.as_deref())))
203+
let body =
204+
this.lower_const_item(span, body_id.unwrap(), expr.as_deref().unwrap());
205+
(ty, body)
204206
},
205207
);
206208
self.lower_define_opaque(hir_id, &define_opaque);
207-
hir::ItemKind::Const(ident, ty, generics, body_id)
209+
hir::ItemKind::Const(ident, ty, generics, body)
208210
}
209211
ItemKind::Fn(box Fn {
210212
sig: FnSig { decl, header, span: fn_sig_span },
@@ -484,21 +486,27 @@ impl<'hir> LoweringContext<'_, 'hir> {
484486
}
485487
}
486488

487-
fn lower_const_item(&mut self, span: Span, body: Option<(NodeId, &Expr)>) -> hir::BodyId {
488-
self.lower_const_body(span, body.map(|b| b.1))
489-
// TODO: code to add next
490-
// let mgca = self.tcx.features().min_generic_const_args();
491-
// let ct_arg = if mgca && let Some((_, expr)) = body {
492-
// self.try_lower_as_const_path(expr)
493-
// } else {
494-
// None
495-
// };
496-
// let body_id = if mgca && ct_arg.is_none() {
497-
// self.lower_const_body_with_const_block(span, body)
498-
// } else {
499-
// self.lower_const_body(span, body.map(|(_, e)| e))
500-
// };
501-
// (body_id, ct_arg)
489+
fn lower_const_item(
490+
&mut self,
491+
span: Span,
492+
body_id: NodeId,
493+
body_expr: &Expr,
494+
) -> &'hir hir::ConstArg<'hir> {
495+
let mgca = self.tcx.features().min_generic_const_args();
496+
if mgca && let Some(ct_arg) = self.try_lower_as_const_path(body_expr) {
497+
return ct_arg;
498+
}
499+
let anon = self.arena.alloc(self.with_new_scopes(span, |this| {
500+
let body = this.lower_const_body(span, Some(body_expr));
501+
hir::AnonConst {
502+
hir_id: this.lower_node_id(body_id),
503+
def_id: this.local_def_id(body_id),
504+
body,
505+
span,
506+
}
507+
}));
508+
self.arena
509+
.alloc(hir::ConstArg { hir_id: self.next_id(), kind: hir::ConstArgKind::Anon(anon) })
502510
}
503511

504512
#[instrument(level = "debug", skip(self))]
@@ -808,9 +816,9 @@ impl<'hir> LoweringContext<'_, 'hir> {
808816
|this| {
809817
let ty = this
810818
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
811-
let body = expr
812-
.as_deref()
813-
.map(|e| this.lower_const_item(i.span, Some((body_id.unwrap(), e))));
819+
let body = body_id
820+
.zip(expr.as_deref())
821+
.map(|(b_id, b_ex)| this.lower_const_item(i.span, b_id, b_ex));
814822
hir::TraitItemKind::Const(ty, body)
815823
},
816824
);
@@ -1004,7 +1012,11 @@ impl<'hir> LoweringContext<'_, 'hir> {
10041012
let ty = this
10051013
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
10061014
this.lower_define_opaque(hir_id, &define_opaque);
1007-
let body = this.lower_const_item(i.span, body_id.zip(expr.as_deref()));
1015+
let body = this.lower_const_item(
1016+
i.span,
1017+
body_id.unwrap(),
1018+
expr.as_deref().unwrap(),
1019+
);
10081020
hir::ImplItemKind::Const(ty, body)
10091021
},
10101022
),
@@ -1281,8 +1293,6 @@ impl<'hir> LoweringContext<'_, 'hir> {
12811293
self.lower_fn_body(decl, contract, |this| this.lower_block_expr(body))
12821294
}
12831295

1284-
// TODO: add lower_const_body_with_const_block
1285-
12861296
pub(super) fn lower_const_body(&mut self, span: Span, expr: Option<&Expr>) -> hir::BodyId {
12871297
self.lower_body(|this| {
12881298
(

compiler/rustc_ast_lowering/src/lib.rs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2084,6 +2084,22 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
20842084
}
20852085
}
20862086

2087+
/// Assumes mgca feature is enabled.
2088+
fn try_lower_as_const_path(&mut self, expr: &Expr) -> Option<&'hir hir::ConstArg<'hir>> {
2089+
let ExprKind::Path(qself, path) = &expr.kind else { return None };
2090+
let qpath = self.lower_qpath(
2091+
expr.id,
2092+
qself,
2093+
path,
2094+
ParamMode::Optional,
2095+
AllowReturnTypeNotation::No,
2096+
ImplTraitContext::Disallowed(ImplTraitPosition::Path),
2097+
None,
2098+
);
2099+
let ct_kind = hir::ConstArgKind::Path(qpath);
2100+
Some(self.arena.alloc(hir::ConstArg { hir_id: self.next_id(), kind: ct_kind }))
2101+
}
2102+
20872103
/// Used when lowering a type argument that turned out to actually be a const argument.
20882104
///
20892105
/// Only use for that purpose since otherwise it will create a duplicate def.

compiler/rustc_hir/src/hir.rs

Lines changed: 39 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -3096,7 +3096,7 @@ impl<'hir> TraitItem<'hir> {
30963096
}
30973097

30983098
expect_methods_self_kind! {
3099-
expect_const, (&'hir Ty<'hir>, Option<BodyId>),
3099+
expect_const, (&'hir Ty<'hir>, Option<&'hir ConstArg<'hir>>),
31003100
TraitItemKind::Const(ty, body), (ty, *body);
31013101

31023102
expect_fn, (&FnSig<'hir>, &TraitFn<'hir>),
@@ -3121,7 +3121,7 @@ pub enum TraitFn<'hir> {
31213121
#[derive(Debug, Clone, Copy, HashStable_Generic)]
31223122
pub enum TraitItemKind<'hir> {
31233123
/// An associated constant with an optional value (otherwise `impl`s must contain a value).
3124-
Const(&'hir Ty<'hir>, Option<BodyId>),
3124+
Const(&'hir Ty<'hir>, Option<&'hir ConstArg<'hir>>),
31253125
/// An associated function with an optional body.
31263126
Fn(FnSig<'hir>, TraitFn<'hir>),
31273127
/// An associated type with (possibly empty) bounds and optional concrete
@@ -3171,9 +3171,9 @@ impl<'hir> ImplItem<'hir> {
31713171
}
31723172

31733173
expect_methods_self_kind! {
3174-
expect_const, (&'hir Ty<'hir>, BodyId), ImplItemKind::Const(ty, body), (ty, *body);
3175-
expect_fn, (&FnSig<'hir>, BodyId), ImplItemKind::Fn(ty, body), (ty, *body);
3176-
expect_type, &'hir Ty<'hir>, ImplItemKind::Type(ty), ty;
3174+
expect_const, (&'hir Ty<'hir>, &'hir ConstArg<'hir>), ImplItemKind::Const(ty, body), (ty, body);
3175+
expect_fn, (&FnSig<'hir>, BodyId), ImplItemKind::Fn(ty, body), (ty, *body);
3176+
expect_type, &'hir Ty<'hir>, ImplItemKind::Type(ty), ty;
31773177
}
31783178
}
31793179

@@ -3182,7 +3182,7 @@ impl<'hir> ImplItem<'hir> {
31823182
pub enum ImplItemKind<'hir> {
31833183
/// An associated constant of the given type, set to the constant result
31843184
/// of the expression.
3185-
Const(&'hir Ty<'hir>, BodyId),
3185+
Const(&'hir Ty<'hir>, &'hir ConstArg<'hir>),
31863186
/// An associated function implementation with the given signature and body.
31873187
Fn(FnSig<'hir>, BodyId),
31883188
/// An associated type.
@@ -4109,8 +4109,8 @@ impl<'hir> Item<'hir> {
41094109
expect_static, (Ident, &'hir Ty<'hir>, Mutability, BodyId),
41104110
ItemKind::Static(ident, ty, mutbl, body), (*ident, ty, *mutbl, *body);
41114111

4112-
expect_const, (Ident, &'hir Ty<'hir>, &'hir Generics<'hir>, BodyId),
4113-
ItemKind::Const(ident, ty, generics, body), (*ident, ty, generics, *body);
4112+
expect_const, (Ident, &'hir Ty<'hir>, &'hir Generics<'hir>, &'hir ConstArg<'hir>),
4113+
ItemKind::Const(ident, ty, generics, ct_arg), (*ident, ty, generics, ct_arg);
41144114

41154115
expect_fn, (Ident, &FnSig<'hir>, &'hir Generics<'hir>, BodyId),
41164116
ItemKind::Fn { ident, sig, generics, body, .. }, (*ident, sig, generics, *body);
@@ -4280,7 +4280,7 @@ pub enum ItemKind<'hir> {
42804280
/// A `static` item.
42814281
Static(Ident, &'hir Ty<'hir>, Mutability, BodyId),
42824282
/// A `const` item.
4283-
Const(Ident, &'hir Ty<'hir>, &'hir Generics<'hir>, BodyId),
4283+
Const(Ident, &'hir Ty<'hir>, &'hir Generics<'hir>, &'hir ConstArg<'hir>),
42844284
/// A function declaration.
42854285
Fn {
42864286
ident: Ident,
@@ -4578,17 +4578,29 @@ impl<'hir> OwnerNode<'hir> {
45784578
OwnerNode::Item(Item {
45794579
kind:
45804580
ItemKind::Static(_, _, _, body)
4581-
| ItemKind::Const(_, _, _, body)
4581+
| ItemKind::Const(
4582+
..,
4583+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4584+
)
45824585
| ItemKind::Fn { body, .. },
45834586
..
45844587
})
45854588
| OwnerNode::TraitItem(TraitItem {
45864589
kind:
4587-
TraitItemKind::Fn(_, TraitFn::Provided(body)) | TraitItemKind::Const(_, Some(body)),
4590+
TraitItemKind::Fn(_, TraitFn::Provided(body))
4591+
| TraitItemKind::Const(
4592+
_,
4593+
Some(ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. }),
4594+
),
45884595
..
45894596
})
45904597
| OwnerNode::ImplItem(ImplItem {
4591-
kind: ImplItemKind::Fn(_, body) | ImplItemKind::Const(_, body),
4598+
kind:
4599+
ImplItemKind::Fn(_, body)
4600+
| ImplItemKind::Const(
4601+
_,
4602+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4603+
),
45924604
..
45934605
}) => Some(*body),
45944606
_ => None,
@@ -4835,20 +4847,32 @@ impl<'hir> Node<'hir> {
48354847
Node::Item(Item {
48364848
owner_id,
48374849
kind:
4838-
ItemKind::Const(_, _, _, body)
4850+
ItemKind::Const(
4851+
..,
4852+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4853+
)
48394854
| ItemKind::Static(.., body)
48404855
| ItemKind::Fn { body, .. },
48414856
..
48424857
})
48434858
| Node::TraitItem(TraitItem {
48444859
owner_id,
48454860
kind:
4846-
TraitItemKind::Const(_, Some(body)) | TraitItemKind::Fn(_, TraitFn::Provided(body)),
4861+
TraitItemKind::Const(
4862+
_,
4863+
Some(ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. }),
4864+
)
4865+
| TraitItemKind::Fn(_, TraitFn::Provided(body)),
48474866
..
48484867
})
48494868
| Node::ImplItem(ImplItem {
48504869
owner_id,
4851-
kind: ImplItemKind::Const(_, body) | ImplItemKind::Fn(_, body),
4870+
kind:
4871+
ImplItemKind::Const(
4872+
_,
4873+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4874+
)
4875+
| ImplItemKind::Fn(_, body),
48524876
..
48534877
}) => Some((owner_id.def_id, *body)),
48544878

compiler/rustc_hir/src/intravisit.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -554,7 +554,7 @@ pub fn walk_item<'v, V: Visitor<'v>>(visitor: &mut V, item: &'v Item<'v>) -> V::
554554
try_visit!(visitor.visit_ident(ident));
555555
try_visit!(visitor.visit_ty_unambig(typ));
556556
try_visit!(visitor.visit_generics(generics));
557-
try_visit!(visitor.visit_nested_body(body));
557+
try_visit!(visitor.visit_const_arg_unambig(body));
558558
}
559559
ItemKind::Fn { ident, sig, generics, body: body_id, .. } => {
560560
try_visit!(visitor.visit_ident(ident));
@@ -1168,7 +1168,7 @@ pub fn walk_trait_item<'v, V: Visitor<'v>>(
11681168
match *kind {
11691169
TraitItemKind::Const(ref ty, default) => {
11701170
try_visit!(visitor.visit_ty_unambig(ty));
1171-
visit_opt!(visitor, visit_nested_body, default);
1171+
visit_opt!(visitor, visit_const_arg_unambig, default);
11721172
}
11731173
TraitItemKind::Fn(ref sig, TraitFn::Required(param_idents)) => {
11741174
try_visit!(visitor.visit_fn_decl(sig.decl));
@@ -1226,7 +1226,7 @@ pub fn walk_impl_item<'v, V: Visitor<'v>>(
12261226
match *kind {
12271227
ImplItemKind::Const(ref ty, body) => {
12281228
try_visit!(visitor.visit_ty_unambig(ty));
1229-
visitor.visit_nested_body(body)
1229+
visitor.visit_const_arg_unambig(body)
12301230
}
12311231
ImplItemKind::Fn(ref sig, body_id) => visitor.visit_fn(
12321232
FnKind::Method(impl_item.ident, sig),

compiler/rustc_hir_analysis/src/collect/type_of.rs

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -157,13 +157,13 @@ pub(super) fn type_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::EarlyBinder<'_
157157
let args = ty::GenericArgs::identity_for_item(tcx, def_id);
158158
Ty::new_fn_def(tcx, def_id.to_def_id(), args)
159159
}
160-
TraitItemKind::Const(ty, body_id) => body_id
161-
.and_then(|body_id| {
160+
TraitItemKind::Const(ty, body) => body
161+
.and_then(|ct_arg| {
162162
ty.is_suggestable_infer_ty().then(|| {
163163
infer_placeholder_type(
164164
icx.lowerer(),
165165
def_id,
166-
body_id,
166+
ct_arg.hir_id,
167167
ty.span,
168168
item.ident,
169169
"associated constant",
@@ -182,12 +182,12 @@ pub(super) fn type_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::EarlyBinder<'_
182182
let args = ty::GenericArgs::identity_for_item(tcx, def_id);
183183
Ty::new_fn_def(tcx, def_id.to_def_id(), args)
184184
}
185-
ImplItemKind::Const(ty, body_id) => {
185+
ImplItemKind::Const(ty, ct_arg) => {
186186
if ty.is_suggestable_infer_ty() {
187187
infer_placeholder_type(
188188
icx.lowerer(),
189189
def_id,
190-
body_id,
190+
ct_arg.hir_id,
191191
ty.span,
192192
item.ident,
193193
"associated constant",
@@ -211,7 +211,7 @@ pub(super) fn type_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::EarlyBinder<'_
211211
infer_placeholder_type(
212212
icx.lowerer(),
213213
def_id,
214-
body_id,
214+
body_id.hir_id,
215215
ty.span,
216216
ident,
217217
"static variable",
@@ -220,12 +220,12 @@ pub(super) fn type_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::EarlyBinder<'_
220220
icx.lower_ty(ty)
221221
}
222222
}
223-
ItemKind::Const(ident, ty, _, body_id) => {
223+
ItemKind::Const(ident, ty, _, body) => {
224224
if ty.is_suggestable_infer_ty() {
225225
infer_placeholder_type(
226226
icx.lowerer(),
227227
def_id,
228-
body_id,
228+
body.hir_id,
229229
ty.span,
230230
ident,
231231
"constant",
@@ -406,13 +406,13 @@ pub(super) fn type_of_opaque_hir_typeck(
406406
fn infer_placeholder_type<'tcx>(
407407
cx: &dyn HirTyLowerer<'tcx>,
408408
def_id: LocalDefId,
409-
body_id: hir::BodyId,
409+
hir_id: HirId,
410410
span: Span,
411411
item_ident: Ident,
412412
kind: &'static str,
413413
) -> Ty<'tcx> {
414414
let tcx = cx.tcx();
415-
let ty = tcx.typeck(def_id).node_type(body_id.hir_id);
415+
let ty = tcx.typeck(def_id).node_type(hir_id);
416416

417417
// If this came from a free `const` or `static mut?` item,
418418
// then the user may have written e.g. `const A = 42;`.
@@ -440,7 +440,7 @@ fn infer_placeholder_type<'tcx>(
440440
);
441441
} else {
442442
with_forced_trimmed_paths!(err.span_note(
443-
tcx.hir_body(body_id).value.span,
443+
tcx.hir_span(hir_id),
444444
format!("however, the inferred type `{ty}` cannot be named"),
445445
));
446446
}
@@ -483,7 +483,7 @@ fn infer_placeholder_type<'tcx>(
483483
);
484484
} else {
485485
with_forced_trimmed_paths!(diag.span_note(
486-
tcx.hir_body(body_id).value.span,
486+
tcx.hir_span(hir_id),
487487
format!("however, the inferred type `{ty}` cannot be named"),
488488
));
489489
}

0 commit comments

Comments
 (0)