-
Notifications
You must be signed in to change notification settings - Fork 12.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add MaybeUninit
method array_assume_init
#80600
Conversation
Thanks for the pull request, and welcome! The Rust team is excited to review your changes, and you should hear from @dtolnay (or someone else) soon. If any changes to this PR are deemed necessary, please add them as extra commits. This ensures that the reviewer can see what has changed since they last reviewed the code. Due to the way GitHub handles out-of-date commits, this should also make it reasonably obvious what issues have or haven't been addressed. Large or tricky changes may require several passes of review and changes. Please see the contribution instructions for more information. |
This comment has been minimized.
This comment has been minimized.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks good to me. Could you please open a tracking issue or pick one of the existing maybeuninit ones to track this under?
Here it is: #80908 |
@bors r+ |
📌 Commit dec8c03 has been approved by |
The job Click to see the possible cause of the failure (guessed by this bot)
|
Okay then let's @bors r- until the new implementation is done. |
@bors r+ |
📌 Commit 985071b has been approved by |
Rollup of 8 pull requests Successful merges: - rust-lang#79757 (Replace tabs earlier in diagnostics) - rust-lang#80600 (Add `MaybeUninit` method `array_assume_init`) - rust-lang#80880 (Move some tests to more reasonable directories) - rust-lang#80897 (driver: Use `atty` instead of rolling our own) - rust-lang#80898 (Add another test case for rust-lang#79808) - rust-lang#80917 (core/slice: remove doc comment about scoped borrow) - rust-lang#80927 (Replace a simple `if let` with the `matches` macro) - rust-lang#80930 (fix typo in trait method mutability mismatch help) Failed merges: r? `@ghost` `@rustbot` modify labels: rollup
// * MaybeUnint does not drop, so there are no double-frees | ||
// And thus the conversion is safe | ||
unsafe { | ||
intrinsics::assert_inhabited::<T>(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this assertion really correct?
I tried this code:
#![feature(maybe_uninit_array_assume_init)]
use std::mem::MaybeUninit;
enum Uninhabited {}
fn main() {
unsafe {
MaybeUninit::<Uninhabited>::array_assume_init([]);
}
}
And it panicked with attempted to instantiate uninhabited type `Uninhabited`
.
Compiling playground v0.0.1 (/playground)
Finished dev [unoptimized + debuginfo] target(s) in 1.12s
Running `target/debug/playground`
thread 'main' panicked at 'attempted to instantiate uninhabited type `Uninhabited`', /rustc/f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed/library/core/src/mem/maybe_uninit.rs:842:13
stack backtrace:
0: rust_begin_unwind
at /rustc/f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed/library/std/src/panicking.rs:493:5
1: core::panicking::panic_fmt
at /rustc/f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed/library/core/src/panicking.rs:92:14
2: core::panicking::panic
at /rustc/f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed/library/core/src/panicking.rs:50:5
3: core::mem::maybe_uninit::MaybeUninit<T>::array_assume_init
at /rustc/f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed/library/core/src/mem/maybe_uninit.rs:842:13
4: playground::main
at ./src/main.rs:9:9
5: core::ops::function::FnOnce::call_once
at /rustc/f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed/library/core/src/ops/function.rs:227:5
note: Some details are omitted, run with `RUST_BACKTRACE=full` for a verbose backtrace.
But it seems that creating an array of uninhabited type with length of zero is not UB (playground):
#![forbid(unsafe_code)]
#[derive(Debug)]
enum Uninhabited {}
fn main() {
let not_ub: [Uninhabited; 0] = [];
dbg!(not_ub);
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good point! This should probably be
if N > 0 { assert_inhabited(); }
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll submit a PR to fix it.
…ertion, r=m-ou-se Fix assertion in `MaybeUninit::array_assume_init()` for zero-length arrays That assertion has a false positive ([playground](https://play.rust-lang.org/?version=nightly&mode=debug&edition=2018&gist=63922b8c897b04112adcdf346deb1d0e)): ```rust #![feature(maybe_uninit_array_assume_init)] use std::mem::MaybeUninit; enum Uninhabited {} fn main() { unsafe { // thread 'main' panicked at 'attempted to instantiate uninhabited type `Uninhabited`' MaybeUninit::<Uninhabited>::array_assume_init([]); } } ``` *Previously reported in rust-lang#80600 (comment) This PR makes it ignore zero-length arrays. cc rust-lang#80908
When initialising an array element-by-element, the conversion to the initialised array is done through
mem::transmute
, which is both ugly and does not work with const generics (see #61956). This PR proposes the associated methodarray_assume_init
, matching the style ofslice_assume_init_*
:Example:
Things I'm unsure about: