|
1 | 1 | #![warn(clippy::transmutes_expressible_as_ptr_casts)]
|
2 | 2 |
|
| 3 | +// rustc_typeck::check::cast contains documentation about when a cast `e as U` is |
| 4 | +// valid, which we quote from below. |
| 5 | +use std::mem::transmute; |
| 6 | + |
3 | 7 | fn main() {
|
4 |
| - // test code goes here |
| 8 | + // e is an integer and U is *U_0, while U_0: Sized; addr-ptr-cast |
| 9 | + let ptr_i32_transmute = unsafe { |
| 10 | + transmute::<isize, *const i32>(-1) |
| 11 | + }; |
| 12 | + let ptr_i32 = -1isize as *const i32; |
| 13 | + |
| 14 | + // e has type *T, U is *U_0, and either U_0: Sized ... |
| 15 | + let ptr_i8_transmute = unsafe { |
| 16 | + transmute::<*const i32, *const i8>(ptr_i32) |
| 17 | + }; |
| 18 | + let ptr_i8 = ptr_i32 as *const i8; |
| 19 | + |
| 20 | + let slice_ptr = &[0,1,2,3] as *const [i32]; |
| 21 | + |
| 22 | + // ... or pointer_kind(T) = pointer_kind(U_0); ptr-ptr-cast |
| 23 | + let ptr_to_unsized_transmute = unsafe { |
| 24 | + transmute::<*const [i32], *const [u16]>(slice_ptr) |
| 25 | + }; |
| 26 | + let ptr_to_unsized = slice_ptr as *const [u16]; |
| 27 | + // TODO: We could try testing vtable casts here too, but maybe |
| 28 | + // we should wait until std::raw::TraitObject is stabilized? |
| 29 | + |
| 30 | + // e has type *T and U is a numeric type, while T: Sized; ptr-addr-cast |
| 31 | + let usize_from_int_ptr_transmute = unsafe { |
| 32 | + transmute::<*const i32, usize>(ptr_i32) |
| 33 | + }; |
| 34 | + let usize_from_int_ptr = ptr_i32 as usize; |
| 35 | + |
| 36 | + let array_ref: &[i32; 4] = &[1,2,3,4]; |
| 37 | + |
| 38 | + // e has type &[T; n] and U is *const T; array-ptr-cast |
| 39 | + let array_ptr_transmute = unsafe { |
| 40 | + transmute::<&[i32; 4], *const [i32; 4]>(array_ref) |
| 41 | + }; |
| 42 | + let array_ptr = array_ref as *const [i32; 4]; |
| 43 | + |
| 44 | + fn foo(_: usize) -> u8 { 42 } |
| 45 | + |
| 46 | + // e is a function pointer type and U has type *T, while T: Sized; fptr-ptr-cast |
| 47 | + let usize_ptr_transmute = unsafe { |
| 48 | + transmute::<fn(usize) -> u8, *const usize>(foo) |
| 49 | + }; |
| 50 | + let usize_ptr_transmute = foo as *const usize; |
| 51 | + |
| 52 | + // e is a function pointer type and U is an integer; fptr-addr-cast |
| 53 | + let usize_from_fn_ptr_transmute = unsafe { |
| 54 | + transmute::<fn(usize) -> u8, usize>(foo) |
| 55 | + }; |
| 56 | + let usize_from_fn_ptr = foo as *const usize; |
5 | 57 | }
|
0 commit comments