blob: 5701c294aa4b0a621a25f6a0e8624595c77b13ee [file] [log] [blame]
Howard Hinnantc51e1022010-05-11 19:42:16 +00001// -*- C++ -*-
2//===--------------------------- future -----------------------------------===//
3//
Chandler Carruthd2012102019-01-19 10:56:40 +00004// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5// See https://llvm.org/LICENSE.txt for license information.
6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
Howard Hinnantc51e1022010-05-11 19:42:16 +00007//
8//===----------------------------------------------------------------------===//
9
10#ifndef _LIBCPP_FUTURE
11#define _LIBCPP_FUTURE
12
13/*
14 future synopsis
15
16namespace std
17{
18
19enum class future_errc
20{
Howard Hinnantf2fd64d2013-09-14 18:20:10 +000021 future_already_retrieved = 1,
Howard Hinnantc51e1022010-05-11 19:42:16 +000022 promise_already_satisfied,
Howard Hinnantf2fd64d2013-09-14 18:20:10 +000023 no_state,
24 broken_promise
Howard Hinnantc51e1022010-05-11 19:42:16 +000025};
26
27enum class launch
28{
Howard Hinnante3df4ea2010-11-23 18:33:54 +000029 async = 1,
30 deferred = 2,
31 any = async | deferred
Howard Hinnantc51e1022010-05-11 19:42:16 +000032};
33
34enum class future_status
35{
36 ready,
37 timeout,
38 deferred
39};
40
41template <> struct is_error_code_enum<future_errc> : public true_type { };
Howard Hinnant22448042012-07-21 17:46:55 +000042error_code make_error_code(future_errc e) noexcept;
43error_condition make_error_condition(future_errc e) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000044
Howard Hinnant22448042012-07-21 17:46:55 +000045const error_category& future_category() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000046
47class future_error
48 : public logic_error
49{
50public:
51 future_error(error_code ec); // exposition only
Marshall Clowd4a669c2016-11-14 18:56:24 +000052 explicit future_error(future_errc); // C++17
Howard Hinnant22448042012-07-21 17:46:55 +000053 const error_code& code() const noexcept;
54 const char* what() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000055};
56
57template <class R>
58class promise
59{
60public:
61 promise();
62 template <class Allocator>
63 promise(allocator_arg_t, const Allocator& a);
Howard Hinnant22448042012-07-21 17:46:55 +000064 promise(promise&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000065 promise(const promise& rhs) = delete;
66 ~promise();
67
68 // assignment
Howard Hinnant22448042012-07-21 17:46:55 +000069 promise& operator=(promise&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000070 promise& operator=(const promise& rhs) = delete;
Howard Hinnant22448042012-07-21 17:46:55 +000071 void swap(promise& other) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000072
73 // retrieving the result
74 future<R> get_future();
75
76 // setting the result
77 void set_value(const R& r);
78 void set_value(R&& r);
79 void set_exception(exception_ptr p);
80
81 // setting the result with deferred notification
82 void set_value_at_thread_exit(const R& r);
83 void set_value_at_thread_exit(R&& r);
84 void set_exception_at_thread_exit(exception_ptr p);
85};
86
87template <class R>
88class promise<R&>
89{
90public:
91 promise();
92 template <class Allocator>
93 promise(allocator_arg_t, const Allocator& a);
Howard Hinnant22448042012-07-21 17:46:55 +000094 promise(promise&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +000095 promise(const promise& rhs) = delete;
96 ~promise();
97
98 // assignment
Howard Hinnant22448042012-07-21 17:46:55 +000099 promise& operator=(promise&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000100 promise& operator=(const promise& rhs) = delete;
Howard Hinnant22448042012-07-21 17:46:55 +0000101 void swap(promise& other) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000102
103 // retrieving the result
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000104 future<R&> get_future();
Howard Hinnantc51e1022010-05-11 19:42:16 +0000105
106 // setting the result
107 void set_value(R& r);
108 void set_exception(exception_ptr p);
109
110 // setting the result with deferred notification
111 void set_value_at_thread_exit(R&);
112 void set_exception_at_thread_exit(exception_ptr p);
113};
114
115template <>
116class promise<void>
117{
118public:
119 promise();
120 template <class Allocator>
121 promise(allocator_arg_t, const Allocator& a);
Howard Hinnant22448042012-07-21 17:46:55 +0000122 promise(promise&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000123 promise(const promise& rhs) = delete;
124 ~promise();
125
126 // assignment
Howard Hinnant22448042012-07-21 17:46:55 +0000127 promise& operator=(promise&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000128 promise& operator=(const promise& rhs) = delete;
Howard Hinnant22448042012-07-21 17:46:55 +0000129 void swap(promise& other) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000130
131 // retrieving the result
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000132 future<void> get_future();
Howard Hinnantc51e1022010-05-11 19:42:16 +0000133
134 // setting the result
135 void set_value();
136 void set_exception(exception_ptr p);
137
138 // setting the result with deferred notification
139 void set_value_at_thread_exit();
140 void set_exception_at_thread_exit(exception_ptr p);
141};
142
Howard Hinnant22448042012-07-21 17:46:55 +0000143template <class R> void swap(promise<R>& x, promise<R>& y) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000144
145template <class R, class Alloc>
146 struct uses_allocator<promise<R>, Alloc> : public true_type {};
147
148template <class R>
149class future
150{
151public:
Howard Hinnant22448042012-07-21 17:46:55 +0000152 future() noexcept;
153 future(future&&) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000154 future(const future& rhs) = delete;
155 ~future();
156 future& operator=(const future& rhs) = delete;
Howard Hinnant22448042012-07-21 17:46:55 +0000157 future& operator=(future&&) noexcept;
Marshall Clow597881d2017-01-25 20:14:03 +0000158 shared_future<R> share() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000159
160 // retrieving the value
161 R get();
162
163 // functions to check state
Howard Hinnant22448042012-07-21 17:46:55 +0000164 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000165
166 void wait() const;
167 template <class Rep, class Period>
168 future_status
169 wait_for(const chrono::duration<Rep, Period>& rel_time) const;
170 template <class Clock, class Duration>
171 future_status
172 wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
173};
174
175template <class R>
176class future<R&>
177{
178public:
Howard Hinnant22448042012-07-21 17:46:55 +0000179 future() noexcept;
180 future(future&&) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000181 future(const future& rhs) = delete;
182 ~future();
183 future& operator=(const future& rhs) = delete;
Howard Hinnant22448042012-07-21 17:46:55 +0000184 future& operator=(future&&) noexcept;
Marshall Clow79e02112017-01-24 23:28:25 +0000185 shared_future<R&> share() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000186
187 // retrieving the value
188 R& get();
189
190 // functions to check state
Howard Hinnant22448042012-07-21 17:46:55 +0000191 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000192
193 void wait() const;
194 template <class Rep, class Period>
195 future_status
196 wait_for(const chrono::duration<Rep, Period>& rel_time) const;
197 template <class Clock, class Duration>
198 future_status
199 wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
200};
201
202template <>
203class future<void>
204{
205public:
Howard Hinnant22448042012-07-21 17:46:55 +0000206 future() noexcept;
207 future(future&&) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000208 future(const future& rhs) = delete;
209 ~future();
210 future& operator=(const future& rhs) = delete;
Howard Hinnant22448042012-07-21 17:46:55 +0000211 future& operator=(future&&) noexcept;
Marshall Clow79e02112017-01-24 23:28:25 +0000212 shared_future<void> share() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000213
214 // retrieving the value
215 void get();
216
217 // functions to check state
Howard Hinnant22448042012-07-21 17:46:55 +0000218 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000219
220 void wait() const;
221 template <class Rep, class Period>
222 future_status
223 wait_for(const chrono::duration<Rep, Period>& rel_time) const;
224 template <class Clock, class Duration>
225 future_status
226 wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
227};
228
229template <class R>
230class shared_future
231{
232public:
Howard Hinnant22448042012-07-21 17:46:55 +0000233 shared_future() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000234 shared_future(const shared_future& rhs);
Howard Hinnant22448042012-07-21 17:46:55 +0000235 shared_future(future<R>&&) noexcept;
236 shared_future(shared_future&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000237 ~shared_future();
238 shared_future& operator=(const shared_future& rhs);
Howard Hinnant22448042012-07-21 17:46:55 +0000239 shared_future& operator=(shared_future&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000240
241 // retrieving the value
242 const R& get() const;
243
244 // functions to check state
Howard Hinnant22448042012-07-21 17:46:55 +0000245 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000246
247 void wait() const;
248 template <class Rep, class Period>
249 future_status
250 wait_for(const chrono::duration<Rep, Period>& rel_time) const;
251 template <class Clock, class Duration>
252 future_status
253 wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
254};
255
256template <class R>
257class shared_future<R&>
258{
259public:
Howard Hinnant22448042012-07-21 17:46:55 +0000260 shared_future() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000261 shared_future(const shared_future& rhs);
Howard Hinnant22448042012-07-21 17:46:55 +0000262 shared_future(future<R&>&&) noexcept;
263 shared_future(shared_future&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000264 ~shared_future();
265 shared_future& operator=(const shared_future& rhs);
Howard Hinnant22448042012-07-21 17:46:55 +0000266 shared_future& operator=(shared_future&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000267
268 // retrieving the value
269 R& get() const;
270
271 // functions to check state
Howard Hinnant22448042012-07-21 17:46:55 +0000272 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000273
274 void wait() const;
275 template <class Rep, class Period>
276 future_status
277 wait_for(const chrono::duration<Rep, Period>& rel_time) const;
278 template <class Clock, class Duration>
279 future_status
280 wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
281};
282
283template <>
284class shared_future<void>
285{
286public:
Howard Hinnant22448042012-07-21 17:46:55 +0000287 shared_future() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000288 shared_future(const shared_future& rhs);
Howard Hinnant22448042012-07-21 17:46:55 +0000289 shared_future(future<void>&&) noexcept;
290 shared_future(shared_future&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000291 ~shared_future();
292 shared_future& operator=(const shared_future& rhs);
Howard Hinnant22448042012-07-21 17:46:55 +0000293 shared_future& operator=(shared_future&& rhs) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000294
295 // retrieving the value
296 void get() const;
297
298 // functions to check state
Howard Hinnant22448042012-07-21 17:46:55 +0000299 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000300
301 void wait() const;
302 template <class Rep, class Period>
303 future_status
304 wait_for(const chrono::duration<Rep, Period>& rel_time) const;
305 template <class Clock, class Duration>
306 future_status
307 wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
308};
309
Howard Hinnantc51e1022010-05-11 19:42:16 +0000310template <class F, class... Args>
Howard Hinnant15579d22013-09-21 18:17:23 +0000311 future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000312 async(F&& f, Args&&... args);
313
314template <class F, class... Args>
Howard Hinnant15579d22013-09-21 18:17:23 +0000315 future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000316 async(launch policy, F&& f, Args&&... args);
317
Howard Hinnantc566dc32010-05-11 21:36:01 +0000318template <class> class packaged_task; // undefined
Howard Hinnantc51e1022010-05-11 19:42:16 +0000319
320template <class R, class... ArgTypes>
321class packaged_task<R(ArgTypes...)>
322{
323public:
Eric Fiselier17f39ed2016-06-01 21:05:53 +0000324 typedef R result_type; // extension
Howard Hinnantc51e1022010-05-11 19:42:16 +0000325
326 // construction and destruction
Howard Hinnant22448042012-07-21 17:46:55 +0000327 packaged_task() noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000328 template <class F>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000329 explicit packaged_task(F&& f);
Marshall Clowa0a057e2017-11-27 20:47:54 +0000330 template <class F, class Allocator>
331 packaged_task(allocator_arg_t, const Allocator& a, F&& f);
Howard Hinnantc51e1022010-05-11 19:42:16 +0000332 ~packaged_task();
333
334 // no copy
Howard Hinnantab500072012-07-21 19:34:12 +0000335 packaged_task(const packaged_task&) = delete;
336 packaged_task& operator=(const packaged_task&) = delete;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000337
338 // move support
Howard Hinnant22448042012-07-21 17:46:55 +0000339 packaged_task(packaged_task&& other) noexcept;
340 packaged_task& operator=(packaged_task&& other) noexcept;
341 void swap(packaged_task& other) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000342
Howard Hinnant22448042012-07-21 17:46:55 +0000343 bool valid() const noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000344
345 // result retrieval
346 future<R> get_future();
347
348 // execution
349 void operator()(ArgTypes... );
350 void make_ready_at_thread_exit(ArgTypes...);
351
352 void reset();
353};
354
355template <class R>
Howard Hinnant22448042012-07-21 17:46:55 +0000356 void swap(packaged_task<R(ArgTypes...)&, packaged_task<R(ArgTypes...)>&) noexcept;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000357
Marshall Clowa0a057e2017-11-27 20:47:54 +0000358template <class R, class Alloc> struct uses_allocator<packaged_task<R>, Alloc>;
359
Howard Hinnantc51e1022010-05-11 19:42:16 +0000360} // std
361
362*/
363
364#include <__config>
Louis Dionne73912b22020-11-04 15:01:25 -0500365#include <__availability>
Arthur O'Dwyer597cac42021-05-12 23:04:03 -0400366#include <__debug>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000367#include <chrono>
368#include <exception>
Arthur O'Dwyer597cac42021-05-12 23:04:03 -0400369#include <memory>
Howard Hinnante6a10852010-09-03 21:46:37 +0000370#include <mutex>
Arthur O'Dwyer597cac42021-05-12 23:04:03 -0400371#include <system_error>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000372#include <thread>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000373
Howard Hinnantaaaa52b2011-10-17 20:05:10 +0000374#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000375#pragma GCC system_header
Howard Hinnantaaaa52b2011-10-17 20:05:10 +0000376#endif
Howard Hinnantc51e1022010-05-11 19:42:16 +0000377
Jonathan Roelofs067218a2014-09-05 20:28:44 +0000378#ifdef _LIBCPP_HAS_NO_THREADS
Jonathan Roelofs39cb6bf2014-09-05 19:45:05 +0000379#error <future> is not supported on this single threaded system
380#else // !_LIBCPP_HAS_NO_THREADS
381
Howard Hinnantc51e1022010-05-11 19:42:16 +0000382_LIBCPP_BEGIN_NAMESPACE_STD
383
384//enum class future_errc
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000385_LIBCPP_DECLARE_STRONG_ENUM(future_errc)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000386{
Howard Hinnantf2fd64d2013-09-14 18:20:10 +0000387 future_already_retrieved = 1,
Howard Hinnantc51e1022010-05-11 19:42:16 +0000388 promise_already_satisfied,
Howard Hinnantf2fd64d2013-09-14 18:20:10 +0000389 no_state,
390 broken_promise
Howard Hinnantc51e1022010-05-11 19:42:16 +0000391};
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000392_LIBCPP_DECLARE_STRONG_ENUM_EPILOG(future_errc)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000393
Howard Hinnant684902d2010-09-22 14:16:26 +0000394template <>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000395struct _LIBCPP_TEMPLATE_VIS is_error_code_enum<future_errc> : public true_type {};
Howard Hinnant96803d92010-08-25 17:32:05 +0000396
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000397#ifdef _LIBCPP_HAS_NO_STRONG_ENUMS
398template <>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000399struct _LIBCPP_TEMPLATE_VIS is_error_code_enum<future_errc::__lx> : public true_type { };
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000400#endif
401
Howard Hinnantc51e1022010-05-11 19:42:16 +0000402//enum class launch
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000403_LIBCPP_DECLARE_STRONG_ENUM(launch)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000404{
Howard Hinnante3df4ea2010-11-23 18:33:54 +0000405 async = 1,
406 deferred = 2,
407 any = async | deferred
Howard Hinnantc51e1022010-05-11 19:42:16 +0000408};
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000409_LIBCPP_DECLARE_STRONG_ENUM_EPILOG(launch)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000410
Howard Hinnantda760a82013-06-29 18:38:17 +0000411#ifndef _LIBCPP_HAS_NO_STRONG_ENUMS
412
Howard Hinnantda760a82013-06-29 18:38:17 +0000413typedef underlying_type<launch>::type __launch_underlying_type;
Howard Hinnantda760a82013-06-29 18:38:17 +0000414
415inline _LIBCPP_INLINE_VISIBILITY
416_LIBCPP_CONSTEXPR
417launch
418operator&(launch __x, launch __y)
419{
420 return static_cast<launch>(static_cast<__launch_underlying_type>(__x) &
421 static_cast<__launch_underlying_type>(__y));
422}
423
424inline _LIBCPP_INLINE_VISIBILITY
425_LIBCPP_CONSTEXPR
426launch
427operator|(launch __x, launch __y)
428{
429 return static_cast<launch>(static_cast<__launch_underlying_type>(__x) |
430 static_cast<__launch_underlying_type>(__y));
431}
432
433inline _LIBCPP_INLINE_VISIBILITY
434_LIBCPP_CONSTEXPR
435launch
436operator^(launch __x, launch __y)
437{
438 return static_cast<launch>(static_cast<__launch_underlying_type>(__x) ^
439 static_cast<__launch_underlying_type>(__y));
440}
441
442inline _LIBCPP_INLINE_VISIBILITY
443_LIBCPP_CONSTEXPR
444launch
445operator~(launch __x)
446{
Howard Hinnant373d7602013-07-02 18:01:41 +0000447 return static_cast<launch>(~static_cast<__launch_underlying_type>(__x) & 3);
Howard Hinnantda760a82013-06-29 18:38:17 +0000448}
449
450inline _LIBCPP_INLINE_VISIBILITY
451launch&
452operator&=(launch& __x, launch __y)
453{
454 __x = __x & __y; return __x;
455}
456
457inline _LIBCPP_INLINE_VISIBILITY
458launch&
459operator|=(launch& __x, launch __y)
460{
461 __x = __x | __y; return __x;
462}
463
464inline _LIBCPP_INLINE_VISIBILITY
465launch&
466operator^=(launch& __x, launch __y)
467{
468 __x = __x ^ __y; return __x;
469}
470
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400471#endif // !_LIBCPP_HAS_NO_STRONG_ENUMS
Howard Hinnantda760a82013-06-29 18:38:17 +0000472
Howard Hinnantc51e1022010-05-11 19:42:16 +0000473//enum class future_status
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000474_LIBCPP_DECLARE_STRONG_ENUM(future_status)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000475{
Howard Hinnantc51e1022010-05-11 19:42:16 +0000476 ready,
477 timeout,
478 deferred
479};
Howard Hinnant09bc0c92011-12-02 19:36:40 +0000480_LIBCPP_DECLARE_STRONG_ENUM_EPILOG(future_status)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000481
Howard Hinnant8331b762013-03-06 23:30:19 +0000482_LIBCPP_FUNC_VIS
Howard Hinnant22448042012-07-21 17:46:55 +0000483const error_category& future_category() _NOEXCEPT;
Howard Hinnant96803d92010-08-25 17:32:05 +0000484
485inline _LIBCPP_INLINE_VISIBILITY
486error_code
Howard Hinnant22448042012-07-21 17:46:55 +0000487make_error_code(future_errc __e) _NOEXCEPT
Howard Hinnant96803d92010-08-25 17:32:05 +0000488{
489 return error_code(static_cast<int>(__e), future_category());
490}
491
492inline _LIBCPP_INLINE_VISIBILITY
493error_condition
Howard Hinnant22448042012-07-21 17:46:55 +0000494make_error_condition(future_errc __e) _NOEXCEPT
Howard Hinnant96803d92010-08-25 17:32:05 +0000495{
496 return error_condition(static_cast<int>(__e), future_category());
497}
498
Mehdi Amini228053d2017-05-04 17:08:54 +0000499class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_FUTURE_ERROR future_error
Howard Hinnant96803d92010-08-25 17:32:05 +0000500 : public logic_error
501{
502 error_code __ec_;
503public:
504 future_error(error_code __ec);
Marek Kurdejf3197922021-04-01 08:29:55 +0200505
Howard Hinnant684902d2010-09-22 14:16:26 +0000506 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +0000507 const error_code& code() const _NOEXCEPT {return __ec_;}
Howard Hinnant0dcdf022011-07-07 21:03:52 +0000508
Dimitry Andric47269ce2020-03-13 19:36:26 +0100509 future_error(const future_error&) _NOEXCEPT = default;
Howard Hinnant0dcdf022011-07-07 21:03:52 +0000510 virtual ~future_error() _NOEXCEPT;
Howard Hinnant96803d92010-08-25 17:32:05 +0000511};
512
Louis Dionne16fe2952018-07-11 23:14:33 +0000513_LIBCPP_NORETURN inline _LIBCPP_INLINE_VISIBILITY
Mehdi Amini228053d2017-05-04 17:08:54 +0000514#ifndef _LIBCPP_NO_EXCEPTIONS
515_LIBCPP_AVAILABILITY_FUTURE_ERROR
516#endif
Eric Fiselier43641592015-10-02 21:25:15 +0000517void __throw_future_error(future_errc _Ev)
Marshall Clow7b3742d2015-09-03 15:11:32 +0000518{
519#ifndef _LIBCPP_NO_EXCEPTIONS
520 throw future_error(make_error_code(_Ev));
521#else
Eric Fiselierb2c89f22016-12-24 01:56:25 +0000522 ((void)_Ev);
Marshall Clow8fea1612016-08-25 15:09:01 +0000523 _VSTD::abort();
Marshall Clow7b3742d2015-09-03 15:11:32 +0000524#endif
525}
526
Mehdi Amini228053d2017-05-04 17:08:54 +0000527class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE __assoc_sub_state
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000528 : public __shared_count
529{
530protected:
531 exception_ptr __exception_;
532 mutable mutex __mut_;
533 mutable condition_variable __cv_;
534 unsigned __state_;
535
Howard Hinnant719bda32011-05-28 14:41:13 +0000536 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnantccdd2032010-08-30 18:46:21 +0000537 void __sub_wait(unique_lock<mutex>& __lk);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000538public:
539 enum
540 {
541 __constructed = 1,
542 __future_attached = 2,
543 ready = 4,
544 deferred = 8
545 };
546
Howard Hinnant684902d2010-09-22 14:16:26 +0000547 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000548 __assoc_sub_state() : __state_(0) {}
549
Howard Hinnant684902d2010-09-22 14:16:26 +0000550 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000551 bool __has_value() const
552 {return (__state_ & __constructed) || (__exception_ != nullptr);}
553
Howard Hinnant684902d2010-09-22 14:16:26 +0000554 _LIBCPP_INLINE_VISIBILITY
Louis Dionne2c0d2262018-08-24 14:00:59 +0000555 void __attach_future() {
Howard Hinnante667ecc2013-01-14 20:01:24 +0000556 lock_guard<mutex> __lk(__mut_);
Louis Dionne2c0d2262018-08-24 14:00:59 +0000557 bool __has_future_attached = (__state_ & __future_attached) != 0;
558 if (__has_future_attached)
559 __throw_future_error(future_errc::future_already_retrieved);
560 this->__add_shared();
Howard Hinnante667ecc2013-01-14 20:01:24 +0000561 __state_ |= __future_attached;
562 }
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000563
Howard Hinnant684902d2010-09-22 14:16:26 +0000564 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantccdd2032010-08-30 18:46:21 +0000565 void __set_deferred() {__state_ |= deferred;}
566
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000567 void __make_ready();
Howard Hinnant684902d2010-09-22 14:16:26 +0000568 _LIBCPP_INLINE_VISIBILITY
Marshall Clowdfcbb432013-10-13 01:02:45 +0000569 bool __is_ready() const {return (__state_ & ready) != 0;}
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000570
571 void set_value();
572 void set_value_at_thread_exit();
573
574 void set_exception(exception_ptr __p);
575 void set_exception_at_thread_exit(exception_ptr __p);
576
577 void copy();
578
Howard Hinnantccdd2032010-08-30 18:46:21 +0000579 void wait();
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000580 template <class _Rep, class _Period>
581 future_status
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000582 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000583 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const;
584 template <class _Clock, class _Duration>
Shoaib Meenai55f3a462017-03-02 03:22:18 +0000585 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000586 future_status
587 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const;
Howard Hinnantccdd2032010-08-30 18:46:21 +0000588
589 virtual void __execute();
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000590};
591
Howard Hinnantf4712b92010-08-28 21:01:06 +0000592template <class _Clock, class _Duration>
593future_status
594__assoc_sub_state::wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
595{
596 unique_lock<mutex> __lk(__mut_);
Howard Hinnantccdd2032010-08-30 18:46:21 +0000597 if (__state_ & deferred)
598 return future_status::deferred;
599 while (!(__state_ & ready) && _Clock::now() < __abs_time)
Howard Hinnantf4712b92010-08-28 21:01:06 +0000600 __cv_.wait_until(__lk, __abs_time);
601 if (__state_ & ready)
602 return future_status::ready;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000603 return future_status::timeout;
604}
605
606template <class _Rep, class _Period>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000607inline
Howard Hinnantf4712b92010-08-28 21:01:06 +0000608future_status
609__assoc_sub_state::wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
610{
Howard Hinnantc8dbd222010-11-20 19:16:30 +0000611 return wait_until(chrono::steady_clock::now() + __rel_time);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000612}
613
Howard Hinnantc834c512011-11-29 18:15:50 +0000614template <class _Rp>
Louis Dionne3b967d02019-12-10 18:00:42 -0500615class _LIBCPP_AVAILABILITY_FUTURE _LIBCPP_HIDDEN __assoc_state
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000616 : public __assoc_sub_state
617{
618 typedef __assoc_sub_state base;
Howard Hinnantc834c512011-11-29 18:15:50 +0000619 typedef typename aligned_storage<sizeof(_Rp), alignment_of<_Rp>::value>::type _Up;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000620protected:
Howard Hinnantc834c512011-11-29 18:15:50 +0000621 _Up __value_;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000622
Howard Hinnant719bda32011-05-28 14:41:13 +0000623 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000624public:
625
626 template <class _Arg>
Louis Dionne7b844362020-07-30 09:42:23 -0400627 void set_value(_Arg&& __arg);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000628
629 template <class _Arg>
Louis Dionne7b844362020-07-30 09:42:23 -0400630 void set_value_at_thread_exit(_Arg&& __arg);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000631
Howard Hinnantc834c512011-11-29 18:15:50 +0000632 _Rp move();
633 typename add_lvalue_reference<_Rp>::type copy();
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000634};
635
Howard Hinnantc834c512011-11-29 18:15:50 +0000636template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000637void
Howard Hinnantc834c512011-11-29 18:15:50 +0000638__assoc_state<_Rp>::__on_zero_shared() _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000639{
640 if (this->__state_ & base::__constructed)
Howard Hinnantc834c512011-11-29 18:15:50 +0000641 reinterpret_cast<_Rp*>(&__value_)->~_Rp();
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000642 delete this;
643}
644
Howard Hinnantc834c512011-11-29 18:15:50 +0000645template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000646template <class _Arg>
Mehdi Amini228053d2017-05-04 17:08:54 +0000647_LIBCPP_AVAILABILITY_FUTURE
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000648void
Howard Hinnantc834c512011-11-29 18:15:50 +0000649__assoc_state<_Rp>::set_value(_Arg&& __arg)
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000650{
651 unique_lock<mutex> __lk(this->__mut_);
652 if (this->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +0000653 __throw_future_error(future_errc::promise_already_satisfied);
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -0500654 ::new ((void*)&__value_) _Rp(_VSTD::forward<_Arg>(__arg));
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000655 this->__state_ |= base::__constructed | base::ready;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000656 __cv_.notify_all();
657}
658
Howard Hinnantc834c512011-11-29 18:15:50 +0000659template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000660template <class _Arg>
661void
Howard Hinnantc834c512011-11-29 18:15:50 +0000662__assoc_state<_Rp>::set_value_at_thread_exit(_Arg&& __arg)
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000663{
664 unique_lock<mutex> __lk(this->__mut_);
665 if (this->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +0000666 __throw_future_error(future_errc::promise_already_satisfied);
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -0500667 ::new ((void*)&__value_) _Rp(_VSTD::forward<_Arg>(__arg));
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000668 this->__state_ |= base::__constructed;
Howard Hinnant15d55052010-10-14 19:18:04 +0000669 __thread_local_data()->__make_ready_at_thread_exit(this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000670}
671
Howard Hinnantc834c512011-11-29 18:15:50 +0000672template <class _Rp>
673_Rp
674__assoc_state<_Rp>::move()
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000675{
676 unique_lock<mutex> __lk(this->__mut_);
Howard Hinnantccdd2032010-08-30 18:46:21 +0000677 this->__sub_wait(__lk);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000678 if (this->__exception_ != nullptr)
679 rethrow_exception(this->__exception_);
Howard Hinnantc834c512011-11-29 18:15:50 +0000680 return _VSTD::move(*reinterpret_cast<_Rp*>(&__value_));
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000681}
682
Howard Hinnantc834c512011-11-29 18:15:50 +0000683template <class _Rp>
684typename add_lvalue_reference<_Rp>::type
685__assoc_state<_Rp>::copy()
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000686{
687 unique_lock<mutex> __lk(this->__mut_);
Howard Hinnantccdd2032010-08-30 18:46:21 +0000688 this->__sub_wait(__lk);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000689 if (this->__exception_ != nullptr)
690 rethrow_exception(this->__exception_);
Howard Hinnantc834c512011-11-29 18:15:50 +0000691 return *reinterpret_cast<_Rp*>(&__value_);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000692}
693
Howard Hinnantc834c512011-11-29 18:15:50 +0000694template <class _Rp>
Mehdi Amini228053d2017-05-04 17:08:54 +0000695class _LIBCPP_AVAILABILITY_FUTURE __assoc_state<_Rp&>
Howard Hinnantf4712b92010-08-28 21:01:06 +0000696 : public __assoc_sub_state
697{
698 typedef __assoc_sub_state base;
Howard Hinnantc834c512011-11-29 18:15:50 +0000699 typedef _Rp* _Up;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000700protected:
Howard Hinnantc834c512011-11-29 18:15:50 +0000701 _Up __value_;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000702
Howard Hinnant719bda32011-05-28 14:41:13 +0000703 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000704public:
705
Howard Hinnantc834c512011-11-29 18:15:50 +0000706 void set_value(_Rp& __arg);
707 void set_value_at_thread_exit(_Rp& __arg);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000708
Howard Hinnantc834c512011-11-29 18:15:50 +0000709 _Rp& copy();
Howard Hinnantf4712b92010-08-28 21:01:06 +0000710};
711
Howard Hinnantc834c512011-11-29 18:15:50 +0000712template <class _Rp>
Howard Hinnantf4712b92010-08-28 21:01:06 +0000713void
Howard Hinnantc834c512011-11-29 18:15:50 +0000714__assoc_state<_Rp&>::__on_zero_shared() _NOEXCEPT
Howard Hinnantf4712b92010-08-28 21:01:06 +0000715{
716 delete this;
717}
718
Howard Hinnantc834c512011-11-29 18:15:50 +0000719template <class _Rp>
Howard Hinnantf4712b92010-08-28 21:01:06 +0000720void
Howard Hinnantc834c512011-11-29 18:15:50 +0000721__assoc_state<_Rp&>::set_value(_Rp& __arg)
Howard Hinnantf4712b92010-08-28 21:01:06 +0000722{
723 unique_lock<mutex> __lk(this->__mut_);
724 if (this->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +0000725 __throw_future_error(future_errc::promise_already_satisfied);
Howard Hinnant8bea6da2013-08-08 18:38:55 +0000726 __value_ = _VSTD::addressof(__arg);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000727 this->__state_ |= base::__constructed | base::ready;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000728 __cv_.notify_all();
729}
730
Howard Hinnantc834c512011-11-29 18:15:50 +0000731template <class _Rp>
Howard Hinnantf4712b92010-08-28 21:01:06 +0000732void
Howard Hinnantc834c512011-11-29 18:15:50 +0000733__assoc_state<_Rp&>::set_value_at_thread_exit(_Rp& __arg)
Howard Hinnantf4712b92010-08-28 21:01:06 +0000734{
735 unique_lock<mutex> __lk(this->__mut_);
736 if (this->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +0000737 __throw_future_error(future_errc::promise_already_satisfied);
Howard Hinnant8bea6da2013-08-08 18:38:55 +0000738 __value_ = _VSTD::addressof(__arg);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000739 this->__state_ |= base::__constructed;
Howard Hinnant15d55052010-10-14 19:18:04 +0000740 __thread_local_data()->__make_ready_at_thread_exit(this);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000741}
742
Howard Hinnantc834c512011-11-29 18:15:50 +0000743template <class _Rp>
744_Rp&
745__assoc_state<_Rp&>::copy()
Howard Hinnantf4712b92010-08-28 21:01:06 +0000746{
747 unique_lock<mutex> __lk(this->__mut_);
Howard Hinnantccdd2032010-08-30 18:46:21 +0000748 this->__sub_wait(__lk);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000749 if (this->__exception_ != nullptr)
750 rethrow_exception(this->__exception_);
751 return *__value_;
752}
753
Howard Hinnantc834c512011-11-29 18:15:50 +0000754template <class _Rp, class _Alloc>
Mehdi Amini228053d2017-05-04 17:08:54 +0000755class _LIBCPP_AVAILABILITY_FUTURE __assoc_state_alloc
Howard Hinnantc834c512011-11-29 18:15:50 +0000756 : public __assoc_state<_Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000757{
Howard Hinnantc834c512011-11-29 18:15:50 +0000758 typedef __assoc_state<_Rp> base;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000759 _Alloc __alloc_;
760
Howard Hinnant719bda32011-05-28 14:41:13 +0000761 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000762public:
Howard Hinnant684902d2010-09-22 14:16:26 +0000763 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000764 explicit __assoc_state_alloc(const _Alloc& __a)
765 : __alloc_(__a) {}
766};
767
Howard Hinnantc834c512011-11-29 18:15:50 +0000768template <class _Rp, class _Alloc>
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000769void
Howard Hinnantc834c512011-11-29 18:15:50 +0000770__assoc_state_alloc<_Rp, _Alloc>::__on_zero_shared() _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000771{
772 if (this->__state_ & base::__constructed)
Howard Hinnant8bea6da2013-08-08 18:38:55 +0000773 reinterpret_cast<_Rp*>(_VSTD::addressof(this->__value_))->~_Rp();
Eric Fiselierf8898c82015-02-05 23:01:40 +0000774 typedef typename __allocator_traits_rebind<_Alloc, __assoc_state_alloc>::type _Al;
775 typedef allocator_traits<_Al> _ATraits;
Eric Fiselier0d109272014-10-23 06:24:45 +0000776 typedef pointer_traits<typename _ATraits::pointer> _PTraits;
Eric Fiselierf8898c82015-02-05 23:01:40 +0000777 _Al __a(__alloc_);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000778 this->~__assoc_state_alloc();
Eric Fiselier0d109272014-10-23 06:24:45 +0000779 __a.deallocate(_PTraits::pointer_to(*this), 1);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000780}
781
Howard Hinnantc834c512011-11-29 18:15:50 +0000782template <class _Rp, class _Alloc>
Mehdi Amini228053d2017-05-04 17:08:54 +0000783class _LIBCPP_AVAILABILITY_FUTURE __assoc_state_alloc<_Rp&, _Alloc>
Howard Hinnantc834c512011-11-29 18:15:50 +0000784 : public __assoc_state<_Rp&>
Howard Hinnantf4712b92010-08-28 21:01:06 +0000785{
Howard Hinnantc834c512011-11-29 18:15:50 +0000786 typedef __assoc_state<_Rp&> base;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000787 _Alloc __alloc_;
788
Howard Hinnant719bda32011-05-28 14:41:13 +0000789 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnantf4712b92010-08-28 21:01:06 +0000790public:
Howard Hinnant684902d2010-09-22 14:16:26 +0000791 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantf4712b92010-08-28 21:01:06 +0000792 explicit __assoc_state_alloc(const _Alloc& __a)
793 : __alloc_(__a) {}
794};
795
Howard Hinnantc834c512011-11-29 18:15:50 +0000796template <class _Rp, class _Alloc>
Howard Hinnantf4712b92010-08-28 21:01:06 +0000797void
Howard Hinnantc834c512011-11-29 18:15:50 +0000798__assoc_state_alloc<_Rp&, _Alloc>::__on_zero_shared() _NOEXCEPT
Howard Hinnantf4712b92010-08-28 21:01:06 +0000799{
Eric Fiselierf8898c82015-02-05 23:01:40 +0000800 typedef typename __allocator_traits_rebind<_Alloc, __assoc_state_alloc>::type _Al;
801 typedef allocator_traits<_Al> _ATraits;
Eric Fiselier0d109272014-10-23 06:24:45 +0000802 typedef pointer_traits<typename _ATraits::pointer> _PTraits;
Eric Fiselierf8898c82015-02-05 23:01:40 +0000803 _Al __a(__alloc_);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000804 this->~__assoc_state_alloc();
Eric Fiselier0d109272014-10-23 06:24:45 +0000805 __a.deallocate(_PTraits::pointer_to(*this), 1);
Howard Hinnantf4712b92010-08-28 21:01:06 +0000806}
807
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000808template <class _Alloc>
Mehdi Amini228053d2017-05-04 17:08:54 +0000809class _LIBCPP_AVAILABILITY_FUTURE __assoc_sub_state_alloc
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000810 : public __assoc_sub_state
811{
812 typedef __assoc_sub_state base;
813 _Alloc __alloc_;
814
Howard Hinnant719bda32011-05-28 14:41:13 +0000815 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000816public:
Howard Hinnant684902d2010-09-22 14:16:26 +0000817 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000818 explicit __assoc_sub_state_alloc(const _Alloc& __a)
819 : __alloc_(__a) {}
820};
821
822template <class _Alloc>
823void
Howard Hinnant719bda32011-05-28 14:41:13 +0000824__assoc_sub_state_alloc<_Alloc>::__on_zero_shared() _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000825{
Eric Fiselierf8898c82015-02-05 23:01:40 +0000826 typedef typename __allocator_traits_rebind<_Alloc, __assoc_sub_state_alloc>::type _Al;
827 typedef allocator_traits<_Al> _ATraits;
Eric Fiselier0d109272014-10-23 06:24:45 +0000828 typedef pointer_traits<typename _ATraits::pointer> _PTraits;
Eric Fiselierf8898c82015-02-05 23:01:40 +0000829 _Al __a(__alloc_);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000830 this->~__assoc_sub_state_alloc();
Eric Fiselier0d109272014-10-23 06:24:45 +0000831 __a.deallocate(_PTraits::pointer_to(*this), 1);
Howard Hinnant3820f6b2010-08-27 20:10:19 +0000832}
833
Howard Hinnantc834c512011-11-29 18:15:50 +0000834template <class _Rp, class _Fp>
Mehdi Amini228053d2017-05-04 17:08:54 +0000835class _LIBCPP_AVAILABILITY_FUTURE __deferred_assoc_state
Howard Hinnantc834c512011-11-29 18:15:50 +0000836 : public __assoc_state<_Rp>
Howard Hinnantccdd2032010-08-30 18:46:21 +0000837{
Howard Hinnantc834c512011-11-29 18:15:50 +0000838 typedef __assoc_state<_Rp> base;
Howard Hinnantccdd2032010-08-30 18:46:21 +0000839
Howard Hinnantc834c512011-11-29 18:15:50 +0000840 _Fp __func_;
Howard Hinnantccdd2032010-08-30 18:46:21 +0000841
842public:
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000843 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +0000844 explicit __deferred_assoc_state(_Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +0000845
846 virtual void __execute();
847};
848
Howard Hinnantc834c512011-11-29 18:15:50 +0000849template <class _Rp, class _Fp>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000850inline
Howard Hinnantc834c512011-11-29 18:15:50 +0000851__deferred_assoc_state<_Rp, _Fp>::__deferred_assoc_state(_Fp&& __f)
852 : __func_(_VSTD::forward<_Fp>(__f))
Howard Hinnantccdd2032010-08-30 18:46:21 +0000853{
854 this->__set_deferred();
855}
856
Howard Hinnantc834c512011-11-29 18:15:50 +0000857template <class _Rp, class _Fp>
Howard Hinnantccdd2032010-08-30 18:46:21 +0000858void
Howard Hinnantc834c512011-11-29 18:15:50 +0000859__deferred_assoc_state<_Rp, _Fp>::__execute()
Howard Hinnantccdd2032010-08-30 18:46:21 +0000860{
861#ifndef _LIBCPP_NO_EXCEPTIONS
862 try
863 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400864#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +0000865 this->set_value(__func_());
866#ifndef _LIBCPP_NO_EXCEPTIONS
867 }
868 catch (...)
869 {
870 this->set_exception(current_exception());
871 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400872#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +0000873}
874
Howard Hinnantc834c512011-11-29 18:15:50 +0000875template <class _Fp>
Mehdi Amini228053d2017-05-04 17:08:54 +0000876class _LIBCPP_AVAILABILITY_FUTURE __deferred_assoc_state<void, _Fp>
Howard Hinnantccdd2032010-08-30 18:46:21 +0000877 : public __assoc_sub_state
878{
879 typedef __assoc_sub_state base;
880
Howard Hinnantc834c512011-11-29 18:15:50 +0000881 _Fp __func_;
Howard Hinnantccdd2032010-08-30 18:46:21 +0000882
883public:
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000884 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +0000885 explicit __deferred_assoc_state(_Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +0000886
887 virtual void __execute();
888};
889
Howard Hinnantc834c512011-11-29 18:15:50 +0000890template <class _Fp>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000891inline
Howard Hinnantc834c512011-11-29 18:15:50 +0000892__deferred_assoc_state<void, _Fp>::__deferred_assoc_state(_Fp&& __f)
893 : __func_(_VSTD::forward<_Fp>(__f))
Howard Hinnantccdd2032010-08-30 18:46:21 +0000894{
895 this->__set_deferred();
896}
897
Howard Hinnantc834c512011-11-29 18:15:50 +0000898template <class _Fp>
Howard Hinnantccdd2032010-08-30 18:46:21 +0000899void
Howard Hinnantc834c512011-11-29 18:15:50 +0000900__deferred_assoc_state<void, _Fp>::__execute()
Howard Hinnantccdd2032010-08-30 18:46:21 +0000901{
902#ifndef _LIBCPP_NO_EXCEPTIONS
903 try
904 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400905#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +0000906 __func_();
907 this->set_value();
908#ifndef _LIBCPP_NO_EXCEPTIONS
909 }
910 catch (...)
911 {
912 this->set_exception(current_exception());
913 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400914#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +0000915}
916
Howard Hinnantc834c512011-11-29 18:15:50 +0000917template <class _Rp, class _Fp>
Mehdi Amini228053d2017-05-04 17:08:54 +0000918class _LIBCPP_AVAILABILITY_FUTURE __async_assoc_state
Howard Hinnantc834c512011-11-29 18:15:50 +0000919 : public __assoc_state<_Rp>
Howard Hinnant95cfd872011-05-19 15:05:04 +0000920{
Howard Hinnantc834c512011-11-29 18:15:50 +0000921 typedef __assoc_state<_Rp> base;
Howard Hinnant95cfd872011-05-19 15:05:04 +0000922
Howard Hinnantc834c512011-11-29 18:15:50 +0000923 _Fp __func_;
Howard Hinnant95cfd872011-05-19 15:05:04 +0000924
Howard Hinnant719bda32011-05-28 14:41:13 +0000925 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnant95cfd872011-05-19 15:05:04 +0000926public:
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000927 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +0000928 explicit __async_assoc_state(_Fp&& __f);
Howard Hinnant95cfd872011-05-19 15:05:04 +0000929
930 virtual void __execute();
931};
932
Howard Hinnantc834c512011-11-29 18:15:50 +0000933template <class _Rp, class _Fp>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000934inline
Howard Hinnantc834c512011-11-29 18:15:50 +0000935__async_assoc_state<_Rp, _Fp>::__async_assoc_state(_Fp&& __f)
936 : __func_(_VSTD::forward<_Fp>(__f))
Howard Hinnant95cfd872011-05-19 15:05:04 +0000937{
938}
939
Howard Hinnantc834c512011-11-29 18:15:50 +0000940template <class _Rp, class _Fp>
Howard Hinnant95cfd872011-05-19 15:05:04 +0000941void
Howard Hinnantc834c512011-11-29 18:15:50 +0000942__async_assoc_state<_Rp, _Fp>::__execute()
Howard Hinnant95cfd872011-05-19 15:05:04 +0000943{
944#ifndef _LIBCPP_NO_EXCEPTIONS
945 try
946 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400947#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnant95cfd872011-05-19 15:05:04 +0000948 this->set_value(__func_());
949#ifndef _LIBCPP_NO_EXCEPTIONS
950 }
951 catch (...)
952 {
953 this->set_exception(current_exception());
954 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400955#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnant95cfd872011-05-19 15:05:04 +0000956}
957
Howard Hinnantc834c512011-11-29 18:15:50 +0000958template <class _Rp, class _Fp>
Howard Hinnant95cfd872011-05-19 15:05:04 +0000959void
Howard Hinnantc834c512011-11-29 18:15:50 +0000960__async_assoc_state<_Rp, _Fp>::__on_zero_shared() _NOEXCEPT
Howard Hinnant95cfd872011-05-19 15:05:04 +0000961{
962 this->wait();
963 base::__on_zero_shared();
964}
965
Howard Hinnantc834c512011-11-29 18:15:50 +0000966template <class _Fp>
Mehdi Amini228053d2017-05-04 17:08:54 +0000967class _LIBCPP_AVAILABILITY_FUTURE __async_assoc_state<void, _Fp>
Howard Hinnant95cfd872011-05-19 15:05:04 +0000968 : public __assoc_sub_state
969{
970 typedef __assoc_sub_state base;
971
Howard Hinnantc834c512011-11-29 18:15:50 +0000972 _Fp __func_;
Howard Hinnant95cfd872011-05-19 15:05:04 +0000973
Howard Hinnant719bda32011-05-28 14:41:13 +0000974 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnant95cfd872011-05-19 15:05:04 +0000975public:
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000976 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +0000977 explicit __async_assoc_state(_Fp&& __f);
Howard Hinnant95cfd872011-05-19 15:05:04 +0000978
979 virtual void __execute();
980};
981
Howard Hinnantc834c512011-11-29 18:15:50 +0000982template <class _Fp>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +0000983inline
Howard Hinnantc834c512011-11-29 18:15:50 +0000984__async_assoc_state<void, _Fp>::__async_assoc_state(_Fp&& __f)
985 : __func_(_VSTD::forward<_Fp>(__f))
Howard Hinnant95cfd872011-05-19 15:05:04 +0000986{
987}
988
Howard Hinnantc834c512011-11-29 18:15:50 +0000989template <class _Fp>
Howard Hinnant95cfd872011-05-19 15:05:04 +0000990void
Howard Hinnantc834c512011-11-29 18:15:50 +0000991__async_assoc_state<void, _Fp>::__execute()
Howard Hinnant95cfd872011-05-19 15:05:04 +0000992{
993#ifndef _LIBCPP_NO_EXCEPTIONS
994 try
995 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -0400996#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnant95cfd872011-05-19 15:05:04 +0000997 __func_();
998 this->set_value();
999#ifndef _LIBCPP_NO_EXCEPTIONS
1000 }
1001 catch (...)
1002 {
1003 this->set_exception(current_exception());
1004 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04001005#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnant95cfd872011-05-19 15:05:04 +00001006}
1007
Howard Hinnantc834c512011-11-29 18:15:50 +00001008template <class _Fp>
Howard Hinnant95cfd872011-05-19 15:05:04 +00001009void
Howard Hinnantc834c512011-11-29 18:15:50 +00001010__async_assoc_state<void, _Fp>::__on_zero_shared() _NOEXCEPT
Howard Hinnant95cfd872011-05-19 15:05:04 +00001011{
1012 this->wait();
1013 base::__on_zero_shared();
1014}
1015
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00001016template <class _Rp> class _LIBCPP_TEMPLATE_VIS promise;
1017template <class _Rp> class _LIBCPP_TEMPLATE_VIS shared_future;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001018
1019// future
1020
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00001021template <class _Rp> class _LIBCPP_TEMPLATE_VIS future;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001022
Howard Hinnantc834c512011-11-29 18:15:50 +00001023template <class _Rp, class _Fp>
Louis Dionne3b967d02019-12-10 18:00:42 -05001024_LIBCPP_INLINE_VISIBILITY future<_Rp>
Howard Hinnantc834c512011-11-29 18:15:50 +00001025__make_deferred_assoc_state(_Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001026
Howard Hinnantc834c512011-11-29 18:15:50 +00001027template <class _Rp, class _Fp>
Louis Dionne3b967d02019-12-10 18:00:42 -05001028_LIBCPP_INLINE_VISIBILITY future<_Rp>
Howard Hinnantc834c512011-11-29 18:15:50 +00001029__make_async_assoc_state(_Fp&& __f);
Howard Hinnant95cfd872011-05-19 15:05:04 +00001030
Howard Hinnantc834c512011-11-29 18:15:50 +00001031template <class _Rp>
Mehdi Amini228053d2017-05-04 17:08:54 +00001032class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE future
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001033{
Howard Hinnantc834c512011-11-29 18:15:50 +00001034 __assoc_state<_Rp>* __state_;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001035
Howard Hinnantc834c512011-11-29 18:15:50 +00001036 explicit future(__assoc_state<_Rp>* __state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001037
1038 template <class> friend class promise;
Howard Hinnant92646c42010-09-03 18:39:25 +00001039 template <class> friend class shared_future;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001040
Howard Hinnantc834c512011-11-29 18:15:50 +00001041 template <class _R1, class _Fp>
1042 friend future<_R1> __make_deferred_assoc_state(_Fp&& __f);
1043 template <class _R1, class _Fp>
1044 friend future<_R1> __make_async_assoc_state(_Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001045
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001046public:
Howard Hinnant684902d2010-09-22 14:16:26 +00001047 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001048 future() _NOEXCEPT : __state_(nullptr) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001049 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001050 future(future&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001051 : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1052 future(const future&) = delete;
1053 future& operator=(const future&) = delete;
Howard Hinnant684902d2010-09-22 14:16:26 +00001054 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001055 future& operator=(future&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001056 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05001057 future(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001058 return *this;
1059 }
Louis Dionne7b844362020-07-30 09:42:23 -04001060
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001061 ~future();
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00001062 _LIBCPP_INLINE_VISIBILITY
Marshall Clow79e02112017-01-24 23:28:25 +00001063 shared_future<_Rp> share() _NOEXCEPT;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001064
1065 // retrieving the value
Howard Hinnantc834c512011-11-29 18:15:50 +00001066 _Rp get();
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001067
Howard Hinnant684902d2010-09-22 14:16:26 +00001068 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001069 void swap(future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001070
1071 // functions to check state
Howard Hinnant684902d2010-09-22 14:16:26 +00001072 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001073 bool valid() const _NOEXCEPT {return __state_ != nullptr;}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001074
Howard Hinnant684902d2010-09-22 14:16:26 +00001075 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001076 void wait() const {__state_->wait();}
1077 template <class _Rep, class _Period>
Howard Hinnant684902d2010-09-22 14:16:26 +00001078 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001079 future_status
1080 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
1081 {return __state_->wait_for(__rel_time);}
1082 template <class _Clock, class _Duration>
Howard Hinnant684902d2010-09-22 14:16:26 +00001083 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001084 future_status
1085 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
1086 {return __state_->wait_until(__abs_time);}
1087};
1088
Howard Hinnantc834c512011-11-29 18:15:50 +00001089template <class _Rp>
1090future<_Rp>::future(__assoc_state<_Rp>* __state)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001091 : __state_(__state)
1092{
Louis Dionne2c0d2262018-08-24 14:00:59 +00001093 __state_->__attach_future();
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001094}
1095
Howard Hinnantccdd2032010-08-30 18:46:21 +00001096struct __release_shared_count
1097{
1098 void operator()(__shared_count* p) {p->__release_shared();}
1099};
1100
Howard Hinnantc834c512011-11-29 18:15:50 +00001101template <class _Rp>
1102future<_Rp>::~future()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001103{
1104 if (__state_)
1105 __state_->__release_shared();
1106}
1107
Howard Hinnantc834c512011-11-29 18:15:50 +00001108template <class _Rp>
1109_Rp
1110future<_Rp>::get()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001111{
Howard Hinnantccdd2032010-08-30 18:46:21 +00001112 unique_ptr<__shared_count, __release_shared_count> __(__state_);
Howard Hinnantc834c512011-11-29 18:15:50 +00001113 __assoc_state<_Rp>* __s = __state_;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001114 __state_ = nullptr;
1115 return __s->move();
1116}
1117
Howard Hinnantc834c512011-11-29 18:15:50 +00001118template <class _Rp>
Mehdi Amini228053d2017-05-04 17:08:54 +00001119class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE future<_Rp&>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001120{
Howard Hinnantc834c512011-11-29 18:15:50 +00001121 __assoc_state<_Rp&>* __state_;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001122
Howard Hinnantc834c512011-11-29 18:15:50 +00001123 explicit future(__assoc_state<_Rp&>* __state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001124
1125 template <class> friend class promise;
Howard Hinnant92646c42010-09-03 18:39:25 +00001126 template <class> friend class shared_future;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001127
Howard Hinnantc834c512011-11-29 18:15:50 +00001128 template <class _R1, class _Fp>
1129 friend future<_R1> __make_deferred_assoc_state(_Fp&& __f);
1130 template <class _R1, class _Fp>
1131 friend future<_R1> __make_async_assoc_state(_Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001132
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001133public:
Howard Hinnant684902d2010-09-22 14:16:26 +00001134 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001135 future() _NOEXCEPT : __state_(nullptr) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001136 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001137 future(future&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001138 : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1139 future(const future&) = delete;
1140 future& operator=(const future&) = delete;
Howard Hinnant684902d2010-09-22 14:16:26 +00001141 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001142 future& operator=(future&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001143 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05001144 future(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001145 return *this;
1146 }
Louis Dionne7b844362020-07-30 09:42:23 -04001147
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001148 ~future();
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00001149 _LIBCPP_INLINE_VISIBILITY
Marshall Clow79e02112017-01-24 23:28:25 +00001150 shared_future<_Rp&> share() _NOEXCEPT;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001151
1152 // retrieving the value
Howard Hinnantc834c512011-11-29 18:15:50 +00001153 _Rp& get();
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001154
Howard Hinnant684902d2010-09-22 14:16:26 +00001155 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001156 void swap(future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001157
1158 // functions to check state
Howard Hinnant684902d2010-09-22 14:16:26 +00001159 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001160 bool valid() const _NOEXCEPT {return __state_ != nullptr;}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001161
Howard Hinnant684902d2010-09-22 14:16:26 +00001162 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001163 void wait() const {__state_->wait();}
1164 template <class _Rep, class _Period>
Howard Hinnant684902d2010-09-22 14:16:26 +00001165 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001166 future_status
1167 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
1168 {return __state_->wait_for(__rel_time);}
1169 template <class _Clock, class _Duration>
Howard Hinnant684902d2010-09-22 14:16:26 +00001170 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001171 future_status
1172 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
1173 {return __state_->wait_until(__abs_time);}
1174};
1175
Howard Hinnantc834c512011-11-29 18:15:50 +00001176template <class _Rp>
1177future<_Rp&>::future(__assoc_state<_Rp&>* __state)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001178 : __state_(__state)
1179{
Louis Dionne2c0d2262018-08-24 14:00:59 +00001180 __state_->__attach_future();
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001181}
1182
Howard Hinnantc834c512011-11-29 18:15:50 +00001183template <class _Rp>
1184future<_Rp&>::~future()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001185{
1186 if (__state_)
1187 __state_->__release_shared();
1188}
1189
Howard Hinnantc834c512011-11-29 18:15:50 +00001190template <class _Rp>
1191_Rp&
1192future<_Rp&>::get()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001193{
Howard Hinnantccdd2032010-08-30 18:46:21 +00001194 unique_ptr<__shared_count, __release_shared_count> __(__state_);
Howard Hinnantc834c512011-11-29 18:15:50 +00001195 __assoc_state<_Rp&>* __s = __state_;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001196 __state_ = nullptr;
1197 return __s->copy();
1198}
1199
1200template <>
Mehdi Amini228053d2017-05-04 17:08:54 +00001201class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE future<void>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001202{
1203 __assoc_sub_state* __state_;
1204
1205 explicit future(__assoc_sub_state* __state);
1206
1207 template <class> friend class promise;
Howard Hinnant92646c42010-09-03 18:39:25 +00001208 template <class> friend class shared_future;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001209
Howard Hinnantc834c512011-11-29 18:15:50 +00001210 template <class _R1, class _Fp>
1211 friend future<_R1> __make_deferred_assoc_state(_Fp&& __f);
1212 template <class _R1, class _Fp>
1213 friend future<_R1> __make_async_assoc_state(_Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001214
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001215public:
Howard Hinnant684902d2010-09-22 14:16:26 +00001216 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001217 future() _NOEXCEPT : __state_(nullptr) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001218 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001219 future(future&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001220 : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1221 future(const future&) = delete;
1222 future& operator=(const future&) = delete;
Howard Hinnant684902d2010-09-22 14:16:26 +00001223 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001224 future& operator=(future&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001225 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05001226 future(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001227 return *this;
1228 }
Louis Dionne7b844362020-07-30 09:42:23 -04001229
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001230 ~future();
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00001231 _LIBCPP_INLINE_VISIBILITY
Marshall Clow79e02112017-01-24 23:28:25 +00001232 shared_future<void> share() _NOEXCEPT;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001233
1234 // retrieving the value
1235 void get();
1236
Howard Hinnant684902d2010-09-22 14:16:26 +00001237 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001238 void swap(future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001239
1240 // functions to check state
Howard Hinnant684902d2010-09-22 14:16:26 +00001241 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001242 bool valid() const _NOEXCEPT {return __state_ != nullptr;}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001243
Howard Hinnant684902d2010-09-22 14:16:26 +00001244 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001245 void wait() const {__state_->wait();}
1246 template <class _Rep, class _Period>
Howard Hinnant684902d2010-09-22 14:16:26 +00001247 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001248 future_status
1249 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
1250 {return __state_->wait_for(__rel_time);}
1251 template <class _Clock, class _Duration>
Howard Hinnant684902d2010-09-22 14:16:26 +00001252 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001253 future_status
1254 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
1255 {return __state_->wait_until(__abs_time);}
1256};
1257
Howard Hinnantc834c512011-11-29 18:15:50 +00001258template <class _Rp>
Howard Hinnant92646c42010-09-03 18:39:25 +00001259inline _LIBCPP_INLINE_VISIBILITY
1260void
Howard Hinnant22448042012-07-21 17:46:55 +00001261swap(future<_Rp>& __x, future<_Rp>& __y) _NOEXCEPT
Howard Hinnant92646c42010-09-03 18:39:25 +00001262{
1263 __x.swap(__y);
1264}
1265
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001266// promise<R>
1267
Howard Hinnant944510a2011-06-14 19:58:17 +00001268template <class _Callable> class packaged_task;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001269
Howard Hinnantc834c512011-11-29 18:15:50 +00001270template <class _Rp>
Mehdi Amini228053d2017-05-04 17:08:54 +00001271class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE promise
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001272{
Howard Hinnantc834c512011-11-29 18:15:50 +00001273 __assoc_state<_Rp>* __state_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001274
Howard Hinnant684902d2010-09-22 14:16:26 +00001275 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001276 explicit promise(nullptr_t) _NOEXCEPT : __state_(nullptr) {}
Howard Hinnantccdd2032010-08-30 18:46:21 +00001277
1278 template <class> friend class packaged_task;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001279public:
1280 promise();
1281 template <class _Alloc>
1282 promise(allocator_arg_t, const _Alloc& __a);
Howard Hinnant684902d2010-09-22 14:16:26 +00001283 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001284 promise(promise&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001285 : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1286 promise(const promise& __rhs) = delete;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001287 ~promise();
1288
1289 // assignment
Howard Hinnant684902d2010-09-22 14:16:26 +00001290 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001291 promise& operator=(promise&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001292 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05001293 promise(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001294 return *this;
1295 }
1296 promise& operator=(const promise& __rhs) = delete;
Louis Dionne7b844362020-07-30 09:42:23 -04001297
Howard Hinnant684902d2010-09-22 14:16:26 +00001298 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001299 void swap(promise& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001300
1301 // retrieving the result
Howard Hinnantc834c512011-11-29 18:15:50 +00001302 future<_Rp> get_future();
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001303
1304 // setting the result
Howard Hinnantc834c512011-11-29 18:15:50 +00001305 void set_value(const _Rp& __r);
Howard Hinnantc834c512011-11-29 18:15:50 +00001306 void set_value(_Rp&& __r);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001307 void set_exception(exception_ptr __p);
1308
1309 // setting the result with deferred notification
Howard Hinnantc834c512011-11-29 18:15:50 +00001310 void set_value_at_thread_exit(const _Rp& __r);
Howard Hinnantc834c512011-11-29 18:15:50 +00001311 void set_value_at_thread_exit(_Rp&& __r);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001312 void set_exception_at_thread_exit(exception_ptr __p);
1313};
1314
Howard Hinnantc834c512011-11-29 18:15:50 +00001315template <class _Rp>
1316promise<_Rp>::promise()
1317 : __state_(new __assoc_state<_Rp>)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001318{
1319}
1320
Howard Hinnantc834c512011-11-29 18:15:50 +00001321template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001322template <class _Alloc>
Howard Hinnantc834c512011-11-29 18:15:50 +00001323promise<_Rp>::promise(allocator_arg_t, const _Alloc& __a0)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001324{
Eric Fiselier0d109272014-10-23 06:24:45 +00001325 typedef __assoc_state_alloc<_Rp, _Alloc> _State;
1326 typedef typename __allocator_traits_rebind<_Alloc, _State>::type _A2;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001327 typedef __allocator_destructor<_A2> _D2;
1328 _A2 __a(__a0);
Eric Fiselier0d109272014-10-23 06:24:45 +00001329 unique_ptr<_State, _D2> __hold(__a.allocate(1), _D2(__a, 1));
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001330 ::new ((void*)_VSTD::addressof(*__hold.get())) _State(__a0);
Eric Fiselier0d109272014-10-23 06:24:45 +00001331 __state_ = _VSTD::addressof(*__hold.release());
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001332}
1333
Howard Hinnantc834c512011-11-29 18:15:50 +00001334template <class _Rp>
1335promise<_Rp>::~promise()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001336{
1337 if (__state_)
1338 {
1339 if (!__state_->__has_value() && __state_->use_count() > 1)
1340 __state_->set_exception(make_exception_ptr(
1341 future_error(make_error_code(future_errc::broken_promise))
1342 ));
1343 __state_->__release_shared();
1344 }
1345}
1346
Howard Hinnantc834c512011-11-29 18:15:50 +00001347template <class _Rp>
1348future<_Rp>
1349promise<_Rp>::get_future()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001350{
1351 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001352 __throw_future_error(future_errc::no_state);
Howard Hinnantc834c512011-11-29 18:15:50 +00001353 return future<_Rp>(__state_);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001354}
1355
Howard Hinnantc834c512011-11-29 18:15:50 +00001356template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001357void
Howard Hinnantc834c512011-11-29 18:15:50 +00001358promise<_Rp>::set_value(const _Rp& __r)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001359{
1360 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001361 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001362 __state_->set_value(__r);
1363}
1364
Howard Hinnantc834c512011-11-29 18:15:50 +00001365template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001366void
Howard Hinnantc834c512011-11-29 18:15:50 +00001367promise<_Rp>::set_value(_Rp&& __r)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001368{
1369 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001370 __throw_future_error(future_errc::no_state);
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001371 __state_->set_value(_VSTD::move(__r));
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001372}
1373
Howard Hinnantc834c512011-11-29 18:15:50 +00001374template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001375void
Howard Hinnantc834c512011-11-29 18:15:50 +00001376promise<_Rp>::set_exception(exception_ptr __p)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001377{
Marshall Clow2b36f572016-05-16 16:55:32 +00001378 _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception: received nullptr" );
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001379 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001380 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001381 __state_->set_exception(__p);
1382}
1383
Howard Hinnantc834c512011-11-29 18:15:50 +00001384template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001385void
Howard Hinnantc834c512011-11-29 18:15:50 +00001386promise<_Rp>::set_value_at_thread_exit(const _Rp& __r)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001387{
1388 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001389 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001390 __state_->set_value_at_thread_exit(__r);
1391}
1392
Howard Hinnantc834c512011-11-29 18:15:50 +00001393template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001394void
Howard Hinnantc834c512011-11-29 18:15:50 +00001395promise<_Rp>::set_value_at_thread_exit(_Rp&& __r)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001396{
1397 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001398 __throw_future_error(future_errc::no_state);
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001399 __state_->set_value_at_thread_exit(_VSTD::move(__r));
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001400}
1401
Howard Hinnantc834c512011-11-29 18:15:50 +00001402template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001403void
Howard Hinnantc834c512011-11-29 18:15:50 +00001404promise<_Rp>::set_exception_at_thread_exit(exception_ptr __p)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001405{
Eric Fiselier9dce2062016-05-31 01:50:55 +00001406 _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception_at_thread_exit: received nullptr" );
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001407 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001408 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001409 __state_->set_exception_at_thread_exit(__p);
1410}
1411
1412// promise<R&>
1413
Howard Hinnantc834c512011-11-29 18:15:50 +00001414template <class _Rp>
Mehdi Amini228053d2017-05-04 17:08:54 +00001415class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE promise<_Rp&>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001416{
Howard Hinnantc834c512011-11-29 18:15:50 +00001417 __assoc_state<_Rp&>* __state_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001418
Howard Hinnant684902d2010-09-22 14:16:26 +00001419 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001420 explicit promise(nullptr_t) _NOEXCEPT : __state_(nullptr) {}
Howard Hinnantccdd2032010-08-30 18:46:21 +00001421
1422 template <class> friend class packaged_task;
1423
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001424public:
1425 promise();
1426 template <class _Allocator>
1427 promise(allocator_arg_t, const _Allocator& __a);
Howard Hinnant684902d2010-09-22 14:16:26 +00001428 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001429 promise(promise&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001430 : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1431 promise(const promise& __rhs) = delete;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001432 ~promise();
1433
1434 // assignment
Howard Hinnant684902d2010-09-22 14:16:26 +00001435 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001436 promise& operator=(promise&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001437 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05001438 promise(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001439 return *this;
1440 }
1441 promise& operator=(const promise& __rhs) = delete;
Louis Dionne7b844362020-07-30 09:42:23 -04001442
Howard Hinnant684902d2010-09-22 14:16:26 +00001443 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001444 void swap(promise& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001445
1446 // retrieving the result
Howard Hinnantc834c512011-11-29 18:15:50 +00001447 future<_Rp&> get_future();
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001448
1449 // setting the result
Howard Hinnantc834c512011-11-29 18:15:50 +00001450 void set_value(_Rp& __r);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001451 void set_exception(exception_ptr __p);
1452
1453 // setting the result with deferred notification
Howard Hinnantc834c512011-11-29 18:15:50 +00001454 void set_value_at_thread_exit(_Rp&);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001455 void set_exception_at_thread_exit(exception_ptr __p);
1456};
1457
Howard Hinnantc834c512011-11-29 18:15:50 +00001458template <class _Rp>
1459promise<_Rp&>::promise()
1460 : __state_(new __assoc_state<_Rp&>)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001461{
1462}
1463
Howard Hinnantc834c512011-11-29 18:15:50 +00001464template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001465template <class _Alloc>
Howard Hinnantc834c512011-11-29 18:15:50 +00001466promise<_Rp&>::promise(allocator_arg_t, const _Alloc& __a0)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001467{
Eric Fiselier0d109272014-10-23 06:24:45 +00001468 typedef __assoc_state_alloc<_Rp&, _Alloc> _State;
1469 typedef typename __allocator_traits_rebind<_Alloc, _State>::type _A2;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001470 typedef __allocator_destructor<_A2> _D2;
1471 _A2 __a(__a0);
Eric Fiselier0d109272014-10-23 06:24:45 +00001472 unique_ptr<_State, _D2> __hold(__a.allocate(1), _D2(__a, 1));
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001473 ::new ((void*)_VSTD::addressof(*__hold.get())) _State(__a0);
Eric Fiselier0d109272014-10-23 06:24:45 +00001474 __state_ = _VSTD::addressof(*__hold.release());
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001475}
1476
Howard Hinnantc834c512011-11-29 18:15:50 +00001477template <class _Rp>
1478promise<_Rp&>::~promise()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001479{
1480 if (__state_)
1481 {
1482 if (!__state_->__has_value() && __state_->use_count() > 1)
1483 __state_->set_exception(make_exception_ptr(
1484 future_error(make_error_code(future_errc::broken_promise))
1485 ));
1486 __state_->__release_shared();
1487 }
1488}
1489
Howard Hinnantc834c512011-11-29 18:15:50 +00001490template <class _Rp>
1491future<_Rp&>
1492promise<_Rp&>::get_future()
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001493{
1494 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001495 __throw_future_error(future_errc::no_state);
Howard Hinnantc834c512011-11-29 18:15:50 +00001496 return future<_Rp&>(__state_);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001497}
1498
Howard Hinnantc834c512011-11-29 18:15:50 +00001499template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001500void
Howard Hinnantc834c512011-11-29 18:15:50 +00001501promise<_Rp&>::set_value(_Rp& __r)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001502{
1503 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001504 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001505 __state_->set_value(__r);
1506}
1507
Howard Hinnantc834c512011-11-29 18:15:50 +00001508template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001509void
Howard Hinnantc834c512011-11-29 18:15:50 +00001510promise<_Rp&>::set_exception(exception_ptr __p)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001511{
Marshall Clow2b36f572016-05-16 16:55:32 +00001512 _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception: received nullptr" );
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001513 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001514 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001515 __state_->set_exception(__p);
1516}
1517
Howard Hinnantc834c512011-11-29 18:15:50 +00001518template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001519void
Howard Hinnantc834c512011-11-29 18:15:50 +00001520promise<_Rp&>::set_value_at_thread_exit(_Rp& __r)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001521{
1522 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001523 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001524 __state_->set_value_at_thread_exit(__r);
1525}
1526
Howard Hinnantc834c512011-11-29 18:15:50 +00001527template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001528void
Howard Hinnantc834c512011-11-29 18:15:50 +00001529promise<_Rp&>::set_exception_at_thread_exit(exception_ptr __p)
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001530{
Eric Fiselier9dce2062016-05-31 01:50:55 +00001531 _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception_at_thread_exit: received nullptr" );
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001532 if (__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001533 __throw_future_error(future_errc::no_state);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001534 __state_->set_exception_at_thread_exit(__p);
1535}
1536
1537// promise<void>
1538
1539template <>
Mehdi Amini228053d2017-05-04 17:08:54 +00001540class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE promise<void>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001541{
1542 __assoc_sub_state* __state_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001543
Howard Hinnant684902d2010-09-22 14:16:26 +00001544 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001545 explicit promise(nullptr_t) _NOEXCEPT : __state_(nullptr) {}
Howard Hinnantccdd2032010-08-30 18:46:21 +00001546
1547 template <class> friend class packaged_task;
1548
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001549public:
1550 promise();
1551 template <class _Allocator>
Shoaib Meenai55f3a462017-03-02 03:22:18 +00001552 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001553 promise(allocator_arg_t, const _Allocator& __a);
Howard Hinnant684902d2010-09-22 14:16:26 +00001554 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001555 promise(promise&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001556 : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1557 promise(const promise& __rhs) = delete;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001558 ~promise();
1559
1560 // assignment
Howard Hinnant684902d2010-09-22 14:16:26 +00001561 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001562 promise& operator=(promise&& __rhs) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001563 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05001564 promise(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001565 return *this;
1566 }
1567 promise& operator=(const promise& __rhs) = delete;
Louis Dionne7b844362020-07-30 09:42:23 -04001568
Howard Hinnant684902d2010-09-22 14:16:26 +00001569 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001570 void swap(promise& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001571
1572 // retrieving the result
1573 future<void> get_future();
1574
1575 // setting the result
1576 void set_value();
1577 void set_exception(exception_ptr __p);
1578
1579 // setting the result with deferred notification
1580 void set_value_at_thread_exit();
1581 void set_exception_at_thread_exit(exception_ptr __p);
1582};
1583
1584template <class _Alloc>
1585promise<void>::promise(allocator_arg_t, const _Alloc& __a0)
1586{
Eric Fiselier0d109272014-10-23 06:24:45 +00001587 typedef __assoc_sub_state_alloc<_Alloc> _State;
1588 typedef typename __allocator_traits_rebind<_Alloc, _State>::type _A2;
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001589 typedef __allocator_destructor<_A2> _D2;
1590 _A2 __a(__a0);
Eric Fiselier0d109272014-10-23 06:24:45 +00001591 unique_ptr<_State, _D2> __hold(__a.allocate(1), _D2(__a, 1));
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001592 ::new ((void*)_VSTD::addressof(*__hold.get())) _State(__a0);
Eric Fiselier0d109272014-10-23 06:24:45 +00001593 __state_ = _VSTD::addressof(*__hold.release());
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001594}
1595
Howard Hinnantc834c512011-11-29 18:15:50 +00001596template <class _Rp>
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001597inline _LIBCPP_INLINE_VISIBILITY
1598void
Howard Hinnant22448042012-07-21 17:46:55 +00001599swap(promise<_Rp>& __x, promise<_Rp>& __y) _NOEXCEPT
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001600{
1601 __x.swap(__y);
1602}
1603
Howard Hinnantc834c512011-11-29 18:15:50 +00001604template <class _Rp, class _Alloc>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00001605 struct _LIBCPP_TEMPLATE_VIS uses_allocator<promise<_Rp>, _Alloc>
Howard Hinnant684902d2010-09-22 14:16:26 +00001606 : public true_type {};
Howard Hinnant3820f6b2010-08-27 20:10:19 +00001607
Howard Hinnantccdd2032010-08-30 18:46:21 +00001608// packaged_task
1609
1610template<class _Fp> class __packaged_task_base;
1611
Howard Hinnantc834c512011-11-29 18:15:50 +00001612template<class _Rp, class ..._ArgTypes>
Mehdi Amini228053d2017-05-04 17:08:54 +00001613class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_base<_Rp(_ArgTypes...)>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001614{
1615 __packaged_task_base(const __packaged_task_base&);
1616 __packaged_task_base& operator=(const __packaged_task_base&);
1617public:
Howard Hinnant684902d2010-09-22 14:16:26 +00001618 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantccdd2032010-08-30 18:46:21 +00001619 __packaged_task_base() {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001620 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantccdd2032010-08-30 18:46:21 +00001621 virtual ~__packaged_task_base() {}
Howard Hinnant22448042012-07-21 17:46:55 +00001622 virtual void __move_to(__packaged_task_base*) _NOEXCEPT = 0;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001623 virtual void destroy() = 0;
1624 virtual void destroy_deallocate() = 0;
Howard Hinnantc834c512011-11-29 18:15:50 +00001625 virtual _Rp operator()(_ArgTypes&& ...) = 0;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001626};
1627
1628template<class _FD, class _Alloc, class _FB> class __packaged_task_func;
1629
Howard Hinnantc834c512011-11-29 18:15:50 +00001630template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
Mehdi Amini228053d2017-05-04 17:08:54 +00001631class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>
Howard Hinnantc834c512011-11-29 18:15:50 +00001632 : public __packaged_task_base<_Rp(_ArgTypes...)>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001633{
Howard Hinnantc834c512011-11-29 18:15:50 +00001634 __compressed_pair<_Fp, _Alloc> __f_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001635public:
Howard Hinnant684902d2010-09-22 14:16:26 +00001636 _LIBCPP_INLINE_VISIBILITY
Eric Fiselier33ebfb62019-12-16 18:23:39 -05001637 explicit __packaged_task_func(const _Fp& __f) : __f_(__f, __default_init_tag()) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001638 _LIBCPP_INLINE_VISIBILITY
Eric Fiselier33ebfb62019-12-16 18:23:39 -05001639 explicit __packaged_task_func(_Fp&& __f) : __f_(_VSTD::move(__f), __default_init_tag()) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001640 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00001641 __packaged_task_func(const _Fp& __f, const _Alloc& __a)
Howard Hinnantccdd2032010-08-30 18:46:21 +00001642 : __f_(__f, __a) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001643 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00001644 __packaged_task_func(_Fp&& __f, const _Alloc& __a)
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001645 : __f_(_VSTD::move(__f), __a) {}
Howard Hinnant22448042012-07-21 17:46:55 +00001646 virtual void __move_to(__packaged_task_base<_Rp(_ArgTypes...)>*) _NOEXCEPT;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001647 virtual void destroy();
1648 virtual void destroy_deallocate();
Howard Hinnantc834c512011-11-29 18:15:50 +00001649 virtual _Rp operator()(_ArgTypes&& ... __args);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001650};
1651
Howard Hinnantc834c512011-11-29 18:15:50 +00001652template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001653void
Howard Hinnantc834c512011-11-29 18:15:50 +00001654__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__move_to(
Howard Hinnant22448042012-07-21 17:46:55 +00001655 __packaged_task_base<_Rp(_ArgTypes...)>* __p) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00001656{
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001657 ::new ((void*)__p) __packaged_task_func(_VSTD::move(__f_.first()), _VSTD::move(__f_.second()));
Howard Hinnantccdd2032010-08-30 18:46:21 +00001658}
1659
Howard Hinnantc834c512011-11-29 18:15:50 +00001660template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001661void
Howard Hinnantc834c512011-11-29 18:15:50 +00001662__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy()
Howard Hinnantccdd2032010-08-30 18:46:21 +00001663{
Howard Hinnantc834c512011-11-29 18:15:50 +00001664 __f_.~__compressed_pair<_Fp, _Alloc>();
Howard Hinnantccdd2032010-08-30 18:46:21 +00001665}
1666
Howard Hinnantc834c512011-11-29 18:15:50 +00001667template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001668void
Howard Hinnantc834c512011-11-29 18:15:50 +00001669__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy_deallocate()
Howard Hinnantccdd2032010-08-30 18:46:21 +00001670{
Eric Fiselier0d109272014-10-23 06:24:45 +00001671 typedef typename __allocator_traits_rebind<_Alloc, __packaged_task_func>::type _Ap;
1672 typedef allocator_traits<_Ap> _ATraits;
1673 typedef pointer_traits<typename _ATraits::pointer> _PTraits;
Howard Hinnantc834c512011-11-29 18:15:50 +00001674 _Ap __a(__f_.second());
1675 __f_.~__compressed_pair<_Fp, _Alloc>();
Eric Fiselier0d109272014-10-23 06:24:45 +00001676 __a.deallocate(_PTraits::pointer_to(*this), 1);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001677}
1678
Howard Hinnantc834c512011-11-29 18:15:50 +00001679template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
1680_Rp
1681__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::operator()(_ArgTypes&& ... __arg)
Howard Hinnantccdd2032010-08-30 18:46:21 +00001682{
Arthur O'Dwyer34465da2020-12-15 19:32:29 -05001683 return _VSTD::__invoke(__f_.first(), _VSTD::forward<_ArgTypes>(__arg)...);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001684}
1685
Howard Hinnant944510a2011-06-14 19:58:17 +00001686template <class _Callable> class __packaged_task_function;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001687
Howard Hinnantc834c512011-11-29 18:15:50 +00001688template<class _Rp, class ..._ArgTypes>
Mehdi Amini228053d2017-05-04 17:08:54 +00001689class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_function<_Rp(_ArgTypes...)>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001690{
Howard Hinnantc834c512011-11-29 18:15:50 +00001691 typedef __packaged_task_base<_Rp(_ArgTypes...)> __base;
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001692
1693 _LIBCPP_INLINE_VISIBILITY _LIBCPP_NO_CFI
1694 __base* __get_buf() { return (__base*)&__buf_; }
1695
Howard Hinnant022c7482013-01-21 17:26:55 +00001696 typename aligned_storage<3*sizeof(void*)>::type __buf_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001697 __base* __f_;
1698
1699public:
Howard Hinnantc834c512011-11-29 18:15:50 +00001700 typedef _Rp result_type;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001701
1702 // construct/copy/destroy:
Howard Hinnant684902d2010-09-22 14:16:26 +00001703 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001704 __packaged_task_function() _NOEXCEPT : __f_(nullptr) {}
Howard Hinnantc834c512011-11-29 18:15:50 +00001705 template<class _Fp>
1706 __packaged_task_function(_Fp&& __f);
1707 template<class _Fp, class _Alloc>
1708 __packaged_task_function(allocator_arg_t, const _Alloc& __a, _Fp&& __f);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001709
Howard Hinnant22448042012-07-21 17:46:55 +00001710 __packaged_task_function(__packaged_task_function&&) _NOEXCEPT;
1711 __packaged_task_function& operator=(__packaged_task_function&&) _NOEXCEPT;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001712
1713 __packaged_task_function(const __packaged_task_function&) = delete;
1714 __packaged_task_function& operator=(const __packaged_task_function&) = delete;
1715
1716 ~__packaged_task_function();
1717
Howard Hinnant22448042012-07-21 17:46:55 +00001718 void swap(__packaged_task_function&) _NOEXCEPT;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001719
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00001720 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00001721 _Rp operator()(_ArgTypes...) const;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001722};
1723
Howard Hinnantc834c512011-11-29 18:15:50 +00001724template<class _Rp, class ..._ArgTypes>
Howard Hinnant22448042012-07-21 17:46:55 +00001725__packaged_task_function<_Rp(_ArgTypes...)>::__packaged_task_function(__packaged_task_function&& __f) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00001726{
1727 if (__f.__f_ == nullptr)
1728 __f_ = nullptr;
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001729 else if (__f.__f_ == __f.__get_buf())
Howard Hinnantccdd2032010-08-30 18:46:21 +00001730 {
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001731 __f.__f_->__move_to(__get_buf());
Howard Hinnantccdd2032010-08-30 18:46:21 +00001732 __f_ = (__base*)&__buf_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001733 }
1734 else
1735 {
1736 __f_ = __f.__f_;
1737 __f.__f_ = nullptr;
1738 }
1739}
1740
Howard Hinnantc834c512011-11-29 18:15:50 +00001741template<class _Rp, class ..._ArgTypes>
1742template <class _Fp>
1743__packaged_task_function<_Rp(_ArgTypes...)>::__packaged_task_function(_Fp&& __f)
Howard Hinnantccdd2032010-08-30 18:46:21 +00001744 : __f_(nullptr)
1745{
Marshall Clow733d60e2014-04-07 13:32:26 +00001746 typedef typename remove_reference<typename decay<_Fp>::type>::type _FR;
Howard Hinnantc834c512011-11-29 18:15:50 +00001747 typedef __packaged_task_func<_FR, allocator<_FR>, _Rp(_ArgTypes...)> _FF;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001748 if (sizeof(_FF) <= sizeof(__buf_))
1749 {
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001750 ::new ((void*)&__buf_) _FF(_VSTD::forward<_Fp>(__f));
Howard Hinnantccdd2032010-08-30 18:46:21 +00001751 __f_ = (__base*)&__buf_;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001752 }
1753 else
1754 {
Howard Hinnantc834c512011-11-29 18:15:50 +00001755 typedef allocator<_FF> _Ap;
1756 _Ap __a;
1757 typedef __allocator_destructor<_Ap> _Dp;
1758 unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001759 ::new ((void*)__hold.get()) _FF(_VSTD::forward<_Fp>(__f), allocator<_FR>(__a));
Howard Hinnantccdd2032010-08-30 18:46:21 +00001760 __f_ = __hold.release();
1761 }
1762}
1763
Howard Hinnantc834c512011-11-29 18:15:50 +00001764template<class _Rp, class ..._ArgTypes>
1765template <class _Fp, class _Alloc>
1766__packaged_task_function<_Rp(_ArgTypes...)>::__packaged_task_function(
1767 allocator_arg_t, const _Alloc& __a0, _Fp&& __f)
Howard Hinnantccdd2032010-08-30 18:46:21 +00001768 : __f_(nullptr)
1769{
Marshall Clow733d60e2014-04-07 13:32:26 +00001770 typedef typename remove_reference<typename decay<_Fp>::type>::type _FR;
Howard Hinnantc834c512011-11-29 18:15:50 +00001771 typedef __packaged_task_func<_FR, _Alloc, _Rp(_ArgTypes...)> _FF;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001772 if (sizeof(_FF) <= sizeof(__buf_))
1773 {
1774 __f_ = (__base*)&__buf_;
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001775 ::new ((void*)__f_) _FF(_VSTD::forward<_Fp>(__f));
Howard Hinnantccdd2032010-08-30 18:46:21 +00001776 }
1777 else
1778 {
Eric Fiselier0d109272014-10-23 06:24:45 +00001779 typedef typename __allocator_traits_rebind<_Alloc, _FF>::type _Ap;
Howard Hinnantc834c512011-11-29 18:15:50 +00001780 _Ap __a(__a0);
1781 typedef __allocator_destructor<_Ap> _Dp;
1782 unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
Arthur O'Dwyer0c4472a2020-12-11 20:30:28 -05001783 ::new ((void*)_VSTD::addressof(*__hold.get()))
Eric Fiselier0d109272014-10-23 06:24:45 +00001784 _FF(_VSTD::forward<_Fp>(__f), _Alloc(__a));
1785 __f_ = _VSTD::addressof(*__hold.release());
Howard Hinnantccdd2032010-08-30 18:46:21 +00001786 }
1787}
1788
Howard Hinnantc834c512011-11-29 18:15:50 +00001789template<class _Rp, class ..._ArgTypes>
1790__packaged_task_function<_Rp(_ArgTypes...)>&
Howard Hinnant22448042012-07-21 17:46:55 +00001791__packaged_task_function<_Rp(_ArgTypes...)>::operator=(__packaged_task_function&& __f) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00001792{
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001793 if (__f_ == __get_buf())
Howard Hinnantccdd2032010-08-30 18:46:21 +00001794 __f_->destroy();
1795 else if (__f_)
1796 __f_->destroy_deallocate();
1797 __f_ = nullptr;
1798 if (__f.__f_ == nullptr)
1799 __f_ = nullptr;
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001800 else if (__f.__f_ == __f.__get_buf())
Howard Hinnantccdd2032010-08-30 18:46:21 +00001801 {
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001802 __f.__f_->__move_to(__get_buf());
1803 __f_ = __get_buf();
Howard Hinnantccdd2032010-08-30 18:46:21 +00001804 }
1805 else
1806 {
1807 __f_ = __f.__f_;
1808 __f.__f_ = nullptr;
1809 }
Argyrios Kyrtzidisaf904652012-10-13 02:03:45 +00001810 return *this;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001811}
1812
Howard Hinnantc834c512011-11-29 18:15:50 +00001813template<class _Rp, class ..._ArgTypes>
1814__packaged_task_function<_Rp(_ArgTypes...)>::~__packaged_task_function()
Howard Hinnantccdd2032010-08-30 18:46:21 +00001815{
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001816 if (__f_ == __get_buf())
Howard Hinnantccdd2032010-08-30 18:46:21 +00001817 __f_->destroy();
1818 else if (__f_)
1819 __f_->destroy_deallocate();
1820}
1821
Howard Hinnantc834c512011-11-29 18:15:50 +00001822template<class _Rp, class ..._ArgTypes>
Evgenii Stepanov9dd5fc22020-08-06 11:32:33 -07001823_LIBCPP_NO_CFI
Howard Hinnantccdd2032010-08-30 18:46:21 +00001824void
Howard Hinnant22448042012-07-21 17:46:55 +00001825__packaged_task_function<_Rp(_ArgTypes...)>::swap(__packaged_task_function& __f) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00001826{
1827 if (__f_ == (__base*)&__buf_ && __f.__f_ == (__base*)&__f.__buf_)
1828 {
1829 typename aligned_storage<sizeof(__buf_)>::type __tempbuf;
1830 __base* __t = (__base*)&__tempbuf;
1831 __f_->__move_to(__t);
1832 __f_->destroy();
1833 __f_ = nullptr;
1834 __f.__f_->__move_to((__base*)&__buf_);
1835 __f.__f_->destroy();
1836 __f.__f_ = nullptr;
1837 __f_ = (__base*)&__buf_;
1838 __t->__move_to((__base*)&__f.__buf_);
1839 __t->destroy();
1840 __f.__f_ = (__base*)&__f.__buf_;
1841 }
1842 else if (__f_ == (__base*)&__buf_)
1843 {
1844 __f_->__move_to((__base*)&__f.__buf_);
1845 __f_->destroy();
1846 __f_ = __f.__f_;
1847 __f.__f_ = (__base*)&__f.__buf_;
1848 }
1849 else if (__f.__f_ == (__base*)&__f.__buf_)
1850 {
1851 __f.__f_->__move_to((__base*)&__buf_);
1852 __f.__f_->destroy();
1853 __f.__f_ = __f_;
1854 __f_ = (__base*)&__buf_;
1855 }
1856 else
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001857 _VSTD::swap(__f_, __f.__f_);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001858}
1859
Howard Hinnantc834c512011-11-29 18:15:50 +00001860template<class _Rp, class ..._ArgTypes>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00001861inline
Howard Hinnantc834c512011-11-29 18:15:50 +00001862_Rp
1863__packaged_task_function<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __arg) const
Howard Hinnantccdd2032010-08-30 18:46:21 +00001864{
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001865 return (*__f_)(_VSTD::forward<_ArgTypes>(__arg)...);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001866}
1867
Howard Hinnantc834c512011-11-29 18:15:50 +00001868template<class _Rp, class ..._ArgTypes>
Mehdi Amini228053d2017-05-04 17:08:54 +00001869class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE packaged_task<_Rp(_ArgTypes...)>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001870{
1871public:
Eric Fiselier17f39ed2016-06-01 21:05:53 +00001872 typedef _Rp result_type; // extension
Howard Hinnantccdd2032010-08-30 18:46:21 +00001873
1874private:
1875 __packaged_task_function<result_type(_ArgTypes...)> __f_;
1876 promise<result_type> __p_;
1877
1878public:
1879 // construction and destruction
Howard Hinnant684902d2010-09-22 14:16:26 +00001880 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001881 packaged_task() _NOEXCEPT : __p_(nullptr) {}
Marshall Clow27a55c02013-10-12 22:49:17 +00001882 template <class _Fp,
1883 class = typename enable_if
1884 <
1885 !is_same<
Louis Dionne173f29e2019-05-29 16:01:36 +00001886 typename __uncvref<_Fp>::type,
Marshall Clow27a55c02013-10-12 22:49:17 +00001887 packaged_task
1888 >::value
1889 >::type
1890 >
Howard Hinnant684902d2010-09-22 14:16:26 +00001891 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00001892 explicit packaged_task(_Fp&& __f) : __f_(_VSTD::forward<_Fp>(__f)) {}
Marshall Clowa0a057e2017-11-27 20:47:54 +00001893 template <class _Fp, class _Allocator,
1894 class = typename enable_if
1895 <
1896 !is_same<
Louis Dionne173f29e2019-05-29 16:01:36 +00001897 typename __uncvref<_Fp>::type,
Marshall Clowa0a057e2017-11-27 20:47:54 +00001898 packaged_task
1899 >::value
1900 >::type
1901 >
1902 _LIBCPP_INLINE_VISIBILITY
1903 packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
1904 : __f_(allocator_arg, __a, _VSTD::forward<_Fp>(__f)),
1905 __p_(allocator_arg, __a) {}
Howard Hinnantccdd2032010-08-30 18:46:21 +00001906 // ~packaged_task() = default;
1907
1908 // no copy
Howard Hinnantab500072012-07-21 19:34:12 +00001909 packaged_task(const packaged_task&) = delete;
1910 packaged_task& operator=(const packaged_task&) = delete;
Howard Hinnantccdd2032010-08-30 18:46:21 +00001911
1912 // move support
Howard Hinnant684902d2010-09-22 14:16:26 +00001913 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001914 packaged_task(packaged_task&& __other) _NOEXCEPT
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001915 : __f_(_VSTD::move(__other.__f_)), __p_(_VSTD::move(__other.__p_)) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00001916 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001917 packaged_task& operator=(packaged_task&& __other) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00001918 {
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001919 __f_ = _VSTD::move(__other.__f_);
1920 __p_ = _VSTD::move(__other.__p_);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001921 return *this;
1922 }
Howard Hinnant684902d2010-09-22 14:16:26 +00001923 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001924 void swap(packaged_task& __other) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00001925 {
1926 __f_.swap(__other.__f_);
1927 __p_.swap(__other.__p_);
1928 }
1929
Howard Hinnant684902d2010-09-22 14:16:26 +00001930 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00001931 bool valid() const _NOEXCEPT {return __p_.__state_ != nullptr;}
Howard Hinnantccdd2032010-08-30 18:46:21 +00001932
1933 // result retrieval
Howard Hinnant684902d2010-09-22 14:16:26 +00001934 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantccdd2032010-08-30 18:46:21 +00001935 future<result_type> get_future() {return __p_.get_future();}
1936
1937 // execution
1938 void operator()(_ArgTypes... __args);
1939 void make_ready_at_thread_exit(_ArgTypes... __args);
1940
1941 void reset();
1942};
1943
Howard Hinnantc834c512011-11-29 18:15:50 +00001944template<class _Rp, class ..._ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001945void
Howard Hinnantc834c512011-11-29 18:15:50 +00001946packaged_task<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __args)
Howard Hinnantccdd2032010-08-30 18:46:21 +00001947{
Howard Hinnantccdd2032010-08-30 18:46:21 +00001948 if (__p_.__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001949 __throw_future_error(future_errc::no_state);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001950 if (__p_.__state_->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +00001951 __throw_future_error(future_errc::promise_already_satisfied);
Marshall Clow7b3742d2015-09-03 15:11:32 +00001952#ifndef _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00001953 try
1954 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04001955#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001956 __p_.set_value(__f_(_VSTD::forward<_ArgTypes>(__args)...));
Howard Hinnantccdd2032010-08-30 18:46:21 +00001957#ifndef _LIBCPP_NO_EXCEPTIONS
1958 }
1959 catch (...)
1960 {
1961 __p_.set_exception(current_exception());
1962 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04001963#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00001964}
1965
Howard Hinnantc834c512011-11-29 18:15:50 +00001966template<class _Rp, class ..._ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001967void
Howard Hinnantc834c512011-11-29 18:15:50 +00001968packaged_task<_Rp(_ArgTypes...)>::make_ready_at_thread_exit(_ArgTypes... __args)
Howard Hinnantccdd2032010-08-30 18:46:21 +00001969{
Howard Hinnantccdd2032010-08-30 18:46:21 +00001970 if (__p_.__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00001971 __throw_future_error(future_errc::no_state);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001972 if (__p_.__state_->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +00001973 __throw_future_error(future_errc::promise_already_satisfied);
Marshall Clow7b3742d2015-09-03 15:11:32 +00001974#ifndef _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00001975 try
1976 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04001977#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00001978 __p_.set_value_at_thread_exit(__f_(_VSTD::forward<_ArgTypes>(__args)...));
Howard Hinnantccdd2032010-08-30 18:46:21 +00001979#ifndef _LIBCPP_NO_EXCEPTIONS
1980 }
1981 catch (...)
1982 {
1983 __p_.set_exception_at_thread_exit(current_exception());
1984 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04001985#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00001986}
1987
Howard Hinnantc834c512011-11-29 18:15:50 +00001988template<class _Rp, class ..._ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001989void
Howard Hinnantc834c512011-11-29 18:15:50 +00001990packaged_task<_Rp(_ArgTypes...)>::reset()
Howard Hinnantccdd2032010-08-30 18:46:21 +00001991{
Howard Hinnant9a7d09c2010-11-30 20:23:32 +00001992 if (!valid())
Eric Fiselier43641592015-10-02 21:25:15 +00001993 __throw_future_error(future_errc::no_state);
Howard Hinnantccdd2032010-08-30 18:46:21 +00001994 __p_ = promise<result_type>();
1995}
1996
1997template<class ..._ArgTypes>
Mehdi Amini228053d2017-05-04 17:08:54 +00001998class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE packaged_task<void(_ArgTypes...)>
Howard Hinnantccdd2032010-08-30 18:46:21 +00001999{
2000public:
Eric Fiselier17f39ed2016-06-01 21:05:53 +00002001 typedef void result_type; // extension
Howard Hinnantccdd2032010-08-30 18:46:21 +00002002
2003private:
2004 __packaged_task_function<result_type(_ArgTypes...)> __f_;
2005 promise<result_type> __p_;
2006
2007public:
2008 // construction and destruction
Howard Hinnant684902d2010-09-22 14:16:26 +00002009 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002010 packaged_task() _NOEXCEPT : __p_(nullptr) {}
Marshall Clow27a55c02013-10-12 22:49:17 +00002011 template <class _Fp,
2012 class = typename enable_if
2013 <
2014 !is_same<
Louis Dionne173f29e2019-05-29 16:01:36 +00002015 typename __uncvref<_Fp>::type,
Marshall Clow27a55c02013-10-12 22:49:17 +00002016 packaged_task
2017 >::value
2018 >::type
2019 >
Howard Hinnant684902d2010-09-22 14:16:26 +00002020 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00002021 explicit packaged_task(_Fp&& __f) : __f_(_VSTD::forward<_Fp>(__f)) {}
Marshall Clowa0a057e2017-11-27 20:47:54 +00002022 template <class _Fp, class _Allocator,
2023 class = typename enable_if
2024 <
2025 !is_same<
Louis Dionne173f29e2019-05-29 16:01:36 +00002026 typename __uncvref<_Fp>::type,
Marshall Clowa0a057e2017-11-27 20:47:54 +00002027 packaged_task
2028 >::value
2029 >::type
Louis Dionne173f29e2019-05-29 16:01:36 +00002030 >
Marshall Clowa0a057e2017-11-27 20:47:54 +00002031 _LIBCPP_INLINE_VISIBILITY
2032 packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
2033 : __f_(allocator_arg, __a, _VSTD::forward<_Fp>(__f)),
2034 __p_(allocator_arg, __a) {}
Howard Hinnantccdd2032010-08-30 18:46:21 +00002035 // ~packaged_task() = default;
2036
2037 // no copy
Howard Hinnantab500072012-07-21 19:34:12 +00002038 packaged_task(const packaged_task&) = delete;
2039 packaged_task& operator=(const packaged_task&) = delete;
Howard Hinnantccdd2032010-08-30 18:46:21 +00002040
2041 // move support
Howard Hinnant684902d2010-09-22 14:16:26 +00002042 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002043 packaged_task(packaged_task&& __other) _NOEXCEPT
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002044 : __f_(_VSTD::move(__other.__f_)), __p_(_VSTD::move(__other.__p_)) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00002045 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002046 packaged_task& operator=(packaged_task&& __other) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00002047 {
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002048 __f_ = _VSTD::move(__other.__f_);
2049 __p_ = _VSTD::move(__other.__p_);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002050 return *this;
2051 }
Howard Hinnant684902d2010-09-22 14:16:26 +00002052 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002053 void swap(packaged_task& __other) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00002054 {
2055 __f_.swap(__other.__f_);
2056 __p_.swap(__other.__p_);
2057 }
2058
Howard Hinnant684902d2010-09-22 14:16:26 +00002059 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002060 bool valid() const _NOEXCEPT {return __p_.__state_ != nullptr;}
Howard Hinnantccdd2032010-08-30 18:46:21 +00002061
2062 // result retrieval
Howard Hinnant684902d2010-09-22 14:16:26 +00002063 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantccdd2032010-08-30 18:46:21 +00002064 future<result_type> get_future() {return __p_.get_future();}
2065
2066 // execution
2067 void operator()(_ArgTypes... __args);
2068 void make_ready_at_thread_exit(_ArgTypes... __args);
2069
2070 void reset();
2071};
2072
2073template<class ..._ArgTypes>
2074void
2075packaged_task<void(_ArgTypes...)>::operator()(_ArgTypes... __args)
2076{
Howard Hinnantccdd2032010-08-30 18:46:21 +00002077 if (__p_.__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00002078 __throw_future_error(future_errc::no_state);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002079 if (__p_.__state_->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +00002080 __throw_future_error(future_errc::promise_already_satisfied);
Marshall Clow7b3742d2015-09-03 15:11:32 +00002081#ifndef _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00002082 try
2083 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04002084#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002085 __f_(_VSTD::forward<_ArgTypes>(__args)...);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002086 __p_.set_value();
2087#ifndef _LIBCPP_NO_EXCEPTIONS
2088 }
2089 catch (...)
2090 {
2091 __p_.set_exception(current_exception());
2092 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04002093#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00002094}
2095
2096template<class ..._ArgTypes>
2097void
2098packaged_task<void(_ArgTypes...)>::make_ready_at_thread_exit(_ArgTypes... __args)
2099{
Howard Hinnantccdd2032010-08-30 18:46:21 +00002100 if (__p_.__state_ == nullptr)
Eric Fiselier43641592015-10-02 21:25:15 +00002101 __throw_future_error(future_errc::no_state);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002102 if (__p_.__state_->__has_value())
Eric Fiselier43641592015-10-02 21:25:15 +00002103 __throw_future_error(future_errc::promise_already_satisfied);
Marshall Clow7b3742d2015-09-03 15:11:32 +00002104#ifndef _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00002105 try
2106 {
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04002107#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002108 __f_(_VSTD::forward<_ArgTypes>(__args)...);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002109 __p_.set_value_at_thread_exit();
2110#ifndef _LIBCPP_NO_EXCEPTIONS
2111 }
2112 catch (...)
2113 {
2114 __p_.set_exception_at_thread_exit(current_exception());
2115 }
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04002116#endif // _LIBCPP_NO_EXCEPTIONS
Howard Hinnantccdd2032010-08-30 18:46:21 +00002117}
2118
2119template<class ..._ArgTypes>
2120void
2121packaged_task<void(_ArgTypes...)>::reset()
2122{
Howard Hinnant9a7d09c2010-11-30 20:23:32 +00002123 if (!valid())
Eric Fiselier43641592015-10-02 21:25:15 +00002124 __throw_future_error(future_errc::no_state);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002125 __p_ = promise<result_type>();
2126}
2127
jasonliubdad63b2021-03-24 22:31:58 +00002128template <class _Rp, class... _ArgTypes>
Howard Hinnantccdd2032010-08-30 18:46:21 +00002129inline _LIBCPP_INLINE_VISIBILITY
2130void
jasonliubdad63b2021-03-24 22:31:58 +00002131swap(packaged_task<_Rp(_ArgTypes...)>& __x, packaged_task<_Rp(_ArgTypes...)>& __y) _NOEXCEPT
Howard Hinnantccdd2032010-08-30 18:46:21 +00002132{
2133 __x.swap(__y);
2134}
2135
Marshall Clowa0a057e2017-11-27 20:47:54 +00002136template <class _Callable, class _Alloc>
2137struct _LIBCPP_TEMPLATE_VIS uses_allocator<packaged_task<_Callable>, _Alloc>
2138 : public true_type {};
2139
Howard Hinnantc834c512011-11-29 18:15:50 +00002140template <class _Rp, class _Fp>
Louis Dionne3b967d02019-12-10 18:00:42 -05002141_LIBCPP_INLINE_VISIBILITY future<_Rp>
Howard Hinnantc834c512011-11-29 18:15:50 +00002142__make_deferred_assoc_state(_Fp&& __f)
Howard Hinnantccdd2032010-08-30 18:46:21 +00002143{
Howard Hinnantc834c512011-11-29 18:15:50 +00002144 unique_ptr<__deferred_assoc_state<_Rp, _Fp>, __release_shared_count>
2145 __h(new __deferred_assoc_state<_Rp, _Fp>(_VSTD::forward<_Fp>(__f)));
2146 return future<_Rp>(__h.get());
Howard Hinnantccdd2032010-08-30 18:46:21 +00002147}
2148
Howard Hinnantc834c512011-11-29 18:15:50 +00002149template <class _Rp, class _Fp>
Louis Dionne3b967d02019-12-10 18:00:42 -05002150_LIBCPP_INLINE_VISIBILITY future<_Rp>
Howard Hinnantc834c512011-11-29 18:15:50 +00002151__make_async_assoc_state(_Fp&& __f)
Howard Hinnant95cfd872011-05-19 15:05:04 +00002152{
Howard Hinnantc834c512011-11-29 18:15:50 +00002153 unique_ptr<__async_assoc_state<_Rp, _Fp>, __release_shared_count>
2154 __h(new __async_assoc_state<_Rp, _Fp>(_VSTD::forward<_Fp>(__f)));
2155 _VSTD::thread(&__async_assoc_state<_Rp, _Fp>::__execute, __h.get()).detach();
2156 return future<_Rp>(__h.get());
Howard Hinnant95cfd872011-05-19 15:05:04 +00002157}
2158
Louis Dionne1a1fc9d2020-07-30 10:00:53 -04002159#ifndef _LIBCPP_CXX03_LANG
2160
Howard Hinnantc834c512011-11-29 18:15:50 +00002161template <class _Fp, class... _Args>
Louis Dionne3b967d02019-12-10 18:00:42 -05002162class _LIBCPP_HIDDEN __async_func
Howard Hinnant95cfd872011-05-19 15:05:04 +00002163{
Howard Hinnantc834c512011-11-29 18:15:50 +00002164 tuple<_Fp, _Args...> __f_;
Howard Hinnant95cfd872011-05-19 15:05:04 +00002165
2166public:
Howard Hinnantc834c512011-11-29 18:15:50 +00002167 typedef typename __invoke_of<_Fp, _Args...>::type _Rp;
Howard Hinnant95cfd872011-05-19 15:05:04 +00002168
2169 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00002170 explicit __async_func(_Fp&& __f, _Args&&... __args)
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002171 : __f_(_VSTD::move(__f), _VSTD::move(__args)...) {}
Howard Hinnant95cfd872011-05-19 15:05:04 +00002172
2173 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002174 __async_func(__async_func&& __f) : __f_(_VSTD::move(__f.__f_)) {}
Howard Hinnant95cfd872011-05-19 15:05:04 +00002175
Howard Hinnantc834c512011-11-29 18:15:50 +00002176 _Rp operator()()
Howard Hinnant95cfd872011-05-19 15:05:04 +00002177 {
2178 typedef typename __make_tuple_indices<1+sizeof...(_Args), 1>::type _Index;
2179 return __execute(_Index());
2180 }
2181private:
2182 template <size_t ..._Indices>
Howard Hinnantc834c512011-11-29 18:15:50 +00002183 _Rp
Howard Hinnant95cfd872011-05-19 15:05:04 +00002184 __execute(__tuple_indices<_Indices...>)
2185 {
Arthur O'Dwyer34465da2020-12-15 19:32:29 -05002186 return _VSTD::__invoke(_VSTD::move(_VSTD::get<0>(__f_)), _VSTD::move(_VSTD::get<_Indices>(__f_))...);
Howard Hinnant95cfd872011-05-19 15:05:04 +00002187 }
2188};
2189
Marshall Clowd56a5b62013-11-03 22:06:53 +00002190inline _LIBCPP_INLINE_VISIBILITY bool __does_policy_contain(launch __policy, launch __value )
Marshall Clow335b7992013-11-03 15:43:35 +00002191{ return (int(__policy) & int(__value)) != 0; }
2192
Howard Hinnantc834c512011-11-29 18:15:50 +00002193template <class _Fp, class... _Args>
Marshall Clow6ac349c2017-11-23 01:25:03 +00002194_LIBCPP_NODISCARD_AFTER_CXX17
Howard Hinnantc834c512011-11-29 18:15:50 +00002195future<typename __invoke_of<typename decay<_Fp>::type, typename decay<_Args>::type...>::type>
2196async(launch __policy, _Fp&& __f, _Args&&... __args)
Howard Hinnantccdd2032010-08-30 18:46:21 +00002197{
Howard Hinnantc834c512011-11-29 18:15:50 +00002198 typedef __async_func<typename decay<_Fp>::type, typename decay<_Args>::type...> _BF;
2199 typedef typename _BF::_Rp _Rp;
Marshall Clow335b7992013-11-03 15:43:35 +00002200
2201#ifndef _LIBCPP_NO_EXCEPTIONS
2202 try
2203 {
2204#endif
2205 if (__does_policy_contain(__policy, launch::async))
Arthur O'Dwyer34465da2020-12-15 19:32:29 -05002206 return _VSTD::__make_async_assoc_state<_Rp>(_BF(_VSTD::__decay_copy(_VSTD::forward<_Fp>(__f)),
2207 _VSTD::__decay_copy(_VSTD::forward<_Args>(__args))...));
Marshall Clow335b7992013-11-03 15:43:35 +00002208#ifndef _LIBCPP_NO_EXCEPTIONS
2209 }
2210 catch ( ... ) { if (__policy == launch::async) throw ; }
2211#endif
2212
2213 if (__does_policy_contain(__policy, launch::deferred))
Arthur O'Dwyer34465da2020-12-15 19:32:29 -05002214 return _VSTD::__make_deferred_assoc_state<_Rp>(_BF(_VSTD::__decay_copy(_VSTD::forward<_Fp>(__f)),
2215 _VSTD::__decay_copy(_VSTD::forward<_Args>(__args))...));
Marshall Clow335b7992013-11-03 15:43:35 +00002216 return future<_Rp>{};
Howard Hinnantccdd2032010-08-30 18:46:21 +00002217}
2218
Howard Hinnantc834c512011-11-29 18:15:50 +00002219template <class _Fp, class... _Args>
Marshall Clow6ac349c2017-11-23 01:25:03 +00002220_LIBCPP_NODISCARD_AFTER_CXX17 inline _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00002221future<typename __invoke_of<typename decay<_Fp>::type, typename decay<_Args>::type...>::type>
2222async(_Fp&& __f, _Args&&... __args)
Howard Hinnantccdd2032010-08-30 18:46:21 +00002223{
Howard Hinnantc834c512011-11-29 18:15:50 +00002224 return _VSTD::async(launch::any, _VSTD::forward<_Fp>(__f),
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002225 _VSTD::forward<_Args>(__args)...);
Howard Hinnantccdd2032010-08-30 18:46:21 +00002226}
2227
Louis Dionne1a1fc9d2020-07-30 10:00:53 -04002228#endif // C++03
Howard Hinnantccdd2032010-08-30 18:46:21 +00002229
Howard Hinnante6a10852010-09-03 21:46:37 +00002230// shared_future
2231
Howard Hinnantc834c512011-11-29 18:15:50 +00002232template <class _Rp>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00002233class _LIBCPP_TEMPLATE_VIS shared_future
Howard Hinnant92646c42010-09-03 18:39:25 +00002234{
Howard Hinnantc834c512011-11-29 18:15:50 +00002235 __assoc_state<_Rp>* __state_;
Howard Hinnant92646c42010-09-03 18:39:25 +00002236
2237public:
Howard Hinnant684902d2010-09-22 14:16:26 +00002238 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002239 shared_future() _NOEXCEPT : __state_(nullptr) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00002240 _LIBCPP_INLINE_VISIBILITY
Marshall Clow6f9c48b2016-11-14 19:58:05 +00002241 shared_future(const shared_future& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002242 {if (__state_) __state_->__add_shared();}
Howard Hinnant684902d2010-09-22 14:16:26 +00002243 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002244 shared_future(future<_Rp>&& __f) _NOEXCEPT : __state_(__f.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002245 {__f.__state_ = nullptr;}
Howard Hinnant684902d2010-09-22 14:16:26 +00002246 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002247 shared_future(shared_future&& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002248 {__rhs.__state_ = nullptr;}
Howard Hinnant92646c42010-09-03 18:39:25 +00002249 ~shared_future();
Marshall Clow6f9c48b2016-11-14 19:58:05 +00002250 shared_future& operator=(const shared_future& __rhs) _NOEXCEPT;
Howard Hinnant684902d2010-09-22 14:16:26 +00002251 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002252 shared_future& operator=(shared_future&& __rhs) _NOEXCEPT
Howard Hinnant92646c42010-09-03 18:39:25 +00002253 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05002254 shared_future(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant92646c42010-09-03 18:39:25 +00002255 return *this;
2256 }
Howard Hinnant92646c42010-09-03 18:39:25 +00002257
2258 // retrieving the value
Howard Hinnant684902d2010-09-22 14:16:26 +00002259 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00002260 const _Rp& get() const {return __state_->copy();}
Howard Hinnant92646c42010-09-03 18:39:25 +00002261
Howard Hinnant684902d2010-09-22 14:16:26 +00002262 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002263 void swap(shared_future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant92646c42010-09-03 18:39:25 +00002264
2265 // functions to check state
Howard Hinnant684902d2010-09-22 14:16:26 +00002266 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002267 bool valid() const _NOEXCEPT {return __state_ != nullptr;}
Howard Hinnant92646c42010-09-03 18:39:25 +00002268
Howard Hinnant684902d2010-09-22 14:16:26 +00002269 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002270 void wait() const {__state_->wait();}
2271 template <class _Rep, class _Period>
Howard Hinnant684902d2010-09-22 14:16:26 +00002272 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002273 future_status
2274 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
2275 {return __state_->wait_for(__rel_time);}
2276 template <class _Clock, class _Duration>
Howard Hinnant684902d2010-09-22 14:16:26 +00002277 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002278 future_status
2279 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
2280 {return __state_->wait_until(__abs_time);}
2281};
2282
Howard Hinnantc834c512011-11-29 18:15:50 +00002283template <class _Rp>
2284shared_future<_Rp>::~shared_future()
Howard Hinnant92646c42010-09-03 18:39:25 +00002285{
2286 if (__state_)
2287 __state_->__release_shared();
2288}
2289
Howard Hinnantc834c512011-11-29 18:15:50 +00002290template <class _Rp>
2291shared_future<_Rp>&
Marshall Clow6f9c48b2016-11-14 19:58:05 +00002292shared_future<_Rp>::operator=(const shared_future& __rhs) _NOEXCEPT
Howard Hinnant92646c42010-09-03 18:39:25 +00002293{
2294 if (__rhs.__state_)
2295 __rhs.__state_->__add_shared();
2296 if (__state_)
2297 __state_->__release_shared();
2298 __state_ = __rhs.__state_;
2299 return *this;
2300}
2301
Howard Hinnantc834c512011-11-29 18:15:50 +00002302template <class _Rp>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00002303class _LIBCPP_TEMPLATE_VIS shared_future<_Rp&>
Howard Hinnant92646c42010-09-03 18:39:25 +00002304{
Howard Hinnantc834c512011-11-29 18:15:50 +00002305 __assoc_state<_Rp&>* __state_;
Howard Hinnant92646c42010-09-03 18:39:25 +00002306
2307public:
Howard Hinnant684902d2010-09-22 14:16:26 +00002308 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002309 shared_future() _NOEXCEPT : __state_(nullptr) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00002310 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002311 shared_future(const shared_future& __rhs) : __state_(__rhs.__state_)
2312 {if (__state_) __state_->__add_shared();}
Howard Hinnant684902d2010-09-22 14:16:26 +00002313 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002314 shared_future(future<_Rp&>&& __f) _NOEXCEPT : __state_(__f.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002315 {__f.__state_ = nullptr;}
Howard Hinnant684902d2010-09-22 14:16:26 +00002316 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002317 shared_future(shared_future&& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002318 {__rhs.__state_ = nullptr;}
Howard Hinnant92646c42010-09-03 18:39:25 +00002319 ~shared_future();
2320 shared_future& operator=(const shared_future& __rhs);
Howard Hinnant684902d2010-09-22 14:16:26 +00002321 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002322 shared_future& operator=(shared_future&& __rhs) _NOEXCEPT
Howard Hinnant92646c42010-09-03 18:39:25 +00002323 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05002324 shared_future(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant92646c42010-09-03 18:39:25 +00002325 return *this;
2326 }
Howard Hinnant92646c42010-09-03 18:39:25 +00002327
2328 // retrieving the value
Howard Hinnant684902d2010-09-22 14:16:26 +00002329 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc834c512011-11-29 18:15:50 +00002330 _Rp& get() const {return __state_->copy();}
Howard Hinnant92646c42010-09-03 18:39:25 +00002331
Howard Hinnant684902d2010-09-22 14:16:26 +00002332 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002333 void swap(shared_future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant92646c42010-09-03 18:39:25 +00002334
2335 // functions to check state
Howard Hinnant684902d2010-09-22 14:16:26 +00002336 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002337 bool valid() const _NOEXCEPT {return __state_ != nullptr;}
Howard Hinnant92646c42010-09-03 18:39:25 +00002338
Howard Hinnant684902d2010-09-22 14:16:26 +00002339 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002340 void wait() const {__state_->wait();}
2341 template <class _Rep, class _Period>
Howard Hinnant684902d2010-09-22 14:16:26 +00002342 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002343 future_status
2344 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
2345 {return __state_->wait_for(__rel_time);}
2346 template <class _Clock, class _Duration>
Howard Hinnant684902d2010-09-22 14:16:26 +00002347 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002348 future_status
2349 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
2350 {return __state_->wait_until(__abs_time);}
2351};
2352
Howard Hinnantc834c512011-11-29 18:15:50 +00002353template <class _Rp>
2354shared_future<_Rp&>::~shared_future()
Howard Hinnant92646c42010-09-03 18:39:25 +00002355{
2356 if (__state_)
2357 __state_->__release_shared();
2358}
2359
Howard Hinnantc834c512011-11-29 18:15:50 +00002360template <class _Rp>
2361shared_future<_Rp&>&
2362shared_future<_Rp&>::operator=(const shared_future& __rhs)
Howard Hinnant92646c42010-09-03 18:39:25 +00002363{
2364 if (__rhs.__state_)
2365 __rhs.__state_->__add_shared();
2366 if (__state_)
2367 __state_->__release_shared();
2368 __state_ = __rhs.__state_;
2369 return *this;
2370}
2371
2372template <>
Mehdi Amini228053d2017-05-04 17:08:54 +00002373class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE shared_future<void>
Howard Hinnant92646c42010-09-03 18:39:25 +00002374{
2375 __assoc_sub_state* __state_;
2376
2377public:
Howard Hinnant684902d2010-09-22 14:16:26 +00002378 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002379 shared_future() _NOEXCEPT : __state_(nullptr) {}
Howard Hinnant684902d2010-09-22 14:16:26 +00002380 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002381 shared_future(const shared_future& __rhs) : __state_(__rhs.__state_)
2382 {if (__state_) __state_->__add_shared();}
Howard Hinnant684902d2010-09-22 14:16:26 +00002383 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002384 shared_future(future<void>&& __f) _NOEXCEPT : __state_(__f.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002385 {__f.__state_ = nullptr;}
Howard Hinnant684902d2010-09-22 14:16:26 +00002386 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002387 shared_future(shared_future&& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
Howard Hinnant92646c42010-09-03 18:39:25 +00002388 {__rhs.__state_ = nullptr;}
Howard Hinnant92646c42010-09-03 18:39:25 +00002389 ~shared_future();
2390 shared_future& operator=(const shared_future& __rhs);
Howard Hinnant684902d2010-09-22 14:16:26 +00002391 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002392 shared_future& operator=(shared_future&& __rhs) _NOEXCEPT
Howard Hinnant92646c42010-09-03 18:39:25 +00002393 {
Arthur O'Dwyer07b22492020-11-27 11:02:06 -05002394 shared_future(_VSTD::move(__rhs)).swap(*this);
Howard Hinnant92646c42010-09-03 18:39:25 +00002395 return *this;
2396 }
Howard Hinnant92646c42010-09-03 18:39:25 +00002397
2398 // retrieving the value
Howard Hinnant684902d2010-09-22 14:16:26 +00002399 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002400 void get() const {__state_->copy();}
2401
Howard Hinnant684902d2010-09-22 14:16:26 +00002402 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002403 void swap(shared_future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
Howard Hinnant92646c42010-09-03 18:39:25 +00002404
2405 // functions to check state
Howard Hinnant684902d2010-09-22 14:16:26 +00002406 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant22448042012-07-21 17:46:55 +00002407 bool valid() const _NOEXCEPT {return __state_ != nullptr;}
Howard Hinnant92646c42010-09-03 18:39:25 +00002408
Howard Hinnant684902d2010-09-22 14:16:26 +00002409 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002410 void wait() const {__state_->wait();}
2411 template <class _Rep, class _Period>
Howard Hinnant684902d2010-09-22 14:16:26 +00002412 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002413 future_status
2414 wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
2415 {return __state_->wait_for(__rel_time);}
2416 template <class _Clock, class _Duration>
Howard Hinnant684902d2010-09-22 14:16:26 +00002417 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant92646c42010-09-03 18:39:25 +00002418 future_status
2419 wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
2420 {return __state_->wait_until(__abs_time);}
2421};
2422
Howard Hinnantc834c512011-11-29 18:15:50 +00002423template <class _Rp>
Howard Hinnant92646c42010-09-03 18:39:25 +00002424inline _LIBCPP_INLINE_VISIBILITY
2425void
Howard Hinnant22448042012-07-21 17:46:55 +00002426swap(shared_future<_Rp>& __x, shared_future<_Rp>& __y) _NOEXCEPT
Howard Hinnant92646c42010-09-03 18:39:25 +00002427{
2428 __x.swap(__y);
2429}
2430
Howard Hinnantc834c512011-11-29 18:15:50 +00002431template <class _Rp>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00002432inline
Howard Hinnantc834c512011-11-29 18:15:50 +00002433shared_future<_Rp>
Marshall Clow79e02112017-01-24 23:28:25 +00002434future<_Rp>::share() _NOEXCEPT
Howard Hinnante6a10852010-09-03 21:46:37 +00002435{
Howard Hinnantc834c512011-11-29 18:15:50 +00002436 return shared_future<_Rp>(_VSTD::move(*this));
Howard Hinnante6a10852010-09-03 21:46:37 +00002437}
2438
Howard Hinnantc834c512011-11-29 18:15:50 +00002439template <class _Rp>
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00002440inline
Howard Hinnantc834c512011-11-29 18:15:50 +00002441shared_future<_Rp&>
Marshall Clow79e02112017-01-24 23:28:25 +00002442future<_Rp&>::share() _NOEXCEPT
Howard Hinnante6a10852010-09-03 21:46:37 +00002443{
Howard Hinnantc834c512011-11-29 18:15:50 +00002444 return shared_future<_Rp&>(_VSTD::move(*this));
Howard Hinnant9a7d09c2010-11-30 20:23:32 +00002445}
2446
Evgeniy Stepanov2fb1cb62015-11-07 01:22:13 +00002447inline
Howard Hinnant9a7d09c2010-11-30 20:23:32 +00002448shared_future<void>
Marshall Clow79e02112017-01-24 23:28:25 +00002449future<void>::share() _NOEXCEPT
Howard Hinnant9a7d09c2010-11-30 20:23:32 +00002450{
Howard Hinnantb1ad5a82011-06-30 21:18:19 +00002451 return shared_future<void>(_VSTD::move(*this));
Howard Hinnante6a10852010-09-03 21:46:37 +00002452}
2453
Howard Hinnantc51e1022010-05-11 19:42:16 +00002454_LIBCPP_END_NAMESPACE_STD
2455
Jonathan Roelofs39cb6bf2014-09-05 19:45:05 +00002456#endif // !_LIBCPP_HAS_NO_THREADS
2457
Louis Dionne2b1ceaa2021-04-20 12:03:32 -04002458#endif // _LIBCPP_FUTURE