You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Rollup merge of rust-lang#119562 - LegionMammal978:rename-pin-pointer, r=Amanieu,dtolnay
Rename `pointer` field on `Pin`
A few days ago, I was helping another user create a self-referential type using `PhantomPinned`. However, I noticed an odd behavior when I tried to access one of the type's fields via `Pin`'s `Deref` impl:
```rust
use std::{marker::PhantomPinned, ptr};
struct Pinned {
data: i32,
pointer: *const i32,
_pin: PhantomPinned,
}
fn main() {
let mut b = Box::pin(Pinned {
data: 42,
pointer: ptr::null(),
_pin: PhantomPinned,
});
{
let pinned = unsafe { b.as_mut().get_unchecked_mut() };
pinned.pointer = &pinned.data;
}
println!("{}", unsafe { *b.pointer });
}
```
```rust
error[E0658]: use of unstable library feature 'unsafe_pin_internals'
--> <source>:19:30
|
19 | println!("{}", unsafe { *b.pointer });
| ^^^^^^^^^
error[E0277]: `Pinned` doesn't implement `std::fmt::Display`
--> <source>:19:20
|
19 | println!("{}", unsafe { *b.pointer });
| ^^^^^^^^^^^^^^^^^^^^^ `Pinned` cannot be formatted with the default formatter
|
= help: the trait `std::fmt::Display` is not implemented for `Pinned`
= note: in format strings you may be able to use `{:?}` (or {:#?} for pretty-print) instead
= note: this error originates in the macro `$crate::format_args_nl` which comes from the expansion of the macro `println` (in Nightly builds, run with -Z macro-backtrace for more info)
```
Since the user named their field `pointer`, it conflicts with the `pointer` field on `Pin`, which is public but unstable since Rust 1.60.0 with rust-lang#93176. On versions from 1.33.0 to 1.59.0, where the field on `Pin` is private, this program compiles and prints `42` as expected.
To avoid this confusing behavior, this PR renames `pointer` to `__pointer`, so that it's less likely to conflict with a `pointer` field on the underlying type, as accessed through the `Deref` impl. This is technically a breaking change for anyone who names their field `__pointer` on the inner type; if this is undesirable, it could be renamed to something more longwinded. It's also a nightly breaking change for any external users of `unsafe_pin_internals`.
// The following implementations aren't derived in order to avoid soundness
1102
-
// issues. `&self.pointer` should not be accessible to untrusted trait
1108
+
// issues. `&self.__pointer` should not be accessible to untrusted trait
1103
1109
// implementations.
1104
1110
//
1105
1111
// See <https://internals.rust-lang.org/t/unsoundness-in-pin/11311/73> for more details.
// instead, dropped _at the end of the enscoping block_.
1942
1948
// For instance,
1943
1949
// ```rust
1944
-
// let p = Pin { pointer: &mut <temporary> };
1950
+
// let p = Pin { __pointer: &mut <temporary> };
1945
1951
// ```
1946
1952
// becomes:
1947
1953
// ```rust
1948
1954
// let mut anon = <temporary>;
1949
-
// let p = Pin { pointer: &mut anon };
1955
+
// let p = Pin { __pointer: &mut anon };
1950
1956
// ```
1951
1957
// which is *exactly* what we want.
1952
1958
//
1953
1959
// See https://doc.rust-lang.org/1.58.1/reference/destructors.html#temporary-lifetime-extension
0 commit comments