1 //===----------------------------------------------------------------------===//
2 //
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
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // UNSUPPORTED: c++03, c++11, c++14
10 
11 // Throwing bad_optional_access is supported starting in macosx10.13
12 // XFAIL: with_system_cxx_lib=macosx10.12 && !no-exceptions
13 // XFAIL: with_system_cxx_lib=macosx10.11 && !no-exceptions
14 // XFAIL: with_system_cxx_lib=macosx10.10 && !no-exceptions
15 // XFAIL: with_system_cxx_lib=macosx10.9 && !no-exceptions
16 
17 // <optional>
18 
19 // constexpr optional(T&& v);
20 
21 #include <optional>
22 #include <type_traits>
23 #include <cassert>
24 
25 #include "test_macros.h"
26 #include "archetypes.h"
27 
28 
29 using std::optional;
30 
31 
32 class Z
33 {
34 public:
35     Z(int) {}
36     Z(Z&&) {TEST_THROW(6);}
37 };
38 
39 
40 int main(int, char**)
41 {
42     {
43         typedef int T;
44         constexpr optional<T> opt(T(5));
45         static_assert(static_cast<bool>(opt) == true, "");
46         static_assert(*opt == 5, "");
47 
48         struct test_constexpr_ctor
49             : public optional<T>
50         {
51             constexpr test_constexpr_ctor(T&&) {}
52         };
53     }
54     {
55         typedef double T;
56         constexpr optional<T> opt(T(3));
57         static_assert(static_cast<bool>(opt) == true, "");
58         static_assert(*opt == 3, "");
59 
60         struct test_constexpr_ctor
61             : public optional<T>
62         {
63             constexpr test_constexpr_ctor(T&&) {}
64         };
65     }
66     {
67         const int x = 42;
68         optional<const int> o(std::move(x));
69         assert(*o == 42);
70     }
71     {
72         typedef TestTypes::TestType T;
73         T::reset();
74         optional<T> opt = T{3};
75         assert(T::alive == 1);
76         assert(T::move_constructed == 1);
77         assert(static_cast<bool>(opt) == true);
78         assert(opt.value().value == 3);
79     }
80     {
81         typedef ExplicitTestTypes::TestType T;
82         static_assert(!std::is_convertible<T&&, optional<T>>::value, "");
83         T::reset();
84         optional<T> opt(T{3});
85         assert(T::alive == 1);
86         assert(T::move_constructed == 1);
87         assert(static_cast<bool>(opt) == true);
88         assert(opt.value().value == 3);
89     }
90     {
91         typedef TestTypes::TestType T;
92         T::reset();
93         optional<T> opt = {3};
94         assert(T::alive == 1);
95         assert(T::value_constructed == 1);
96         assert(T::copy_constructed == 0);
97         assert(T::move_constructed == 0);
98         assert(static_cast<bool>(opt) == true);
99         assert(opt.value().value == 3);
100     }
101     {
102         typedef ConstexprTestTypes::TestType T;
103         constexpr optional<T> opt = {T(3)};
104         static_assert(static_cast<bool>(opt) == true, "");
105         static_assert(opt.value().value == 3, "");
106 
107         struct test_constexpr_ctor
108             : public optional<T>
109         {
110             constexpr test_constexpr_ctor(const T&) {}
111         };
112     }
113     {
114         typedef ConstexprTestTypes::TestType T;
115         constexpr optional<T> opt = {3};
116         static_assert(static_cast<bool>(opt) == true, "");
117         static_assert(opt.value().value == 3, "");
118 
119         struct test_constexpr_ctor
120             : public optional<T>
121         {
122             constexpr test_constexpr_ctor(const T&) {}
123         };
124     }
125     {
126         typedef ExplicitConstexprTestTypes::TestType T;
127         static_assert(!std::is_convertible<T&&, optional<T>>::value, "");
128         constexpr optional<T> opt(T{3});
129         static_assert(static_cast<bool>(opt) == true, "");
130         static_assert(opt.value().value == 3, "");
131 
132         struct test_constexpr_ctor
133             : public optional<T>
134         {
135             constexpr test_constexpr_ctor(T&&) {}
136         };
137 
138     }
139 #ifndef TEST_HAS_NO_EXCEPTIONS
140     {
141         struct Z {
142             Z(int) {}
143             Z(Z&&) {throw 6;}
144         };
145         typedef Z T;
146         try
147         {
148             T t(3);
149             optional<T> opt(std::move(t));
150             assert(false);
151         }
152         catch (int i)
153         {
154             assert(i == 6);
155         }
156     }
157 #endif
158 
159   return 0;
160 }
161