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: libcpp-has-no-threads
11 
12 // <future>
13 
14 // class future<R>
15 
16 // R future::get();
17 // R& future<R&>::get();
18 // void future<void>::get();
19 
20 #include <future>
21 #include <cassert>
22 
func1(std::promise<int> p)23 void func1(std::promise<int> p)
24 {
25     std::this_thread::sleep_for(std::chrono::milliseconds(500));
26     p.set_value(3);
27 }
28 
func2(std::promise<int> p)29 void func2(std::promise<int> p)
30 {
31     std::this_thread::sleep_for(std::chrono::milliseconds(500));
32     p.set_exception(std::make_exception_ptr(3));
33 }
34 
35 int j = 0;
36 
func3(std::promise<int &> p)37 void func3(std::promise<int&> p)
38 {
39     std::this_thread::sleep_for(std::chrono::milliseconds(500));
40     j = 5;
41     p.set_value(j);
42 }
43 
func4(std::promise<int &> p)44 void func4(std::promise<int&> p)
45 {
46     std::this_thread::sleep_for(std::chrono::milliseconds(500));
47     p.set_exception(std::make_exception_ptr(3.5));
48 }
49 
func5(std::promise<void> p)50 void func5(std::promise<void> p)
51 {
52     std::this_thread::sleep_for(std::chrono::milliseconds(500));
53     p.set_value();
54 }
55 
func6(std::promise<void> p)56 void func6(std::promise<void> p)
57 {
58     std::this_thread::sleep_for(std::chrono::milliseconds(500));
59     p.set_exception(std::make_exception_ptr('c'));
60 }
61 
main()62 int main()
63 {
64     {
65         typedef int T;
66         {
67             std::promise<T> p;
68             std::future<T> f = p.get_future();
69             std::thread(func1, std::move(p)).detach();
70             assert(f.valid());
71             assert(f.get() == 3);
72             assert(!f.valid());
73         }
74         {
75             std::promise<T> p;
76             std::future<T> f = p.get_future();
77             std::thread(func2, std::move(p)).detach();
78             try
79             {
80                 assert(f.valid());
81                 assert(f.get() == 3);
82                 assert(false);
83             }
84             catch (int i)
85             {
86                 assert(i == 3);
87             }
88             assert(!f.valid());
89         }
90     }
91     {
92         typedef int& T;
93         {
94             std::promise<T> p;
95             std::future<T> f = p.get_future();
96             std::thread(func3, std::move(p)).detach();
97             assert(f.valid());
98             assert(f.get() == 5);
99             assert(!f.valid());
100         }
101         {
102             std::promise<T> p;
103             std::future<T> f = p.get_future();
104             std::thread(func4, std::move(p)).detach();
105             try
106             {
107                 assert(f.valid());
108                 assert(f.get() == 3);
109                 assert(false);
110             }
111             catch (double i)
112             {
113                 assert(i == 3.5);
114             }
115             assert(!f.valid());
116         }
117     }
118     {
119         typedef void T;
120         {
121             std::promise<T> p;
122             std::future<T> f = p.get_future();
123             std::thread(func5, std::move(p)).detach();
124             assert(f.valid());
125             f.get();
126             assert(!f.valid());
127         }
128         {
129             std::promise<T> p;
130             std::future<T> f = p.get_future();
131             std::thread(func6, std::move(p)).detach();
132             try
133             {
134                 assert(f.valid());
135                 f.get();
136                 assert(false);
137             }
138             catch (char i)
139             {
140                 assert(i == 'c');
141             }
142             assert(!f.valid());
143         }
144     }
145 }
146