about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2015-05-03 17:22:09 +0000
committerbors <bors@rust-lang.org>2015-05-03 17:22:09 +0000
commit1a60dc4fc4b66760b71f1700cdb8b151cb8a67d9 (patch)
tree3998daf2afd0c715a001ea3f4ae962e5827d7b97 /src
parent26933a638c360442412b51aa70fe25e419f44314 (diff)
parent57d8289754767e046a01abaab6054b7146c51f74 (diff)
downloadrust-1a60dc4fc4b66760b71f1700cdb8b151cb8a67d9.tar.gz
rust-1a60dc4fc4b66760b71f1700cdb8b151cb8a67d9.zip
Auto merge of #24737 - P1start:dst-cell, r=alexcrichton
This + DST coercions (#24619) would allow code like `Rc<RefCell<Box<Trait>>>` to be simplified to `Rc<RefCell<Trait>>`.
Diffstat (limited to 'src')
-rw-r--r--src/libcore/cell.rs59
-rw-r--r--src/libcore/fmt/mod.rs6
-rw-r--r--src/libcoretest/cell.rs24
-rw-r--r--src/libstd/sync/mutex.rs44
-rw-r--r--src/libstd/sync/rwlock.rs53
-rw-r--r--src/test/compile-fail/bad-sized.rs4
6 files changed, 122 insertions, 68 deletions
diff --git a/src/libcore/cell.rs b/src/libcore/cell.rs
index 9ff447a87f1..c717b608a24 100644
--- a/src/libcore/cell.rs
+++ b/src/libcore/cell.rs
@@ -144,7 +144,7 @@
 use clone::Clone;
 use cmp::PartialEq;
 use default::Default;
-use marker::{Copy, Send, Sync};
+use marker::{Copy, Send, Sync, Sized};
 use ops::{Deref, DerefMut, Drop};
 use option::Option;
 use option::Option::{None, Some};
@@ -266,9 +266,9 @@ impl<T:PartialEq + Copy> PartialEq for Cell<T> {
 ///
 /// See the [module-level documentation](index.html) for more.
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct RefCell<T> {
-    value: UnsafeCell<T>,
+pub struct RefCell<T: ?Sized> {
     borrow: Cell<BorrowFlag>,
+    value: UnsafeCell<T>,
 }
 
 /// An enumeration of values returned from the `state` method on a `RefCell<T>`.
@@ -328,7 +328,9 @@ impl<T> RefCell<T> {
         debug_assert!(self.borrow.get() == UNUSED);
         unsafe { self.value.into_inner() }
     }
+}
 
+impl<T: ?Sized> RefCell<T> {
     /// Query the current state of this `RefCell`
     ///
     /// The returned value can be dispatched on to determine if a call to
@@ -449,7 +451,7 @@ impl<T> RefCell<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-unsafe impl<T> Send for RefCell<T> where T: Send {}
+unsafe impl<T: ?Sized> Send for RefCell<T> where T: Send {}
 
 #[stable(feature = "rust1", since = "1.0.0")]
 impl<T: Clone> Clone for RefCell<T> {
@@ -469,7 +471,7 @@ impl<T:Default> Default for RefCell<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: PartialEq> PartialEq for RefCell<T> {
+impl<T: ?Sized + PartialEq> PartialEq for RefCell<T> {
     #[inline]
     fn eq(&self, other: &RefCell<T>) -> bool {
         *self.borrow() == *other.borrow()
@@ -519,7 +521,7 @@ impl<'b> Clone for BorrowRef<'b> {
 ///
 /// See the [module-level documentation](index.html) for more.
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct Ref<'b, T:'b> {
+pub struct Ref<'b, T: ?Sized + 'b> {
     // FIXME #12808: strange name to try to avoid interfering with
     // field accesses of the contained type via Deref
     _value: &'b T,
@@ -527,7 +529,7 @@ pub struct Ref<'b, T:'b> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'b, T> Deref for Ref<'b, T> {
+impl<'b, T: ?Sized> Deref for Ref<'b, T> {
     type Target = T;
 
     #[inline]
@@ -582,7 +584,7 @@ impl<'b> BorrowRefMut<'b> {
 ///
 /// See the [module-level documentation](index.html) for more.
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct RefMut<'b, T:'b> {
+pub struct RefMut<'b, T: ?Sized + 'b> {
     // FIXME #12808: strange name to try to avoid interfering with
     // field accesses of the contained type via Deref
     _value: &'b mut T,
@@ -590,7 +592,7 @@ pub struct RefMut<'b, T:'b> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'b, T> Deref for RefMut<'b, T> {
+impl<'b, T: ?Sized> Deref for RefMut<'b, T> {
     type Target = T;
 
     #[inline]
@@ -600,7 +602,7 @@ impl<'b, T> Deref for RefMut<'b, T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'b, T> DerefMut for RefMut<'b, T> {
+impl<'b, T: ?Sized> DerefMut for RefMut<'b, T> {
     #[inline]
     fn deref_mut<'a>(&'a mut self) -> &'a mut T {
         self._value
@@ -633,7 +635,7 @@ impl<'b, T> DerefMut for RefMut<'b, T> {
 /// recommended to access its fields directly, `get` should be used instead.
 #[lang="unsafe_cell"]
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct UnsafeCell<T> {
+pub struct UnsafeCell<T: ?Sized> {
     /// Wrapped value
     ///
     /// This field should not be accessed directly, it is made public for static
@@ -642,7 +644,7 @@ pub struct UnsafeCell<T> {
     pub value: T,
 }
 
-impl<T> !Sync for UnsafeCell<T> {}
+impl<T: ?Sized> !Sync for UnsafeCell<T> {}
 
 impl<T> UnsafeCell<T> {
     /// Constructs a new instance of `UnsafeCell` which will wrap the specified
@@ -664,7 +666,12 @@ impl<T> UnsafeCell<T> {
         UnsafeCell { value: value }
     }
 
-    /// Gets a mutable pointer to the wrapped value.
+    /// Unwraps the value.
+    ///
+    /// # Unsafety
+    ///
+    /// This function is unsafe because there is no guarantee that this or other threads are
+    /// currently inspecting the inner value.
     ///
     /// # Examples
     ///
@@ -673,22 +680,15 @@ impl<T> UnsafeCell<T> {
     ///
     /// let uc = UnsafeCell::new(5);
     ///
-    /// let five = uc.get();
+    /// let five = unsafe { uc.into_inner() };
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
-    pub fn get(&self) -> *mut T {
-        // FIXME(#23542) Replace with type ascription.
-        #![allow(trivial_casts)]
-        &self.value as *const T as *mut T
-    }
+    pub unsafe fn into_inner(self) -> T { self.value }
+}
 
-    /// Unwraps the value.
-    ///
-    /// # Unsafety
-    ///
-    /// This function is unsafe because there is no guarantee that this or other threads are
-    /// currently inspecting the inner value.
+impl<T: ?Sized> UnsafeCell<T> {
+    /// Gets a mutable pointer to the wrapped value.
     ///
     /// # Examples
     ///
@@ -697,9 +697,14 @@ impl<T> UnsafeCell<T> {
     ///
     /// let uc = UnsafeCell::new(5);
     ///
-    /// let five = unsafe { uc.into_inner() };
+    /// let five = uc.get();
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
-    pub unsafe fn into_inner(self) -> T { self.value }
+    pub fn get(&self) -> *mut T {
+        // FIXME(#23542) Replace with type ascription.
+        #![allow(trivial_casts)]
+        &self.value as *const T as *mut T
+    }
+
 }
diff --git a/src/libcore/fmt/mod.rs b/src/libcore/fmt/mod.rs
index 73778bfd038..f8a1ef96bcc 100644
--- a/src/libcore/fmt/mod.rs
+++ b/src/libcore/fmt/mod.rs
@@ -1062,7 +1062,7 @@ impl<T: Copy + Debug> Debug for Cell<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: Debug> Debug for RefCell<T> {
+impl<T: ?Sized + Debug> Debug for RefCell<T> {
     fn fmt(&self, f: &mut Formatter) -> Result {
         match self.borrow_state() {
             BorrowState::Unused | BorrowState::Reading => {
@@ -1074,14 +1074,14 @@ impl<T: Debug> Debug for RefCell<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'b, T: Debug> Debug for Ref<'b, T> {
+impl<'b, T: ?Sized + Debug> Debug for Ref<'b, T> {
     fn fmt(&self, f: &mut Formatter) -> Result {
         Debug::fmt(&**self, f)
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'b, T: Debug> Debug for RefMut<'b, T> {
+impl<'b, T: ?Sized + Debug> Debug for RefMut<'b, T> {
     fn fmt(&self, f: &mut Formatter) -> Result {
         Debug::fmt(&*(self.deref()), f)
     }
diff --git a/src/libcoretest/cell.rs b/src/libcoretest/cell.rs
index 85dd1039003..0bd0b66318f 100644
--- a/src/libcoretest/cell.rs
+++ b/src/libcoretest/cell.rs
@@ -159,3 +159,27 @@ fn refcell_default() {
     let cell: RefCell<u64> = Default::default();
     assert_eq!(0, *cell.borrow());
 }
+
+#[test]
+fn unsafe_cell_unsized() {
+    let cell: &UnsafeCell<[i32]> = &UnsafeCell::new([1, 2, 3]);
+    {
+        let val: &mut [i32] = unsafe { &mut *cell.get() };
+        val[0] = 4;
+        val[2] = 5;
+    }
+    let comp: &mut [i32] = &mut [4, 2, 5];
+    assert_eq!(unsafe { &mut *cell.get() }, comp);
+}
+
+#[test]
+fn refcell_unsized() {
+    let cell: &RefCell<[i32]> = &RefCell::new([1, 2, 3]);
+    {
+        let b = &mut *cell.borrow_mut();
+        b[0] = 4;
+        b[2] = 5;
+    }
+    let comp: &mut [i32] = &mut [4, 2, 5];
+    assert_eq!(&*cell.borrow(), comp);
+}
diff --git a/src/libstd/sync/mutex.rs b/src/libstd/sync/mutex.rs
index 30c7407a96d..222aff9188a 100644
--- a/src/libstd/sync/mutex.rs
+++ b/src/libstd/sync/mutex.rs
@@ -112,7 +112,7 @@ use sys_common::poison::{self, TryLockError, TryLockResult, LockResult};
 /// *guard += 1;
 /// ```
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct Mutex<T> {
+pub struct Mutex<T: ?Sized> {
     // Note that this static mutex is in a *box*, not inlined into the struct
     // itself. Once a native mutex has been used once, its address can never
     // change (it can't be moved). This mutex type can be safely moved at any
@@ -124,9 +124,9 @@ pub struct Mutex<T> {
 
 // these are the only places where `T: Send` matters; all other
 // functionality works fine on a single thread.
-unsafe impl<T: Send> Send for Mutex<T> { }
+unsafe impl<T: ?Sized + Send> Send for Mutex<T> { }
 
-unsafe impl<T: Send> Sync for Mutex<T> { }
+unsafe impl<T: ?Sized + Send> Sync for Mutex<T> { }
 
 /// The static mutex type is provided to allow for static allocation of mutexes.
 ///
@@ -164,7 +164,7 @@ pub struct StaticMutex {
 /// `Deref` and `DerefMut` implementations
 #[must_use]
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct MutexGuard<'a, T: 'a> {
+pub struct MutexGuard<'a, T: ?Sized + 'a> {
     // funny underscores due to how Deref/DerefMut currently work (they
     // disregard field privacy).
     __lock: &'a StaticMutex,
@@ -172,7 +172,7 @@ pub struct MutexGuard<'a, T: 'a> {
     __poison: poison::Guard,
 }
 
-impl<'a, T> !marker::Send for MutexGuard<'a, T> {}
+impl<'a, T: ?Sized> !marker::Send for MutexGuard<'a, T> {}
 
 /// Static initialization of a mutex. This constant can be used to initialize
 /// other mutex constants.
@@ -192,7 +192,9 @@ impl<T> Mutex<T> {
             data: UnsafeCell::new(t),
         }
     }
+}
 
+impl<T: ?Sized> Mutex<T> {
     /// Acquires a mutex, blocking the current task until it is able to do so.
     ///
     /// This function will block the local task until it is available to acquire
@@ -245,7 +247,7 @@ impl<T> Mutex<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T> Drop for Mutex<T> {
+impl<T: ?Sized> Drop for Mutex<T> {
     fn drop(&mut self) {
         // This is actually safe b/c we know that there is no further usage of
         // this mutex (it's up to the user to arrange for a mutex to get
@@ -255,12 +257,12 @@ impl<T> Drop for Mutex<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: fmt::Debug + 'static> fmt::Debug for Mutex<T> {
+impl<T: ?Sized + fmt::Debug + 'static> fmt::Debug for Mutex<T> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         match self.try_lock() {
-            Ok(guard) => write!(f, "Mutex {{ data: {:?} }}", *guard),
+            Ok(guard) => write!(f, "Mutex {{ data: {:?} }}", &*guard),
             Err(TryLockError::Poisoned(err)) => {
-                write!(f, "Mutex {{ data: Poisoned({:?}) }}", **err.get_ref())
+                write!(f, "Mutex {{ data: Poisoned({:?}) }}", &**err.get_ref())
             },
             Err(TryLockError::WouldBlock) => write!(f, "Mutex {{ <locked> }}")
         }
@@ -310,7 +312,7 @@ impl StaticMutex {
     }
 }
 
-impl<'mutex, T> MutexGuard<'mutex, T> {
+impl<'mutex, T: ?Sized> MutexGuard<'mutex, T> {
 
     fn new(lock: &'mutex StaticMutex, data: &'mutex UnsafeCell<T>)
            -> LockResult<MutexGuard<'mutex, T>> {
@@ -325,7 +327,7 @@ impl<'mutex, T> MutexGuard<'mutex, T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'mutex, T> Deref for MutexGuard<'mutex, T> {
+impl<'mutex, T: ?Sized> Deref for MutexGuard<'mutex, T> {
     type Target = T;
 
     fn deref<'a>(&'a self) -> &'a T {
@@ -333,14 +335,14 @@ impl<'mutex, T> Deref for MutexGuard<'mutex, T> {
     }
 }
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'mutex, T> DerefMut for MutexGuard<'mutex, T> {
+impl<'mutex, T: ?Sized> DerefMut for MutexGuard<'mutex, T> {
     fn deref_mut<'a>(&'a mut self) -> &'a mut T {
         unsafe { &mut *self.__data.get() }
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'a, T> Drop for MutexGuard<'a, T> {
+impl<'a, T: ?Sized> Drop for MutexGuard<'a, T> {
     #[inline]
     fn drop(&mut self) {
         unsafe {
@@ -350,11 +352,11 @@ impl<'a, T> Drop for MutexGuard<'a, T> {
     }
 }
 
-pub fn guard_lock<'a, T>(guard: &MutexGuard<'a, T>) -> &'a sys::Mutex {
+pub fn guard_lock<'a, T: ?Sized>(guard: &MutexGuard<'a, T>) -> &'a sys::Mutex {
     &guard.__lock.lock
 }
 
-pub fn guard_poison<'a, T>(guard: &MutexGuard<'a, T>) -> &'a poison::Flag {
+pub fn guard_poison<'a, T: ?Sized>(guard: &MutexGuard<'a, T>) -> &'a poison::Flag {
     &guard.__lock.poison
 }
 
@@ -528,4 +530,16 @@ mod tests {
         let lock = arc.lock().unwrap();
         assert_eq!(*lock, 2);
     }
+
+    #[test]
+    fn test_mutex_unsized() {
+        let mutex: &Mutex<[i32]> = &Mutex::new([1, 2, 3]);
+        {
+            let b = &mut *mutex.lock().unwrap();
+            b[0] = 4;
+            b[2] = 5;
+        }
+        let comp: &[i32] = &[4, 2, 5];
+        assert_eq!(&*mutex.lock().unwrap(), comp);
+    }
 }
diff --git a/src/libstd/sync/rwlock.rs b/src/libstd/sync/rwlock.rs
index a133bb01b61..9294fb64783 100644
--- a/src/libstd/sync/rwlock.rs
+++ b/src/libstd/sync/rwlock.rs
@@ -60,13 +60,13 @@ use sys_common::rwlock as sys;
 /// } // write lock is dropped here
 /// ```
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct RwLock<T> {
+pub struct RwLock<T: ?Sized> {
     inner: Box<StaticRwLock>,
     data: UnsafeCell<T>,
 }
 
-unsafe impl<T: Send + Sync> Send for RwLock<T> {}
-unsafe impl<T: Send + Sync> Sync for RwLock<T> {}
+unsafe impl<T: ?Sized + Send + Sync> Send for RwLock<T> {}
+unsafe impl<T: ?Sized + Send + Sync> Sync for RwLock<T> {}
 
 /// Structure representing a statically allocated RwLock.
 ///
@@ -111,24 +111,24 @@ pub const RW_LOCK_INIT: StaticRwLock = StaticRwLock {
 /// dropped.
 #[must_use]
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct RwLockReadGuard<'a, T: 'a> {
+pub struct RwLockReadGuard<'a, T: ?Sized + 'a> {
     __lock: &'a StaticRwLock,
     __data: &'a UnsafeCell<T>,
 }
 
-impl<'a, T> !marker::Send for RwLockReadGuard<'a, T> {}
+impl<'a, T: ?Sized> !marker::Send for RwLockReadGuard<'a, T> {}
 
 /// RAII structure used to release the exclusive write access of a lock when
 /// dropped.
 #[must_use]
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct RwLockWriteGuard<'a, T: 'a> {
+pub struct RwLockWriteGuard<'a, T: ?Sized + 'a> {
     __lock: &'a StaticRwLock,
     __data: &'a UnsafeCell<T>,
     __poison: poison::Guard,
 }
 
-impl<'a, T> !marker::Send for RwLockWriteGuard<'a, T> {}
+impl<'a, T: ?Sized> !marker::Send for RwLockWriteGuard<'a, T> {}
 
 impl<T> RwLock<T> {
     /// Creates a new instance of an `RwLock<T>` which is unlocked.
@@ -144,7 +144,9 @@ impl<T> RwLock<T> {
     pub fn new(t: T) -> RwLock<T> {
         RwLock { inner: box RW_LOCK_INIT, data: UnsafeCell::new(t) }
     }
+}
 
+impl<T: ?Sized> RwLock<T> {
     /// Locks this rwlock with shared read access, blocking the current thread
     /// until it can be acquired.
     ///
@@ -250,19 +252,19 @@ impl<T> RwLock<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T> Drop for RwLock<T> {
+impl<T: ?Sized> Drop for RwLock<T> {
     fn drop(&mut self) {
         unsafe { self.inner.lock.destroy() }
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: fmt::Debug> fmt::Debug for RwLock<T> {
+impl<T: ?Sized + fmt::Debug> fmt::Debug for RwLock<T> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         match self.try_read() {
-            Ok(guard) => write!(f, "RwLock {{ data: {:?} }}", *guard),
+            Ok(guard) => write!(f, "RwLock {{ data: {:?} }}", &*guard),
             Err(TryLockError::Poisoned(err)) => {
-                write!(f, "RwLock {{ data: Poisoned({:?}) }}", **err.get_ref())
+                write!(f, "RwLock {{ data: Poisoned({:?}) }}", &**err.get_ref())
             },
             Err(TryLockError::WouldBlock) => write!(f, "RwLock {{ <locked> }}")
         }
@@ -341,8 +343,7 @@ impl StaticRwLock {
     }
 }
 
-impl<'rwlock, T> RwLockReadGuard<'rwlock, T> {
-
+impl<'rwlock, T: ?Sized> RwLockReadGuard<'rwlock, T> {
     fn new(lock: &'rwlock StaticRwLock, data: &'rwlock UnsafeCell<T>)
            -> LockResult<RwLockReadGuard<'rwlock, T>> {
         poison::map_result(lock.poison.borrow(), |_| {
@@ -353,8 +354,8 @@ impl<'rwlock, T> RwLockReadGuard<'rwlock, T> {
         })
     }
 }
-impl<'rwlock, T> RwLockWriteGuard<'rwlock, T> {
 
+impl<'rwlock, T: ?Sized> RwLockWriteGuard<'rwlock, T> {
     fn new(lock: &'rwlock StaticRwLock, data: &'rwlock UnsafeCell<T>)
            -> LockResult<RwLockWriteGuard<'rwlock, T>> {
         poison::map_result(lock.poison.borrow(), |guard| {
@@ -368,33 +369,35 @@ impl<'rwlock, T> RwLockWriteGuard<'rwlock, T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'rwlock, T> Deref for RwLockReadGuard<'rwlock, T> {
+impl<'rwlock, T: ?Sized> Deref for RwLockReadGuard<'rwlock, T> {
     type Target = T;
 
     fn deref(&self) -> &T { unsafe { &*self.__data.get() } }
 }
+
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'rwlock, T> Deref for RwLockWriteGuard<'rwlock, T> {
+impl<'rwlock, T: ?Sized> Deref for RwLockWriteGuard<'rwlock, T> {
     type Target = T;
 
     fn deref(&self) -> &T { unsafe { &*self.__data.get() } }
 }
+
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'rwlock, T> DerefMut for RwLockWriteGuard<'rwlock, T> {
+impl<'rwlock, T: ?Sized> DerefMut for RwLockWriteGuard<'rwlock, T> {
     fn deref_mut(&mut self) -> &mut T {
         unsafe { &mut *self.__data.get() }
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'a, T> Drop for RwLockReadGuard<'a, T> {
+impl<'a, T: ?Sized> Drop for RwLockReadGuard<'a, T> {
     fn drop(&mut self) {
         unsafe { self.__lock.lock.read_unlock(); }
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<'a, T> Drop for RwLockWriteGuard<'a, T> {
+impl<'a, T: ?Sized> Drop for RwLockWriteGuard<'a, T> {
     fn drop(&mut self) {
         self.__lock.poison.done(&self.__poison);
         unsafe { self.__lock.lock.write_unlock(); }
@@ -562,4 +565,16 @@ mod tests {
         let lock = arc.read().unwrap();
         assert_eq!(*lock, 2);
     }
+
+    #[test]
+    fn test_rwlock_unsized() {
+        let rw: &RwLock<[i32]> = &RwLock::new([1, 2, 3]);
+        {
+            let b = &mut *rw.write().unwrap();
+            b[0] = 4;
+            b[2] = 5;
+        }
+        let comp: &[i32] = &[4, 2, 5];
+        assert_eq!(&*rw.read().unwrap(), comp);
+    }
 }
diff --git a/src/test/compile-fail/bad-sized.rs b/src/test/compile-fail/bad-sized.rs
index fca74e457c2..8c13ff70515 100644
--- a/src/test/compile-fail/bad-sized.rs
+++ b/src/test/compile-fail/bad-sized.rs
@@ -8,14 +8,10 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use std::cell::RefCell;
-
 trait Trait {}
 
 pub fn main() {
     let x: Vec<Trait + Sized> = Vec::new();
     //~^ ERROR the trait `core::marker::Sized` is not implemented
     //~^^ ERROR the trait `core::marker::Sized` is not implemented
-    let x: Vec<Box<RefCell<Trait + Sized>>> = Vec::new();
-    //~^ ERROR the trait `core::marker::Sized` is not implemented
 }