Join GitHub today
GitHub is home to over 40 million developers working together to host and review code, manage projects, and build software together.Sign up
remove confusing remarks about mixed volatile and non-volatile accesses #60972
These comments were originally added by @ecstatic-morse in 911d35f and then later edited by me. The intention, I think, was to make sure people do both their reads and writes with these methods if the affected memory really is used for communication with external devices.
However, people read this as saying that mixed volatile/non-volatile accesses are UB, which -- to my knowledge -- they are not. So better remove this.
I couldn't for the life of me describe how volatile and non-volatile accesses to the same memory location interact, but that's more of a consequence of the fact that the rules of volatile accesses in general are enormously under-specified in LLVM and the languages LLVM mostly takes cues from. There doesn't seem to be anything in LLVM docs explicitly saying that such mixed-volatile accesses are UB, though. Plus, intuitively it seems like such mixed accesses can be made sense of -- with the caveat that the non-volatile ones are just as subject to the optimizers' whims as any other non-volatile accesses.
I have sympathies for the position that in such cases (some behavior is not specified and there's not even much of a shared informal understanding of what it should be), it's almost as bad as UB to rely on. But we can't very well make volatile go away until it's all figured out, so we have to be more pragmatic and try to guide people to implement the operations they need in the way least likely to be broken.
Certainly there is some truth to this warning and it would be nice to keep it in some form (in particular I feel confident saying it must be adhered to for correct MMIO), but as you say it causes some confusion. That confusion is perhaps warranted (see above) but a blanket avoidance of volatile for the use case that kicked this off (memory zeroing) seems a net loss. Perhaps we can weaken this wording, throw in some weasel words about how avoiding non-volatile accesses for "common use cases" and perhaps name MMIO as a clear-cut example?
remove confusing remarks about mixed volatile and non-volatile accesses These comments were originally added by @ecstatic-morse in rust-lang@911d35f and then later edited by me. The intention, I think, was to make sure people do both their reads and writes with these methods if the affected memory really is used for communication with external devices. However, [people read this as saying that mixed volatile/non-volatile accesses are UB](rust-lang#58599 (comment)), which -- to my knowledge -- they are not. So better remove this. Cc @rkruppe @rust-lang/wg-unsafe-code-guidelines
Rollup of 11 pull requests Successful merges: - #60383 (Fix position source code files toggle) - #60453 (Fall back to `/dev/urandom` on `EPERM` for `getrandom`) - #60487 (Fix search sidebar width when no crate select is present) - #60511 (Fix intra-doc link resolution failure on re-exporting libstd) - #60823 (Fix incremental compilation of cdylib emitting spurious unused_attributes lint) - #60915 (stable hashing: Remove unused field and add documentation.) - #60942 (Misc changes to rustc_metadata) - #60952 (Document BinaryHeap time complexity) - #60959 (rustc: Improve type size assertions) - #60972 (remove confusing remarks about mixed volatile and non-volatile accesses) - #60983 (Set -funwind-tables and -fno-exceptions unconditionally for LLVM's libunwind) Failed merges: r? @ghost
TBH I think the shared confusion is mostly about how to express the guarantee, while the intuitive understanding of it seems to be fairly universally shared. At least so far I have not encountered a version of their semantics that is in conflict with the one in my head. ;)
Personally, I'd specify
Things get more subtle when it comes to tearing of large volatile accesses, but that's mostly a matter of underspecification: beyond some size, a
The problem is that MMIO has some additional problems due to
I think there are tricky details where there's potential for disagreement about the end result, for example:
But your point that writing a guide for MMIO specifically will open a huge can of worms that goes beyond just volatile accesses is a good one.
The documentation previously included a lengthy essay about potential caveats in what it can guarantee as mixed volatile/non-volatile writes were previously assumed to be undefined behavior due to language to that effect in the official documentation for `write_volatile`. That language has subsequently been removed after discussion about the safety implications: rust-lang/rust#60972 Though generally it's not a good idea to mix volatile and non-volatile writes when using volatile accesses to communicate with e.g. memory mapped external devices, for the particular usage pattern in this crate, i.e. writing a zero-value, it can be considered well-defined.