self
}
+ /// Returns a raw pointer to the vector's buffer.
+ ///
+ /// The caller must ensure that the vector outlives the pointer this
+ /// function returns, or else it will end up pointing to garbage.
+ /// Modifying the vector may cause its buffer to be reallocated,
+ /// which would also make any pointers to it invalid.
+ ///
+ /// The caller must also ensure that the memory the pointer (non-transitively) points to
+ /// is never written to (except inside an `UnsafeCell`) using this pointer or any pointer
+ /// derived from it. If you need to mutate the contents of the slice, use [`as_mut_ptr`].
+ ///
+ /// # Examples
+ ///
+ /// ```
+ /// let x = vec![1, 2, 4];
+ /// let x_ptr = x.as_ptr();
+ ///
+ /// unsafe {
+ /// for i in 0..x.len() {
+ /// assert_eq!(*x_ptr.add(i), 1 << i);
+ /// }
+ /// }
+ /// ```
+ ///
+ /// [`as_mut_ptr`]: #method.as_mut_ptr
+ #[stable(feature = "vec_as_ptr", since = "1.37.0")]
+ #[inline]
+ pub fn as_ptr(&self) -> *const T {
+ // We shadow the slice method of the same name to avoid going through
+ // `deref`, which creates an intermediate reference.
+ let ptr = self.buf.ptr();
+ unsafe { assume(!ptr.is_null()); }
+ ptr
+ }
+
+ /// Returns an unsafe mutable pointer to the vector's buffer.
+ ///
+ /// The caller must ensure that the vector outlives the pointer this
+ /// function returns, or else it will end up pointing to garbage.
+ /// Modifying the vector may cause its buffer to be reallocated,
+ /// which would also make any pointers to it invalid.
+ ///
+ /// # Examples
+ ///
+ /// ```
+ /// // Allocate vector big enough for 4 elements.
+ /// let size = 4;
+ /// let mut x: Vec<i32> = Vec::with_capacity(size);
+ /// let x_ptr = x.as_mut_ptr();
+ ///
+ /// // Initialize elements via raw pointer writes, then set length.
+ /// unsafe {
+ /// for i in 0..size {
+ /// *x_ptr.add(i) = i as i32;
+ /// }
+ /// x.set_len(size);
+ /// }
+ /// assert_eq!(&*x, &[0,1,2,3]);
+ /// ```
+ #[stable(feature = "vec_as_ptr", since = "1.37.0")]
+ #[inline]
+ pub fn as_mut_ptr(&mut self) -> *mut T {
+ // We shadow the slice method of the same name to avoid going through
+ // `deref_mut`, which creates an intermediate reference.
+ let ptr = self.buf.ptr();
+ unsafe { assume(!ptr.is_null()); }
+ ptr
+ }
+
/// Forces the length of the vector to `new_len`.
///
/// This is a low-level operation that maintains none of the normal
let count = (*other).len();
self.reserve(count);
let len = self.len();
- ptr::copy_nonoverlapping(other as *const T, self.get_unchecked_mut(len), count);
+ ptr::copy_nonoverlapping(other as *const T, self.as_mut_ptr().add(len), count);
self.len += count;
}
fn deref(&self) -> &[T] {
unsafe {
- let p = self.buf.ptr();
- assume(!p.is_null());
- slice::from_raw_parts(p, self.len)
+ slice::from_raw_parts(self.as_ptr(), self.len)
}
}
}
impl<T> ops::DerefMut for Vec<T> {
fn deref_mut(&mut self) -> &mut [T] {
unsafe {
- let ptr = self.buf.ptr();
- assume(!ptr.is_null());
- slice::from_raw_parts_mut(ptr, self.len)
+ slice::from_raw_parts_mut(self.as_mut_ptr(), self.len)
}
}
}
fn into_iter(mut self) -> IntoIter<T> {
unsafe {
let begin = self.as_mut_ptr();
- assume(!begin.is_null());
let end = if mem::size_of::<T>() == 0 {
arith_offset(begin as *const i8, self.len() as isize) as *const T
} else {
/// with the given `replace_with` iterator and yields the removed items.
/// `replace_with` does not need to be the same length as `range`.
///
- /// Note 1: The element range is removed even if the iterator is not
- /// consumed until the end.
+ /// The element range is removed even if the iterator is not consumed until the end.
///
- /// Note 2: It is unspecified how many elements are removed from the vector,
+ /// It is unspecified how many elements are removed from the vector
/// if the `Splice` value is leaked.
///
- /// Note 3: The input iterator `replace_with` is only consumed
- /// when the `Splice` value is dropped.
+ /// The input iterator `replace_with` is only consumed when the `Splice` value is dropped.
///
- /// Note 4: This is optimal if:
+ /// This is optimal if:
///
/// * The tail (elements in the vector after `range`) is empty,
/// * or `replace_with` yields fewer elements than `range`’s length