mirror of
https://github.com/rust-lang/rust.git
synced 2025-06-19 11:07:32 +00:00
Add support for custom allocators in Vec
This commit is contained in:
parent
7d747db0d5
commit
8725e4c337
@ -1336,9 +1336,10 @@ impl<I> FromIterator<I> for Box<[I]> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[stable(feature = "box_slice_clone", since = "1.3.0")]
|
#[stable(feature = "box_slice_clone", since = "1.3.0")]
|
||||||
impl<T: Clone> Clone for Box<[T]> {
|
impl<T: Clone, A: AllocRef + Clone> Clone for Box<[T], A> {
|
||||||
fn clone(&self) -> Self {
|
fn clone(&self) -> Self {
|
||||||
self.to_vec().into_boxed_slice()
|
let alloc = Box::alloc_ref(self).clone();
|
||||||
|
self.to_vec_in(alloc).into_boxed_slice()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn clone_from(&mut self, other: &Self) {
|
fn clone_from(&mut self, other: &Self) {
|
||||||
|
@ -233,15 +233,10 @@ impl<T, A: AllocRef> RawVec<T, A> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Returns a shared reference to the allocator backing this `RawVec`.
|
/// Returns a shared reference to the allocator backing this `RawVec`.
|
||||||
pub fn alloc(&self) -> &A {
|
pub fn alloc_ref(&self) -> &A {
|
||||||
&self.alloc
|
&self.alloc
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns a mutable reference to the allocator backing this `RawVec`.
|
|
||||||
pub fn alloc_mut(&mut self) -> &mut A {
|
|
||||||
&mut self.alloc
|
|
||||||
}
|
|
||||||
|
|
||||||
fn current_memory(&self) -> Option<(NonNull<u8>, Layout)> {
|
fn current_memory(&self) -> Option<(NonNull<u8>, Layout)> {
|
||||||
if mem::size_of::<T>() == 0 || self.cap == 0 {
|
if mem::size_of::<T>() == 0 || self.cap == 0 {
|
||||||
None
|
None
|
||||||
|
@ -87,6 +87,7 @@ use core::cmp::Ordering::{self, Less};
|
|||||||
use core::mem::{self, size_of};
|
use core::mem::{self, size_of};
|
||||||
use core::ptr;
|
use core::ptr;
|
||||||
|
|
||||||
|
use crate::alloc::{AllocRef, Global};
|
||||||
use crate::borrow::ToOwned;
|
use crate::borrow::ToOwned;
|
||||||
use crate::boxed::Box;
|
use crate::boxed::Box;
|
||||||
use crate::vec::Vec;
|
use crate::vec::Vec;
|
||||||
@ -137,26 +138,28 @@ pub use hack::to_vec;
|
|||||||
// `core::slice::SliceExt` - we need to supply these functions for the
|
// `core::slice::SliceExt` - we need to supply these functions for the
|
||||||
// `test_permutations` test
|
// `test_permutations` test
|
||||||
mod hack {
|
mod hack {
|
||||||
|
use core::alloc::AllocRef;
|
||||||
|
|
||||||
use crate::boxed::Box;
|
use crate::boxed::Box;
|
||||||
use crate::vec::Vec;
|
use crate::vec::Vec;
|
||||||
|
|
||||||
// We shouldn't add inline attribute to this since this is used in
|
// We shouldn't add inline attribute to this since this is used in
|
||||||
// `vec!` macro mostly and causes perf regression. See #71204 for
|
// `vec!` macro mostly and causes perf regression. See #71204 for
|
||||||
// discussion and perf results.
|
// discussion and perf results.
|
||||||
pub fn into_vec<T>(b: Box<[T]>) -> Vec<T> {
|
pub fn into_vec<T, A: AllocRef>(b: Box<[T], A>) -> Vec<T, A> {
|
||||||
unsafe {
|
unsafe {
|
||||||
let len = b.len();
|
let len = b.len();
|
||||||
let b = Box::into_raw(b);
|
let (b, alloc) = Box::into_raw_with_alloc(b);
|
||||||
Vec::from_raw_parts(b as *mut T, len, len)
|
Vec::from_raw_parts_in(b as *mut T, len, len, alloc)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn to_vec<T>(s: &[T]) -> Vec<T>
|
pub fn to_vec<T, A: AllocRef>(s: &[T], alloc: A) -> Vec<T, A>
|
||||||
where
|
where
|
||||||
T: Clone,
|
T: Clone,
|
||||||
{
|
{
|
||||||
let mut vec = Vec::with_capacity(s.len());
|
let mut vec = Vec::with_capacity_in(s.len(), alloc);
|
||||||
vec.extend_from_slice(s);
|
vec.extend_from_slice(s);
|
||||||
vec
|
vec
|
||||||
}
|
}
|
||||||
@ -388,11 +391,33 @@ impl<T> [T] {
|
|||||||
#[stable(feature = "rust1", since = "1.0.0")]
|
#[stable(feature = "rust1", since = "1.0.0")]
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn to_vec(&self) -> Vec<T>
|
pub fn to_vec(&self) -> Vec<T>
|
||||||
|
where
|
||||||
|
T: Clone,
|
||||||
|
{
|
||||||
|
self.to_vec_in(Global)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Copies `self` into a new `Vec` with an allocator.
|
||||||
|
///
|
||||||
|
/// # Examples
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// #![feature(allocator_api)]
|
||||||
|
///
|
||||||
|
/// use std::alloc::System;
|
||||||
|
///
|
||||||
|
/// let s = [10, 40, 30];
|
||||||
|
/// let x = s.to_vec_in(System);
|
||||||
|
/// // Here, `s` and `x` can be modified independently.
|
||||||
|
/// ```
|
||||||
|
#[inline]
|
||||||
|
#[unstable(feature = "allocator_api", issue = "32838")]
|
||||||
|
pub fn to_vec_in<A: AllocRef>(&self, alloc: A) -> Vec<T, A>
|
||||||
where
|
where
|
||||||
T: Clone,
|
T: Clone,
|
||||||
{
|
{
|
||||||
// N.B., see the `hack` module in this file for more details.
|
// N.B., see the `hack` module in this file for more details.
|
||||||
hack::to_vec(self)
|
hack::to_vec(self, alloc)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Converts `self` into a vector without clones or allocation.
|
/// Converts `self` into a vector without clones or allocation.
|
||||||
@ -411,7 +436,7 @@ impl<T> [T] {
|
|||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "rust1", since = "1.0.0")]
|
#[stable(feature = "rust1", since = "1.0.0")]
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn into_vec(self: Box<Self>) -> Vec<T> {
|
pub fn into_vec<A: AllocRef>(self: Box<Self, A>) -> Vec<T, A> {
|
||||||
// N.B., see the `hack` module in this file for more details.
|
// N.B., see the `hack` module in this file for more details.
|
||||||
hack::into_vec(self)
|
hack::into_vec(self)
|
||||||
}
|
}
|
||||||
@ -730,7 +755,7 @@ impl<T: Clone> ToOwned for [T] {
|
|||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
fn to_owned(&self) -> Vec<T> {
|
fn to_owned(&self) -> Vec<T> {
|
||||||
hack::to_vec(self)
|
hack::to_vec(self, Global)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn clone_into(&self, target: &mut Vec<T>) {
|
fn clone_into(&self, target: &mut Vec<T>) {
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -1,10 +1,11 @@
|
|||||||
// aux-build:impl_trait_aux.rs
|
// aux-build:impl_trait_aux.rs
|
||||||
// edition:2018
|
// edition:2018
|
||||||
|
// ignore-tidy-linelength
|
||||||
|
|
||||||
extern crate impl_trait_aux;
|
extern crate impl_trait_aux;
|
||||||
|
|
||||||
// @has impl_trait/fn.func.html
|
// @has impl_trait/fn.func.html
|
||||||
// @has - '//pre[@class="rust fn"]' "pub fn func<'a>(_x: impl Clone + Into<Vec<u8>> + 'a)"
|
// @has - '//pre[@class="rust fn"]' "pub fn func<'a>(_x: impl Clone + Into<Vec<u8, Global>> + 'a)"
|
||||||
// @!has - '//pre[@class="rust fn"]' 'where'
|
// @!has - '//pre[@class="rust fn"]' 'where'
|
||||||
pub use impl_trait_aux::func;
|
pub use impl_trait_aux::func;
|
||||||
|
|
||||||
@ -31,7 +32,7 @@ pub use impl_trait_aux::func4;
|
|||||||
pub use impl_trait_aux::async_fn;
|
pub use impl_trait_aux::async_fn;
|
||||||
|
|
||||||
// @has impl_trait/struct.Foo.html
|
// @has impl_trait/struct.Foo.html
|
||||||
// @has - '//*[@id="method.method"]//code' "pub fn method<'a>(_x: impl Clone + Into<Vec<u8>> + 'a)"
|
// @has - '//*[@id="method.method"]//code' "pub fn method<'a>(_x: impl Clone + Into<Vec<u8, Global>> + 'a)"
|
||||||
// @!has - '//*[@id="method.method"]//code' 'where'
|
// @!has - '//*[@id="method.method"]//code' 'where'
|
||||||
pub use impl_trait_aux::Foo;
|
pub use impl_trait_aux::Foo;
|
||||||
|
|
||||||
|
@ -6,7 +6,7 @@ LL | type Ty = Vec<[u8]>;
|
|||||||
|
|
|
|
||||||
::: $SRC_DIR/alloc/src/vec.rs:LL:COL
|
::: $SRC_DIR/alloc/src/vec.rs:LL:COL
|
||||||
|
|
|
|
||||||
LL | pub struct Vec<T> {
|
LL | pub struct Vec<T, #[unstable(feature = "allocator_api", issue = "32838")] A: AllocRef = Global> {
|
||||||
| - required by this bound in `Vec`
|
| - required by this bound in `Vec`
|
||||||
|
|
|
|
||||||
= help: the trait `Sized` is not implemented for `[u8]`
|
= help: the trait `Sized` is not implemented for `[u8]`
|
||||||
|
@ -17,7 +17,7 @@ LL | let x: Vec<dyn Trait + Sized> = Vec::new();
|
|||||||
|
|
|
|
||||||
::: $SRC_DIR/alloc/src/vec.rs:LL:COL
|
::: $SRC_DIR/alloc/src/vec.rs:LL:COL
|
||||||
|
|
|
|
||||||
LL | pub struct Vec<T> {
|
LL | pub struct Vec<T, #[unstable(feature = "allocator_api", issue = "32838")] A: AllocRef = Global> {
|
||||||
| - required by this bound in `Vec`
|
| - required by this bound in `Vec`
|
||||||
|
|
|
|
||||||
= help: the trait `Sized` is not implemented for `dyn Trait`
|
= help: the trait `Sized` is not implemented for `dyn Trait`
|
||||||
|
@ -6,7 +6,7 @@ LL | fn iceman(c: Vec<[i32]>) {}
|
|||||||
|
|
|
|
||||||
::: $SRC_DIR/alloc/src/vec.rs:LL:COL
|
::: $SRC_DIR/alloc/src/vec.rs:LL:COL
|
||||||
|
|
|
|
||||||
LL | pub struct Vec<T> {
|
LL | pub struct Vec<T, #[unstable(feature = "allocator_api", issue = "32838")] A: AllocRef = Global> {
|
||||||
| - required by this bound in `Vec`
|
| - required by this bound in `Vec`
|
||||||
|
|
|
|
||||||
= help: the trait `Sized` is not implemented for `[i32]`
|
= help: the trait `Sized` is not implemented for `[i32]`
|
||||||
|
@ -7,7 +7,7 @@ impl Reactor {
|
|||||||
input_cells: Vec::new()
|
input_cells: Vec::new()
|
||||||
//~^ ERROR cannot find value `input_cells` in this scope
|
//~^ ERROR cannot find value `input_cells` in this scope
|
||||||
//~| ERROR parenthesized type parameters may only be used with a `Fn` trait
|
//~| ERROR parenthesized type parameters may only be used with a `Fn` trait
|
||||||
//~| ERROR wrong number of type arguments: expected 1, found 0
|
//~| ERROR wrong number of type arguments: expected at least 1, found 0
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -10,11 +10,11 @@ error[E0214]: parenthesized type parameters may only be used with a `Fn` trait
|
|||||||
LL | input_cells: Vec::new()
|
LL | input_cells: Vec::new()
|
||||||
| ^^^^^ only `Fn` traits may use parentheses
|
| ^^^^^ only `Fn` traits may use parentheses
|
||||||
|
|
||||||
error[E0107]: wrong number of type arguments: expected 1, found 0
|
error[E0107]: wrong number of type arguments: expected at least 1, found 0
|
||||||
--> $DIR/issue-34255-1.rs:7:22
|
--> $DIR/issue-34255-1.rs:7:22
|
||||||
|
|
|
|
||||||
LL | input_cells: Vec::new()
|
LL | input_cells: Vec::new()
|
||||||
| ^^^^^^^^^^ expected 1 type argument
|
| ^^^^^^^^^^ expected at least 1 type argument
|
||||||
|
|
||||||
error: aborting due to 3 previous errors
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user