From 5b535401665cc6aa96d54a5c9b0901153d97210f Mon Sep 17 00:00:00 2001 From: Abseil Team Date: Wed, 18 Apr 2018 05:56:39 -0700 Subject: - ed0ba496fe01eb8edfa86beade8a37768e7c12ef Updates the API for Exception Safety testing to use build... by Abseil Team - c4b7a4e517c9404932c45f2f9f92eb7dc694e45d Internal change by Abseil Team - 76c78ed9385f65d881511645446e0bb8ababf6ec Add missing ABSL_PREDICT_FALSE to one of FixedArray::at()... by Abseil Team - 1204fb1c46f007dd9dfb7d9abf3e96c58835d193 Internal change. by Greg Falcon - f1f47c98a026bc5e425ae83ff4a2eb391bbd3d9b Add internal-only functionality to examine the stack, to ... by Derek Mauro - 30d63097cd268d912f917526f6511005580465c4 fix typo by Abseil Team - 942d7efa6cf54cd248ca57dcaf3c245188b52a76 Remove unnecessary semicolons from comment examples. by Abseil Team - 7db0669cf23a06d934d3ed8c76aee4e4e23b7e04 Remove malloc_hook and malloc_extension from our internal... by Greg Falcon - 0190f1063d101b1ded355019df2e1d325931f6c7 Make the maximum length of a string view equal difference... by Abseil Team - c8ae37cbce29449b02115a0ebd435ddc3d7ab062 Add namespace qualification. by Shaindel Schwartz - ff70afe2e6e3dd39f51ce9829e3e1f18231bf4d7 Fix internal/direct_mmap.h for non-linux builds. by Greg Falcon GitOrigin-RevId: ed0ba496fe01eb8edfa86beade8a37768e7c12ef Change-Id: I7595ee3480d1d6724fd3797c15ba9d9be0d17e62 --- absl/types/any_exception_safety_test.cc | 158 +++++++++++++------------------- 1 file changed, 63 insertions(+), 95 deletions(-) (limited to 'absl/types/any_exception_safety_test.cc') diff --git a/absl/types/any_exception_safety_test.cc b/absl/types/any_exception_safety_test.cc index f4ca52eb..82c176b5 100644 --- a/absl/types/any_exception_safety_test.cc +++ b/absl/types/any_exception_safety_test.cc @@ -21,15 +21,21 @@ #include "absl/base/internal/exception_safety_testing.h" using Thrower = absl::ThrowingValue<>; +using NoThrowMoveThrower = + absl::ThrowingValue; using ThrowerList = std::initializer_list; using ThrowerVec = std::vector; using ThrowingAlloc = absl::ThrowingAllocator; using ThrowingThrowerVec = std::vector; -namespace absl { +namespace { + +class AnyExceptionSafety : public ::testing::Test { + private: + absl::ConstructorTracker inspector_; +}; -testing::AssertionResult AbslCheckInvariants(absl::any* a, - InternalAbslNamespaceFinder) { +testing::AssertionResult AnyInvariants(absl::any* a) { using testing::AssertionFailure; using testing::AssertionSuccess; @@ -69,17 +75,10 @@ testing::AssertionResult AbslCheckInvariants(absl::any* a, return AssertionSuccess(); } -} // namespace absl - -namespace { - -class AnyExceptionSafety : public ::testing::Test { - private: - absl::ConstructorTracker inspector_; -}; - testing::AssertionResult AnyIsEmpty(absl::any* a) { - if (!a->has_value()) return testing::AssertionSuccess(); + if (!a->has_value()) { + return testing::AssertionSuccess(); + } return testing::AssertionFailure() << "a should be empty, but instead has value " << absl::any_cast(*a).Get(); @@ -100,101 +99,70 @@ TEST_F(AnyExceptionSafety, Ctors) { absl::in_place_type_t(), {val}, ThrowingAlloc()); } -struct OneFactory { - std::unique_ptr operator()() const { - return absl::make_unique(absl::in_place_type_t(), 1, - absl::no_throw_ctor); - } -}; - -struct EmptyFactory { - std::unique_ptr operator()() const { - return absl::make_unique(); - } -}; - TEST_F(AnyExceptionSafety, Assignment) { - auto thrower_comp = [](const absl::any& l, const absl::any& r) { - return absl::any_cast(l) == absl::any_cast(r); + auto original = + absl::any(absl::in_place_type_t(), 1, absl::no_throw_ctor); + auto any_is_strong = [original](absl::any* ap) { + return testing::AssertionResult(ap->has_value() && + absl::any_cast(original) == + absl::any_cast(*ap)); }; + auto any_strong_tester = absl::MakeExceptionSafetyTester() + .WithInitialValue(original) + .WithInvariants(AnyInvariants, any_is_strong); - OneFactory one_factory; - - absl::ThrowingValue - moveable_val(2); Thrower val(2); absl::any any_val(val); + NoThrowMoveThrower mv_val(2); - EXPECT_TRUE(absl::TestExceptionSafety( - one_factory, [&any_val](absl::any* ap) { *ap = any_val; }, - absl::StrongGuarantee(one_factory, thrower_comp))); - - EXPECT_TRUE(absl::TestExceptionSafety( - one_factory, [&val](absl::any* ap) { *ap = val; }, - absl::StrongGuarantee(one_factory, thrower_comp))); - - EXPECT_TRUE(absl::TestExceptionSafety( - one_factory, [&val](absl::any* ap) { *ap = std::move(val); }, - absl::StrongGuarantee(one_factory, thrower_comp))); + auto assign_any = [&any_val](absl::any* ap) { *ap = any_val; }; + auto assign_val = [&val](absl::any* ap) { *ap = val; }; + auto move = [&val](absl::any* ap) { *ap = std::move(val); }; + auto move_movable = [&mv_val](absl::any* ap) { *ap = std::move(mv_val); }; - EXPECT_TRUE(absl::TestExceptionSafety( - one_factory, - [&moveable_val](absl::any* ap) { *ap = std::move(moveable_val); }, - absl::StrongGuarantee(one_factory, thrower_comp))); + EXPECT_TRUE(any_strong_tester.Test(assign_any)); + EXPECT_TRUE(any_strong_tester.Test(assign_val)); + EXPECT_TRUE(any_strong_tester.Test(move)); + EXPECT_TRUE(any_strong_tester.Test(move_movable)); - EmptyFactory empty_factory; - auto empty_comp = [](const absl::any& l, const absl::any& r) { - return !(l.has_value() || r.has_value()); + auto empty_any_is_strong = [](absl::any* ap) { + return testing::AssertionResult{!ap->has_value()}; }; - - EXPECT_TRUE(absl::TestExceptionSafety( - empty_factory, [&any_val](absl::any* ap) { *ap = any_val; }, - absl::StrongGuarantee(empty_factory, empty_comp))); - - EXPECT_TRUE(absl::TestExceptionSafety( - empty_factory, [&val](absl::any* ap) { *ap = val; }, - absl::StrongGuarantee(empty_factory, empty_comp))); - - EXPECT_TRUE(absl::TestExceptionSafety( - empty_factory, [&val](absl::any* ap) { *ap = std::move(val); }, - absl::StrongGuarantee(empty_factory, empty_comp))); + auto strong_empty_any_tester = + absl::MakeExceptionSafetyTester() + .WithInitialValue(absl::any{}) + .WithInvariants(AnyInvariants, empty_any_is_strong); + + EXPECT_TRUE(strong_empty_any_tester.Test(assign_any)); + EXPECT_TRUE(strong_empty_any_tester.Test(assign_val)); + EXPECT_TRUE(strong_empty_any_tester.Test(move)); } // libstdc++ std::any fails this test #if !defined(ABSL_HAVE_STD_ANY) TEST_F(AnyExceptionSafety, Emplace) { - OneFactory one_factory; - - EXPECT_TRUE(absl::TestExceptionSafety( - one_factory, [](absl::any* ap) { ap->emplace(2); }, AnyIsEmpty)); - - EXPECT_TRUE(absl::TestExceptionSafety( - one_factory, - [](absl::any* ap) { - ap->emplace>(2); - }, - AnyIsEmpty)); - - EXPECT_TRUE(absl::TestExceptionSafety(one_factory, - [](absl::any* ap) { - std::initializer_list il{ - Thrower(2, absl::no_throw_ctor)}; - ap->emplace(il); - }, - AnyIsEmpty)); - - EmptyFactory empty_factory; - EXPECT_TRUE(absl::TestExceptionSafety( - empty_factory, [](absl::any* ap) { ap->emplace(2); }, - AnyIsEmpty)); - - EXPECT_TRUE(absl::TestExceptionSafety(empty_factory, - [](absl::any* ap) { - std::initializer_list il{ - Thrower(2, absl::no_throw_ctor)}; - ap->emplace(il); - }, - AnyIsEmpty)); + auto initial_val = + absl::any{absl::in_place_type_t(), 1, absl::no_throw_ctor}; + auto one_tester = absl::MakeExceptionSafetyTester() + .WithInitialValue(initial_val) + .WithInvariants(AnyInvariants, AnyIsEmpty); + + auto emp_thrower = [](absl::any* ap) { ap->emplace(2); }; + auto emp_throwervec = [](absl::any* ap) { + std::initializer_list il{Thrower(2, absl::no_throw_ctor)}; + ap->emplace(il); + }; + auto emp_movethrower = [](absl::any* ap) { + ap->emplace(2); + }; + + EXPECT_TRUE(one_tester.Test(emp_thrower)); + EXPECT_TRUE(one_tester.Test(emp_throwervec)); + EXPECT_TRUE(one_tester.Test(emp_movethrower)); + + auto empty_tester = one_tester.WithInitialValue(absl::any{}); + + EXPECT_TRUE(empty_tester.Test(emp_thrower)); + EXPECT_TRUE(empty_tester.Test(emp_throwervec)); } #endif // ABSL_HAVE_STD_ANY -- cgit v1.2.3