Make (A)Rc
/Weak
allocator_api
APIs more consistent by zachs18 · Pull Request #119761 · rust-lang/rust (original) (raw)
Make Arc
/sync::Weak
/Rc
/rc::Weak
unstable feature(allocator_api)
APIs more consistent with other containers (well, Box
), and with each other.
fn into_raw_with_allocator
for all.- Pairs with
from_raw_in
(which already exists on all 4 types). - Name matches
Box::into_raw_with_allocator
. - Associated fns on
Rc
/Arc
, methods onWeak
s.
- Pairs with
fn allocator
for all.- For
Rc
/Arc
, the existing associated fns are changed to allow unsized pointees. - For
Weak
s, methods are added.
- For
- Remove
where A: Clone
bound on (stable)Rc::downcast
anddowncast_unchecked
, (unstable)assume_init
s, and some (stable) trait impls- (
Arc::{downcast{,_unchecked}, assume_init}
were changed by Fix some Arc allocator leaks #120445) downcast(_unchecked)
andassume_init
semantically should not require cloning the allocator; they are essentially just ((un)checked) pointer casts.- Remove
A: Clone
bound fromFrom<Vec<T, A>> for Arc<[T], A>
(Rc
's already didn't have aA: Clone
bound)and(done by Fix some Arc allocator leaks #120445) (see below forTryFrom<Arc<[T], A>> for Arc<[T; N], A>
Rc
)
- (
- Make
TryFrom<Rc<[T]>> for Rc<[T; N]>
allocator-aware.
This is adding 61 new unstable functions, changing the bounds on 6 3 unstable functions, and changing the (unstable) bounds on 7 5 stable functions, so I think it needs at least a libs-api FCP? If it also needs an ACP I can make one. (If the parts of this PR should be split I can do that too.)
@rustbot label +A-allocators +T-libs-api -T-libs
Future PR
As a follow-on to this PR, I plan to make a PR/ACP later to move into_raw(_parts)
from Container<_, A: Allocator>
to only Container<_, Global>
(where Container
= Vec
/Box
/Rc
/rc::Weak
/Arc
/sync::Weak
) so that users of non-Global
allocators have to explicitly handle the allocator when using into_raw
-like APIs.
The current behaviors of stdlib containers are inconsistent with respect to what happens to the allocator when into_raw
is called (which does not return the allocator)
Type | into_raw currently callable with | behavior of into_raw |
---|---|---|
Box | any allocator | allocator is dropped |
Vec | any allocator | allocator is forgotten |
Arc/Rc/Weak | any allocator | allocator is forgotten(Arc) (sync::Weak) (Rc) (rc::Weak) |
In my opinion, neither implicitly dropping nor implicitly forgetting the allocator is ideal; dropping it could immediately invalidate the returned pointer, and forgetting it could unintentionally leak memory. My (to-be) proposed solution is to just forbid calling into_raw(_parts)
on containers with non-Global
allocators, and require calling into_raw_with_allocator
(/Vec::into_raw_parts_with_alloc
)
Footnotes
- Technically 5 new and 1 renamed, since
rc::Weak::into_raw_with_allocator
is not newly added, as it was modified and renamed fromrc::Weak::into_raw_and_alloc
. ↩