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 // UNSUPPORTED: c++98, c++03, c++11, c++14
11
12 // <any>
13
14 // template <class ValueType>
15 // ValueType const* any_cast(any const *) noexcept;
16 //
17 // template <class ValueType>
18 // ValueType * any_cast(any *) noexcept;
19
20 #include <any>
21 #include <type_traits>
22 #include <cassert>
23
24 #include "any_helpers.h"
25
26 using std::any;
27 using std::any_cast;
28
29 // Test that the operators are properly noexcept.
test_cast_is_noexcept()30 void test_cast_is_noexcept() {
31 any a;
32 static_assert(noexcept(any_cast<int>(&a)), "");
33
34 any const& ca = a;
35 static_assert(noexcept(any_cast<int>(&ca)), "");
36 }
37
38 // Test that the return type of any_cast is correct.
test_cast_return_type()39 void test_cast_return_type() {
40 any a;
41 static_assert(std::is_same<decltype(any_cast<int>(&a)), int*>::value, "");
42 static_assert(std::is_same<decltype(any_cast<int const>(&a)), int const*>::value, "");
43
44 any const& ca = a;
45 static_assert(std::is_same<decltype(any_cast<int>(&ca)), int const*>::value, "");
46 static_assert(std::is_same<decltype(any_cast<int const>(&ca)), int const*>::value, "");
47 }
48
49 // Test that any_cast handles null pointers.
test_cast_nullptr()50 void test_cast_nullptr() {
51 any* a = nullptr;
52 assert(nullptr == any_cast<int>(a));
53 assert(nullptr == any_cast<int const>(a));
54
55 any const* ca = nullptr;
56 assert(nullptr == any_cast<int>(ca));
57 assert(nullptr == any_cast<int const>(ca));
58 }
59
60 // Test casting an empty object.
test_cast_empty()61 void test_cast_empty() {
62 {
63 any a;
64 assert(nullptr == any_cast<int>(&a));
65 assert(nullptr == any_cast<int const>(&a));
66
67 any const& ca = a;
68 assert(nullptr == any_cast<int>(&ca));
69 assert(nullptr == any_cast<int const>(&ca));
70 }
71 // Create as non-empty, then make empty and run test.
72 {
73 any a(42);
74 a.reset();
75 assert(nullptr == any_cast<int>(&a));
76 assert(nullptr == any_cast<int const>(&a));
77
78 any const& ca = a;
79 assert(nullptr == any_cast<int>(&ca));
80 assert(nullptr == any_cast<int const>(&ca));
81 }
82 }
83
84 template <class Type>
test_cast()85 void test_cast() {
86 assert(Type::count == 0);
87 Type::reset();
88 {
89 any a((Type(42)));
90 any const& ca = a;
91 assert(Type::count == 1);
92 assert(Type::copied == 0);
93 assert(Type::moved == 1);
94
95 // Try a cast to a bad type.
96 // NOTE: Type cannot be an int.
97 assert(any_cast<int>(&a) == nullptr);
98 assert(any_cast<int const>(&a) == nullptr);
99 assert(any_cast<int const volatile>(&a) == nullptr);
100
101 // Try a cast to the right type, but as a pointer.
102 assert(any_cast<Type*>(&a) == nullptr);
103 assert(any_cast<Type const*>(&a) == nullptr);
104
105 // Check getting a unqualified type from a non-const any.
106 Type* v = any_cast<Type>(&a);
107 assert(v != nullptr);
108 assert(v->value == 42);
109
110 // change the stored value and later check for the new value.
111 v->value = 999;
112
113 // Check getting a const qualified type from a non-const any.
114 Type const* cv = any_cast<Type const>(&a);
115 assert(cv != nullptr);
116 assert(cv == v);
117 assert(cv->value == 999);
118
119 // Check getting a unqualified type from a const any.
120 cv = any_cast<Type>(&ca);
121 assert(cv != nullptr);
122 assert(cv == v);
123 assert(cv->value == 999);
124
125 // Check getting a const-qualified type from a const any.
126 cv = any_cast<Type const>(&ca);
127 assert(cv != nullptr);
128 assert(cv == v);
129 assert(cv->value == 999);
130
131 // Check that no more objects were created, copied or moved.
132 assert(Type::count == 1);
133 assert(Type::copied == 0);
134 assert(Type::moved == 1);
135 }
136 assert(Type::count == 0);
137 }
138
test_cast_non_copyable_type()139 void test_cast_non_copyable_type()
140 {
141 // Even though 'any' never stores non-copyable types
142 // we still need to support any_cast<NoCopy>(ptr)
143 struct NoCopy { NoCopy(NoCopy const&) = delete; };
144 std::any a(42);
145 std::any const& ca = a;
146 assert(std::any_cast<NoCopy>(&a) == nullptr);
147 assert(std::any_cast<NoCopy>(&ca) == nullptr);
148 }
149
test_fn()150 void test_fn() {}
151
test_cast_function_pointer()152 void test_cast_function_pointer() {
153 using T = void(*)();
154 std::any a(test_fn);
155 // An any can never store a function type, but we should at least be able
156 // to ask.
157 assert(std::any_cast<void()>(&a) == nullptr);
158 T fn_ptr = std::any_cast<T>(a);
159 assert(fn_ptr == test_fn);
160 }
161
main()162 int main() {
163 test_cast_is_noexcept();
164 test_cast_return_type();
165 test_cast_nullptr();
166 test_cast_empty();
167 test_cast<small>();
168 test_cast<large>();
169 test_cast_non_copyable_type();
170 test_cast_function_pointer();
171 }
172