| David Tolnay | 3384c14 | 2020-09-14 00:26:47 -0400 | [diff] [blame] | 1 | use core::mem; |
| 2 | use core::ptr::NonNull; |
| 3 | use core::slice; |
| 4 | use core::str; |
| David Tolnay | 7db7369 | 2019-10-20 14:51:12 -0400 | [diff] [blame] | 5 | |
| 6 | // Not necessarily ABI compatible with &str. Codegen performs the translation. |
| 7 | #[repr(C)] |
| 8 | #[derive(Copy, Clone)] |
| 9 | pub struct RustStr { |
| David Tolnay | ebef4a2 | 2020-03-17 15:33:47 -0700 | [diff] [blame] | 10 | pub(crate) ptr: NonNull<u8>, |
| 11 | pub(crate) len: usize, |
| David Tolnay | 7db7369 | 2019-10-20 14:51:12 -0400 | [diff] [blame] | 12 | } |
| 13 | |
| 14 | impl RustStr { |
| 15 | pub fn from(s: &str) -> Self { |
| 16 | RustStr { |
| David Tolnay | 792d022 | 2020-03-16 21:57:47 -0700 | [diff] [blame] | 17 | ptr: NonNull::from(s).cast::<u8>(), |
| David Tolnay | 7db7369 | 2019-10-20 14:51:12 -0400 | [diff] [blame] | 18 | len: s.len(), |
| 19 | } |
| 20 | } |
| 21 | |
| 22 | pub unsafe fn as_str<'a>(self) -> &'a str { |
| David Tolnay | 792d022 | 2020-03-16 21:57:47 -0700 | [diff] [blame] | 23 | let slice = slice::from_raw_parts(self.ptr.as_ptr(), self.len); |
| David Tolnay | 7db7369 | 2019-10-20 14:51:12 -0400 | [diff] [blame] | 24 | str::from_utf8_unchecked(slice) |
| 25 | } |
| 26 | } |
| 27 | |
| David Tolnay | ad7186a | 2020-04-24 15:37:45 -0700 | [diff] [blame] | 28 | const_assert_eq!(mem::size_of::<Option<RustStr>>(), mem::size_of::<RustStr>()); |