Skip to content

Commit d1f14ee

Browse files
committed
Added several more migrations under ops.rs, failing some tests though
1 parent 33e8aaf commit d1f14ee

File tree

3 files changed

+187
-98
lines changed

3 files changed

+187
-98
lines changed

compiler/rustc_const_eval/src/errors.rs

+81
Original file line numberDiff line numberDiff line change
@@ -111,3 +111,84 @@ pub(crate) struct UnstableConstFn {
111111
pub span: Span,
112112
pub def_id: String,
113113
}
114+
115+
#[derive(SessionDiagnostic)]
116+
#[error(const_eval::unallowed_mutable_refs, code = "E0764")]
117+
pub(crate) struct UnallowedMutableRefs {
118+
#[primary_span]
119+
pub span: Span,
120+
pub kind: ConstContext,
121+
#[note(const_eval::teach_note)]
122+
pub teach: Option<()>,
123+
}
124+
125+
#[derive(SessionDiagnostic)]
126+
#[error(const_eval::unallowed_mutable_refs_raw, code = "E0764")]
127+
pub(crate) struct UnallowedMutableRefsRaw {
128+
#[primary_span]
129+
pub span: Span,
130+
pub kind: ConstContext,
131+
#[note(const_eval::teach_note)]
132+
pub teach: Option<()>,
133+
}
134+
#[derive(SessionDiagnostic)]
135+
#[error(const_eval::non_const_fmt_macro_call, code = "E0015")]
136+
pub(crate) struct NonConstFmtMacroCall {
137+
#[primary_span]
138+
pub span: Span,
139+
pub kind: ConstContext,
140+
}
141+
142+
#[derive(SessionDiagnostic)]
143+
#[error(const_eval::non_const_fn_call, code = "E0015")]
144+
pub(crate) struct NonConstFnCall {
145+
#[primary_span]
146+
pub span: Span,
147+
pub def_path_str: String,
148+
pub kind: ConstContext,
149+
}
150+
151+
#[derive(SessionDiagnostic)]
152+
#[error(const_eval::unallowed_op_in_const_context)]
153+
pub(crate) struct UnallowedOpInConstContext {
154+
#[primary_span]
155+
pub span: Span,
156+
pub msg: String,
157+
}
158+
159+
#[derive(SessionDiagnostic)]
160+
#[error(const_eval::unallowed_heap_allocations, code = "E0010")]
161+
pub(crate) struct UnallowedHeapAllocations {
162+
#[primary_span]
163+
pub span: Span,
164+
pub kind: ConstContext,
165+
#[note(const_eval::teach_note)]
166+
pub teach: Option<()>,
167+
}
168+
169+
#[derive(SessionDiagnostic)]
170+
#[error(const_eval::unallowed_inline_asm, code = "E0015")]
171+
pub(crate) struct UnallowedInlineAsm {
172+
#[primary_span]
173+
pub span: Span,
174+
pub kind: ConstContext,
175+
}
176+
177+
#[derive(SessionDiagnostic)]
178+
#[error(const_eval::interior_mutable_data_refer, code = "E0492")]
179+
pub(crate) struct InteriorMutableDataRefer {
180+
#[primary_span]
181+
pub span: Span,
182+
#[help]
183+
pub opt_help: Option<()>,
184+
pub kind: ConstContext,
185+
#[note(const_eval::teach_note)]
186+
pub teach: Option<()>,
187+
}
188+
189+
#[derive(SessionDiagnostic)]
190+
#[error(const_eval::interior_mutability_borrow)]
191+
pub(crate) struct InteriorMutabilityBorrow {
192+
#[primary_span]
193+
pub span: Span,
194+
}

compiler/rustc_const_eval/src/transform/check_consts/ops.rs

+57-97
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,11 @@ use rustc_trait_selection::traits::SelectionContext;
2424

2525
use super::ConstCx;
2626
use crate::errors::{
27-
MutDerefErr, NonConstOpErr, PanicNonStrErr, RawPtrToIntErr, StaticAccessErr,
28-
TransientMutBorrowErr, TransientMutBorrowErrRaw, UnallowedFnPointerCall, UnstableConstFn,
27+
InteriorMutabilityBorrow, InteriorMutableDataRefer, MutDerefErr, NonConstFmtMacroCall,
28+
NonConstFnCall, NonConstOpErr, PanicNonStrErr, RawPtrToIntErr, StaticAccessErr,
29+
TransientMutBorrowErr, TransientMutBorrowErrRaw, UnallowedFnPointerCall,
30+
UnallowedHeapAllocations, UnallowedInlineAsm, UnallowedMutableRefs, UnallowedMutableRefsRaw,
31+
UnallowedOpInConstContext, UnstableConstFn,
2932
};
3033
use crate::util::{call_kind, CallDesugaringKind, CallKind};
3134

@@ -305,22 +308,13 @@ impl<'tcx> NonConstOp<'tcx> for FnCallNonConst<'tcx> {
305308
err
306309
}
307310
_ if tcx.opt_parent(callee) == tcx.get_diagnostic_item(sym::ArgumentV1Methods) => {
308-
struct_span_err!(
309-
ccx.tcx.sess,
310-
span,
311-
E0015,
312-
"cannot call non-const formatting macro in {}s",
313-
ccx.const_kind(),
314-
)
311+
ccx.tcx.sess.create_err(NonConstFmtMacroCall { span, kind: ccx.const_kind() })
315312
}
316-
_ => struct_span_err!(
317-
ccx.tcx.sess,
313+
_ => ccx.tcx.sess.create_err(NonConstFnCall {
318314
span,
319-
E0015,
320-
"cannot call non-const fn `{}` in {}s",
321-
ccx.tcx.def_path_str_with_substs(callee, substs),
322-
ccx.const_kind(),
323-
),
315+
def_path_str: ccx.tcx.def_path_str_with_substs(callee, substs),
316+
kind: ccx.const_kind(),
317+
}),
324318
};
325319

326320
err.note(&format!(
@@ -387,9 +381,12 @@ impl<'tcx> NonConstOp<'tcx> for Generator {
387381
) -> DiagnosticBuilder<'tcx, ErrorGuaranteed> {
388382
let msg = format!("{}s are not allowed in {}s", self.0, ccx.const_kind());
389383
if let hir::GeneratorKind::Async(hir::AsyncGeneratorKind::Block) = self.0 {
390-
feature_err(&ccx.tcx.sess.parse_sess, sym::const_async_blocks, span, &msg)
384+
ccx.tcx.sess.create_feature_err(
385+
UnallowedOpInConstContext { span, msg },
386+
sym::const_async_blocks,
387+
)
391388
} else {
392-
ccx.tcx.sess.struct_span_err(span, &msg)
389+
ccx.tcx.sess.create_err(UnallowedOpInConstContext { span, msg })
393390
}
394391
}
395392
}
@@ -402,23 +399,11 @@ impl<'tcx> NonConstOp<'tcx> for HeapAllocation {
402399
ccx: &ConstCx<'_, 'tcx>,
403400
span: Span,
404401
) -> DiagnosticBuilder<'tcx, ErrorGuaranteed> {
405-
let mut err = struct_span_err!(
406-
ccx.tcx.sess,
402+
ccx.tcx.sess.create_err(UnallowedHeapAllocations {
407403
span,
408-
E0010,
409-
"allocations are not allowed in {}s",
410-
ccx.const_kind()
411-
);
412-
err.span_label(span, format!("allocation not allowed in {}s", ccx.const_kind()));
413-
if ccx.tcx.sess.teach(&err.get_code().unwrap()) {
414-
err.note(
415-
"The value of statics and constants must be known at compile time, \
416-
and they live for the entire lifetime of a program. Creating a boxed \
417-
value allocates memory on the heap at runtime, and therefore cannot \
418-
be done at compile time.",
419-
);
420-
}
421-
err
404+
kind: ccx.const_kind(),
405+
teach: ccx.tcx.sess.teach(&error_code!(E0010)).then_some(()),
406+
})
422407
}
423408
}
424409

@@ -430,13 +415,7 @@ impl<'tcx> NonConstOp<'tcx> for InlineAsm {
430415
ccx: &ConstCx<'_, 'tcx>,
431416
span: Span,
432417
) -> DiagnosticBuilder<'tcx, ErrorGuaranteed> {
433-
struct_span_err!(
434-
ccx.tcx.sess,
435-
span,
436-
E0015,
437-
"inline assembly is not allowed in {}s",
438-
ccx.const_kind()
439-
)
418+
ccx.tcx.sess.create_err(UnallowedInlineAsm { span, kind: ccx.const_kind() })
440419
}
441420
}
442421

@@ -482,12 +461,7 @@ impl<'tcx> NonConstOp<'tcx> for TransientCellBorrow {
482461
ccx: &ConstCx<'_, 'tcx>,
483462
span: Span,
484463
) -> DiagnosticBuilder<'tcx, ErrorGuaranteed> {
485-
feature_err(
486-
&ccx.tcx.sess.parse_sess,
487-
sym::const_refs_to_cell,
488-
span,
489-
"cannot borrow here, since the borrowed element may contain interior mutability",
490-
)
464+
ccx.tcx.sess.create_feature_err(InteriorMutabilityBorrow { span }, sym::const_refs_to_cell)
491465
}
492466
}
493467

@@ -502,32 +476,22 @@ impl<'tcx> NonConstOp<'tcx> for CellBorrow {
502476
ccx: &ConstCx<'_, 'tcx>,
503477
span: Span,
504478
) -> DiagnosticBuilder<'tcx, ErrorGuaranteed> {
505-
let mut err = struct_span_err!(
506-
ccx.tcx.sess,
507-
span,
508-
E0492,
509-
"{}s cannot refer to interior mutable data",
510-
ccx.const_kind(),
511-
);
512-
err.span_label(
513-
span,
514-
"this borrow of an interior mutable value may end up in the final value",
515-
);
479+
// FIXME: Maybe a more elegant solution to this if else case
516480
if let hir::ConstContext::Static(_) = ccx.const_kind() {
517-
err.help(
518-
"to fix this, the value can be extracted to a separate \
519-
`static` item and then referenced",
520-
);
521-
}
522-
if ccx.tcx.sess.teach(&err.get_code().unwrap()) {
523-
err.note(
524-
"A constant containing interior mutable data behind a reference can allow you
525-
to modify that data. This would make multiple uses of a constant to be able to
526-
see different values and allow circumventing the `Send` and `Sync` requirements
527-
for shared mutable data, which is unsound.",
528-
);
481+
ccx.tcx.sess.create_err(InteriorMutableDataRefer {
482+
span,
483+
opt_help: Some(()),
484+
kind: ccx.const_kind(),
485+
teach: ccx.tcx.sess.teach(&error_code!(E0492)).then_some(()),
486+
})
487+
} else {
488+
ccx.tcx.sess.create_err(InteriorMutableDataRefer {
489+
span,
490+
opt_help: None,
491+
kind: ccx.const_kind(),
492+
teach: ccx.tcx.sess.teach(&error_code!(E0492)).then_some(()),
493+
})
529494
}
530-
err
531495
}
532496
}
533497

@@ -553,33 +517,29 @@ impl<'tcx> NonConstOp<'tcx> for MutBorrow {
553517
ccx: &ConstCx<'_, 'tcx>,
554518
span: Span,
555519
) -> DiagnosticBuilder<'tcx, ErrorGuaranteed> {
556-
let raw = match self.0 {
557-
hir::BorrowKind::Raw => "raw ",
558-
hir::BorrowKind::Ref => "",
559-
};
560-
561-
let mut err = struct_span_err!(
562-
ccx.tcx.sess,
563-
span,
564-
E0764,
565-
"{}mutable references are not allowed in the final value of {}s",
566-
raw,
567-
ccx.const_kind(),
568-
);
569-
570-
if ccx.tcx.sess.teach(&err.get_code().unwrap()) {
571-
err.note(
572-
"References in statics and constants may only refer \
573-
to immutable values.\n\n\
574-
Statics are shared everywhere, and if they refer to \
575-
mutable data one might violate memory safety since \
576-
holding multiple mutable references to shared data \
577-
is not allowed.\n\n\
578-
If you really want global mutable state, try using \
579-
static mut or a global UnsafeCell.",
580-
);
520+
// let raw = match self.0 {
521+
// hir::BorrowKind::Raw => "raw ",
522+
// hir::BorrowKind::Ref => "",
523+
// };
524+
525+
// ccx.tcx.sess.create_err(UnallowedMutableRefs {
526+
// span,
527+
// raw,
528+
// kind: ccx.const_kind(),
529+
// teach: ccx.tcx.sess.teach(&error_code!(E0764)).then_some(()),
530+
// })
531+
match self.0 {
532+
hir::BorrowKind::Raw => ccx.tcx.sess.create_err(UnallowedMutableRefsRaw {
533+
span,
534+
kind: ccx.const_kind(),
535+
teach: ccx.tcx.sess.teach(&error_code!(E0764)).then_some(()),
536+
}),
537+
hir::BorrowKind::Ref => ccx.tcx.sess.create_err(UnallowedMutableRefs {
538+
span,
539+
kind: ccx.const_kind(),
540+
teach: ccx.tcx.sess.teach(&error_code!(E0764)).then_some(()),
541+
}),
581542
}
582-
err
583543
}
584544
}
585545

compiler/rustc_error_messages/locales/en-US/const_eval.ftl

+49-1
Original file line numberDiff line numberDiff line change
@@ -34,4 +34,52 @@ const_evaL_max_num_nodes_exceeded = maximum number of nodes exceeded in constant
3434
3535
const_eval_unallowed_fn_pointer_call = function pointer calls are not allowed in {$kind}s
3636
37-
const_eval_unstable_const_fn = `{$def_id}` is not yet stable as a const fn
37+
const_eval_unstable_const_fn = `{$def_id}` is not yet stable as a const fn
38+
39+
const_eval_unallowed_mutable_refs =
40+
mutable references are not allowed in the final value of {$kind}s
41+
.teach_note =
42+
References in statics and constants may only refer to immutable values.\n\n
43+
Statics are shared everywhere, and if they refer to mutable data one might violate memory
44+
safety since holding multiple mutable references to shared data is not allowed.\n\n
45+
If you really want global mutable state, try using static mut or a global UnsafeCell.
46+
47+
const_eval_unallowed_mutable_refs_raw =
48+
raw mutable references are not allowed in the final value of {$kind}s
49+
.teach_note =
50+
References in statics and constants may only refer to immutable values.\n\n
51+
Statics are shared everywhere, and if they refer to mutable data one might violate memory
52+
safety since holding multiple mutable references to shared data is not allowed.\n\n
53+
If you really want global mutable state, try using static mut or a global UnsafeCell.
54+
55+
const_eval_non_const_fmt_macro_call =
56+
cannot call non-const formatting macro in {$kind}s
57+
58+
const_eval_non_const_fn_call =
59+
cannot call non-const fn `{$def_path_str}` in {$kind}s
60+
61+
const_eval_unallowed_op_in_const_context =
62+
{$msg}
63+
64+
const_eval_unallowed_heap_allocations =
65+
allocations are not allowed in {$kind}s
66+
.label = allocation not allowed in {$kind}s
67+
.teach_note =
68+
The value of statics and constants must be known at compile time, and they live for the entire
69+
lifetime of a program. Creating a boxed value allocates memory on the heap at runtime, and
70+
therefore cannot be done at compile time.
71+
72+
const_eval_unallowed_inline_asm =
73+
inline assembly is not allowed in {$kind}s
74+
75+
const_eval_interior_mutable_data_refer =
76+
{$kind}s cannot refer to interior mutable data
77+
.label = this borrow of an interior mutable value may end up in the final value
78+
.help = to fix this, the value can be extracted to a separate `static` item and then referenced
79+
.teach_note =
80+
A constant containing interior mutable data behind a reference can allow you to modify that data.
81+
This would make multiple uses of a constant to be able to see different values and allow circumventing
82+
the `Send` and `Sync` requirements for shared mutable data, which is unsound.
83+
84+
const_eval_interior_mutability_borrow =
85+
cannot borrow here, since the borrowed element may contain interior mutability

0 commit comments

Comments
 (0)