1+ use std:: mem;
2+ use std:: ptr:: NonNull ;
3+
14use crate :: dimension:: { self , stride_offset} ;
25use crate :: extension:: nonnull:: nonnull_debug_checked_from_ptr;
36use crate :: imp_prelude:: * ;
@@ -11,16 +14,20 @@ where
1114 ///
1215 /// Unsafe because caller is responsible for ensuring that the array will
1316 /// meet all of the invariants of the `ArrayBase` type.
14- #[ inline( always ) ]
15- pub ( crate ) unsafe fn new_ ( ptr : * const A , dim : D , strides : D ) -> Self {
17+ #[ inline]
18+ pub ( crate ) unsafe fn new ( ptr : NonNull < A > , dim : D , strides : D ) -> Self {
1619 RawArrayView {
1720 data : RawViewRepr :: new ( ) ,
18- ptr : nonnull_debug_checked_from_ptr ( ptr as * mut _ ) ,
21+ ptr,
1922 dim,
2023 strides,
2124 }
2225 }
2326
27+ unsafe fn new_ ( ptr : * const A , dim : D , strides : D ) -> Self {
28+ Self :: new ( nonnull_debug_checked_from_ptr ( ptr as * mut A ) , dim, strides)
29+ }
30+
2431 /// Create an `RawArrayView<A, D>` from shape information and a raw pointer
2532 /// to the elements.
2633 ///
7683 /// ensure that all of the data is valid and choose the correct lifetime.
7784 #[ inline]
7885 pub unsafe fn deref_into_view < ' a > ( self ) -> ArrayView < ' a , A , D > {
79- ArrayView :: new_ ( self . ptr . as_ptr ( ) , self . dim , self . strides )
86+ ArrayView :: new ( self . ptr , self . dim , self . strides )
8087 }
8188
8289 /// Split the array view along `axis` and return one array pointer strictly
@@ -105,6 +112,32 @@ where
105112
106113 ( left, right)
107114 }
115+
116+ /// Cast the raw pointer of the raw array view to a different type
117+ ///
118+ /// **Panics** if element size is not compatible.
119+ ///
120+ /// Lack of panic does not imply it is a valid cast. The cast works the same
121+ /// way as regular raw pointer casts.
122+ ///
123+ /// While this method is safe, for the same reason as regular raw pointer
124+ /// casts are safe, access through the produced raw view is only possible
125+ /// in an unsafe block or function.
126+ pub fn cast < B > ( self ) -> RawArrayView < B , D > {
127+ assert_eq ! (
128+ mem:: size_of:: <B >( ) ,
129+ mem:: size_of:: <A >( ) ,
130+ "size mismatch in raw view cast"
131+ ) ;
132+ let ptr = self . ptr . cast :: < B > ( ) ;
133+ debug_assert ! (
134+ is_aligned( ptr. as_ptr( ) ) ,
135+ "alignment mismatch in raw view cast"
136+ ) ;
137+ /* Alignment checked with debug assertion: alignment could be dynamically correct,
138+ * and we don't have a check that compiles out for that. */
139+ unsafe { RawArrayView :: new ( ptr, self . dim , self . strides ) }
140+ }
108141}
109142
110143impl < A , D > RawArrayViewMut < A , D >
@@ -115,16 +148,20 @@ where
115148 ///
116149 /// Unsafe because caller is responsible for ensuring that the array will
117150 /// meet all of the invariants of the `ArrayBase` type.
118- #[ inline( always ) ]
119- pub ( crate ) unsafe fn new_ ( ptr : * mut A , dim : D , strides : D ) -> Self {
151+ #[ inline]
152+ pub ( crate ) unsafe fn new ( ptr : NonNull < A > , dim : D , strides : D ) -> Self {
120153 RawArrayViewMut {
121154 data : RawViewRepr :: new ( ) ,
122- ptr : nonnull_debug_checked_from_ptr ( ptr ) ,
155+ ptr,
123156 dim,
124157 strides,
125158 }
126159 }
127160
161+ unsafe fn new_ ( ptr : * mut A , dim : D , strides : D ) -> Self {
162+ Self :: new ( nonnull_debug_checked_from_ptr ( ptr) , dim, strides)
163+ }
164+
128165 /// Create an `RawArrayViewMut<A, D>` from shape information and a raw
129166 /// pointer to the elements.
130167 ///
@@ -176,7 +213,7 @@ where
176213 /// Converts to a non-mutable `RawArrayView`.
177214 #[ inline]
178215 pub ( crate ) fn into_raw_view ( self ) -> RawArrayView < A , D > {
179- unsafe { RawArrayView :: new_ ( self . ptr . as_ptr ( ) , self . dim , self . strides ) }
216+ unsafe { RawArrayView :: new ( self . ptr , self . dim , self . strides ) }
180217 }
181218
182219 /// Converts to a read-only view of the array.
@@ -186,7 +223,7 @@ where
186223 /// ensure that all of the data is valid and choose the correct lifetime.
187224 #[ inline]
188225 pub unsafe fn deref_into_view < ' a > ( self ) -> ArrayView < ' a , A , D > {
189- ArrayView :: new_ ( self . ptr . as_ptr ( ) , self . dim , self . strides )
226+ ArrayView :: new ( self . ptr , self . dim , self . strides )
190227 }
191228
192229 /// Converts to a mutable view of the array.
@@ -196,7 +233,7 @@ where
196233 /// ensure that all of the data is valid and choose the correct lifetime.
197234 #[ inline]
198235 pub unsafe fn deref_into_view_mut < ' a > ( self ) -> ArrayViewMut < ' a , A , D > {
199- ArrayViewMut :: new_ ( self . ptr . as_ptr ( ) , self . dim , self . strides )
236+ ArrayViewMut :: new ( self . ptr , self . dim , self . strides )
200237 }
201238
202239 /// Split the array view along `axis` and return one array pointer strictly
@@ -207,9 +244,35 @@ where
207244 let ( left, right) = self . into_raw_view ( ) . split_at ( axis, index) ;
208245 unsafe {
209246 (
210- Self :: new_ ( left. ptr . as_ptr ( ) , left. dim , left. strides ) ,
211- Self :: new_ ( right. ptr . as_ptr ( ) , right. dim , right. strides ) ,
247+ Self :: new ( left. ptr , left. dim , left. strides ) ,
248+ Self :: new ( right. ptr , right. dim , right. strides ) ,
212249 )
213250 }
214251 }
252+
253+ /// Cast the raw pointer of the raw array view to a different type
254+ ///
255+ /// **Panics** if element size is not compatible.
256+ ///
257+ /// Lack of panic does not imply it is a valid cast. The cast works the same
258+ /// way as regular raw pointer casts.
259+ ///
260+ /// While this method is safe, for the same reason as regular raw pointer
261+ /// casts are safe, access through the produced raw view is only possible
262+ /// in an unsafe block or function.
263+ pub fn cast < B > ( self ) -> RawArrayViewMut < B , D > {
264+ assert_eq ! (
265+ mem:: size_of:: <B >( ) ,
266+ mem:: size_of:: <A >( ) ,
267+ "size mismatch in raw view cast"
268+ ) ;
269+ let ptr = self . ptr . cast :: < B > ( ) ;
270+ debug_assert ! (
271+ is_aligned( ptr. as_ptr( ) ) ,
272+ "alignment mismatch in raw view cast"
273+ ) ;
274+ /* Alignment checked with debug assertion: alignment could be dynamically correct,
275+ * and we don't have a check that compiles out for that. */
276+ unsafe { RawArrayViewMut :: new ( ptr, self . dim , self . strides ) }
277+ }
215278}
0 commit comments