Skip to content

Commit a46aa4c

Browse files
committed
wip on using ConstArg for const item bodies
1 parent e9568e8 commit a46aa4c

File tree

12 files changed

+160
-92
lines changed

12 files changed

+160
-92
lines changed

compiler/rustc_ast_lowering/src/item.rs

Lines changed: 34 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -205,18 +205,20 @@ impl<'hir> LoweringContext<'_, 'hir> {
205205
..
206206
}) => {
207207
let ident = self.lower_ident(*ident);
208-
let (generics, (ty, body_id)) = self.lower_generics(
208+
let (generics, (ty, body)) = self.lower_generics(
209209
generics,
210210
id,
211211
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
212212
|this| {
213213
let ty = this
214214
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
215-
(ty, this.lower_const_item(span, body_id.zip(expr.as_deref())))
215+
let body =
216+
this.lower_const_item(span, body_id.unwrap(), expr.as_deref().unwrap());
217+
(ty, body)
216218
},
217219
);
218220
self.lower_define_opaque(hir_id, &define_opaque);
219-
hir::ItemKind::Const(ident, ty, generics, body_id)
221+
hir::ItemKind::Const(ident, ty, generics, body)
220222
}
221223
ItemKind::Fn(box Fn {
222224
sig: FnSig { decl, header, span: fn_sig_span },
@@ -496,21 +498,27 @@ impl<'hir> LoweringContext<'_, 'hir> {
496498
}
497499
}
498500

499-
fn lower_const_item(&mut self, span: Span, body: Option<(NodeId, &Expr)>) -> hir::BodyId {
500-
self.lower_const_body(span, body.map(|b| b.1))
501-
// TODO: code to add next
502-
// let mgca = self.tcx.features().min_generic_const_args();
503-
// let ct_arg = if mgca && let Some((_, expr)) = body {
504-
// self.try_lower_as_const_path(expr)
505-
// } else {
506-
// None
507-
// };
508-
// let body_id = if mgca && ct_arg.is_none() {
509-
// self.lower_const_body_with_const_block(span, body)
510-
// } else {
511-
// self.lower_const_body(span, body.map(|(_, e)| e))
512-
// };
513-
// (body_id, ct_arg)
501+
fn lower_const_item(
502+
&mut self,
503+
span: Span,
504+
body_id: NodeId,
505+
body_expr: &Expr,
506+
) -> &'hir hir::ConstArg<'hir> {
507+
let mgca = self.tcx.features().min_generic_const_args();
508+
if mgca && let Some(ct_arg) = self.try_lower_as_const_path(body_expr) {
509+
return ct_arg;
510+
}
511+
let anon = self.arena.alloc(self.with_new_scopes(span, |this| {
512+
let body = this.lower_const_body(span, Some(body_expr));
513+
hir::AnonConst {
514+
hir_id: this.lower_node_id(body_id),
515+
def_id: this.local_def_id(body_id),
516+
body,
517+
span,
518+
}
519+
}));
520+
self.arena
521+
.alloc(hir::ConstArg { hir_id: self.next_id(), kind: hir::ConstArgKind::Anon(anon) })
514522
}
515523

516524
#[instrument(level = "debug", skip(self))]
@@ -820,9 +828,9 @@ impl<'hir> LoweringContext<'_, 'hir> {
820828
|this| {
821829
let ty = this
822830
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
823-
let body = expr
824-
.as_deref()
825-
.map(|e| this.lower_const_item(i.span, Some((body_id.unwrap(), e))));
831+
let body = body_id
832+
.zip(expr.as_deref())
833+
.map(|(b_id, b_ex)| this.lower_const_item(i.span, b_id, b_ex));
826834
hir::TraitItemKind::Const(ty, body)
827835
},
828836
);
@@ -1016,7 +1024,11 @@ impl<'hir> LoweringContext<'_, 'hir> {
10161024
let ty = this
10171025
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
10181026
this.lower_define_opaque(hir_id, &define_opaque);
1019-
let body = this.lower_const_item(i.span, body_id.zip(expr.as_deref()));
1027+
let body = this.lower_const_item(
1028+
i.span,
1029+
body_id.unwrap(),
1030+
expr.as_deref().unwrap(),
1031+
);
10201032
hir::ImplItemKind::Const(ty, body)
10211033
},
10221034
),
@@ -1293,8 +1305,6 @@ impl<'hir> LoweringContext<'_, 'hir> {
12931305
self.lower_fn_body(decl, contract, |this| this.lower_block_expr(body))
12941306
}
12951307

1296-
// TODO: add lower_const_body_with_const_block
1297-
12981308
pub(super) fn lower_const_body(&mut self, span: Span, expr: Option<&Expr>) -> hir::BodyId {
12991309
self.lower_body(|this| {
13001310
(

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
@@ -3094,7 +3094,7 @@ impl<'hir> TraitItem<'hir> {
30943094
}
30953095

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

31003100
expect_fn, (&FnSig<'hir>, &TraitFn<'hir>),
@@ -3119,7 +3119,7 @@ pub enum TraitFn<'hir> {
31193119
#[derive(Debug, Clone, Copy, HashStable_Generic)]
31203120
pub enum TraitItemKind<'hir> {
31213121
/// An associated constant with an optional value (otherwise `impl`s must contain a value).
3122-
Const(&'hir Ty<'hir>, Option<BodyId>),
3122+
Const(&'hir Ty<'hir>, Option<&'hir ConstArg<'hir>>),
31233123
/// An associated function with an optional body.
31243124
Fn(FnSig<'hir>, TraitFn<'hir>),
31253125
/// An associated type with (possibly empty) bounds and optional concrete
@@ -3169,9 +3169,9 @@ impl<'hir> ImplItem<'hir> {
31693169
}
31703170

31713171
expect_methods_self_kind! {
3172-
expect_const, (&'hir Ty<'hir>, BodyId), ImplItemKind::Const(ty, body), (ty, *body);
3173-
expect_fn, (&FnSig<'hir>, BodyId), ImplItemKind::Fn(ty, body), (ty, *body);
3174-
expect_type, &'hir Ty<'hir>, ImplItemKind::Type(ty), ty;
3172+
expect_const, (&'hir Ty<'hir>, &'hir ConstArg<'hir>), ImplItemKind::Const(ty, body), (ty, body);
3173+
expect_fn, (&FnSig<'hir>, BodyId), ImplItemKind::Fn(ty, body), (ty, *body);
3174+
expect_type, &'hir Ty<'hir>, ImplItemKind::Type(ty), ty;
31753175
}
31763176
}
31773177

@@ -3180,7 +3180,7 @@ impl<'hir> ImplItem<'hir> {
31803180
pub enum ImplItemKind<'hir> {
31813181
/// An associated constant of the given type, set to the constant result
31823182
/// of the expression.
3183-
Const(&'hir Ty<'hir>, BodyId),
3183+
Const(&'hir Ty<'hir>, &'hir ConstArg<'hir>),
31843184
/// An associated function implementation with the given signature and body.
31853185
Fn(FnSig<'hir>, BodyId),
31863186
/// An associated type.
@@ -4107,8 +4107,8 @@ impl<'hir> Item<'hir> {
41074107
expect_static, (Ident, &'hir Ty<'hir>, Mutability, BodyId),
41084108
ItemKind::Static(ident, ty, mutbl, body), (*ident, ty, *mutbl, *body);
41094109

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

41134113
expect_fn, (Ident, &FnSig<'hir>, &'hir Generics<'hir>, BodyId),
41144114
ItemKind::Fn { ident, sig, generics, body, .. }, (*ident, sig, generics, *body);
@@ -4278,7 +4278,7 @@ pub enum ItemKind<'hir> {
42784278
/// A `static` item.
42794279
Static(Ident, &'hir Ty<'hir>, Mutability, BodyId),
42804280
/// A `const` item.
4281-
Const(Ident, &'hir Ty<'hir>, &'hir Generics<'hir>, BodyId),
4281+
Const(Ident, &'hir Ty<'hir>, &'hir Generics<'hir>, &'hir ConstArg<'hir>),
42824282
/// A function declaration.
42834283
Fn {
42844284
ident: Ident,
@@ -4576,17 +4576,29 @@ impl<'hir> OwnerNode<'hir> {
45764576
OwnerNode::Item(Item {
45774577
kind:
45784578
ItemKind::Static(_, _, _, body)
4579-
| ItemKind::Const(_, _, _, body)
4579+
| ItemKind::Const(
4580+
..,
4581+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4582+
)
45804583
| ItemKind::Fn { body, .. },
45814584
..
45824585
})
45834586
| OwnerNode::TraitItem(TraitItem {
45844587
kind:
4585-
TraitItemKind::Fn(_, TraitFn::Provided(body)) | TraitItemKind::Const(_, Some(body)),
4588+
TraitItemKind::Fn(_, TraitFn::Provided(body))
4589+
| TraitItemKind::Const(
4590+
_,
4591+
Some(ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. }),
4592+
),
45864593
..
45874594
})
45884595
| OwnerNode::ImplItem(ImplItem {
4589-
kind: ImplItemKind::Fn(_, body) | ImplItemKind::Const(_, body),
4596+
kind:
4597+
ImplItemKind::Fn(_, body)
4598+
| ImplItemKind::Const(
4599+
_,
4600+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4601+
),
45904602
..
45914603
}) => Some(*body),
45924604
_ => None,
@@ -4833,20 +4845,32 @@ impl<'hir> Node<'hir> {
48334845
Node::Item(Item {
48344846
owner_id,
48354847
kind:
4836-
ItemKind::Const(_, _, _, body)
4848+
ItemKind::Const(
4849+
..,
4850+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4851+
)
48374852
| ItemKind::Static(.., body)
48384853
| ItemKind::Fn { body, .. },
48394854
..
48404855
})
48414856
| Node::TraitItem(TraitItem {
48424857
owner_id,
48434858
kind:
4844-
TraitItemKind::Const(_, Some(body)) | TraitItemKind::Fn(_, TraitFn::Provided(body)),
4859+
TraitItemKind::Const(
4860+
_,
4861+
Some(ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. }),
4862+
)
4863+
| TraitItemKind::Fn(_, TraitFn::Provided(body)),
48454864
..
48464865
})
48474866
| Node::ImplItem(ImplItem {
48484867
owner_id,
4849-
kind: ImplItemKind::Const(_, body) | ImplItemKind::Fn(_, body),
4868+
kind:
4869+
ImplItemKind::Const(
4870+
_,
4871+
ConstArg { kind: ConstArgKind::Anon(AnonConst { body, .. }), .. },
4872+
)
4873+
| ImplItemKind::Fn(_, body),
48504874
..
48514875
}) => Some((owner_id.def_id, *body)),
48524876

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)