@@ -353,6 +353,8 @@ impl<T: ?Sized> NonNull<T> {
353
353
#[ rustc_never_returns_null_ptr]
354
354
#[ must_use]
355
355
#[ inline( always) ]
356
+ //Ensures address of resulting pointer is same as original
357
+ #[ ensures( |result: & * mut T | * result == self . pointer as * mut T ) ]
356
358
pub const fn as_ptr ( self ) -> * mut T {
357
359
self . pointer as * mut T
358
360
}
@@ -454,6 +456,8 @@ impl<T: ?Sized> NonNull<T> {
454
456
#[ must_use = "this returns the result of the operation, \
455
457
without modifying the original"]
456
458
#[ inline]
459
+ // Address preservation
460
+ #[ ensures( |result: & NonNull <U >| result. as_ptr( ) . addr( ) == self . as_ptr( ) . addr( ) ) ]
457
461
pub const fn cast < U > ( self ) -> NonNull < U > {
458
462
// SAFETY: `self` is a `NonNull` pointer which is necessarily non-null
459
463
unsafe { NonNull { pointer : self . as_ptr ( ) as * mut U } }
@@ -1470,6 +1474,8 @@ impl<T> NonNull<[T]> {
1470
1474
#[ inline]
1471
1475
#[ must_use]
1472
1476
#[ unstable( feature = "slice_ptr_get" , issue = "74265" ) ]
1477
+ // Address preservation
1478
+ #[ ensures( |result: & NonNull <T >| result. as_ptr( ) . addr( ) == self . as_ptr( ) . addr( ) ) ]
1473
1479
pub const fn as_non_null_ptr ( self ) -> NonNull < T > {
1474
1480
self . cast ( )
1475
1481
}
@@ -1489,6 +1495,8 @@ impl<T> NonNull<[T]> {
1489
1495
#[ must_use]
1490
1496
#[ unstable( feature = "slice_ptr_get" , issue = "74265" ) ]
1491
1497
#[ rustc_never_returns_null_ptr]
1498
+ // Address preservation
1499
+ #[ ensures( |result: & * mut T | * result == self . pointer as * mut T ) ]
1492
1500
pub const fn as_mut_ptr ( self ) -> * mut T {
1493
1501
self . as_non_null_ptr ( ) . as_ptr ( )
1494
1502
}
@@ -2186,6 +2194,42 @@ mod verify {
2186
2194
}
2187
2195
}
2188
2196
2197
+ #[ kani:: proof_for_contract( NonNull :: as_ptr) ]
2198
+ pub fn non_null_check_as_ptr ( ) {
2199
+ // Create a non-null pointer to a random value
2200
+ let non_null_ptr: * mut i32 = kani:: any :: < usize > ( ) as * mut i32 ;
2201
+ if let Some ( ptr) = NonNull :: new ( non_null_ptr) {
2202
+ let result = ptr. as_ptr ( ) ;
2203
+ }
2204
+
2205
+ }
2206
+
2207
+ #[ kani:: proof_for_contract( NonNull :: <[ T ] >:: as_mut_ptr) ]
2208
+ pub fn non_null_check_as_mut_ptr ( ) {
2209
+ const ARR_LEN : usize = 100 ;
2210
+ let mut values: [ i32 ; ARR_LEN ] = kani:: any ( ) ;
2211
+ let slice = kani:: slice:: any_slice_of_array_mut ( & mut values) ;
2212
+ let non_null_ptr = NonNull :: new ( slice as * mut [ i32 ] ) . unwrap ( ) ;
2213
+ let result = non_null_ptr. as_mut_ptr ( ) ;
2214
+ }
2215
+ #[ kani:: proof_for_contract( NonNull :: <T >:: cast) ]
2216
+ pub fn non_null_check_cast ( ) {
2217
+ // Create a non-null pointer to a random value
2218
+ let non_null_ptr: * mut i32 = kani:: any :: < usize > ( ) as * mut i32 ;
2219
+ if let Some ( ptr) = NonNull :: new ( non_null_ptr) {
2220
+ let result: NonNull < u8 > = ptr. cast ( ) ;
2221
+ }
2222
+ }
2223
+
2224
+ #[ kani:: proof_for_contract( NonNull :: <[ T ] >:: as_non_null_ptr) ]
2225
+ pub fn non_null_check_as_non_null_ptr ( ) {
2226
+ const ARR_LEN : usize = 100 ;
2227
+ let mut values: [ i32 ; ARR_LEN ] = kani:: any ( ) ;
2228
+ let slice = kani:: slice:: any_slice_of_array_mut ( & mut values) ;
2229
+ let non_null_ptr = NonNull :: new ( slice as * mut [ i32 ] ) . unwrap ( ) ;
2230
+ let result = non_null_ptr. as_non_null_ptr ( ) ;
2231
+ }
2232
+
2189
2233
#[ kani:: proof]
2190
2234
pub fn non_null_check_len ( ) {
2191
2235
// Create a non-deterministic NonNull pointer using kani::any()
0 commit comments