From 9c44d80c83eb250594ecad05ea5340e0b51af525 Mon Sep 17 00:00:00 2001 From: Jack O'Connor Date: Wed, 11 Aug 2021 14:38:20 -0400 Subject: [PATCH] add Cell::as_array_of_cells, similar to Cell::as_slice_of_cells Previously, converting `&mut [T; N]` to `&[Cell; N]` looks like this: let array = &mut [1, 2, 3]; let cells: &[Cell; 3] = Cell::from_mut(&mut array[..]) .as_slice_of_cells() .try_into() .unwrap(); With this new helper method, it looks like this: let array = &mut [1, 2, 3]; let cells: &[Cell; 3] = Cell::from_mut(array).as_array_of_cells(); --- library/core/src/cell.rs | 20 +++++++++++++++++++ src/test/ui/rfcs/rfc-1789-as-cell/from-mut.rs | 9 +++++++++ 2 files changed, 29 insertions(+) diff --git a/library/core/src/cell.rs b/library/core/src/cell.rs index f0c934edf3977..85b43f4884760 100644 --- a/library/core/src/cell.rs +++ b/library/core/src/cell.rs @@ -576,6 +576,26 @@ impl Cell<[T]> { } } +impl Cell<[T; N]> { + /// Returns a `&[Cell; N]` from a `&Cell<[T; N]>` + /// + /// # Examples + /// + /// ``` + /// #![feature(as_array_of_cells)] + /// use std::cell::Cell; + /// + /// let mut array: [i32; 3] = [1, 2, 3]; + /// let cell_array: &Cell<[i32; 3]> = Cell::from_mut(&mut array); + /// let array_cell: &[Cell; 3] = cell_array.as_array_of_cells(); + /// ``` + #[unstable(feature = "as_array_of_cells", issue = "88248")] + pub fn as_array_of_cells(&self) -> &[Cell; N] { + // SAFETY: `Cell` has the same memory layout as `T`. + unsafe { &*(self as *const Cell<[T; N]> as *const [Cell; N]) } + } +} + /// A mutable memory location with dynamically checked borrow rules /// /// See the [module-level documentation](self) for more. diff --git a/src/test/ui/rfcs/rfc-1789-as-cell/from-mut.rs b/src/test/ui/rfcs/rfc-1789-as-cell/from-mut.rs index ea3ad7aed4926..329fadb150fcd 100644 --- a/src/test/ui/rfcs/rfc-1789-as-cell/from-mut.rs +++ b/src/test/ui/rfcs/rfc-1789-as-cell/from-mut.rs @@ -1,5 +1,7 @@ // run-pass +#![feature(as_array_of_cells)] + use std::cell::Cell; fn main() { @@ -8,4 +10,11 @@ fn main() { let slice_cell: &[Cell] = cell_slice.as_slice_of_cells(); assert_eq!(slice_cell.len(), 3); + + let mut array: [i32; 3] = [1, 2, 3]; + let cell_array: &Cell<[i32; 3]> = Cell::from_mut(&mut array); + let array_cell: &[Cell; 3] = cell_array.as_array_of_cells(); + + array_cell[0].set(99); + assert_eq!(array, [99, 2, 3]); }