|
1 |
| -use core::{fmt, ops}; |
| 1 | +use core::{fmt, ops, ptr}; |
2 | 2 |
|
3 | 3 | pub trait Address:
|
4 | 4 | Copy
|
@@ -117,19 +117,40 @@ pub trait Address:
|
117 | 117 | self.is_aligned(core::mem::align_of::<T>())
|
118 | 118 | }
|
119 | 119 |
|
| 120 | + /// Converts this address into a const pointer to a value of type `T`. |
| 121 | + /// |
| 122 | + /// # Panics |
| 123 | + /// |
| 124 | + /// - If `self` is not aligned for a `T`-typed value. |
| 125 | + #[inline] |
| 126 | + #[track_caller] |
| 127 | + fn as_ptr<T>(self) -> *const T { |
| 128 | + // Some architectures permit unaligned reads, but Rust considers |
| 129 | + // dereferencing a pointer that isn't type-aligned to be UB. |
| 130 | + assert!( |
| 131 | + self.is_aligned_for::<T>(), |
| 132 | + "assertion failed: self.is_aligned_for::<{}>();\n\tself={self:?}", |
| 133 | + core::any::type_name::<T>(), |
| 134 | + ); |
| 135 | + ptr::with_exposed_provenance(self.as_usize()) |
| 136 | + } |
| 137 | + |
| 138 | + /// Converts this address into a mutable pointer to a value of type `T`. |
| 139 | + /// |
120 | 140 | /// # Panics
|
121 | 141 | ///
|
122 | 142 | /// - If `self` is not aligned for a `T`-typed value.
|
| 143 | + #[inline] |
123 | 144 | #[track_caller]
|
124 |
| - fn as_ptr<T>(self) -> *mut T { |
| 145 | + fn as_mut_ptr<T>(self) -> *mut T { |
125 | 146 | // Some architectures permit unaligned reads, but Rust considers
|
126 | 147 | // dereferencing a pointer that isn't type-aligned to be UB.
|
127 | 148 | assert!(
|
128 | 149 | self.is_aligned_for::<T>(),
|
129 | 150 | "assertion failed: self.is_aligned_for::<{}>();\n\tself={self:?}",
|
130 | 151 | core::any::type_name::<T>(),
|
131 | 152 | );
|
132 |
| - self.as_usize() as *mut T |
| 153 | + ptr::with_exposed_provenance_mut(self.as_usize()) |
133 | 154 | }
|
134 | 155 | }
|
135 | 156 |
|
@@ -327,13 +348,27 @@ macro_rules! impl_addrs {
|
327 | 348 | Address::is_aligned_for::<T>(self)
|
328 | 349 | }
|
329 | 350 |
|
| 351 | + /// Converts this address into a const pointer to a value of type `T`. |
| 352 | + /// |
330 | 353 | /// # Panics
|
331 | 354 | ///
|
332 | 355 | /// - If `self` is not aligned for a `T`-typed value.
|
333 | 356 | #[inline]
|
334 |
| - pub fn as_ptr<T>(self) -> *mut T { |
| 357 | + #[track_caller] |
| 358 | + pub fn as_ptr<T>(self) -> *const T { |
335 | 359 | Address::as_ptr(self)
|
336 | 360 | }
|
| 361 | + |
| 362 | + /// Converts this address into a mutable pointer to a value of type `T`. |
| 363 | + /// |
| 364 | + /// # Panics |
| 365 | + /// |
| 366 | + /// - If `self` is not aligned for a `T`-typed value. |
| 367 | + #[inline] |
| 368 | + #[track_caller] |
| 369 | + pub fn as_mut_ptr<T>(self) -> *mut T { |
| 370 | + Address::as_mut_ptr(self) |
| 371 | + } |
337 | 372 | }
|
338 | 373 | )+
|
339 | 374 | }
|
@@ -392,9 +427,15 @@ impl VAddr {
|
392 | 427 | Self(u)
|
393 | 428 | }
|
394 | 429 |
|
| 430 | + /// Constructs a `VAddr` from a `*const T` pointer, exposing its provenance. |
| 431 | + #[inline] |
| 432 | + pub fn from_ptr<T: ?Sized>(ptr: *const T) -> Self { |
| 433 | + Self::from_usize(ptr.expose_provenance()) |
| 434 | + } |
| 435 | + |
395 | 436 | #[inline]
|
396 | 437 | pub fn of<T: ?Sized>(pointee: &T) -> Self {
|
397 |
| - Self::from_usize(pointee as *const _ as *const () as usize) |
| 438 | + Self::from_ptr(pointee as *const T) |
398 | 439 | }
|
399 | 440 | }
|
400 | 441 |
|
|
0 commit comments