Skip to content

Commit 8b50cc9

Browse files
committed
Auto merge of #85769 - jhpratt:stabilize-const-transmute-union, r=RalfJung
Stabilize `const_fn_transmute`, `const_fn_union` This PR stabilizes the `const_fn_transmute` and `const_fn_union` features. It _does not_ stabilize any methods (obviously aside from `transmute`) that are blocked on only these features. Closes #53605. Closes #51909.
2 parents 2faabf5 + 37af399 commit 8b50cc9

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

47 files changed

+147
-535
lines changed

compiler/rustc_ast/src/lib.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
)]
1111
#![feature(box_syntax)]
1212
#![feature(box_patterns)]
13-
#![feature(const_fn_transmute)]
13+
#![cfg_attr(bootstrap, feature(const_fn_transmute))]
1414
#![feature(crate_visibility_modifier)]
1515
#![feature(iter_zip)]
1616
#![feature(label_break_value)]

compiler/rustc_feature/src/accepted.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -290,6 +290,10 @@ declare_features! (
290290
/// Allows bindings in the subpattern of a binding pattern.
291291
/// For example, you can write `x @ Some(y)`.
292292
(accepted, bindings_after_at, "1.54.0", Some(65490), None),
293+
/// Allows calling `transmute` in const fn
294+
(accepted, const_fn_transmute, "1.56.0", Some(53605), None),
295+
/// Allows accessing fields of unions inside `const` functions.
296+
(accepted, const_fn_union, "1.56.0", Some(51909), None),
293297

294298
// -------------------------------------------------------------------------
295299
// feature-group-end: accepted features

compiler/rustc_feature/src/active.rs

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -413,9 +413,6 @@ declare_features! (
413413
/// Allows inferring `'static` outlives requirements (RFC 2093).
414414
(active, infer_static_outlives_requirements, "1.26.0", Some(54185), None),
415415

416-
/// Allows accessing fields of unions inside `const` functions.
417-
(active, const_fn_union, "1.27.0", Some(51909), None),
418-
419416
/// Allows dereferencing raw pointers during const eval.
420417
(active, const_raw_ptr_deref, "1.27.0", Some(51911), None),
421418

@@ -565,9 +562,6 @@ declare_features! (
565562
/// Lazily evaluate constants. This allows constants to depend on type parameters.
566563
(incomplete, lazy_normalization_consts, "1.46.0", Some(72219), None),
567564

568-
/// Allows calling `transmute` in const fn
569-
(active, const_fn_transmute, "1.46.0", Some(53605), None),
570-
571565
/// Allows `if let` guard in match arms.
572566
(incomplete, if_let_guard, "1.47.0", Some(51114), None),
573567

compiler/rustc_mir/src/transform/check_consts/check.rs

Lines changed: 1 addition & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -748,12 +748,7 @@ impl Visitor<'tcx> for Checker<'mir, 'tcx> {
748748
| ProjectionElem::Downcast(..)
749749
| ProjectionElem::Subslice { .. }
750750
| ProjectionElem::Field(..)
751-
| ProjectionElem::Index(_) => {
752-
let base_ty = Place::ty_from(place_local, proj_base, self.body, self.tcx).ty;
753-
if base_ty.is_union() {
754-
self.check_op(ops::UnionAccess);
755-
}
756-
}
751+
| ProjectionElem::Index(_) => {}
757752
}
758753
}
759754

@@ -876,15 +871,6 @@ impl Visitor<'tcx> for Checker<'mir, 'tcx> {
876871

877872
let is_intrinsic = tcx.fn_sig(callee).abi() == RustIntrinsic;
878873

879-
// HACK: This is to "unstabilize" the `transmute` intrinsic
880-
// within const fns. `transmute` is allowed in all other const contexts.
881-
// This won't really scale to more intrinsics or functions. Let's allow const
882-
// transmutes in const fn before we add more hacks to this.
883-
if is_intrinsic && tcx.item_name(callee) == sym::transmute {
884-
self.check_op(ops::Transmute);
885-
return;
886-
}
887-
888874
if !tcx.is_const_fn_raw(callee) {
889875
let mut permitted = false;
890876

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

Lines changed: 0 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -501,51 +501,6 @@ impl NonConstOp for ThreadLocalAccess {
501501
}
502502
}
503503

504-
#[derive(Debug)]
505-
pub struct Transmute;
506-
impl NonConstOp for Transmute {
507-
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
508-
if ccx.const_kind() != hir::ConstContext::ConstFn {
509-
Status::Allowed
510-
} else {
511-
Status::Unstable(sym::const_fn_transmute)
512-
}
513-
}
514-
515-
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
516-
let mut err = feature_err(
517-
&ccx.tcx.sess.parse_sess,
518-
sym::const_fn_transmute,
519-
span,
520-
&format!("`transmute` is not allowed in {}s", ccx.const_kind()),
521-
);
522-
err.note("`transmute` is only allowed in constants and statics for now");
523-
err
524-
}
525-
}
526-
527-
#[derive(Debug)]
528-
pub struct UnionAccess;
529-
impl NonConstOp for UnionAccess {
530-
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
531-
// Union accesses are stable in all contexts except `const fn`.
532-
if ccx.const_kind() != hir::ConstContext::ConstFn {
533-
Status::Allowed
534-
} else {
535-
Status::Unstable(sym::const_fn_union)
536-
}
537-
}
538-
539-
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
540-
feature_err(
541-
&ccx.tcx.sess.parse_sess,
542-
sym::const_fn_union,
543-
span,
544-
"unions in const fn are unstable",
545-
)
546-
}
547-
}
548-
549504
// Types that cannot appear in the signature or locals of a `const fn`.
550505
pub mod ty {
551506
use super::*;

library/core/src/intrinsics.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -911,6 +911,9 @@ extern "rust-intrinsic" {
911911
/// cause [undefined behavior][ub] with this function. `transmute` should be
912912
/// the absolute last resort.
913913
///
914+
/// Transmuting pointers to integers in a `const` context is [undefined behavior][ub].
915+
/// Any attempt to use the resulting value for integer operations will abort const-evaluation.
916+
///
914917
/// The [nomicon](../../nomicon/transmutes.html) has additional
915918
/// documentation.
916919
///
@@ -1128,8 +1131,6 @@ extern "rust-intrinsic" {
11281131
/// }
11291132
/// ```
11301133
#[stable(feature = "rust1", since = "1.0.0")]
1131-
// NOTE: While this makes the intrinsic const stable, we have some custom code in const fn
1132-
// checks that prevent its use within `const fn`.
11331134
#[rustc_const_stable(feature = "const_transmute", since = "1.46.0")]
11341135
#[rustc_diagnostic_item = "transmute"]
11351136
pub fn transmute<T, U>(e: T) -> U;

library/core/src/lib.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@
8686
#![feature(const_refs_to_cell)]
8787
#![feature(const_panic)]
8888
#![feature(const_pin)]
89-
#![feature(const_fn_union)]
89+
#![cfg_attr(bootstrap, feature(const_fn_union))]
9090
#![feature(const_impl_trait)]
9191
#![feature(const_fn_floating_point_arithmetic)]
9292
#![feature(const_fn_fn_ptr_basics)]
@@ -159,7 +159,7 @@
159159
#![feature(rtm_target_feature)]
160160
#![feature(f16c_target_feature)]
161161
#![feature(hexagon_target_feature)]
162-
#![feature(const_fn_transmute)]
162+
#![cfg_attr(bootstrap, feature(const_fn_transmute))]
163163
#![feature(abi_unadjusted)]
164164
#![feature(adx_target_feature)]
165165
#![feature(associated_type_bounds)]

library/core/src/num/int_macros.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2096,7 +2096,7 @@ macro_rules! int_impl {
20962096
#[rustc_const_stable(feature = "const_int_conversion", since = "1.44.0")]
20972097
// SAFETY: const sound because integers are plain old datatypes so we can always
20982098
// transmute them to arrays of bytes
2099-
#[rustc_allow_const_fn_unstable(const_fn_transmute)]
2099+
#[cfg_attr(bootstrap, rustc_allow_const_fn_unstable(const_fn_transmute))]
21002100
#[inline]
21012101
pub const fn to_ne_bytes(self) -> [u8; mem::size_of::<Self>()] {
21022102
// SAFETY: integers are plain old datatypes so we can always transmute them to
@@ -2202,7 +2202,7 @@ macro_rules! int_impl {
22022202
#[rustc_const_stable(feature = "const_int_conversion", since = "1.44.0")]
22032203
// SAFETY: const sound because integers are plain old datatypes so we can always
22042204
// transmute to them
2205-
#[rustc_allow_const_fn_unstable(const_fn_transmute)]
2205+
#[cfg_attr(bootstrap, rustc_allow_const_fn_unstable(const_fn_transmute))]
22062206
#[inline]
22072207
pub const fn from_ne_bytes(bytes: [u8; mem::size_of::<Self>()]) -> Self {
22082208
// SAFETY: integers are plain old datatypes so we can always transmute to them

library/core/src/num/uint_macros.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1926,7 +1926,7 @@ macro_rules! uint_impl {
19261926
#[rustc_const_stable(feature = "const_int_conversion", since = "1.44.0")]
19271927
// SAFETY: const sound because integers are plain old datatypes so we can always
19281928
// transmute them to arrays of bytes
1929-
#[rustc_allow_const_fn_unstable(const_fn_transmute)]
1929+
#[cfg_attr(bootstrap, rustc_allow_const_fn_unstable(const_fn_transmute))]
19301930
#[inline]
19311931
pub const fn to_ne_bytes(self) -> [u8; mem::size_of::<Self>()] {
19321932
// SAFETY: integers are plain old datatypes so we can always transmute them to
@@ -2032,7 +2032,7 @@ macro_rules! uint_impl {
20322032
#[rustc_const_stable(feature = "const_int_conversion", since = "1.44.0")]
20332033
// SAFETY: const sound because integers are plain old datatypes so we can always
20342034
// transmute to them
2035-
#[rustc_allow_const_fn_unstable(const_fn_transmute)]
2035+
#[cfg_attr(bootstrap, rustc_allow_const_fn_unstable(const_fn_transmute))]
20362036
#[inline]
20372037
pub const fn from_ne_bytes(bytes: [u8; mem::size_of::<Self>()]) -> Self {
20382038
// SAFETY: integers are plain old datatypes so we can always transmute to them

library/core/src/slice/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -100,7 +100,7 @@ impl<T> [T] {
100100
#[rustc_const_stable(feature = "const_slice_len", since = "1.39.0")]
101101
#[inline]
102102
// SAFETY: const sound because we transmute out the length field as a usize (which it must be)
103-
#[rustc_allow_const_fn_unstable(const_fn_union)]
103+
#[cfg_attr(bootstrap, rustc_allow_const_fn_unstable(const_fn_union))]
104104
pub const fn len(&self) -> usize {
105105
// FIXME: Replace with `crate::ptr::metadata(self)` when that is const-stable.
106106
// As of this writing this causes a "Const-stable functions can only call other

0 commit comments

Comments
 (0)