struct_reflection_test.cpp 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119
  1. // Part of the Carbon Language project, under the Apache License v2.0 with LLVM
  2. // Exceptions. See /LICENSE for license information.
  3. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  4. #include "common/struct_reflection.h"
  5. #include <gtest/gtest.h>
  6. namespace Carbon::StructReflection {
  7. namespace {
  8. struct ZeroFields {};
  9. struct OneField {
  10. int x;
  11. };
  12. struct TwoFields {
  13. int x;
  14. int y;
  15. };
  16. struct SixFields {
  17. int one;
  18. int two;
  19. int three;
  20. int four;
  21. int five;
  22. int six;
  23. };
  24. struct ReferenceField {
  25. int& ref;
  26. };
  27. struct NoDefaultConstructor {
  28. explicit NoDefaultConstructor(int n) : v(n) {}
  29. int v;
  30. };
  31. struct OneFieldNoDefaultConstructor {
  32. NoDefaultConstructor x;
  33. };
  34. struct TwoFieldsNoDefaultConstructor {
  35. NoDefaultConstructor x;
  36. NoDefaultConstructor y;
  37. };
  38. TEST(StructReflectionTest, CanListInitialize) {
  39. {
  40. using Type = OneField;
  41. using Field = Internal::AnyField<Type>;
  42. static_assert(Internal::CanListInitialize<Type>(nullptr));
  43. static_assert(Internal::CanListInitialize<Type, Field>(nullptr));
  44. static_assert(!Internal::CanListInitialize<Type, Field, Field>(0));
  45. }
  46. {
  47. using Type = OneFieldNoDefaultConstructor;
  48. using Field = Internal::AnyField<Type>;
  49. static_assert(!Internal::CanListInitialize<Type>(0));
  50. static_assert(Internal::CanListInitialize<Type, Field>(nullptr));
  51. static_assert(!Internal::CanListInitialize<Type, Field, Field>(0));
  52. }
  53. }
  54. TEST(StructReflectionTest, CountFields) {
  55. static_assert(Internal::CountFields<ZeroFields>() == 0);
  56. static_assert(Internal::CountFields<OneField>() == 1);
  57. static_assert(Internal::CountFields<TwoFields>() == 2);
  58. static_assert(Internal::CountFields<SixFields>() == 6);
  59. static_assert(Internal::CountFields<ReferenceField>() == 1);
  60. static_assert(Internal::CountFields<OneFieldNoDefaultConstructor>() == 1);
  61. }
  62. TEST(StructReflectionTest, EmptyStruct) {
  63. std::tuple<> fields = AsTuple(ZeroFields());
  64. static_cast<void>(fields);
  65. }
  66. TEST(StructReflectionTest, OneField) {
  67. std::tuple<int> fields = AsTuple(OneField{.x = 1});
  68. EXPECT_EQ(std::get<0>(fields), 1);
  69. }
  70. TEST(StructReflectionTest, TwoFields) {
  71. std::tuple<int, int> fields = AsTuple(TwoFields{.x = 1, .y = 2});
  72. EXPECT_EQ(std::get<0>(fields), 1);
  73. EXPECT_EQ(std::get<1>(fields), 2);
  74. }
  75. TEST(StructReflectionTest, SixFields) {
  76. std::tuple<int, int, int, int, int, int> fields = AsTuple(SixFields{
  77. .one = 1, .two = 2, .three = 3, .four = 4, .five = 5, .six = 6});
  78. EXPECT_EQ(std::get<0>(fields), 1);
  79. EXPECT_EQ(std::get<1>(fields), 2);
  80. EXPECT_EQ(std::get<2>(fields), 3);
  81. EXPECT_EQ(std::get<3>(fields), 4);
  82. EXPECT_EQ(std::get<4>(fields), 5);
  83. EXPECT_EQ(std::get<5>(fields), 6);
  84. }
  85. TEST(StructReflectionTest, NoDefaultConstructor) {
  86. std::tuple<NoDefaultConstructor, NoDefaultConstructor> fields =
  87. AsTuple(TwoFieldsNoDefaultConstructor{.x = NoDefaultConstructor(1),
  88. .y = NoDefaultConstructor(2)});
  89. EXPECT_EQ(std::get<0>(fields).v, 1);
  90. EXPECT_EQ(std::get<1>(fields).v, 2);
  91. }
  92. TEST(StructReflectionTest, ReferenceField) {
  93. int n = 0;
  94. std::tuple<int&> fields = AsTuple(ReferenceField{.ref = n});
  95. EXPECT_EQ(&std::get<0>(fields), &n);
  96. }
  97. } // namespace
  98. } // namespace Carbon::StructReflection