Skip to content

Document & implement the transmutation modeled by BikeshedIntrinsicFrom #129032

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Aug 27, 2024

Conversation

jswrenn
Copy link
Member

@jswrenn jswrenn commented Aug 12, 2024

Documents that BikeshedIntrinsicFrom models transmute-via-union, which is slightly more expressive than the transmute-via-cast implemented by transmute_copy. Additionally, we provide an implementation of transmute-via-union as a method on the BikeshedIntrinsicFrom trait with additional documentation on the boundary between trait invariants and caller obligations.

Whether or not transmute-via-union is the right kind of transmute to model remains up for discussion [1]. Regardless, it seems wise to document the present behavior.

[1] https://rust-lang.zulipchat.com/#narrow/stream/216762-project-safe-transmute/topic/What.20'kind'.20of.20transmute.20to.20model.3F/near/426331967

Tracking Issue: #99571

r? @compiler-errors

cc @scottmcm, @Lokathor

@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-libs Relevant to the library team, which will review and decide on the PR/issue. labels Aug 12, 2024
@rust-log-analyzer

This comment has been minimized.

/// This trait cannot be implemented explicitly. It is implemented on-the-fly by
/// the compiler for all types `Src` and `Self` such that, given a set of safety
/// obligations on the programmer (see [`Assume`]), the compiler has proved that
/// the bits of a value of type `Src` can be soundly reinterpreted as `Self`.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
/// the bits of a value of type `Src` can be soundly reinterpreted as `Self`.
/// the bits of a value of type `Src` can be soundly reinterpreted as a `Self`.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't actually agree with this change. "as Self" sounds more correct in my idiolect.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My thinking is that the left-hand side refers to a runtime object - "a value of type Src" - and so the right-hand side should too. Conservatively, we could say "a value of type Self", but IIUC "a Self" is a common shorthand for that.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we take the Self part out for a moment, it would be common to say "as an i32", or "as an array", so "a Self" probably fits.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm inclined to agree with @Lokathor's argument, so I've opted for "a Self".

Comment on lines 21 to 29
/// union Transmute<T, U> {
/// src: ManuallyDrop<T>,
/// dst: ManuallyDrop<U>,
/// }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
/// union Transmute<T, U> {
/// src: ManuallyDrop<T>,
/// dst: ManuallyDrop<U>,
/// }
/// union Transmute<S, D> {
/// src: ManuallyDrop<S>,
/// dst: ManuallyDrop<D>,
/// }

I assume your intention is to not confuse the reader by re-using Src and Dst? In that case, IMO using S and D makes the correspondence with Src and Dst clearer.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Comment on lines 42 to 50
/// Implementations of this trait do not provide any guarantee of portability
/// across toolchains or compilations. This trait may be implemented for certain
/// combinations of `Src`, `Self` and `ASSUME` on some toolchains, but not
/// others. For example, if the layouts of `Src` or `Self` are
/// non-deterministic, the presence or absence of an implementation of this
/// trait may also be non-deterministic. Even if `Src` and `Self` have
/// deterministic layouts (e.g., they are `repr(C)` structs), Rust does not
/// specify the alignments of its primitive integer types, and layouts that
/// involve these types may vary across toolchains.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also mention varying across target architecture and target OS? Both can affect alignment, and architecture can affect size (maybe OS can too? not sure).

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

One change left:

Rust does not specify the alignments of its primitive integer types, and layouts that involve these types may vary across toolchains.

This should say "across toolchains or targets" or something similar.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Comment on lines 36 to 38
/// Note that this construction supports some transmutations forbidden by
/// [`mem::transmute_copy`](super::transmute_copy), namely transmutations that
/// extend the trailing padding of `Src` to fill `Dst`.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This strikes me as a bit ambiguous. I'd clarify in particular that you're referring to a situation where:

  • size_of::<Src>() < size_of::<Dst>()
  • The trailing size_of::<Dst>() - size_of::<Src>() bytes of Dst are permitted to be uninitialized (e.g., are padding)

Copy link
Member Author

@jswrenn jswrenn Aug 14, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Comment on lines 47 to 50
/// trait may also be non-deterministic. Even if `Src` and `Self` have
/// deterministic layouts (e.g., they are `repr(C)` structs), Rust does not
/// specify the alignments of its primitive integer types, and layouts that
/// involve these types may vary across toolchains.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would maybe phrase this as "stability hazards may exist" and mention the alignments of primitive types as one example of such hazards. Don't want to imply by omission that they're the only hazard.

@rust-log-analyzer

This comment has been minimized.

@jswrenn jswrenn force-pushed the transmute-method branch 2 times, most recently from 43dfc04 to b17b899 Compare August 14, 2024 15:16
@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

Copy link
Contributor

@joshlf joshlf left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A few optional changes requested, but LGTM!

@bors
Copy link
Collaborator

bors commented Aug 20, 2024

☔ The latest upstream changes (presumably #122551) made this pull request unmergeable. Please resolve the merge conflicts.

@jswrenn jswrenn force-pushed the transmute-method branch 2 times, most recently from f31c502 to 5ab5080 Compare August 22, 2024 20:03
@jswrenn
Copy link
Member Author

jswrenn commented Aug 22, 2024

@joshlf, could you take another look at this?

@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

Documents that `BikeshedIntrinsicFrom` models transmute-via-union,
which is slightly more expressive than the transmute-via-cast
implemented by `transmute_copy`. Additionally, we provide an
implementation of transmute-via-union as a method on the
`BikeshedIntrinsicFrom` trait with additional documentation on
the boundary between trait invariants and caller obligations.

Whether or not transmute-via-union is the right kind of transmute
to model remains up for discussion [1]. Regardless, it seems wise
to document the present behavior.

[1] https://rust-lang.zulipchat.com/#narrow/stream/216762-project-safe-transmute/topic/What.20'kind'.20of.20transmute.20to.20model.3F/near/426331967
@compiler-errors
Copy link
Member

@bors r+

@bors
Copy link
Collaborator

bors commented Aug 26, 2024

📌 Commit 2540070 has been approved by compiler-errors

It is now in the queue for this repository.

@bors bors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Aug 26, 2024
matthiaskrgr added a commit to matthiaskrgr/rust that referenced this pull request Aug 26, 2024
…er-errors

Document & implement the transmutation modeled by `BikeshedIntrinsicFrom`

Documents that `BikeshedIntrinsicFrom` models transmute-via-union, which is slightly more expressive than the transmute-via-cast implemented by `transmute_copy`. Additionally, we provide an implementation of transmute-via-union as a method on the `BikeshedIntrinsicFrom` trait with additional documentation on the boundary between trait invariants and caller obligations.

Whether or not transmute-via-union is the right kind of transmute to model remains up for discussion [1]. Regardless, it seems wise to document the present behavior.

[1] https://rust-lang.zulipchat.com/#narrow/stream/216762-project-safe-transmute/topic/What.20'kind'.20of.20transmute.20to.20model.3F/near/426331967

Tracking Issue: rust-lang#99571

r? `@compiler-errors`

cc `@scottmcm,` `@Lokathor`
bors added a commit to rust-lang-ci/rust that referenced this pull request Aug 26, 2024
…iaskrgr

Rollup of 9 pull requests

Successful merges:

 - rust-lang#126013 (Add `#[warn(unreachable_pub)]` to a bunch of compiler crates)
 - rust-lang#128157 (deduplicate and clarify rules for converting pointers to references)
 - rust-lang#129032 (Document & implement the transmutation modeled by `BikeshedIntrinsicFrom`)
 - rust-lang#129250 (Do not ICE on non-ADT rcvr type when looking for crate version collision)
 - rust-lang#129340 (Remove Duplicate E0381 Label)
 - rust-lang#129560 ([rustdoc] Generate source link on impl associated types)
 - rust-lang#129622 (Remove a couple of unused feature enables)
 - rust-lang#129625 (Rename `ParenthesizedGenericArgs` to `GenericArgsMode`)
 - rust-lang#129626 (Remove `ParamMode::ExplicitNamed`)

Failed merges:

 - rust-lang#128166 (Improved `checked_isqrt` and `isqrt` methods)

r? `@ghost`
`@rustbot` modify labels: rollup
@bors bors merged commit 29923b6 into rust-lang:master Aug 27, 2024
6 checks passed
@rustbot rustbot added this to the 1.82.0 milestone Aug 27, 2024
rust-timer added a commit to rust-lang-ci/rust that referenced this pull request Aug 27, 2024
Rollup merge of rust-lang#129032 - jswrenn:transmute-method, r=compiler-errors

Document & implement the transmutation modeled by `BikeshedIntrinsicFrom`

Documents that `BikeshedIntrinsicFrom` models transmute-via-union, which is slightly more expressive than the transmute-via-cast implemented by `transmute_copy`. Additionally, we provide an implementation of transmute-via-union as a method on the `BikeshedIntrinsicFrom` trait with additional documentation on the boundary between trait invariants and caller obligations.

Whether or not transmute-via-union is the right kind of transmute to model remains up for discussion [1]. Regardless, it seems wise to document the present behavior.

[1] https://rust-lang.zulipchat.com/#narrow/stream/216762-project-safe-transmute/topic/What.20'kind'.20of.20transmute.20to.20model.3F/near/426331967

Tracking Issue: rust-lang#99571

r? `@compiler-errors`

cc `@scottmcm,` `@Lokathor`
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. T-libs Relevant to the library team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

8 participants