[PATCH] PR libstdc++/87431 re-adjust never-valueless optimizations
Jonathan Wakely
jwakely@redhat.com
Fri Apr 5 16:59:00 GMT 2019
On 03/04/19 17:25 +0100, Jonathan Wakely wrote:
>Avoid creating arbitrarily large objects on the stack when creating
>temporaries in order to provide the strong exception-safety guarantee.
>
>Also implement Antony Polukhin's suggestion to whitelist specific types
>that can be efficiently move-assigned, so that emplacing those types
>never causes a variant to become valueless. The whitelisted types are:
>all trivially copyable types no greater than 256 bytes in size,
>std::shared_ptr, std::weak_ptr, std::unique_ptr, std::function, and
>std::any. Additionally, std::basic_string, std::vector, and
>__gnu_debug::vector are whitelisted if their allocator traits give them
>a non-throwing move assignment operator. Specifically, this means
>std::string is whitelisted, but std::pmr::string is not.
>
> PR libstdc++/87431 (again)
> * include/bits/basic_string.h (__variant::_Never_valueless_alt):
> Define partial specialization for basic_string.
> * include/bits/shared_ptr.h (_Never_valueless_alt): Likewise for
> shared_ptr and weak_ptr.
> * include/bits/std_function.h (_Never_valueless_alt): Likewise for
> function.
> * include/bits/stl_vector.h (_Never_valueless_alt): Likewise for
> vector.
> * include/bits/unique_ptr.h (_Never_valueless_alt): Likewise for
> unique_ptr.
> * include/debug/vector (_Never_valueless_alt): Likewise for debug
> vector.
> * include/std/any (_Never_valueless_alt): Define explicit
> specialization for any.
> * include/std/variant (_Never_valueless_alt): Define primary template.
> (__never_valueless): Use _Never_valueless_alt instead of
> is_trivially_copyable.
> (variant::emplace<N>(Args&&...)): Add special case for non-throwing
> initializations to avoid try-catch overhead. Add special case for
> scalars produced by potentially-throwing conversions. Use
> _Never_valueless_alt instead of is_trivially_copyable for the
> remaining strong exception-safety cases.
> (variant::emplace<N>(initializer_list<U>, Args&&...)): Likewise.
> * testsuite/20_util/variant/87431.cc: Run both test functions.
> * testsuite/20_util/variant/exception_safety.cc: New test.
> * testsuite/20_util/variant/run.cc: Use pmr::string instead of string,
> so the variant becomes valueless.
>
>I'd like to commit this to trunk this week. Does anybody see any
>problems with this approach?
I've committed this patch.
We can still consider whitelisting other types until the GCC 9
release, but we should do it soon.
More information about the Libstdc++
mailing list