diff options
Diffstat (limited to 'test/core/gprpp/inlined_vector_test.cc')
-rw-r--r-- | test/core/gprpp/inlined_vector_test.cc | 192 |
1 files changed, 174 insertions, 18 deletions
diff --git a/test/core/gprpp/inlined_vector_test.cc b/test/core/gprpp/inlined_vector_test.cc index 41f4338f8a..e9d1eb2c76 100644 --- a/test/core/gprpp/inlined_vector_test.cc +++ b/test/core/gprpp/inlined_vector_test.cc @@ -17,20 +17,32 @@ */ #include "src/core/lib/gprpp/inlined_vector.h" +#include <grpc/support/log.h> #include <gtest/gtest.h> #include "src/core/lib/gprpp/memory.h" #include "test/core/util/test_config.h" namespace grpc_core { namespace testing { +namespace { + +template <typename Vector> +static void FillVector(Vector* v, int len, int start = 0) { + for (int i = 0; i < len; i++) { + v->push_back(i + start); + EXPECT_EQ(i + 1UL, v->size()); + } + EXPECT_EQ(static_cast<size_t>(len), v->size()); + EXPECT_LE(static_cast<size_t>(len), v->capacity()); +} + +} // namespace TEST(InlinedVectorTest, CreateAndIterate) { const int kNumElements = 9; InlinedVector<int, 2> v; EXPECT_TRUE(v.empty()); - for (int i = 0; i < kNumElements; ++i) { - v.push_back(i); - } + FillVector(&v, kNumElements); EXPECT_EQ(static_cast<size_t>(kNumElements), v.size()); EXPECT_FALSE(v.empty()); for (int i = 0; i < kNumElements; ++i) { @@ -42,9 +54,7 @@ TEST(InlinedVectorTest, CreateAndIterate) { TEST(InlinedVectorTest, ValuesAreInlined) { const int kNumElements = 5; InlinedVector<int, 10> v; - for (int i = 0; i < kNumElements; ++i) { - v.push_back(i); - } + FillVector(&v, kNumElements); EXPECT_EQ(static_cast<size_t>(kNumElements), v.size()); for (int i = 0; i < kNumElements; ++i) { EXPECT_EQ(i, v[i]); @@ -71,19 +81,13 @@ TEST(InlinedVectorTest, ClearAndRepopulate) { const int kNumElements = 10; InlinedVector<int, 5> v; EXPECT_EQ(0UL, v.size()); - for (int i = 0; i < kNumElements; ++i) { - v.push_back(i); - EXPECT_EQ(i + 1UL, v.size()); - } + FillVector(&v, kNumElements); for (int i = 0; i < kNumElements; ++i) { EXPECT_EQ(i, v[i]); } v.clear(); EXPECT_EQ(0UL, v.size()); - for (int i = 0; i < kNumElements; ++i) { - v.push_back(kNumElements + i); - EXPECT_EQ(i + 1UL, v.size()); - } + FillVector(&v, kNumElements, kNumElements); for (int i = 0; i < kNumElements; ++i) { EXPECT_EQ(kNumElements + i, v[i]); } @@ -93,10 +97,7 @@ TEST(InlinedVectorTest, ConstIndexOperator) { constexpr int kNumElements = 10; InlinedVector<int, 5> v; EXPECT_EQ(0UL, v.size()); - for (int i = 0; i < kNumElements; ++i) { - v.push_back(i); - EXPECT_EQ(i + 1UL, v.size()); - } + FillVector(&v, kNumElements); // The following lambda function is exceptionally allowed to use an anonymous // capture due to the erroneous behavior of the MSVC compiler, that refuses to // capture the kNumElements constexpr, something allowed by the standard. @@ -108,6 +109,161 @@ TEST(InlinedVectorTest, ConstIndexOperator) { const_func(v); } +// the following constants and typedefs are used for copy/move +// construction/assignment +const size_t kInlinedLength = 8; +typedef InlinedVector<int, kInlinedLength> IntVec8; +const size_t kInlinedFillSize = kInlinedLength - 1; +const size_t kAllocatedFillSize = kInlinedLength + 1; + +TEST(InlinedVectorTest, CopyConstructerInlined) { + IntVec8 original; + FillVector(&original, kInlinedFillSize); + IntVec8 copy_constructed(original); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], copy_constructed[i]); + } +} + +TEST(InlinedVectorTest, CopyConstructerAllocated) { + IntVec8 original; + FillVector(&original, kAllocatedFillSize); + IntVec8 copy_constructed(original); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], copy_constructed[i]); + } +} + +TEST(InlinedVectorTest, CopyAssignementInlinedInlined) { + IntVec8 original; + FillVector(&original, kInlinedFillSize); + IntVec8 copy_assigned; + FillVector(©_assigned, kInlinedFillSize, 99); + copy_assigned = original; + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], copy_assigned[i]); + } +} + +TEST(InlinedVectorTest, CopyAssignementInlinedAllocated) { + IntVec8 original; + FillVector(&original, kInlinedFillSize); + IntVec8 copy_assigned; + FillVector(©_assigned, kAllocatedFillSize, 99); + copy_assigned = original; + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], copy_assigned[i]); + } +} + +TEST(InlinedVectorTest, CopyAssignementAllocatedInlined) { + IntVec8 original; + FillVector(&original, kAllocatedFillSize); + IntVec8 copy_assigned; + FillVector(©_assigned, kInlinedFillSize, 99); + copy_assigned = original; + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], copy_assigned[i]); + } +} + +TEST(InlinedVectorTest, CopyAssignementAllocatedAllocated) { + IntVec8 original; + FillVector(&original, kAllocatedFillSize); + IntVec8 copy_assigned; + FillVector(©_assigned, kAllocatedFillSize, 99); + copy_assigned = original; + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], copy_assigned[i]); + } +} + +TEST(InlinedVectorTest, MoveConstructorInlined) { + IntVec8 original; + FillVector(&original, kInlinedFillSize); + IntVec8 tmp(original); + auto* old_data = tmp.data(); + IntVec8 move_constructed(std::move(tmp)); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], move_constructed[i]); + } + // original data was inlined so it should have been copied, not moved. + EXPECT_NE(move_constructed.data(), old_data); +} + +TEST(InlinedVectorTest, MoveConstructorAllocated) { + IntVec8 original; + FillVector(&original, kAllocatedFillSize); + IntVec8 tmp(original); + auto* old_data = tmp.data(); + IntVec8 move_constructed(std::move(tmp)); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], move_constructed[i]); + } + // original data was allocated, so it should been moved, not copied + EXPECT_EQ(move_constructed.data(), old_data); +} + +TEST(InlinedVectorTest, MoveAssignmentInlinedInlined) { + IntVec8 original; + FillVector(&original, kInlinedFillSize); + IntVec8 move_assigned; + FillVector(&move_assigned, kInlinedFillSize, 99); // Add dummy elements + IntVec8 tmp(original); + auto* old_data = tmp.data(); + move_assigned = std::move(tmp); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], move_assigned[i]); + } + // original data was inlined so it should have been copied, not moved. + EXPECT_NE(move_assigned.data(), old_data); +} + +TEST(InlinedVectorTest, MoveAssignmentInlinedAllocated) { + IntVec8 original; + FillVector(&original, kInlinedFillSize); + IntVec8 move_assigned; + FillVector(&move_assigned, kAllocatedFillSize, 99); // Add dummy elements + IntVec8 tmp(original); + auto* old_data = tmp.data(); + move_assigned = std::move(tmp); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], move_assigned[i]); + } + // original data was inlined so it should have been copied, not moved. + EXPECT_NE(move_assigned.data(), old_data); +} + +TEST(InlinedVectorTest, MoveAssignmentAllocatedInlined) { + IntVec8 original; + FillVector(&original, kAllocatedFillSize); + IntVec8 move_assigned; + FillVector(&move_assigned, kInlinedFillSize, 99); // Add dummy elements + IntVec8 tmp(original); + auto* old_data = tmp.data(); + move_assigned = std::move(tmp); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], move_assigned[i]); + } + // original data was allocated so it should have been moved, not copied. + EXPECT_EQ(move_assigned.data(), old_data); +} + +TEST(InlinedVectorTest, MoveAssignmentAllocatedAllocated) { + IntVec8 original; + FillVector(&original, kAllocatedFillSize); + IntVec8 move_assigned; + FillVector(&move_assigned, kAllocatedFillSize, 99); // Add dummy elements + IntVec8 tmp(original); + auto* old_data = tmp.data(); + move_assigned = std::move(tmp); + for (size_t i = 0; i < original.size(); ++i) { + EXPECT_EQ(original[i], move_assigned[i]); + } + // original data was allocated so it should have been moved, not copied. + EXPECT_EQ(move_assigned.data(), old_data); +} + } // namespace testing } // namespace grpc_core |