Auto merge of #91311 - matthiaskrgr:rollup-ju9xizl, r=matthiaskrgr
Rollup of 3 pull requests Successful merges: - #90896 (Stabilize some `MaybeUninit` behavior as const) - #91254 (Only check for errors in predicate when skipping impl assembly) - #91303 (Miri: fix alignment check in array initialization) Failed merges: r? `@ghost` `@rustbot` modify labels: rollup
This commit is contained in:
commit
58f9efd36d
12 changed files with 74 additions and 41 deletions
|
|
@ -242,11 +242,15 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
|
|||
let elem_size = first.layout.size;
|
||||
let first_ptr = first.ptr;
|
||||
let rest_ptr = first_ptr.offset(elem_size, self)?;
|
||||
// For the alignment of `rest_ptr`, we crucially do *not* use `first.align` as
|
||||
// that place might be more aligned than its type mandates (a `u8` array could
|
||||
// be 4-aligned if it sits at the right spot in a struct). Instead we use
|
||||
// `first.layout.align`, i.e., the alignment given by the type.
|
||||
self.memory.copy_repeatedly(
|
||||
first_ptr,
|
||||
first.align,
|
||||
rest_ptr,
|
||||
first.align,
|
||||
first.layout.align.abi,
|
||||
elem_size,
|
||||
length - 1,
|
||||
/*nonoverlapping:*/ true,
|
||||
|
|
|
|||
|
|
@ -536,7 +536,10 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||
// This helps us avoid overflow: see issue #72839
|
||||
// Since compilation is already guaranteed to fail, this is just
|
||||
// to try to show the 'nicest' possible errors to the user.
|
||||
if obligation.references_error() {
|
||||
// We don't check for errors in the `ParamEnv` - in practice,
|
||||
// it seems to cause us to be overly aggressive in deciding
|
||||
// to give up searching for candidates, leading to spurious errors.
|
||||
if obligation.predicate.references_error() {
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -853,7 +853,7 @@ extern "rust-intrinsic" {
|
|||
/// This will statically either panic, or do nothing.
|
||||
///
|
||||
/// This intrinsic does not have a stable counterpart.
|
||||
#[rustc_const_unstable(feature = "const_assert_type", issue = "none")]
|
||||
#[rustc_const_stable(feature = "const_assert_type", since = "1.59.0")]
|
||||
pub fn assert_inhabited<T>();
|
||||
|
||||
/// A guard for unsafe functions that cannot ever be executed if `T` does not permit
|
||||
|
|
|
|||
|
|
@ -101,7 +101,6 @@
|
|||
#![feature(const_align_of_val)]
|
||||
#![feature(const_alloc_layout)]
|
||||
#![feature(const_arguments_as_str)]
|
||||
#![feature(const_assert_type)]
|
||||
#![feature(const_bigint_helper_methods)]
|
||||
#![feature(const_caller_location)]
|
||||
#![feature(const_cell_into_inner)]
|
||||
|
|
@ -117,7 +116,7 @@
|
|||
#![feature(const_intrinsic_copy)]
|
||||
#![feature(const_intrinsic_forget)]
|
||||
#![feature(const_likely)]
|
||||
#![feature(const_maybe_uninit_as_ptr)]
|
||||
#![feature(const_maybe_uninit_as_mut_ptr)]
|
||||
#![feature(const_maybe_uninit_assume_init)]
|
||||
#![feature(const_num_from_num)]
|
||||
#![feature(const_ops)]
|
||||
|
|
|
|||
|
|
@ -528,7 +528,7 @@ impl<T> MaybeUninit<T> {
|
|||
/// (Notice that the rules around references to uninitialized data are not finalized yet, but
|
||||
/// until they are, it is advisable to avoid them.)
|
||||
#[stable(feature = "maybe_uninit", since = "1.36.0")]
|
||||
#[rustc_const_unstable(feature = "const_maybe_uninit_as_ptr", issue = "75251")]
|
||||
#[rustc_const_stable(feature = "const_maybe_uninit_as_ptr", since = "1.59.0")]
|
||||
#[inline(always)]
|
||||
pub const fn as_ptr(&self) -> *const T {
|
||||
// `MaybeUninit` and `ManuallyDrop` are both `repr(transparent)` so we can cast the pointer.
|
||||
|
|
@ -567,7 +567,7 @@ impl<T> MaybeUninit<T> {
|
|||
/// (Notice that the rules around references to uninitialized data are not finalized yet, but
|
||||
/// until they are, it is advisable to avoid them.)
|
||||
#[stable(feature = "maybe_uninit", since = "1.36.0")]
|
||||
#[rustc_const_unstable(feature = "const_maybe_uninit_as_ptr", issue = "75251")]
|
||||
#[rustc_const_unstable(feature = "const_maybe_uninit_as_mut_ptr", issue = "75251")]
|
||||
#[inline(always)]
|
||||
pub const fn as_mut_ptr(&mut self) -> *mut T {
|
||||
// `MaybeUninit` and `ManuallyDrop` are both `repr(transparent)` so we can cast the pointer.
|
||||
|
|
@ -620,7 +620,7 @@ impl<T> MaybeUninit<T> {
|
|||
/// // `x` had not been initialized yet, so this last line caused undefined behavior. ⚠️
|
||||
/// ```
|
||||
#[stable(feature = "maybe_uninit", since = "1.36.0")]
|
||||
#[rustc_const_unstable(feature = "const_maybe_uninit_assume_init", issue = "none")]
|
||||
#[rustc_const_stable(feature = "const_maybe_uninit_assume_init", since = "1.59.0")]
|
||||
#[inline(always)]
|
||||
#[rustc_diagnostic_item = "assume_init"]
|
||||
#[track_caller]
|
||||
|
|
@ -788,7 +788,8 @@ impl<T> MaybeUninit<T> {
|
|||
/// }
|
||||
/// ```
|
||||
#[stable(feature = "maybe_uninit_ref", since = "1.55.0")]
|
||||
#[rustc_const_unstable(feature = "const_maybe_uninit_assume_init", issue = "none")]
|
||||
#[rustc_const_stable(feature = "const_maybe_uninit_assume_init", since = "1.59.0")]
|
||||
#[cfg_attr(bootstrap, rustc_allow_const_fn_unstable(const_raw_ptr_deref))]
|
||||
#[inline(always)]
|
||||
pub const unsafe fn assume_init_ref(&self) -> &T {
|
||||
// SAFETY: the caller must guarantee that `self` is initialized.
|
||||
|
|
@ -968,7 +969,7 @@ impl<T> MaybeUninit<T> {
|
|||
///
|
||||
/// [`assume_init_ref`]: MaybeUninit::assume_init_ref
|
||||
#[unstable(feature = "maybe_uninit_slice", issue = "63569")]
|
||||
#[rustc_const_unstable(feature = "const_maybe_uninit_assume_init", issue = "none")]
|
||||
#[rustc_const_unstable(feature = "maybe_uninit_slice", issue = "63569")]
|
||||
#[inline(always)]
|
||||
pub const unsafe fn slice_assume_init_ref(slice: &[Self]) -> &[T] {
|
||||
// SAFETY: casting slice to a `*const [T]` is safe since the caller guarantees that
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@
|
|||
#![feature(const_assume)]
|
||||
#![feature(const_cell_into_inner)]
|
||||
#![feature(const_convert)]
|
||||
#![feature(const_maybe_uninit_as_mut_ptr)]
|
||||
#![feature(const_maybe_uninit_assume_init)]
|
||||
#![feature(const_ptr_read)]
|
||||
#![feature(const_ptr_write)]
|
||||
|
|
|
|||
|
|
@ -269,3 +269,35 @@ fn uninit_const_assume_init_read() {
|
|||
const FOO: u32 = unsafe { MaybeUninit::new(42).assume_init_read() };
|
||||
assert_eq!(FOO, 42);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn const_maybe_uninit() {
|
||||
use std::ptr;
|
||||
|
||||
#[derive(Debug, PartialEq)]
|
||||
struct Foo {
|
||||
x: u8,
|
||||
y: u8,
|
||||
}
|
||||
|
||||
const FIELD_BY_FIELD: Foo = unsafe {
|
||||
let mut val = MaybeUninit::uninit();
|
||||
init_y(&mut val); // order shouldn't matter
|
||||
init_x(&mut val);
|
||||
val.assume_init()
|
||||
};
|
||||
|
||||
const fn init_x(foo: &mut MaybeUninit<Foo>) {
|
||||
unsafe {
|
||||
*ptr::addr_of_mut!((*foo.as_mut_ptr()).x) = 1;
|
||||
}
|
||||
}
|
||||
|
||||
const fn init_y(foo: &mut MaybeUninit<Foo>) {
|
||||
unsafe {
|
||||
*ptr::addr_of_mut!((*foo.as_mut_ptr()).y) = 2;
|
||||
}
|
||||
}
|
||||
|
||||
assert_eq!(FIELD_BY_FIELD, Foo { x: 1, y: 2 });
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
error: generic parameters may not be used in const operations
|
||||
--> $DIR/issue-72787.rs:12:17
|
||||
--> $DIR/issue-72787.rs:11:17
|
||||
|
|
||||
LL | Condition<{ LHS <= RHS }>: True
|
||||
| ^^^ cannot perform const operation using `LHS`
|
||||
|
|
@ -8,7 +8,7 @@ LL | Condition<{ LHS <= RHS }>: True
|
|||
= help: use `#![feature(generic_const_exprs)]` to allow generic const expressions
|
||||
|
||||
error: generic parameters may not be used in const operations
|
||||
--> $DIR/issue-72787.rs:12:24
|
||||
--> $DIR/issue-72787.rs:11:24
|
||||
|
|
||||
LL | Condition<{ LHS <= RHS }>: True
|
||||
| ^^^ cannot perform const operation using `RHS`
|
||||
|
|
@ -17,7 +17,7 @@ LL | Condition<{ LHS <= RHS }>: True
|
|||
= help: use `#![feature(generic_const_exprs)]` to allow generic const expressions
|
||||
|
||||
error: generic parameters may not be used in const operations
|
||||
--> $DIR/issue-72787.rs:26:25
|
||||
--> $DIR/issue-72787.rs:25:25
|
||||
|
|
||||
LL | IsLessOrEqual<{ 8 - I }, { 8 - J }>: True,
|
||||
| ^ cannot perform const operation using `I`
|
||||
|
|
@ -26,7 +26,7 @@ LL | IsLessOrEqual<{ 8 - I }, { 8 - J }>: True,
|
|||
= help: use `#![feature(generic_const_exprs)]` to allow generic const expressions
|
||||
|
||||
error: generic parameters may not be used in const operations
|
||||
--> $DIR/issue-72787.rs:26:36
|
||||
--> $DIR/issue-72787.rs:25:36
|
||||
|
|
||||
LL | IsLessOrEqual<{ 8 - I }, { 8 - J }>: True,
|
||||
| ^ cannot perform const operation using `J`
|
||||
|
|
@ -35,15 +35,7 @@ LL | IsLessOrEqual<{ 8 - I }, { 8 - J }>: True,
|
|||
= help: use `#![feature(generic_const_exprs)]` to allow generic const expressions
|
||||
|
||||
error[E0283]: type annotations needed
|
||||
--> $DIR/issue-72787.rs:10:38
|
||||
|
|
||||
LL | impl<const LHS: u32, const RHS: u32> True for IsLessOrEqual<LHS, RHS> where
|
||||
| ^^^^ cannot infer type for struct `IsLessOrEqual<LHS, RHS>`
|
||||
|
|
||||
= note: cannot satisfy `IsLessOrEqual<LHS, RHS>: True`
|
||||
|
||||
error[E0283]: type annotations needed
|
||||
--> $DIR/issue-72787.rs:22:26
|
||||
--> $DIR/issue-72787.rs:21:26
|
||||
|
|
||||
LL | IsLessOrEqual<I, 8>: True,
|
||||
| ^^^^ cannot infer type for struct `IsLessOrEqual<I, 8_u32>`
|
||||
|
|
@ -51,13 +43,13 @@ LL | IsLessOrEqual<I, 8>: True,
|
|||
= note: cannot satisfy `IsLessOrEqual<I, 8_u32>: True`
|
||||
|
||||
error[E0283]: type annotations needed
|
||||
--> $DIR/issue-72787.rs:22:26
|
||||
--> $DIR/issue-72787.rs:21:26
|
||||
|
|
||||
LL | IsLessOrEqual<I, 8>: True,
|
||||
| ^^^^ cannot infer type for struct `IsLessOrEqual<I, 8_u32>`
|
||||
|
|
||||
= note: cannot satisfy `IsLessOrEqual<I, 8_u32>: True`
|
||||
|
||||
error: aborting due to 7 previous errors
|
||||
error: aborting due to 6 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0283`.
|
||||
|
|
|
|||
|
|
@ -8,7 +8,6 @@ pub struct Condition<const CONDITION: bool>;
|
|||
pub trait True {}
|
||||
|
||||
impl<const LHS: u32, const RHS: u32> True for IsLessOrEqual<LHS, RHS> where
|
||||
//[min]~^ ERROR type annotations needed
|
||||
Condition<{ LHS <= RHS }>: True
|
||||
//[min]~^ Error generic parameters may not be used in const operations
|
||||
//[min]~| Error generic parameters may not be used in const operations
|
||||
|
|
|
|||
|
|
@ -10,4 +10,4 @@ struct Multiply<N, M> {
|
|||
}
|
||||
impl<N, M> TypeVal<usize> for Multiply<N, M> where N: TypeVal<VAL> {}
|
||||
//~^ ERROR cannot find type `VAL` in this scope
|
||||
//~| ERROR type annotations needed
|
||||
//~| ERROR not all trait items implemented, missing: `VAL`
|
||||
|
|
|
|||
|
|
@ -17,15 +17,16 @@ LL | impl<N, M> TypeVal<usize> for Multiply<N, M> where N: TypeVal<VAL> {}
|
|||
| |
|
||||
| help: you might be missing a type parameter: `, VAL`
|
||||
|
||||
error[E0283]: type annotations needed
|
||||
--> $DIR/issue-77919.rs:11:12
|
||||
error[E0046]: not all trait items implemented, missing: `VAL`
|
||||
--> $DIR/issue-77919.rs:11:1
|
||||
|
|
||||
LL | const VAL: T;
|
||||
| ------------- `VAL` from trait
|
||||
...
|
||||
LL | impl<N, M> TypeVal<usize> for Multiply<N, M> where N: TypeVal<VAL> {}
|
||||
| ^^^^^^^^^^^^^^ cannot infer type for struct `Multiply<N, M>`
|
||||
|
|
||||
= note: cannot satisfy `Multiply<N, M>: TypeVal<usize>`
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ missing `VAL` in implementation
|
||||
|
||||
error: aborting due to 3 previous errors
|
||||
|
||||
Some errors have detailed explanations: E0283, E0412.
|
||||
For more information about an error, try `rustc --explain E0283`.
|
||||
Some errors have detailed explanations: E0046, E0412.
|
||||
For more information about an error, try `rustc --explain E0046`.
|
||||
|
|
|
|||
|
|
@ -21,15 +21,16 @@ LL | impl<N, M> TypeVal<usize> for Multiply<N, M> where N: TypeVal<VAL> {}
|
|||
| |
|
||||
| help: you might be missing a type parameter: `, VAL`
|
||||
|
||||
error[E0283]: type annotations needed
|
||||
--> $DIR/ice-6252.rs:10:12
|
||||
error[E0046]: not all trait items implemented, missing: `VAL`
|
||||
--> $DIR/ice-6252.rs:10:1
|
||||
|
|
||||
LL | const VAL: T;
|
||||
| ------------- `VAL` from trait
|
||||
...
|
||||
LL | impl<N, M> TypeVal<usize> for Multiply<N, M> where N: TypeVal<VAL> {}
|
||||
| ^^^^^^^^^^^^^^ cannot infer type for struct `Multiply<N, M>`
|
||||
|
|
||||
= note: cannot satisfy `Multiply<N, M>: TypeVal<usize>`
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ missing `VAL` in implementation
|
||||
|
||||
error: aborting due to 3 previous errors
|
||||
|
||||
Some errors have detailed explanations: E0283, E0412.
|
||||
For more information about an error, try `rustc --explain E0283`.
|
||||
Some errors have detailed explanations: E0046, E0412.
|
||||
For more information about an error, try `rustc --explain E0046`.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue