CaseyCarter updated this revision to Diff 97834. CaseyCarter added a comment.
The constexpr variant tests were enabled separate commit (https://reviews.llvm.org/rL302158). This differential now contains only the fine-grained SMF triviality extension test. https://reviews.llvm.org/D32671 Files: test/std/utilities/variant/variant.variant/variant.assign/copy.pass.cpp test/std/utilities/variant/variant.variant/variant.assign/move.pass.cpp test/std/utilities/variant/variant.variant/variant.ctor/copy.pass.cpp test/std/utilities/variant/variant.variant/variant.ctor/move.pass.cpp
Index: test/std/utilities/variant/variant.variant/variant.ctor/move.pass.cpp =================================================================== --- test/std/utilities/variant/variant.variant/variant.ctor/move.pass.cpp +++ test/std/utilities/variant/variant.variant/variant.ctor/move.pass.cpp @@ -197,10 +197,30 @@ #endif } +template<class...Ts> +constexpr bool triviality_test = + std::is_trivially_move_constructible<std::variant<Ts...>>::value == + std::conjunction<std::is_trivially_move_constructible<Ts>...>::value; + +void test_triviality_extension() { +#if defined(_MSVC_STL_VER) + static_assert(triviality_test<int>, ""); + static_assert(triviality_test<MoveOnly>, ""); + static_assert(triviality_test<MoveOnlyNT>, ""); + static_assert(triviality_test<int, long>, ""); + static_assert(triviality_test<int, MoveOnly>, ""); + static_assert(triviality_test<int, MoveOnlyNT>, ""); + static_assert(triviality_test<int, ThrowsMove>, ""); + static_assert(triviality_test<int, NoCopy>, ""); + static_assert(triviality_test<int, MakeEmptyT>, ""); +#endif +} + int main() { test_move_ctor_basic(); test_move_ctor_valueless_by_exception(); test_move_noexcept(); test_move_ctor_sfinae(); test_constexpr_move_ctor_extension(); + test_triviality_extension(); } Index: test/std/utilities/variant/variant.variant/variant.ctor/copy.pass.cpp =================================================================== --- test/std/utilities/variant/variant.variant/variant.ctor/copy.pass.cpp +++ test/std/utilities/variant/variant.variant/variant.ctor/copy.pass.cpp @@ -159,9 +159,27 @@ #endif } +template<class...Ts> +constexpr bool triviality_test = + std::is_trivially_copy_constructible<std::variant<Ts...>>::value == + std::conjunction<std::is_trivially_copy_constructible<Ts>...>::value; + +void test_triviality_extension() { +#if defined(_MSVC_STL_VER) + static_assert(triviality_test<int>, ""); + static_assert(triviality_test<NonT>, ""); + static_assert(triviality_test<int, long>, ""); + static_assert(triviality_test<int, NoCopy>, ""); + static_assert(triviality_test<int, MoveOnly>, ""); + static_assert(triviality_test<int, MoveOnlyNT>, ""); + static_assert(triviality_test<int, MakeEmptyT>, ""); +#endif +} + int main() { test_copy_ctor_basic(); test_copy_ctor_valueless_by_exception(); test_copy_ctor_sfinae(); test_constexpr_copy_ctor_extension(); + test_triviality_extension(); } Index: test/std/utilities/variant/variant.variant/variant.assign/move.pass.cpp =================================================================== --- test/std/utilities/variant/variant.variant/variant.assign/move.pass.cpp +++ test/std/utilities/variant/variant.variant/variant.assign/move.pass.cpp @@ -308,12 +308,63 @@ #endif } +template<class...Ts> +constexpr bool triviality_test = + // move assignment of variant<Ts...> is trivial when + std::is_trivially_move_assignable<std::variant<Ts...>>::value == + std::conjunction< + // All Ts are trivially destructible and + std::is_trivially_destructible<Ts>..., + // either + std::disjunction< + // All Ts are trivially move (constructible and assignable) so that + // variant's move assignment operator is non-deleted and trivial, or + std::conjunction< + std::is_trivially_move_constructible<Ts>..., + std::is_trivially_move_assignable<Ts>...>, + // At least one of the Ts is not move (constructible or assignable) so + // that variant's move assignment operator is *implicitly* deleted but + // all of the Ts are trivially *copy* (constructible and assignable) so + // that move assignment actually invokes the trivial copy assignment + // operator. + std::conjunction< + std::disjunction< + std::negation<std::is_move_constructible<Ts>>..., + std::negation<std::is_move_assignable<Ts>>...>, + std::is_trivially_copy_constructible<Ts>..., + std::is_trivially_copy_assignable<Ts>...>>>::value; + +void test_triviality_extension() { +#if defined(_MSVC_STL_VER) + struct TrivialCopyNontrivialMove { + TrivialCopyNontrivialMove(TrivialCopyNontrivialMove const&) = default; + TrivialCopyNontrivialMove(TrivialCopyNontrivialMove&&) noexcept {} + TrivialCopyNontrivialMove& operator=(TrivialCopyNontrivialMove const&) = default; + TrivialCopyNontrivialMove& operator=(TrivialCopyNontrivialMove&&) noexcept { + return *this; + } + }; + + static_assert(triviality_test<int>, ""); + static_assert(triviality_test<std::string>, ""); + static_assert(triviality_test<int, long>, ""); + static_assert(triviality_test<int, std::string>, ""); + static_assert(triviality_test<int, NoCopy>, ""); + static_assert(triviality_test<int, CopyOnly>, ""); + static_assert(triviality_test<int, MoveOnly>, ""); + static_assert(triviality_test<int, MoveAssign>, ""); + static_assert(triviality_test<int, MoveAssignOnly>, ""); + static_assert(triviality_test<int, TrivialCopyNontrivialMove>, ""); +#endif +} + int main() { test_move_assignment_empty_empty(); test_move_assignment_non_empty_empty(); test_move_assignment_empty_non_empty(); test_move_assignment_same_index(); test_move_assignment_different_index(); test_move_assignment_sfinae(); test_move_assignment_noexcept(); + test_triviality_extension(); } Index: test/std/utilities/variant/variant.variant/variant.assign/copy.pass.cpp =================================================================== --- test/std/utilities/variant/variant.variant/variant.assign/copy.pass.cpp +++ test/std/utilities/variant/variant.variant/variant.assign/copy.pass.cpp @@ -385,6 +385,27 @@ #endif } +template<class...Ts> +constexpr bool triviality_test = + std::is_trivially_copy_assignable<std::variant<Ts...>>::value == + std::conjunction< + std::is_trivially_destructible<Ts>..., + std::is_trivially_copy_constructible<Ts>..., + std::is_trivially_copy_assignable<Ts>...>::value; + +void test_triviality_extension() { +#if defined(_MSVC_STL_VER) + static_assert(triviality_test<int>, ""); + static_assert(triviality_test<std::string>, ""); + static_assert(triviality_test<int, long>, ""); + static_assert(triviality_test<int, std::string>, ""); + static_assert(triviality_test<int, NoCopy>, ""); + static_assert(triviality_test<int, NothrowCopy>, ""); + static_assert(triviality_test<int, CopyOnly>, ""); + static_assert(triviality_test<int, MoveOnly>, ""); + static_assert(triviality_test<int, CopyAssign>, ""); +#endif +} int main() { test_copy_assignment_empty_empty(); @@ -394,4 +415,5 @@ test_copy_assignment_different_index(); test_copy_assignment_sfinae(); test_copy_assignment_not_noexcept(); + test_triviality_extension(); }
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits