1 //===----------------------------------------------------------------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is dual licensed under the MIT and the University of Illinois Open 6 // Source Licenses. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #ifndef TEST_SUPPORT_UNIQUE_PTR_TEST_HELPER_H 11 #define TEST_SUPPORT_UNIQUE_PTR_TEST_HELPER_H 12 13 #include <memory> 14 #include <type_traits> 15 16 #include "test_macros.h" 17 #include "deleter_types.h" 18 19 struct A { 20 static int count; 21 A() { ++count; } 22 A(const A&) { ++count; } 23 virtual ~A() { --count; } 24 }; 25 26 int A::count = 0; 27 28 struct B : public A { 29 static int count; 30 B() { ++count; } 31 B(const B&) { ++count; } 32 virtual ~B() { --count; } 33 }; 34 35 int B::count = 0; 36 37 template <class T> 38 typename std::enable_if<!std::is_array<T>::value, T*>::type 39 newValue(int num_elements) { 40 assert(num_elements == 1); 41 return new T; 42 } 43 44 template <class T> 45 typename std::enable_if<std::is_array<T>::value, 46 typename std::remove_all_extents<T>::type*>::type 47 newValue(int num_elements) { 48 typedef typename std::remove_all_extents<T>::type VT; 49 assert(num_elements >= 1); 50 return new VT[num_elements]; 51 } 52 53 struct IncompleteType; 54 55 void checkNumIncompleteTypeAlive(int i); 56 int getNumIncompleteTypeAlive(); 57 IncompleteType* getNewIncomplete(); 58 IncompleteType* getNewIncompleteArray(int size); 59 60 #if TEST_STD_VER >= 11 61 template <class ThisT, class ...Args> 62 struct args_is_this_type : std::false_type {}; 63 64 template <class ThisT, class A1> 65 struct args_is_this_type<ThisT, A1> : std::is_same<ThisT, typename std::decay<A1>::type> {}; 66 #endif 67 68 template <class IncompleteT = IncompleteType, 69 class Del = std::default_delete<IncompleteT> > 70 struct StoresIncomplete { 71 static_assert((std::is_same<IncompleteT, IncompleteType>::value || 72 std::is_same<IncompleteT, IncompleteType[]>::value), ""); 73 74 std::unique_ptr<IncompleteT, Del> m_ptr; 75 76 #if TEST_STD_VER >= 11 77 StoresIncomplete(StoresIncomplete const&) = delete; 78 StoresIncomplete(StoresIncomplete&&) = default; 79 80 template <class ...Args> 81 StoresIncomplete(Args&&... args) : m_ptr(std::forward<Args>(args)...) { 82 static_assert(!args_is_this_type<StoresIncomplete, Args...>::value, ""); 83 } 84 #else 85 private: 86 StoresIncomplete(); 87 StoresIncomplete(StoresIncomplete const&); 88 public: 89 #endif 90 91 ~StoresIncomplete(); 92 93 IncompleteType* get() const { return m_ptr.get(); } 94 Del& get_deleter() { return m_ptr.get_deleter(); } 95 }; 96 97 #if TEST_STD_VER >= 11 98 template <class IncompleteT = IncompleteType, 99 class Del = std::default_delete<IncompleteT>, class... Args> 100 void doIncompleteTypeTest(int expect_alive, Args&&... ctor_args) { 101 using ValueT = typename std::remove_all_extents<IncompleteT>::type; 102 checkNumIncompleteTypeAlive(expect_alive); 103 { 104 StoresIncomplete<IncompleteT, Del> sptr(std::forward<Args>(ctor_args)...); 105 checkNumIncompleteTypeAlive(expect_alive); 106 if (expect_alive == 0) 107 assert(sptr.get() == nullptr); 108 else 109 assert(sptr.get() != nullptr); 110 } 111 checkNumIncompleteTypeAlive(0); 112 } 113 #endif 114 115 #define INCOMPLETE_TEST_EPILOGUE() \ 116 int is_incomplete_test_anchor = is_incomplete_test(); \ 117 \ 118 struct IncompleteType { \ 119 static int count; \ 120 IncompleteType() { ++count; } \ 121 ~IncompleteType() { --count; } \ 122 }; \ 123 \ 124 int IncompleteType::count = 0; \ 125 \ 126 void checkNumIncompleteTypeAlive(int i) { \ 127 assert(IncompleteType::count == i); \ 128 } \ 129 int getNumIncompleteTypeAlive() { return IncompleteType::count; } \ 130 IncompleteType* getNewIncomplete() { return new IncompleteType; } \ 131 IncompleteType* getNewIncompleteArray(int size) { \ 132 return new IncompleteType[size]; \ 133 } \ 134 \ 135 template <class IncompleteT, class Del> \ 136 StoresIncomplete<IncompleteT, Del>::~StoresIncomplete() {} 137 # 138 139 #if defined(__GNUC__) 140 #pragma GCC diagnostic push 141 #pragma GCC diagnostic ignored "-Wvariadic-macros" 142 #endif 143 144 #if TEST_STD_VER >= 11 145 #define DEFINE_AND_RUN_IS_INCOMPLETE_TEST(...) \ 146 static int is_incomplete_test() { __VA_ARGS__ return 0; } \ 147 INCOMPLETE_TEST_EPILOGUE() 148 #else 149 #define DEFINE_AND_RUN_IS_INCOMPLETE_TEST(...) \ 150 static int is_incomplete_test() { return 0; } \ 151 INCOMPLETE_TEST_EPILOGUE() 152 #endif 153 154 #if defined(__GNUC__) 155 #pragma GCC diagnostic pop 156 #endif 157 158 #endif // TEST_SUPPORT_UNIQUE_PTR_TEST_HELPER_H 159