about summary refs log tree commit diff
diff options
context:
space:
mode:
authorBrian Anderson <banderson@mozilla.com>2014-05-29 17:40:18 -0700
committerBrian Anderson <banderson@mozilla.com>2014-06-04 18:21:21 -0700
commit9b228f8424d207fc412bf549d3d9dc8262415f27 (patch)
tree169d7f666b23207484a732ff533715b2ca16535e
parentaa09561bb606bb622136ac9ad3702ab1179db5b2 (diff)
core: Apply stability attributes to ptr mod
* null and mut_null are unstable. Their names may change if the unsafe
  pointer types change.
* copy_memory and copy_overlapping_memory are unstable. We think they
  aren't going to change.
* set_memory and zero_memory are experimental. Both the names and
  the semantics are under question.
* swap and replace are unstable and probably won't change.
* read is unstable, probably won't change
* read_and_zero is experimental. It's necessity is in doubt.
* mem::overwrite is now called ptr::write to match read and is
  unstable. mem::overwrite is now deprecated
* array_each, array_each_with_len, buf_len, and position are
  all deprecated because they use old style iteration and their
  utility is generally under question.
-rw-r--r--src/doc/guide-unsafe.md4
-rw-r--r--src/libarena/lib.rs12
-rw-r--r--src/libcollections/priority_queue.rs11
-rw-r--r--src/libcore/mem.rs6
-rw-r--r--src/libcore/ptr.rs90
-rw-r--r--src/libcore/should_not_exist.rs2
-rw-r--r--src/libcore/slice.rs3
7 files changed, 80 insertions, 48 deletions
diff --git a/src/doc/guide-unsafe.md b/src/doc/guide-unsafe.md
index 4e1a96710be..e0a48682963 100644
--- a/src/doc/guide-unsafe.md
+++ b/src/doc/guide-unsafe.md
@@ -213,14 +213,14 @@ pub struct Unique<T> {
 impl<T: Send> Unique<T> {
     pub fn new(value: T) -> Unique<T> {
         unsafe {
-            let ptr = malloc(std::mem::size_of::<T>() as size_t) as *mut T;
+            let ptr = malloc(mem::size_of::<T>() as size_t) as *mut T;
             // we *need* valid pointer.
             assert!(!ptr.is_null());
             // `*ptr` is uninitialized, and `*ptr = value` would
             // attempt to destroy it `overwrite` moves a value into
             // this memory without attempting to drop the original
             // value.
-            mem::overwrite(&mut *ptr, value);
+            ptr::write(&mut *ptr, value);
             Unique{ptr: ptr}
         }
     }
diff --git a/src/libarena/lib.rs b/src/libarena/lib.rs
index 7acef128016..871f8197c9a 100644
--- a/src/libarena/lib.rs
+++ b/src/libarena/lib.rs
@@ -36,7 +36,7 @@ use std::intrinsics::{TyDesc, get_tydesc};
 use std::intrinsics;
 use std::mem;
 use std::num;
-use std::ptr::read;
+use std::ptr;
 use std::rc::Rc;
 use std::rt::heap::allocate;
 
@@ -209,7 +209,7 @@ impl Arena {
             let ptr = self.alloc_copy_inner(mem::size_of::<T>(),
                                             mem::min_align_of::<T>());
             let ptr = ptr as *mut T;
-            mem::overwrite(&mut (*ptr), op());
+            ptr::write(&mut (*ptr), op());
             return &*ptr;
         }
     }
@@ -262,7 +262,7 @@ impl Arena {
             // has *not* been initialized yet.
             *ty_ptr = mem::transmute(tydesc);
             // Actually initialize it
-            mem::overwrite(&mut(*ptr), op());
+            ptr::write(&mut(*ptr), op());
             // Now that we are done, update the tydesc to indicate that
             // the object is there.
             *ty_ptr = bitpack_tydesc_ptr(tydesc, true);
@@ -360,7 +360,7 @@ impl<T> TypedArenaChunk<T> {
         let mut chunk = unsafe {
             let chunk = allocate(size, mem::min_align_of::<TypedArenaChunk<T>>());
             let mut chunk: Box<TypedArenaChunk<T>> = mem::transmute(chunk);
-            mem::overwrite(&mut chunk.next, next);
+            ptr::write(&mut chunk.next, next);
             chunk
         };
 
@@ -376,7 +376,7 @@ impl<T> TypedArenaChunk<T> {
         if intrinsics::needs_drop::<T>() {
             let mut start = self.start();
             for _ in range(0, len) {
-                read(start as *T); // run the destructor on the pointer
+                ptr::read(start as *T); // run the destructor on the pointer
                 start = start.offset(mem::size_of::<T>() as int)
             }
         }
@@ -442,7 +442,7 @@ impl<T> TypedArena<T> {
             }
 
             let ptr: &'a mut T = mem::transmute(this.ptr);
-            mem::overwrite(ptr, object);
+            ptr::write(ptr, object);
             this.ptr = this.ptr.offset(1);
             let ptr: &'a T = ptr;
             ptr
diff --git a/src/libcollections/priority_queue.rs b/src/libcollections/priority_queue.rs
index 3c1337a0382..d73c07ee17d 100644
--- a/src/libcollections/priority_queue.rs
+++ b/src/libcollections/priority_queue.rs
@@ -13,7 +13,8 @@
 #![allow(missing_doc)]
 
 use std::clone::Clone;
-use std::mem::{overwrite, zeroed, replace, swap};
+use std::mem::{zeroed, replace, swap};
+use std::ptr;
 use std::slice;
 
 /// A priority queue implemented with a binary heap
@@ -163,13 +164,13 @@ impl<T: Ord> PriorityQueue<T> {
                 let parent = (pos - 1) >> 1;
                 if new > *self.data.get(parent) {
                     let x = replace(self.data.get_mut(parent), zeroed());
-                    overwrite(self.data.get_mut(pos), x);
+                    ptr::write(self.data.get_mut(pos), x);
                     pos = parent;
                     continue
                 }
                 break
             }
-            overwrite(self.data.get_mut(pos), new);
+            ptr::write(self.data.get_mut(pos), new);
         }
     }
 
@@ -185,12 +186,12 @@ impl<T: Ord> PriorityQueue<T> {
                     child = right;
                 }
                 let x = replace(self.data.get_mut(child), zeroed());
-                overwrite(self.data.get_mut(pos), x);
+                ptr::write(self.data.get_mut(pos), x);
                 pos = child;
                 child = 2 * pos + 1;
             }
 
-            overwrite(self.data.get_mut(pos), new);
+            ptr::write(self.data.get_mut(pos), new);
             self.siftup(start, pos);
         }
     }
diff --git a/src/libcore/mem.rs b/src/libcore/mem.rs
index 157be76b8f1..8933c95350d 100644
--- a/src/libcore/mem.rs
+++ b/src/libcore/mem.rs
@@ -155,16 +155,16 @@ pub unsafe fn uninit<T>() -> T {
 /// contained at the location `dst`. This could leak allocations or resources,
 /// so care must be taken to previously deallocate the value at `dst`.
 #[inline]
-#[stable]
+#[deprecated = "use ptr::write"]
 pub unsafe fn overwrite<T>(dst: *mut T, src: T) {
     intrinsics::move_val_init(&mut *dst, src)
 }
 
 /// Deprecated, use `overwrite` instead
 #[inline]
-#[deprecated = "this function has been renamed to `overwrite`"]
+#[deprecated = "use ptr::write"]
 pub unsafe fn move_val_init<T>(dst: &mut T, src: T) {
-    overwrite(dst, src)
+    ptr::write(dst, src)
 }
 
 /// Convert an u16 to little endian from the target's endianness.
diff --git a/src/libcore/ptr.rs b/src/libcore/ptr.rs
index dacbba61856..b2776b78b1c 100644
--- a/src/libcore/ptr.rs
+++ b/src/libcore/ptr.rs
@@ -95,36 +95,6 @@ use option::{Some, None, Option};
 
 #[cfg(not(test))] use cmp::{PartialEq, Eq, PartialOrd, Equiv};
 
-/// Return the offset of the first null pointer in `buf`.
-#[inline]
-pub unsafe fn buf_len<T>(buf: **T) -> uint {
-    position(buf, |i| *i == null())
-}
-
-impl<T> Clone for *T {
-    #[inline]
-    fn clone(&self) -> *T {
-        *self
-    }
-}
-
-impl<T> Clone for *mut T {
-    #[inline]
-    fn clone(&self) -> *mut T {
-        *self
-    }
-}
-
-/// Return the first offset `i` such that `f(buf[i]) == true`.
-#[inline]
-pub unsafe fn position<T>(buf: *T, f: |&T| -> bool) -> uint {
-    let mut i = 0;
-    loop {
-        if f(&(*buf.offset(i as int))) { return i; }
-        else { i += 1; }
-    }
-}
-
 /// Create a null pointer.
 ///
 /// # Example
@@ -136,6 +106,7 @@ pub unsafe fn position<T>(buf: *T, f: |&T| -> bool) -> uint {
 /// assert!(p.is_null());
 /// ```
 #[inline]
+#[unstable = "may need a different name after pending changes to pointer types"]
 pub fn null<T>() -> *T { 0 as *T }
 
 /// Create an unsafe mutable null pointer.
@@ -149,6 +120,7 @@ pub fn null<T>() -> *T { 0 as *T }
 /// assert!(p.is_null());
 /// ```
 #[inline]
+#[unstable = "may need a different name after pending changes to pointer types"]
 pub fn mut_null<T>() -> *mut T { 0 as *mut T }
 
 /// Copies data from one location to another.
@@ -174,6 +146,7 @@ pub fn mut_null<T>() -> *mut T { 0 as *mut T }
 /// ```
 ///
 #[inline]
+#[unstable]
 pub unsafe fn copy_memory<T>(dst: *mut T, src: *T, count: uint) {
     intrinsics::copy_memory(dst, src, count)
 }
@@ -215,6 +188,7 @@ pub unsafe fn copy_memory<T>(dst: *mut T, src: *T, count: uint) {
 /// If the source and destination overlap then the behavior of this
 /// function is undefined.
 #[inline]
+#[unstable]
 pub unsafe fn copy_nonoverlapping_memory<T>(dst: *mut T,
                                             src: *T,
                                             count: uint) {
@@ -224,12 +198,15 @@ pub unsafe fn copy_nonoverlapping_memory<T>(dst: *mut T,
 /// Invokes memset on the specified pointer, setting `count * size_of::<T>()`
 /// bytes of memory starting at `dst` to `c`.
 #[inline]
+#[experimental = "uncertain about naming and semantics"]
 pub unsafe fn set_memory<T>(dst: *mut T, c: u8, count: uint) {
     intrinsics::set_memory(dst, c, count)
 }
 
 /// Zeroes out `count * size_of::<T>` bytes of memory at `dst`
 #[inline]
+#[experimental = "uncertain about naming and semantics"]
+#[allow(experimental)]
 pub unsafe fn zero_memory<T>(dst: *mut T, count: uint) {
     set_memory(dst, 0, count);
 }
@@ -237,6 +214,7 @@ pub unsafe fn zero_memory<T>(dst: *mut T, count: uint) {
 /// Swap the values at two mutable locations of the same type, without
 /// deinitialising either. They may overlap.
 #[inline]
+#[unstable]
 pub unsafe fn swap<T>(x: *mut T, y: *mut T) {
     // Give ourselves some scratch space to work with
     let mut tmp: T = mem::uninitialized();
@@ -255,6 +233,7 @@ pub unsafe fn swap<T>(x: *mut T, y: *mut T) {
 /// Replace the value at a mutable location with a new one, returning the old
 /// value, without deinitialising either.
 #[inline]
+#[unstable]
 pub unsafe fn replace<T>(dest: *mut T, mut src: T) -> T {
     mem::swap(mem::transmute(dest), &mut src); // cannot overlap
     src
@@ -262,6 +241,7 @@ pub unsafe fn replace<T>(dest: *mut T, mut src: T) -> T {
 
 /// Reads the value from `*src` and returns it.
 #[inline(always)]
+#[unstable]
 pub unsafe fn read<T>(src: *T) -> T {
     let mut tmp: T = mem::uninitialized();
     copy_nonoverlapping_memory(&mut tmp, src, 1);
@@ -271,6 +251,8 @@ pub unsafe fn read<T>(src: *T) -> T {
 /// Reads the value from `*src` and nulls it out.
 /// This currently prevents destructors from executing.
 #[inline(always)]
+#[experimental]
+#[allow(experimental)]
 pub unsafe fn read_and_zero<T>(dest: *mut T) -> T {
     // Copy the data out from `dest`:
     let tmp = read(&*dest);
@@ -281,9 +263,22 @@ pub unsafe fn read_and_zero<T>(dest: *mut T) -> T {
     tmp
 }
 
+/// Unsafely overwrite a memory location with the given value without destroying
+/// the old value.
+///
+/// This operation is unsafe because it does not destroy the previous value
+/// contained at the location `dst`. This could leak allocations or resources,
+/// so care must be taken to previously deallocate the value at `dst`.
+#[inline]
+#[unstable]
+pub unsafe fn write<T>(dst: *mut T, src: T) {
+    intrinsics::move_val_init(&mut *dst, src)
+}
+
 /// Given a **T (pointer to an array of pointers),
 /// iterate through each *T, up to the provided `len`,
 /// passing to the provided callback function
+#[deprecated = "old-style iteration. use a loop and RawPtr::offset"]
 pub unsafe fn array_each_with_len<T>(arr: **T, len: uint, cb: |*T|) {
     if arr.is_null() {
         fail!("ptr::array_each_with_len failure: arr input is null pointer");
@@ -303,6 +298,8 @@ pub unsafe fn array_each_with_len<T>(arr: **T, len: uint, cb: |*T|) {
 ///
 /// This will only work with a null-terminated
 /// pointer array.
+#[deprecated = "old-style iteration. use a loop and RawPtr::offset"]
+#[allow(deprecated)]
 pub unsafe fn array_each<T>(arr: **T, cb: |*T|) {
     if arr.is_null()  {
         fail!("ptr::array_each_with_len failure: arr input is null pointer");
@@ -311,6 +308,25 @@ pub unsafe fn array_each<T>(arr: **T, cb: |*T|) {
     array_each_with_len(arr, len, cb);
 }
 
+/// Return the offset of the first null pointer in `buf`.
+#[inline]
+#[deprecated = "use a loop and RawPtr::offset"]
+#[allow(deprecated)]
+pub unsafe fn buf_len<T>(buf: **T) -> uint {
+    position(buf, |i| *i == null())
+}
+
+/// Return the first offset `i` such that `f(buf[i]) == true`.
+#[inline]
+#[deprecated = "old-style iteration. use a loop and RawPtr::offset"]
+pub unsafe fn position<T>(buf: *T, f: |&T| -> bool) -> uint {
+    let mut i = 0;
+    loop {
+        if f(&(*buf.offset(i as int))) { return i; }
+        else { i += 1; }
+    }
+}
+
 /// Methods on raw pointers
 pub trait RawPtr<T> {
     /// Returns the null pointer.
@@ -426,6 +442,20 @@ impl<T> Equiv<*T> for *mut T {
     }
 }
 
+impl<T> Clone for *T {
+    #[inline]
+    fn clone(&self) -> *T {
+        *self
+    }
+}
+
+impl<T> Clone for *mut T {
+    #[inline]
+    fn clone(&self) -> *mut T {
+        *self
+    }
+}
+
 // Equality for extern "C" fn pointers
 #[cfg(not(test))]
 mod externfnpointers {
diff --git a/src/libcore/should_not_exist.rs b/src/libcore/should_not_exist.rs
index 9a0e3ad7ca4..2c6f2978aa7 100644
--- a/src/libcore/should_not_exist.rs
+++ b/src/libcore/should_not_exist.rs
@@ -77,7 +77,7 @@ impl<A: Clone> Clone for ~[A] {
             try_finally(
                 &mut i, (),
                 |i, ()| while *i < len {
-                    mem::overwrite(
+                    ptr::write(
                         &mut(*p.offset(*i as int)),
                         self.unsafe_ref(*i).clone());
                     *i += 1;
diff --git a/src/libcore/slice.rs b/src/libcore/slice.rs
index 5673d0c020d..6312d9115ef 100644
--- a/src/libcore/slice.rs
+++ b/src/libcore/slice.rs
@@ -1093,7 +1093,7 @@ impl<'a,T> MutableVector<'a, T> for &'a mut [T] {
 
     #[inline]
     unsafe fn init_elem(self, i: uint, val: T) {
-        mem::overwrite(&mut (*self.as_mut_ptr().offset(i as int)), val);
+        ptr::write(&mut (*self.as_mut_ptr().offset(i as int)), val);
     }
 
     #[inline]
@@ -1218,6 +1218,7 @@ pub mod bytes {
 
     impl<'a> MutableByteVector for &'a mut [u8] {
         #[inline]
+        #[allow(experimental)]
         fn set_memory(self, value: u8) {
             unsafe { ptr::set_memory(self.as_mut_ptr(), value, self.len()) };
         }