-
Notifications
You must be signed in to change notification settings - Fork 22
Description
Proposal
Problem statement
MaybeUninit<T>
is required for references in order to maintain soundness, but no such restrictions exist for pointers, and *const MaybeUninit<T>
is mostly just an unnecessary layer of abstraction. The goal is to make it easier to convert *const MaybeUninit<T>
to *const T
, especially due to the fact that <[MaybeUninit<T>]>::as_ptr
returns it.
Motivating examples or use cases
Right now, the MaybeUninit::slice_as_ptr
and MaybeUninit::slice_as_mut_ptr
methods exist to do a direct conversion from &[MaybeUninit<T>]
to *const T
and &mut [MaybeUninit<T>]
to *mut T
, but these methods are clunky and it's not clear how to fix this.
As stated, since pointers don't have the same initialization requirements as methods, it can be very desirable to use pointer-based write methods instead of those for slices, especially due to the lack of initialization requirements. However, these methods will require the "initialized" pointers, not the MaybeUninit<T>
ones, and it's nice to be able to have an easy way to perform this cast without requiring additional type ascriptions (cast::<T>()
).
Additionally, this way of doing MaybeUninit<T>
-> T
pointer conversion is more flexible than an inherent slice-based method such as <[MaybeUninit<T>]>::as_init_ptr
, and would avoid the potential variability between calling such an as_init_ptr
method and as_ptr().cast_init()
.
Solution sketch
Essentially, add the following methods:
impl<T> *const MaybeUninit<T> {
pub const fn cast_init(self) -> *const T { self.cast() }
}
impl<T> *mut MaybeUninit<T> {
pub const fn cast_init(self) -> *mut T { self.cast() }
}
Alternatives
There are currently three alternates:
- Keep the
MaybeUninit::slice_as_ptr
andMaybeUninit::slice_as_mut_ptr
methods, don't add these. This option is undesirable because this method requires the explicit function call syntax as well as importingMaybeUninit
in code that may not otherwise need to do so. - Replace the explicit functions with real methods on
[MaybeUninit<T>]
slices. This is still not preferred due to the fact thatcast_init
can work on pointers obtained in other ways too. - Remove all these methods and don't add a replacement. This isn't great because
cast::<T>()
will require type ascriptions, butcast::<T>()
isn't necessarily any worse thancast_init()
, just a little less clear.
Links and related work
- Previously accepted ACP Remove
MaybeUninit::slice_as_(mut_)ptr
and optionally add*const/*mut MaybeUninit<T> -> *const/*mut T
type safe conversions #245 proposes alternative 2 above and has an incomplete implementation Nuke slice_as{,_mut}_ptr methods of MaybeUninit rust#103133. - This proposal was originally stated in this comment: Tracking issue for
#![feature(maybe_uninit_slice)]
rust#63569 (comment)
What happens now?
This issue contains an API change proposal (or ACP) and is part of the libs-api team feature lifecycle. Once this issue is filed, the libs-api team will review open proposals as capability becomes available. Current response times do not have a clear estimate, but may be up to several months.
Possible responses
The libs team may respond in various different ways. First, the team will consider the problem (this doesn't require any concrete solution or alternatives to have been proposed):
- We think this problem seems worth solving, and the standard library might be the right place to solve it.
- We think that this probably doesn't belong in the standard library.
Second, if there's a concrete solution:
- We think this specific solution looks roughly right, approved, you or someone else should implement this. (Further review will still happen on the subsequent implementation PR.)
- We're not sure this is the right solution, and the alternatives or other materials don't give us enough information to be sure about that. Here are some questions we have that aren't answered, or rough ideas about alternatives we'd want to see discussed.