1 //===----------------------------------------------------------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 #ifndef TEST_SUPPORT_UNIQUE_PTR_TEST_HELPER_H
10 #define TEST_SUPPORT_UNIQUE_PTR_TEST_HELPER_H
13 #include <type_traits>
15 #include "test_macros.h"
16 #include "deleter_types.h"
21 A(const A
&) { ++count
; }
22 virtual ~A() { --count
; }
30 B(const B
& other
) : A(other
) { ++count
; }
31 virtual ~B() { --count
; }
37 typename
std::enable_if
<!std::is_array
<T
>::value
, T
*>::type
38 newValue(int num_elements
) {
39 assert(num_elements
== 1);
44 typename
std::enable_if
<std::is_array
<T
>::value
,
45 typename
std::remove_all_extents
<T
>::type
*>::type
46 newValue(int num_elements
) {
47 typedef typename
std::remove_all_extents
<T
>::type VT
;
48 assert(num_elements
>= 1);
49 return new VT
[num_elements
];
52 struct IncompleteType
;
54 void checkNumIncompleteTypeAlive(int i
);
55 int getNumIncompleteTypeAlive();
56 IncompleteType
* getNewIncomplete();
57 IncompleteType
* getNewIncompleteArray(int size
);
59 #if TEST_STD_VER >= 11
60 template <class ThisT
, class ...Args
>
61 struct args_is_this_type
: std::false_type
{};
63 template <class ThisT
, class A1
>
64 struct args_is_this_type
<ThisT
, A1
> : std::is_same
<ThisT
, typename
std::decay
<A1
>::type
> {};
67 template <class IncompleteT
= IncompleteType
,
68 class Del
= std::default_delete
<IncompleteT
> >
69 struct StoresIncomplete
{
70 static_assert((std::is_same
<IncompleteT
, IncompleteType
>::value
||
71 std::is_same
<IncompleteT
, IncompleteType
[]>::value
), "");
73 std::unique_ptr
<IncompleteT
, Del
> m_ptr
;
75 #if TEST_STD_VER >= 11
76 StoresIncomplete(StoresIncomplete
const&) = delete;
77 StoresIncomplete(StoresIncomplete
&&) = default;
79 template <class ...Args
>
80 StoresIncomplete(Args
&&... args
) : m_ptr(std::forward
<Args
>(args
)...) {
81 static_assert(!args_is_this_type
<StoresIncomplete
, Args
...>::value
, "");
86 StoresIncomplete(StoresIncomplete
const&);
92 IncompleteType
* get() const { return m_ptr
.get(); }
93 Del
& get_deleter() { return m_ptr
.get_deleter(); }
96 #if TEST_STD_VER >= 11
97 template <class IncompleteT
= IncompleteType
,
98 class Del
= std::default_delete
<IncompleteT
>, class... Args
>
99 void doIncompleteTypeTest(int expect_alive
, Args
&&... ctor_args
) {
100 checkNumIncompleteTypeAlive(expect_alive
);
102 StoresIncomplete
<IncompleteT
, Del
> sptr(std::forward
<Args
>(ctor_args
)...);
103 checkNumIncompleteTypeAlive(expect_alive
);
104 if (expect_alive
== 0)
105 assert(sptr
.get() == nullptr);
107 assert(sptr
.get() != nullptr);
109 checkNumIncompleteTypeAlive(0);
113 #define INCOMPLETE_TEST_EPILOGUE() \
114 int is_incomplete_test_anchor = is_incomplete_test(); \
116 struct IncompleteType { \
118 IncompleteType() { ++count; } \
119 ~IncompleteType() { --count; } \
122 int IncompleteType::count = 0; \
124 void checkNumIncompleteTypeAlive(int i) { \
125 assert(IncompleteType::count == i); \
127 int getNumIncompleteTypeAlive() { return IncompleteType::count; } \
128 IncompleteType* getNewIncomplete() { return new IncompleteType; } \
129 IncompleteType* getNewIncompleteArray(int size) { \
130 return new IncompleteType[size]; \
133 template <class IncompleteT, class Del> \
134 StoresIncomplete<IncompleteT, Del>::~StoresIncomplete() {}
137 #if defined(__GNUC__)
138 #pragma GCC diagnostic push
139 #pragma GCC diagnostic ignored "-Wvariadic-macros"
142 #if TEST_STD_VER >= 11
143 #define DEFINE_AND_RUN_IS_INCOMPLETE_TEST(...) \
144 static int is_incomplete_test() { __VA_ARGS__ return 0; } \
145 INCOMPLETE_TEST_EPILOGUE()
147 #define DEFINE_AND_RUN_IS_INCOMPLETE_TEST(...) \
148 static int is_incomplete_test() { return 0; } \
149 INCOMPLETE_TEST_EPILOGUE()
152 #if defined(__GNUC__)
153 #pragma GCC diagnostic pop
156 #endif // TEST_SUPPORT_UNIQUE_PTR_TEST_HELPER_H