[PATCH 3/6] libstdc++: port bitwise relocatable away from is_trivial
Giuseppe D'Angelo
giuseppe.dangelo@kdab.com
Tue Dec 10 10:48:16 GMT 2024
Hi,
On 10/12/2024 10:56, Jonathan Wakely wrote:
> We need this to depend on is_trivially_copyable too, so we can use memcpy.
>
> I'm testing a fix now to fix bootstrap.
There's a broader question I think, which is how much we want to "bend"
the language rules.
[basic] isn't really super-explicit at giving us the rights to bit-blast
bytes into uninitialized storage, and pretend there are objects there.
There are a couple of provisions that deal with trivially copyable types:
https://eel.is/c++draft/basic.types.general#2
https://eel.is/c++draft/basic.types.general#3
which guarantee that one can memcpy the representation of an live object
onto another live object, possibly itself. However, they don't
necessarily talk about creating/starting the lifetime of new objects
elsewhere.
That could be achieved through implicit-lifetime, but trivially copyable
doesn't imply implicit-lifetime, AFAICS; consider the corner case of a
type with deleted constructors but only trivial assignments and
destruction, which is TC but not IL. This is why I think the facilities
in P2590R2 talk about "trivially-copyable implicit-lifetime" types.
Maybe however the relocate functions are only called on types that we
know are move constructible (e.g. from std::vector) so if they're TC we
also know they're IL?
(The only thing missing is possibly a call to an abstract machine "magic
function", such as start_lifetime_as?)
Explicitly checking for a trivial move constructor + trivial destructor
(that is, the code after my patch) implies that the type is IL, but that
doesn't really gives us the rights to assume that the object in the new
storage have the same values than the old ones, as that's only
guaranteed for TC types.
In short it looks like a bit of a lose-lose situation. I hope P3279 will
bring clarity in the area.
Then, if the problem is just suppressing the warning, this does it:
> diff --git a/libstdc++-v3/include/bits/stl_uninitialized.h b/libstdc++-v3/include/bits/stl_uninitialized.h
> index 916288352d7..374f30ee645 100644
> --- a/libstdc++-v3/include/bits/stl_uninitialized.h
> +++ b/libstdc++-v3/include/bits/stl_uninitialized.h
> @@ -1294,7 +1294,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
> return __out.base();
> }
> #endif
> - __builtin_memcpy(__result, __first, __count * sizeof(_Tp));
> + // Cast to void* in order to suppress -Wclass-memaccess.
> + __builtin_memcpy(static_cast<void *>(__result), static_cast<const void *>(__first), __count * sizeof(_Tp));
> }
> return __result + __count;
> }
It's the trick we use in Qt; or similarly just suppressing the warning
via #pragmas, however I'm not sure if Clang likes that.
What do you think?
Thank you,
--
Giuseppe D'Angelo
-------------- next part --------------
A non-text attachment was scrubbed...
Name: smime.p7s
Type: application/pkcs7-signature
Size: 4244 bytes
Desc: S/MIME Cryptographic Signature
URL: <https://gcc.gnu.org/pipermail/libstdc++/attachments/20241210/73b12d02/attachment.p7s>
More information about the Libstdc++
mailing list