Looking at the answer to this question:
std::is_trivially_copyable - Why are volatile scalar types not trivially copyable?
I see that the standard says a type is not trivially copyable if it has a volatile member, even when that member is a basic type. This appears to be due to a need to ensure that volatile members are updated atomically, and the byte-by-byte copy implied by trivial copyability can be violated.
But doesn't this also imply that is_trivially_default_constructible should fail on these types?
It seems that this is the correct check to see if a class can "correctly" be zero initialized (memset-able) in the same way is_trivially_copyable is used to detect memcpy-ability. And the memset may be non-atomic for the same basic reason.
However maybe this assumption is wrong. Is it incorrect to assume that a trivially constructible class is memset-initializable? If it is incorrect, what is the correct check to determine this?
To be a little clearer, I'm not assuming that is_trivially_default_constructible actually tells me anything about the semantic correctness of memset constructibility, zero initializability, or any of that. I just mean that it can tell me if that is possible in the same way as memcpy-ability. Maybe is_trivially_copyable is sufficient for all cases, since construction as a buffer is logically equivalent to copying some (possibly static or algorithmically definable) buffer into the object after construction?