On Sun, Nov 10, 2024 at 6:04 PM Brian Bi via Std-Discussion
<std-discussion@lists.isocpp.org> wrote:
> Unless I've misunderstood, the C23 draft appears to say that as soon as you write to any member of a struct, all padding bits are reset to unspecified values.
>
> 6.2.6.1/6: When a value is stored in an object of structure or union type, including in a member object, the bytes of the object representation that correspond to any padding bytes take unspecified values [...]
>
> That seems to prevent the use of `memcmp` for comparing the values of struct objects in most cases.
>
> Or is the C standard only talking about writes of struct type? (Which, as you probably know, don't exist in C++: an assignment operator, possibly a trivial one, is always called.)
The question is, does "When a value is stored ... including in a
member object" mean, "When a value is stored in an object, or in any
object that is a member of that object", or "When a value is stored in
an object, which may just happen to be a member of some other object"?
I'd be inclined toward the latter (i.e., it only applies to padding
within writes of struct type), since otherwise 6.2.6.1/7 would be
totally redundant, and it would also cause silly things like data
races if you memcmp() one member while concurrently writing another
member a mile away. But a "compiler writers should be given as many
liberties as possible" enthusiast would be inclined toward the former.
N691, which introduced the clause, was primarily concerned with writes
of struct type. It was listed in N2013 as having an unclear meaning
(see Q60-Q72), but it looks like no one in WG14 discussed it much
further. (Too bad wording cleanups are much less shiny than new
features...) Gustedt interpreted it in N2159 as meaning "any object
that is a member", but the minutes are very vague in the N2187
minutes, and there don't seem to be any other WG14 interpretations
about it. In practice, the big compilers don't write into padding on
member writes since they're deathly afraid of data races on any level
of the IR.
If all implementations are happy to avoid disturbing padding bytes upon writes, then, paradoxically, we don't need to put specific words in the C++ standard that say that; they don't change simply because there is no wording that can make them change.
However, for trivial copy operations, I think we need to say something. The operation may or may not affect the padding bits of the destination.
Matthew House