xref: /llvm-project-15.0.7/libcxx/include/future (revision aec12c12)
1// -*- C++ -*-
2//===--------------------------- future -----------------------------------===//
3//
4// 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
7//
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{
21    future_already_retrieved = 1,
22    promise_already_satisfied,
23    no_state,
24    broken_promise
25};
26
27enum class launch
28{
29    async = 1,
30    deferred = 2,
31    any = async | deferred
32};
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 { };
42error_code make_error_code(future_errc e) noexcept;
43error_condition make_error_condition(future_errc e) noexcept;
44
45const error_category& future_category() noexcept;
46
47class future_error
48    : public logic_error
49{
50public:
51    future_error(error_code ec);  // exposition only
52    explicit future_error(future_errc); // C++17
53    const error_code& code() const noexcept;
54    const char*       what() const noexcept;
55};
56
57template <class R>
58class promise
59{
60public:
61    promise();
62    template <class Allocator>
63        promise(allocator_arg_t, const Allocator& a);
64    promise(promise&& rhs) noexcept;
65    promise(const promise& rhs) = delete;
66    ~promise();
67
68    // assignment
69    promise& operator=(promise&& rhs) noexcept;
70    promise& operator=(const promise& rhs) = delete;
71    void swap(promise& other) noexcept;
72
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);
94    promise(promise&& rhs) noexcept;
95    promise(const promise& rhs) = delete;
96    ~promise();
97
98    // assignment
99    promise& operator=(promise&& rhs) noexcept;
100    promise& operator=(const promise& rhs) = delete;
101    void swap(promise& other) noexcept;
102
103    // retrieving the result
104    future<R&> get_future();
105
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);
122    promise(promise&& rhs) noexcept;
123    promise(const promise& rhs) = delete;
124    ~promise();
125
126    // assignment
127    promise& operator=(promise&& rhs) noexcept;
128    promise& operator=(const promise& rhs) = delete;
129    void swap(promise& other) noexcept;
130
131    // retrieving the result
132    future<void> get_future();
133
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
143template <class R> void swap(promise<R>& x, promise<R>& y) noexcept;
144
145template <class R, class Alloc>
146    struct uses_allocator<promise<R>, Alloc> : public true_type {};
147
148template <class R>
149class future
150{
151public:
152    future() noexcept;
153    future(future&&) noexcept;
154    future(const future& rhs) = delete;
155    ~future();
156    future& operator=(const future& rhs) = delete;
157    future& operator=(future&&) noexcept;
158    shared_future<R> share() noexcept;
159
160    // retrieving the value
161    R get();
162
163    // functions to check state
164    bool valid() const noexcept;
165
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:
179    future() noexcept;
180    future(future&&) noexcept;
181    future(const future& rhs) = delete;
182    ~future();
183    future& operator=(const future& rhs) = delete;
184    future& operator=(future&&) noexcept;
185    shared_future<R&> share() noexcept;
186
187    // retrieving the value
188    R& get();
189
190    // functions to check state
191    bool valid() const noexcept;
192
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:
206    future() noexcept;
207    future(future&&) noexcept;
208    future(const future& rhs) = delete;
209    ~future();
210    future& operator=(const future& rhs) = delete;
211    future& operator=(future&&) noexcept;
212    shared_future<void> share() noexcept;
213
214    // retrieving the value
215    void get();
216
217    // functions to check state
218    bool valid() const noexcept;
219
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:
233    shared_future() noexcept;
234    shared_future(const shared_future& rhs);
235    shared_future(future<R>&&) noexcept;
236    shared_future(shared_future&& rhs) noexcept;
237    ~shared_future();
238    shared_future& operator=(const shared_future& rhs);
239    shared_future& operator=(shared_future&& rhs) noexcept;
240
241    // retrieving the value
242    const R& get() const;
243
244    // functions to check state
245    bool valid() const noexcept;
246
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:
260    shared_future() noexcept;
261    shared_future(const shared_future& rhs);
262    shared_future(future<R&>&&) noexcept;
263    shared_future(shared_future&& rhs) noexcept;
264    ~shared_future();
265    shared_future& operator=(const shared_future& rhs);
266    shared_future& operator=(shared_future&& rhs) noexcept;
267
268    // retrieving the value
269    R& get() const;
270
271    // functions to check state
272    bool valid() const noexcept;
273
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:
287    shared_future() noexcept;
288    shared_future(const shared_future& rhs);
289    shared_future(future<void>&&) noexcept;
290    shared_future(shared_future&& rhs) noexcept;
291    ~shared_future();
292    shared_future& operator=(const shared_future& rhs);
293    shared_future& operator=(shared_future&& rhs) noexcept;
294
295    // retrieving the value
296    void get() const;
297
298    // functions to check state
299    bool valid() const noexcept;
300
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
310template <class F, class... Args>
311  future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
312  async(F&& f, Args&&... args);
313
314template <class F, class... Args>
315  future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
316  async(launch policy, F&& f, Args&&... args);
317
318template <class> class packaged_task; // undefined
319
320template <class R, class... ArgTypes>
321class packaged_task<R(ArgTypes...)>
322{
323public:
324    typedef R result_type; // extension
325
326    // construction and destruction
327    packaged_task() noexcept;
328    template <class F>
329        explicit packaged_task(F&& f);
330    template <class F, class Allocator>
331        packaged_task(allocator_arg_t, const Allocator& a, F&& f);
332    ~packaged_task();
333
334    // no copy
335    packaged_task(const packaged_task&) = delete;
336    packaged_task& operator=(const packaged_task&) = delete;
337
338    // move support
339    packaged_task(packaged_task&& other) noexcept;
340    packaged_task& operator=(packaged_task&& other) noexcept;
341    void swap(packaged_task& other) noexcept;
342
343    bool valid() const noexcept;
344
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>
356  void swap(packaged_task<R(ArgTypes...)&, packaged_task<R(ArgTypes...)>&) noexcept;
357
358template <class R, class Alloc> struct uses_allocator<packaged_task<R>, Alloc>;
359
360}  // std
361
362*/
363
364#include <__config>
365#include <system_error>
366#include <memory>
367#include <chrono>
368#include <exception>
369#include <mutex>
370#include <thread>
371
372#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
373#pragma GCC system_header
374#endif
375
376#ifdef _LIBCPP_HAS_NO_THREADS
377#error <future> is not supported on this single threaded system
378#else // !_LIBCPP_HAS_NO_THREADS
379
380_LIBCPP_BEGIN_NAMESPACE_STD
381
382//enum class future_errc
383_LIBCPP_DECLARE_STRONG_ENUM(future_errc)
384{
385    future_already_retrieved = 1,
386    promise_already_satisfied,
387    no_state,
388    broken_promise
389};
390_LIBCPP_DECLARE_STRONG_ENUM_EPILOG(future_errc)
391
392template <>
393struct _LIBCPP_TEMPLATE_VIS is_error_code_enum<future_errc> : public true_type {};
394
395#ifdef _LIBCPP_HAS_NO_STRONG_ENUMS
396template <>
397struct _LIBCPP_TEMPLATE_VIS is_error_code_enum<future_errc::__lx> : public true_type { };
398#endif
399
400//enum class launch
401_LIBCPP_DECLARE_STRONG_ENUM(launch)
402{
403    async = 1,
404    deferred = 2,
405    any = async | deferred
406};
407_LIBCPP_DECLARE_STRONG_ENUM_EPILOG(launch)
408
409#ifndef _LIBCPP_HAS_NO_STRONG_ENUMS
410
411typedef underlying_type<launch>::type __launch_underlying_type;
412
413inline _LIBCPP_INLINE_VISIBILITY
414_LIBCPP_CONSTEXPR
415launch
416operator&(launch __x, launch __y)
417{
418    return static_cast<launch>(static_cast<__launch_underlying_type>(__x) &
419                               static_cast<__launch_underlying_type>(__y));
420}
421
422inline _LIBCPP_INLINE_VISIBILITY
423_LIBCPP_CONSTEXPR
424launch
425operator|(launch __x, launch __y)
426{
427    return static_cast<launch>(static_cast<__launch_underlying_type>(__x) |
428                               static_cast<__launch_underlying_type>(__y));
429}
430
431inline _LIBCPP_INLINE_VISIBILITY
432_LIBCPP_CONSTEXPR
433launch
434operator^(launch __x, launch __y)
435{
436    return static_cast<launch>(static_cast<__launch_underlying_type>(__x) ^
437                               static_cast<__launch_underlying_type>(__y));
438}
439
440inline _LIBCPP_INLINE_VISIBILITY
441_LIBCPP_CONSTEXPR
442launch
443operator~(launch __x)
444{
445    return static_cast<launch>(~static_cast<__launch_underlying_type>(__x) & 3);
446}
447
448inline _LIBCPP_INLINE_VISIBILITY
449launch&
450operator&=(launch& __x, launch __y)
451{
452    __x = __x & __y; return __x;
453}
454
455inline _LIBCPP_INLINE_VISIBILITY
456launch&
457operator|=(launch& __x, launch __y)
458{
459    __x = __x | __y; return __x;
460}
461
462inline _LIBCPP_INLINE_VISIBILITY
463launch&
464operator^=(launch& __x, launch __y)
465{
466    __x = __x ^ __y; return __x;
467}
468
469#endif  // !_LIBCPP_HAS_NO_STRONG_ENUMS
470
471//enum class future_status
472_LIBCPP_DECLARE_STRONG_ENUM(future_status)
473{
474    ready,
475    timeout,
476    deferred
477};
478_LIBCPP_DECLARE_STRONG_ENUM_EPILOG(future_status)
479
480_LIBCPP_FUNC_VIS
481const error_category& future_category() _NOEXCEPT;
482
483inline _LIBCPP_INLINE_VISIBILITY
484error_code
485make_error_code(future_errc __e) _NOEXCEPT
486{
487    return error_code(static_cast<int>(__e), future_category());
488}
489
490inline _LIBCPP_INLINE_VISIBILITY
491error_condition
492make_error_condition(future_errc __e) _NOEXCEPT
493{
494    return error_condition(static_cast<int>(__e), future_category());
495}
496
497class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_FUTURE_ERROR future_error
498    : public logic_error
499{
500    error_code __ec_;
501public:
502    future_error(error_code __ec);
503#if _LIBCPP_STD_VERS > 14
504    explicit future_error(future_errc _Ev) : logic_error(), __ec_(make_error_code(_Ev)) {}
505#endif
506    _LIBCPP_INLINE_VISIBILITY
507    const error_code& code() const _NOEXCEPT {return __ec_;}
508
509    future_error(const future_error&) _NOEXCEPT = default;
510    virtual ~future_error() _NOEXCEPT;
511};
512
513_LIBCPP_NORETURN inline _LIBCPP_INLINE_VISIBILITY
514#ifndef _LIBCPP_NO_EXCEPTIONS
515_LIBCPP_AVAILABILITY_FUTURE_ERROR
516#endif
517void __throw_future_error(future_errc _Ev)
518{
519#ifndef _LIBCPP_NO_EXCEPTIONS
520    throw future_error(make_error_code(_Ev));
521#else
522    ((void)_Ev);
523    _VSTD::abort();
524#endif
525}
526
527class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE __assoc_sub_state
528    : public __shared_count
529{
530protected:
531    exception_ptr __exception_;
532    mutable mutex __mut_;
533    mutable condition_variable __cv_;
534    unsigned __state_;
535
536    virtual void __on_zero_shared() _NOEXCEPT;
537    void __sub_wait(unique_lock<mutex>& __lk);
538public:
539    enum
540    {
541        __constructed = 1,
542        __future_attached = 2,
543        ready = 4,
544        deferred = 8
545    };
546
547    _LIBCPP_INLINE_VISIBILITY
548    __assoc_sub_state() : __state_(0) {}
549
550    _LIBCPP_INLINE_VISIBILITY
551    bool __has_value() const
552        {return (__state_ & __constructed) || (__exception_ != nullptr);}
553
554    _LIBCPP_INLINE_VISIBILITY
555    void __attach_future() {
556        lock_guard<mutex> __lk(__mut_);
557        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();
561        __state_ |= __future_attached;
562    }
563
564    _LIBCPP_INLINE_VISIBILITY
565    void __set_deferred() {__state_ |= deferred;}
566
567    void __make_ready();
568    _LIBCPP_INLINE_VISIBILITY
569    bool __is_ready() const {return (__state_ & ready) != 0;}
570
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
579    void wait();
580    template <class _Rep, class _Period>
581        future_status
582        _LIBCPP_INLINE_VISIBILITY
583        wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const;
584    template <class _Clock, class _Duration>
585        _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS
586        future_status
587        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const;
588
589    virtual void __execute();
590};
591
592template <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_);
597    if (__state_ & deferred)
598        return future_status::deferred;
599    while (!(__state_ & ready) && _Clock::now() < __abs_time)
600        __cv_.wait_until(__lk, __abs_time);
601    if (__state_ & ready)
602        return future_status::ready;
603    return future_status::timeout;
604}
605
606template <class _Rep, class _Period>
607inline
608future_status
609__assoc_sub_state::wait_for(const chrono::duration<_Rep, _Period>& __rel_time) const
610{
611    return wait_until(chrono::steady_clock::now() + __rel_time);
612}
613
614template <class _Rp>
615class _LIBCPP_AVAILABILITY_FUTURE _LIBCPP_HIDDEN __assoc_state
616    : public __assoc_sub_state
617{
618    typedef __assoc_sub_state base;
619    typedef typename aligned_storage<sizeof(_Rp), alignment_of<_Rp>::value>::type _Up;
620protected:
621    _Up __value_;
622
623    virtual void __on_zero_shared() _NOEXCEPT;
624public:
625
626    template <class _Arg>
627    void set_value(_Arg&& __arg);
628
629    template <class _Arg>
630    void set_value_at_thread_exit(_Arg&& __arg);
631
632    _Rp move();
633    typename add_lvalue_reference<_Rp>::type copy();
634};
635
636template <class _Rp>
637void
638__assoc_state<_Rp>::__on_zero_shared() _NOEXCEPT
639{
640    if (this->__state_ & base::__constructed)
641        reinterpret_cast<_Rp*>(&__value_)->~_Rp();
642    delete this;
643}
644
645template <class _Rp>
646template <class _Arg>
647_LIBCPP_AVAILABILITY_FUTURE
648void
649__assoc_state<_Rp>::set_value(_Arg&& __arg)
650{
651    unique_lock<mutex> __lk(this->__mut_);
652    if (this->__has_value())
653        __throw_future_error(future_errc::promise_already_satisfied);
654    ::new(&__value_) _Rp(_VSTD::forward<_Arg>(__arg));
655    this->__state_ |= base::__constructed | base::ready;
656    __cv_.notify_all();
657}
658
659template <class _Rp>
660template <class _Arg>
661void
662__assoc_state<_Rp>::set_value_at_thread_exit(_Arg&& __arg)
663{
664    unique_lock<mutex> __lk(this->__mut_);
665    if (this->__has_value())
666        __throw_future_error(future_errc::promise_already_satisfied);
667    ::new(&__value_) _Rp(_VSTD::forward<_Arg>(__arg));
668    this->__state_ |= base::__constructed;
669    __thread_local_data()->__make_ready_at_thread_exit(this);
670}
671
672template <class _Rp>
673_Rp
674__assoc_state<_Rp>::move()
675{
676    unique_lock<mutex> __lk(this->__mut_);
677    this->__sub_wait(__lk);
678    if (this->__exception_ != nullptr)
679        rethrow_exception(this->__exception_);
680    return _VSTD::move(*reinterpret_cast<_Rp*>(&__value_));
681}
682
683template <class _Rp>
684typename add_lvalue_reference<_Rp>::type
685__assoc_state<_Rp>::copy()
686{
687    unique_lock<mutex> __lk(this->__mut_);
688    this->__sub_wait(__lk);
689    if (this->__exception_ != nullptr)
690        rethrow_exception(this->__exception_);
691    return *reinterpret_cast<_Rp*>(&__value_);
692}
693
694template <class _Rp>
695class _LIBCPP_AVAILABILITY_FUTURE __assoc_state<_Rp&>
696    : public __assoc_sub_state
697{
698    typedef __assoc_sub_state base;
699    typedef _Rp* _Up;
700protected:
701    _Up __value_;
702
703    virtual void __on_zero_shared() _NOEXCEPT;
704public:
705
706    void set_value(_Rp& __arg);
707    void set_value_at_thread_exit(_Rp& __arg);
708
709    _Rp& copy();
710};
711
712template <class _Rp>
713void
714__assoc_state<_Rp&>::__on_zero_shared() _NOEXCEPT
715{
716    delete this;
717}
718
719template <class _Rp>
720void
721__assoc_state<_Rp&>::set_value(_Rp& __arg)
722{
723    unique_lock<mutex> __lk(this->__mut_);
724    if (this->__has_value())
725        __throw_future_error(future_errc::promise_already_satisfied);
726    __value_ = _VSTD::addressof(__arg);
727    this->__state_ |= base::__constructed | base::ready;
728    __cv_.notify_all();
729}
730
731template <class _Rp>
732void
733__assoc_state<_Rp&>::set_value_at_thread_exit(_Rp& __arg)
734{
735    unique_lock<mutex> __lk(this->__mut_);
736    if (this->__has_value())
737        __throw_future_error(future_errc::promise_already_satisfied);
738    __value_ = _VSTD::addressof(__arg);
739    this->__state_ |= base::__constructed;
740    __thread_local_data()->__make_ready_at_thread_exit(this);
741}
742
743template <class _Rp>
744_Rp&
745__assoc_state<_Rp&>::copy()
746{
747    unique_lock<mutex> __lk(this->__mut_);
748    this->__sub_wait(__lk);
749    if (this->__exception_ != nullptr)
750        rethrow_exception(this->__exception_);
751    return *__value_;
752}
753
754template <class _Rp, class _Alloc>
755class _LIBCPP_AVAILABILITY_FUTURE __assoc_state_alloc
756    : public __assoc_state<_Rp>
757{
758    typedef __assoc_state<_Rp> base;
759    _Alloc __alloc_;
760
761    virtual void __on_zero_shared() _NOEXCEPT;
762public:
763    _LIBCPP_INLINE_VISIBILITY
764    explicit __assoc_state_alloc(const _Alloc& __a)
765        : __alloc_(__a) {}
766};
767
768template <class _Rp, class _Alloc>
769void
770__assoc_state_alloc<_Rp, _Alloc>::__on_zero_shared() _NOEXCEPT
771{
772    if (this->__state_ & base::__constructed)
773        reinterpret_cast<_Rp*>(_VSTD::addressof(this->__value_))->~_Rp();
774    typedef typename __allocator_traits_rebind<_Alloc, __assoc_state_alloc>::type _Al;
775    typedef allocator_traits<_Al> _ATraits;
776    typedef pointer_traits<typename _ATraits::pointer> _PTraits;
777    _Al __a(__alloc_);
778    this->~__assoc_state_alloc();
779    __a.deallocate(_PTraits::pointer_to(*this), 1);
780}
781
782template <class _Rp, class _Alloc>
783class _LIBCPP_AVAILABILITY_FUTURE __assoc_state_alloc<_Rp&, _Alloc>
784    : public __assoc_state<_Rp&>
785{
786    typedef __assoc_state<_Rp&> base;
787    _Alloc __alloc_;
788
789    virtual void __on_zero_shared() _NOEXCEPT;
790public:
791    _LIBCPP_INLINE_VISIBILITY
792    explicit __assoc_state_alloc(const _Alloc& __a)
793        : __alloc_(__a) {}
794};
795
796template <class _Rp, class _Alloc>
797void
798__assoc_state_alloc<_Rp&, _Alloc>::__on_zero_shared() _NOEXCEPT
799{
800    typedef typename __allocator_traits_rebind<_Alloc, __assoc_state_alloc>::type _Al;
801    typedef allocator_traits<_Al> _ATraits;
802    typedef pointer_traits<typename _ATraits::pointer> _PTraits;
803    _Al __a(__alloc_);
804    this->~__assoc_state_alloc();
805    __a.deallocate(_PTraits::pointer_to(*this), 1);
806}
807
808template <class _Alloc>
809class _LIBCPP_AVAILABILITY_FUTURE __assoc_sub_state_alloc
810    : public __assoc_sub_state
811{
812    typedef __assoc_sub_state base;
813    _Alloc __alloc_;
814
815    virtual void __on_zero_shared() _NOEXCEPT;
816public:
817    _LIBCPP_INLINE_VISIBILITY
818    explicit __assoc_sub_state_alloc(const _Alloc& __a)
819        : __alloc_(__a) {}
820};
821
822template <class _Alloc>
823void
824__assoc_sub_state_alloc<_Alloc>::__on_zero_shared() _NOEXCEPT
825{
826    typedef typename __allocator_traits_rebind<_Alloc, __assoc_sub_state_alloc>::type _Al;
827    typedef allocator_traits<_Al> _ATraits;
828    typedef pointer_traits<typename _ATraits::pointer> _PTraits;
829    _Al __a(__alloc_);
830    this->~__assoc_sub_state_alloc();
831    __a.deallocate(_PTraits::pointer_to(*this), 1);
832}
833
834template <class _Rp, class _Fp>
835class _LIBCPP_AVAILABILITY_FUTURE __deferred_assoc_state
836    : public __assoc_state<_Rp>
837{
838    typedef __assoc_state<_Rp> base;
839
840    _Fp __func_;
841
842public:
843    _LIBCPP_INLINE_VISIBILITY
844    explicit __deferred_assoc_state(_Fp&& __f);
845
846    virtual void __execute();
847};
848
849template <class _Rp, class _Fp>
850inline
851__deferred_assoc_state<_Rp, _Fp>::__deferred_assoc_state(_Fp&& __f)
852    : __func_(_VSTD::forward<_Fp>(__f))
853{
854    this->__set_deferred();
855}
856
857template <class _Rp, class _Fp>
858void
859__deferred_assoc_state<_Rp, _Fp>::__execute()
860{
861#ifndef _LIBCPP_NO_EXCEPTIONS
862    try
863    {
864#endif  // _LIBCPP_NO_EXCEPTIONS
865        this->set_value(__func_());
866#ifndef _LIBCPP_NO_EXCEPTIONS
867    }
868    catch (...)
869    {
870        this->set_exception(current_exception());
871    }
872#endif  // _LIBCPP_NO_EXCEPTIONS
873}
874
875template <class _Fp>
876class _LIBCPP_AVAILABILITY_FUTURE __deferred_assoc_state<void, _Fp>
877    : public __assoc_sub_state
878{
879    typedef __assoc_sub_state base;
880
881    _Fp __func_;
882
883public:
884    _LIBCPP_INLINE_VISIBILITY
885    explicit __deferred_assoc_state(_Fp&& __f);
886
887    virtual void __execute();
888};
889
890template <class _Fp>
891inline
892__deferred_assoc_state<void, _Fp>::__deferred_assoc_state(_Fp&& __f)
893    : __func_(_VSTD::forward<_Fp>(__f))
894{
895    this->__set_deferred();
896}
897
898template <class _Fp>
899void
900__deferred_assoc_state<void, _Fp>::__execute()
901{
902#ifndef _LIBCPP_NO_EXCEPTIONS
903    try
904    {
905#endif  // _LIBCPP_NO_EXCEPTIONS
906        __func_();
907        this->set_value();
908#ifndef _LIBCPP_NO_EXCEPTIONS
909    }
910    catch (...)
911    {
912        this->set_exception(current_exception());
913    }
914#endif  // _LIBCPP_NO_EXCEPTIONS
915}
916
917template <class _Rp, class _Fp>
918class _LIBCPP_AVAILABILITY_FUTURE __async_assoc_state
919    : public __assoc_state<_Rp>
920{
921    typedef __assoc_state<_Rp> base;
922
923    _Fp __func_;
924
925    virtual void __on_zero_shared() _NOEXCEPT;
926public:
927    _LIBCPP_INLINE_VISIBILITY
928    explicit __async_assoc_state(_Fp&& __f);
929
930    virtual void __execute();
931};
932
933template <class _Rp, class _Fp>
934inline
935__async_assoc_state<_Rp, _Fp>::__async_assoc_state(_Fp&& __f)
936    : __func_(_VSTD::forward<_Fp>(__f))
937{
938}
939
940template <class _Rp, class _Fp>
941void
942__async_assoc_state<_Rp, _Fp>::__execute()
943{
944#ifndef _LIBCPP_NO_EXCEPTIONS
945    try
946    {
947#endif  // _LIBCPP_NO_EXCEPTIONS
948        this->set_value(__func_());
949#ifndef _LIBCPP_NO_EXCEPTIONS
950    }
951    catch (...)
952    {
953        this->set_exception(current_exception());
954    }
955#endif  // _LIBCPP_NO_EXCEPTIONS
956}
957
958template <class _Rp, class _Fp>
959void
960__async_assoc_state<_Rp, _Fp>::__on_zero_shared() _NOEXCEPT
961{
962    this->wait();
963    base::__on_zero_shared();
964}
965
966template <class _Fp>
967class _LIBCPP_AVAILABILITY_FUTURE __async_assoc_state<void, _Fp>
968    : public __assoc_sub_state
969{
970    typedef __assoc_sub_state base;
971
972    _Fp __func_;
973
974    virtual void __on_zero_shared() _NOEXCEPT;
975public:
976    _LIBCPP_INLINE_VISIBILITY
977    explicit __async_assoc_state(_Fp&& __f);
978
979    virtual void __execute();
980};
981
982template <class _Fp>
983inline
984__async_assoc_state<void, _Fp>::__async_assoc_state(_Fp&& __f)
985    : __func_(_VSTD::forward<_Fp>(__f))
986{
987}
988
989template <class _Fp>
990void
991__async_assoc_state<void, _Fp>::__execute()
992{
993#ifndef _LIBCPP_NO_EXCEPTIONS
994    try
995    {
996#endif  // _LIBCPP_NO_EXCEPTIONS
997        __func_();
998        this->set_value();
999#ifndef _LIBCPP_NO_EXCEPTIONS
1000    }
1001    catch (...)
1002    {
1003        this->set_exception(current_exception());
1004    }
1005#endif  // _LIBCPP_NO_EXCEPTIONS
1006}
1007
1008template <class _Fp>
1009void
1010__async_assoc_state<void, _Fp>::__on_zero_shared() _NOEXCEPT
1011{
1012    this->wait();
1013    base::__on_zero_shared();
1014}
1015
1016template <class _Rp> class _LIBCPP_TEMPLATE_VIS promise;
1017template <class _Rp> class _LIBCPP_TEMPLATE_VIS shared_future;
1018
1019// future
1020
1021template <class _Rp> class _LIBCPP_TEMPLATE_VIS future;
1022
1023template <class _Rp, class _Fp>
1024_LIBCPP_INLINE_VISIBILITY future<_Rp>
1025__make_deferred_assoc_state(_Fp&& __f);
1026
1027template <class _Rp, class _Fp>
1028_LIBCPP_INLINE_VISIBILITY future<_Rp>
1029__make_async_assoc_state(_Fp&& __f);
1030
1031template <class _Rp>
1032class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE future
1033{
1034    __assoc_state<_Rp>* __state_;
1035
1036    explicit future(__assoc_state<_Rp>* __state);
1037
1038    template <class> friend class promise;
1039    template <class> friend class shared_future;
1040
1041    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);
1045
1046public:
1047    _LIBCPP_INLINE_VISIBILITY
1048    future() _NOEXCEPT : __state_(nullptr) {}
1049    _LIBCPP_INLINE_VISIBILITY
1050    future(future&& __rhs) _NOEXCEPT
1051        : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1052    future(const future&) = delete;
1053    future& operator=(const future&) = delete;
1054    _LIBCPP_INLINE_VISIBILITY
1055    future& operator=(future&& __rhs) _NOEXCEPT
1056        {
1057            future(std::move(__rhs)).swap(*this);
1058            return *this;
1059        }
1060
1061    ~future();
1062    _LIBCPP_INLINE_VISIBILITY
1063    shared_future<_Rp> share() _NOEXCEPT;
1064
1065    // retrieving the value
1066    _Rp get();
1067
1068    _LIBCPP_INLINE_VISIBILITY
1069    void swap(future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
1070
1071    // functions to check state
1072    _LIBCPP_INLINE_VISIBILITY
1073    bool valid() const _NOEXCEPT {return __state_ != nullptr;}
1074
1075    _LIBCPP_INLINE_VISIBILITY
1076    void wait() const {__state_->wait();}
1077    template <class _Rep, class _Period>
1078        _LIBCPP_INLINE_VISIBILITY
1079        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>
1083        _LIBCPP_INLINE_VISIBILITY
1084        future_status
1085        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
1086            {return __state_->wait_until(__abs_time);}
1087};
1088
1089template <class _Rp>
1090future<_Rp>::future(__assoc_state<_Rp>* __state)
1091    : __state_(__state)
1092{
1093    __state_->__attach_future();
1094}
1095
1096struct __release_shared_count
1097{
1098    void operator()(__shared_count* p) {p->__release_shared();}
1099};
1100
1101template <class _Rp>
1102future<_Rp>::~future()
1103{
1104    if (__state_)
1105        __state_->__release_shared();
1106}
1107
1108template <class _Rp>
1109_Rp
1110future<_Rp>::get()
1111{
1112    unique_ptr<__shared_count, __release_shared_count> __(__state_);
1113    __assoc_state<_Rp>* __s = __state_;
1114    __state_ = nullptr;
1115    return __s->move();
1116}
1117
1118template <class _Rp>
1119class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE future<_Rp&>
1120{
1121    __assoc_state<_Rp&>* __state_;
1122
1123    explicit future(__assoc_state<_Rp&>* __state);
1124
1125    template <class> friend class promise;
1126    template <class> friend class shared_future;
1127
1128    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);
1132
1133public:
1134    _LIBCPP_INLINE_VISIBILITY
1135    future() _NOEXCEPT : __state_(nullptr) {}
1136    _LIBCPP_INLINE_VISIBILITY
1137    future(future&& __rhs) _NOEXCEPT
1138        : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1139    future(const future&) = delete;
1140    future& operator=(const future&) = delete;
1141    _LIBCPP_INLINE_VISIBILITY
1142    future& operator=(future&& __rhs) _NOEXCEPT
1143        {
1144            future(std::move(__rhs)).swap(*this);
1145            return *this;
1146        }
1147
1148    ~future();
1149    _LIBCPP_INLINE_VISIBILITY
1150    shared_future<_Rp&> share() _NOEXCEPT;
1151
1152    // retrieving the value
1153    _Rp& get();
1154
1155    _LIBCPP_INLINE_VISIBILITY
1156    void swap(future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
1157
1158    // functions to check state
1159    _LIBCPP_INLINE_VISIBILITY
1160    bool valid() const _NOEXCEPT {return __state_ != nullptr;}
1161
1162    _LIBCPP_INLINE_VISIBILITY
1163    void wait() const {__state_->wait();}
1164    template <class _Rep, class _Period>
1165        _LIBCPP_INLINE_VISIBILITY
1166        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>
1170        _LIBCPP_INLINE_VISIBILITY
1171        future_status
1172        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
1173            {return __state_->wait_until(__abs_time);}
1174};
1175
1176template <class _Rp>
1177future<_Rp&>::future(__assoc_state<_Rp&>* __state)
1178    : __state_(__state)
1179{
1180    __state_->__attach_future();
1181}
1182
1183template <class _Rp>
1184future<_Rp&>::~future()
1185{
1186    if (__state_)
1187        __state_->__release_shared();
1188}
1189
1190template <class _Rp>
1191_Rp&
1192future<_Rp&>::get()
1193{
1194    unique_ptr<__shared_count, __release_shared_count> __(__state_);
1195    __assoc_state<_Rp&>* __s = __state_;
1196    __state_ = nullptr;
1197    return __s->copy();
1198}
1199
1200template <>
1201class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE future<void>
1202{
1203    __assoc_sub_state* __state_;
1204
1205    explicit future(__assoc_sub_state* __state);
1206
1207    template <class> friend class promise;
1208    template <class> friend class shared_future;
1209
1210    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);
1214
1215public:
1216    _LIBCPP_INLINE_VISIBILITY
1217    future() _NOEXCEPT : __state_(nullptr) {}
1218    _LIBCPP_INLINE_VISIBILITY
1219    future(future&& __rhs) _NOEXCEPT
1220        : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1221    future(const future&) = delete;
1222    future& operator=(const future&) = delete;
1223    _LIBCPP_INLINE_VISIBILITY
1224    future& operator=(future&& __rhs) _NOEXCEPT
1225        {
1226            future(std::move(__rhs)).swap(*this);
1227            return *this;
1228        }
1229
1230    ~future();
1231    _LIBCPP_INLINE_VISIBILITY
1232    shared_future<void> share() _NOEXCEPT;
1233
1234    // retrieving the value
1235    void get();
1236
1237    _LIBCPP_INLINE_VISIBILITY
1238    void swap(future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
1239
1240    // functions to check state
1241    _LIBCPP_INLINE_VISIBILITY
1242    bool valid() const _NOEXCEPT {return __state_ != nullptr;}
1243
1244    _LIBCPP_INLINE_VISIBILITY
1245    void wait() const {__state_->wait();}
1246    template <class _Rep, class _Period>
1247        _LIBCPP_INLINE_VISIBILITY
1248        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>
1252        _LIBCPP_INLINE_VISIBILITY
1253        future_status
1254        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
1255            {return __state_->wait_until(__abs_time);}
1256};
1257
1258template <class _Rp>
1259inline _LIBCPP_INLINE_VISIBILITY
1260void
1261swap(future<_Rp>& __x, future<_Rp>& __y) _NOEXCEPT
1262{
1263    __x.swap(__y);
1264}
1265
1266// promise<R>
1267
1268template <class _Callable> class packaged_task;
1269
1270template <class _Rp>
1271class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE promise
1272{
1273    __assoc_state<_Rp>* __state_;
1274
1275    _LIBCPP_INLINE_VISIBILITY
1276    explicit promise(nullptr_t) _NOEXCEPT : __state_(nullptr) {}
1277
1278    template <class> friend class packaged_task;
1279public:
1280    promise();
1281    template <class _Alloc>
1282        promise(allocator_arg_t, const _Alloc& __a);
1283    _LIBCPP_INLINE_VISIBILITY
1284    promise(promise&& __rhs) _NOEXCEPT
1285        : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1286    promise(const promise& __rhs) = delete;
1287    ~promise();
1288
1289    // assignment
1290    _LIBCPP_INLINE_VISIBILITY
1291    promise& operator=(promise&& __rhs) _NOEXCEPT
1292        {
1293            promise(std::move(__rhs)).swap(*this);
1294            return *this;
1295        }
1296    promise& operator=(const promise& __rhs) = delete;
1297
1298    _LIBCPP_INLINE_VISIBILITY
1299    void swap(promise& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
1300
1301    // retrieving the result
1302    future<_Rp> get_future();
1303
1304    // setting the result
1305    void set_value(const _Rp& __r);
1306    void set_value(_Rp&& __r);
1307    void set_exception(exception_ptr __p);
1308
1309    // setting the result with deferred notification
1310    void set_value_at_thread_exit(const _Rp& __r);
1311    void set_value_at_thread_exit(_Rp&& __r);
1312    void set_exception_at_thread_exit(exception_ptr __p);
1313};
1314
1315template <class _Rp>
1316promise<_Rp>::promise()
1317    : __state_(new __assoc_state<_Rp>)
1318{
1319}
1320
1321template <class _Rp>
1322template <class _Alloc>
1323promise<_Rp>::promise(allocator_arg_t, const _Alloc& __a0)
1324{
1325    typedef __assoc_state_alloc<_Rp, _Alloc> _State;
1326    typedef typename __allocator_traits_rebind<_Alloc, _State>::type _A2;
1327    typedef __allocator_destructor<_A2> _D2;
1328    _A2 __a(__a0);
1329    unique_ptr<_State, _D2> __hold(__a.allocate(1), _D2(__a, 1));
1330    ::new(static_cast<void*>(_VSTD::addressof(*__hold.get()))) _State(__a0);
1331    __state_ = _VSTD::addressof(*__hold.release());
1332}
1333
1334template <class _Rp>
1335promise<_Rp>::~promise()
1336{
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
1347template <class _Rp>
1348future<_Rp>
1349promise<_Rp>::get_future()
1350{
1351    if (__state_ == nullptr)
1352        __throw_future_error(future_errc::no_state);
1353    return future<_Rp>(__state_);
1354}
1355
1356template <class _Rp>
1357void
1358promise<_Rp>::set_value(const _Rp& __r)
1359{
1360    if (__state_ == nullptr)
1361        __throw_future_error(future_errc::no_state);
1362    __state_->set_value(__r);
1363}
1364
1365template <class _Rp>
1366void
1367promise<_Rp>::set_value(_Rp&& __r)
1368{
1369    if (__state_ == nullptr)
1370        __throw_future_error(future_errc::no_state);
1371    __state_->set_value(_VSTD::move(__r));
1372}
1373
1374template <class _Rp>
1375void
1376promise<_Rp>::set_exception(exception_ptr __p)
1377{
1378    _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception: received nullptr" );
1379    if (__state_ == nullptr)
1380        __throw_future_error(future_errc::no_state);
1381    __state_->set_exception(__p);
1382}
1383
1384template <class _Rp>
1385void
1386promise<_Rp>::set_value_at_thread_exit(const _Rp& __r)
1387{
1388    if (__state_ == nullptr)
1389        __throw_future_error(future_errc::no_state);
1390    __state_->set_value_at_thread_exit(__r);
1391}
1392
1393template <class _Rp>
1394void
1395promise<_Rp>::set_value_at_thread_exit(_Rp&& __r)
1396{
1397    if (__state_ == nullptr)
1398        __throw_future_error(future_errc::no_state);
1399    __state_->set_value_at_thread_exit(_VSTD::move(__r));
1400}
1401
1402template <class _Rp>
1403void
1404promise<_Rp>::set_exception_at_thread_exit(exception_ptr __p)
1405{
1406    _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception_at_thread_exit: received nullptr" );
1407    if (__state_ == nullptr)
1408        __throw_future_error(future_errc::no_state);
1409    __state_->set_exception_at_thread_exit(__p);
1410}
1411
1412// promise<R&>
1413
1414template <class _Rp>
1415class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE promise<_Rp&>
1416{
1417    __assoc_state<_Rp&>* __state_;
1418
1419    _LIBCPP_INLINE_VISIBILITY
1420    explicit promise(nullptr_t) _NOEXCEPT : __state_(nullptr) {}
1421
1422    template <class> friend class packaged_task;
1423
1424public:
1425    promise();
1426    template <class _Allocator>
1427        promise(allocator_arg_t, const _Allocator& __a);
1428    _LIBCPP_INLINE_VISIBILITY
1429    promise(promise&& __rhs) _NOEXCEPT
1430        : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1431    promise(const promise& __rhs) = delete;
1432    ~promise();
1433
1434    // assignment
1435    _LIBCPP_INLINE_VISIBILITY
1436    promise& operator=(promise&& __rhs) _NOEXCEPT
1437        {
1438            promise(std::move(__rhs)).swap(*this);
1439            return *this;
1440        }
1441    promise& operator=(const promise& __rhs) = delete;
1442
1443    _LIBCPP_INLINE_VISIBILITY
1444    void swap(promise& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
1445
1446    // retrieving the result
1447    future<_Rp&> get_future();
1448
1449    // setting the result
1450    void set_value(_Rp& __r);
1451    void set_exception(exception_ptr __p);
1452
1453    // setting the result with deferred notification
1454    void set_value_at_thread_exit(_Rp&);
1455    void set_exception_at_thread_exit(exception_ptr __p);
1456};
1457
1458template <class _Rp>
1459promise<_Rp&>::promise()
1460    : __state_(new __assoc_state<_Rp&>)
1461{
1462}
1463
1464template <class _Rp>
1465template <class _Alloc>
1466promise<_Rp&>::promise(allocator_arg_t, const _Alloc& __a0)
1467{
1468    typedef __assoc_state_alloc<_Rp&, _Alloc> _State;
1469    typedef typename __allocator_traits_rebind<_Alloc, _State>::type _A2;
1470    typedef __allocator_destructor<_A2> _D2;
1471    _A2 __a(__a0);
1472    unique_ptr<_State, _D2> __hold(__a.allocate(1), _D2(__a, 1));
1473    ::new(static_cast<void*>(_VSTD::addressof(*__hold.get()))) _State(__a0);
1474    __state_ = _VSTD::addressof(*__hold.release());
1475}
1476
1477template <class _Rp>
1478promise<_Rp&>::~promise()
1479{
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
1490template <class _Rp>
1491future<_Rp&>
1492promise<_Rp&>::get_future()
1493{
1494    if (__state_ == nullptr)
1495        __throw_future_error(future_errc::no_state);
1496    return future<_Rp&>(__state_);
1497}
1498
1499template <class _Rp>
1500void
1501promise<_Rp&>::set_value(_Rp& __r)
1502{
1503    if (__state_ == nullptr)
1504        __throw_future_error(future_errc::no_state);
1505    __state_->set_value(__r);
1506}
1507
1508template <class _Rp>
1509void
1510promise<_Rp&>::set_exception(exception_ptr __p)
1511{
1512    _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception: received nullptr" );
1513    if (__state_ == nullptr)
1514        __throw_future_error(future_errc::no_state);
1515    __state_->set_exception(__p);
1516}
1517
1518template <class _Rp>
1519void
1520promise<_Rp&>::set_value_at_thread_exit(_Rp& __r)
1521{
1522    if (__state_ == nullptr)
1523        __throw_future_error(future_errc::no_state);
1524    __state_->set_value_at_thread_exit(__r);
1525}
1526
1527template <class _Rp>
1528void
1529promise<_Rp&>::set_exception_at_thread_exit(exception_ptr __p)
1530{
1531    _LIBCPP_ASSERT( __p != nullptr, "promise::set_exception_at_thread_exit: received nullptr" );
1532    if (__state_ == nullptr)
1533        __throw_future_error(future_errc::no_state);
1534    __state_->set_exception_at_thread_exit(__p);
1535}
1536
1537// promise<void>
1538
1539template <>
1540class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE promise<void>
1541{
1542    __assoc_sub_state* __state_;
1543
1544    _LIBCPP_INLINE_VISIBILITY
1545    explicit promise(nullptr_t) _NOEXCEPT : __state_(nullptr) {}
1546
1547    template <class> friend class packaged_task;
1548
1549public:
1550    promise();
1551    template <class _Allocator>
1552        _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS
1553        promise(allocator_arg_t, const _Allocator& __a);
1554    _LIBCPP_INLINE_VISIBILITY
1555    promise(promise&& __rhs) _NOEXCEPT
1556        : __state_(__rhs.__state_) {__rhs.__state_ = nullptr;}
1557    promise(const promise& __rhs) = delete;
1558    ~promise();
1559
1560    // assignment
1561    _LIBCPP_INLINE_VISIBILITY
1562    promise& operator=(promise&& __rhs) _NOEXCEPT
1563        {
1564            promise(std::move(__rhs)).swap(*this);
1565            return *this;
1566        }
1567    promise& operator=(const promise& __rhs) = delete;
1568
1569    _LIBCPP_INLINE_VISIBILITY
1570    void swap(promise& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
1571
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{
1587    typedef __assoc_sub_state_alloc<_Alloc> _State;
1588    typedef typename __allocator_traits_rebind<_Alloc, _State>::type _A2;
1589    typedef __allocator_destructor<_A2> _D2;
1590    _A2 __a(__a0);
1591    unique_ptr<_State, _D2> __hold(__a.allocate(1), _D2(__a, 1));
1592    ::new(static_cast<void*>(_VSTD::addressof(*__hold.get()))) _State(__a0);
1593    __state_ = _VSTD::addressof(*__hold.release());
1594}
1595
1596template <class _Rp>
1597inline _LIBCPP_INLINE_VISIBILITY
1598void
1599swap(promise<_Rp>& __x, promise<_Rp>& __y) _NOEXCEPT
1600{
1601    __x.swap(__y);
1602}
1603
1604template <class _Rp, class _Alloc>
1605    struct _LIBCPP_TEMPLATE_VIS uses_allocator<promise<_Rp>, _Alloc>
1606        : public true_type {};
1607
1608#ifndef _LIBCPP_HAS_NO_VARIADICS
1609
1610// packaged_task
1611
1612template<class _Fp> class __packaged_task_base;
1613
1614template<class _Rp, class ..._ArgTypes>
1615class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_base<_Rp(_ArgTypes...)>
1616{
1617    __packaged_task_base(const __packaged_task_base&);
1618    __packaged_task_base& operator=(const __packaged_task_base&);
1619public:
1620    _LIBCPP_INLINE_VISIBILITY
1621    __packaged_task_base() {}
1622    _LIBCPP_INLINE_VISIBILITY
1623    virtual ~__packaged_task_base() {}
1624    virtual void __move_to(__packaged_task_base*) _NOEXCEPT = 0;
1625    virtual void destroy() = 0;
1626    virtual void destroy_deallocate() = 0;
1627    virtual _Rp operator()(_ArgTypes&& ...) = 0;
1628};
1629
1630template<class _FD, class _Alloc, class _FB> class __packaged_task_func;
1631
1632template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
1633class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>
1634    : public  __packaged_task_base<_Rp(_ArgTypes...)>
1635{
1636    __compressed_pair<_Fp, _Alloc> __f_;
1637public:
1638    _LIBCPP_INLINE_VISIBILITY
1639    explicit __packaged_task_func(const _Fp& __f) : __f_(__f, __default_init_tag()) {}
1640    _LIBCPP_INLINE_VISIBILITY
1641    explicit __packaged_task_func(_Fp&& __f) : __f_(_VSTD::move(__f), __default_init_tag()) {}
1642    _LIBCPP_INLINE_VISIBILITY
1643    __packaged_task_func(const _Fp& __f, const _Alloc& __a)
1644        : __f_(__f, __a) {}
1645    _LIBCPP_INLINE_VISIBILITY
1646    __packaged_task_func(_Fp&& __f, const _Alloc& __a)
1647        : __f_(_VSTD::move(__f), __a) {}
1648    virtual void __move_to(__packaged_task_base<_Rp(_ArgTypes...)>*) _NOEXCEPT;
1649    virtual void destroy();
1650    virtual void destroy_deallocate();
1651    virtual _Rp operator()(_ArgTypes&& ... __args);
1652};
1653
1654template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
1655void
1656__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::__move_to(
1657                              __packaged_task_base<_Rp(_ArgTypes...)>* __p) _NOEXCEPT
1658{
1659    ::new (__p) __packaged_task_func(_VSTD::move(__f_.first()), _VSTD::move(__f_.second()));
1660}
1661
1662template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
1663void
1664__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy()
1665{
1666    __f_.~__compressed_pair<_Fp, _Alloc>();
1667}
1668
1669template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
1670void
1671__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::destroy_deallocate()
1672{
1673    typedef typename __allocator_traits_rebind<_Alloc, __packaged_task_func>::type _Ap;
1674    typedef allocator_traits<_Ap> _ATraits;
1675    typedef pointer_traits<typename _ATraits::pointer> _PTraits;
1676    _Ap __a(__f_.second());
1677    __f_.~__compressed_pair<_Fp, _Alloc>();
1678    __a.deallocate(_PTraits::pointer_to(*this), 1);
1679}
1680
1681template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes>
1682_Rp
1683__packaged_task_func<_Fp, _Alloc, _Rp(_ArgTypes...)>::operator()(_ArgTypes&& ... __arg)
1684{
1685    return __invoke(__f_.first(), _VSTD::forward<_ArgTypes>(__arg)...);
1686}
1687
1688template <class _Callable> class __packaged_task_function;
1689
1690template<class _Rp, class ..._ArgTypes>
1691class _LIBCPP_AVAILABILITY_FUTURE __packaged_task_function<_Rp(_ArgTypes...)>
1692{
1693    typedef __packaged_task_base<_Rp(_ArgTypes...)> __base;
1694
1695    _LIBCPP_INLINE_VISIBILITY _LIBCPP_NO_CFI
1696    __base* __get_buf() { return (__base*)&__buf_; }
1697
1698    typename aligned_storage<3*sizeof(void*)>::type __buf_;
1699    __base* __f_;
1700
1701public:
1702    typedef _Rp result_type;
1703
1704    // construct/copy/destroy:
1705    _LIBCPP_INLINE_VISIBILITY
1706    __packaged_task_function() _NOEXCEPT : __f_(nullptr) {}
1707    template<class _Fp>
1708      __packaged_task_function(_Fp&& __f);
1709    template<class _Fp, class _Alloc>
1710      __packaged_task_function(allocator_arg_t, const _Alloc& __a, _Fp&& __f);
1711
1712    __packaged_task_function(__packaged_task_function&&) _NOEXCEPT;
1713    __packaged_task_function& operator=(__packaged_task_function&&) _NOEXCEPT;
1714
1715    __packaged_task_function(const __packaged_task_function&) =  delete;
1716    __packaged_task_function& operator=(const __packaged_task_function&) =  delete;
1717
1718    ~__packaged_task_function();
1719
1720    void swap(__packaged_task_function&) _NOEXCEPT;
1721
1722    _LIBCPP_INLINE_VISIBILITY
1723    _Rp operator()(_ArgTypes...) const;
1724};
1725
1726template<class _Rp, class ..._ArgTypes>
1727__packaged_task_function<_Rp(_ArgTypes...)>::__packaged_task_function(__packaged_task_function&& __f) _NOEXCEPT
1728{
1729    if (__f.__f_ == nullptr)
1730        __f_ = nullptr;
1731    else if (__f.__f_ == __f.__get_buf())
1732    {
1733        __f.__f_->__move_to(__get_buf());
1734        __f_ = (__base*)&__buf_;
1735    }
1736    else
1737    {
1738        __f_ = __f.__f_;
1739        __f.__f_ = nullptr;
1740    }
1741}
1742
1743template<class _Rp, class ..._ArgTypes>
1744template <class _Fp>
1745__packaged_task_function<_Rp(_ArgTypes...)>::__packaged_task_function(_Fp&& __f)
1746    : __f_(nullptr)
1747{
1748    typedef typename remove_reference<typename decay<_Fp>::type>::type _FR;
1749    typedef __packaged_task_func<_FR, allocator<_FR>, _Rp(_ArgTypes...)> _FF;
1750    if (sizeof(_FF) <= sizeof(__buf_))
1751    {
1752        ::new (&__buf_) _FF(_VSTD::forward<_Fp>(__f));
1753        __f_ = (__base*)&__buf_;
1754    }
1755    else
1756    {
1757        typedef allocator<_FF> _Ap;
1758        _Ap __a;
1759        typedef __allocator_destructor<_Ap> _Dp;
1760        unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
1761        ::new (__hold.get()) _FF(_VSTD::forward<_Fp>(__f), allocator<_FR>(__a));
1762        __f_ = __hold.release();
1763    }
1764}
1765
1766template<class _Rp, class ..._ArgTypes>
1767template <class _Fp, class _Alloc>
1768__packaged_task_function<_Rp(_ArgTypes...)>::__packaged_task_function(
1769                                  allocator_arg_t, const _Alloc& __a0, _Fp&& __f)
1770    : __f_(nullptr)
1771{
1772    typedef typename remove_reference<typename decay<_Fp>::type>::type _FR;
1773    typedef __packaged_task_func<_FR, _Alloc, _Rp(_ArgTypes...)> _FF;
1774    if (sizeof(_FF) <= sizeof(__buf_))
1775    {
1776        __f_ = (__base*)&__buf_;
1777        ::new (__f_) _FF(_VSTD::forward<_Fp>(__f));
1778    }
1779    else
1780    {
1781        typedef typename __allocator_traits_rebind<_Alloc, _FF>::type _Ap;
1782        _Ap __a(__a0);
1783        typedef __allocator_destructor<_Ap> _Dp;
1784        unique_ptr<__base, _Dp> __hold(__a.allocate(1), _Dp(__a, 1));
1785        ::new (static_cast<void*>(_VSTD::addressof(*__hold.get())))
1786            _FF(_VSTD::forward<_Fp>(__f), _Alloc(__a));
1787        __f_ = _VSTD::addressof(*__hold.release());
1788    }
1789}
1790
1791template<class _Rp, class ..._ArgTypes>
1792__packaged_task_function<_Rp(_ArgTypes...)>&
1793__packaged_task_function<_Rp(_ArgTypes...)>::operator=(__packaged_task_function&& __f) _NOEXCEPT
1794{
1795    if (__f_ == __get_buf())
1796        __f_->destroy();
1797    else if (__f_)
1798        __f_->destroy_deallocate();
1799    __f_ = nullptr;
1800    if (__f.__f_ == nullptr)
1801        __f_ = nullptr;
1802    else if (__f.__f_ == __f.__get_buf())
1803    {
1804        __f.__f_->__move_to(__get_buf());
1805        __f_ = __get_buf();
1806    }
1807    else
1808    {
1809        __f_ = __f.__f_;
1810        __f.__f_ = nullptr;
1811    }
1812    return *this;
1813}
1814
1815template<class _Rp, class ..._ArgTypes>
1816__packaged_task_function<_Rp(_ArgTypes...)>::~__packaged_task_function()
1817{
1818    if (__f_ == __get_buf())
1819        __f_->destroy();
1820    else if (__f_)
1821        __f_->destroy_deallocate();
1822}
1823
1824template<class _Rp, class ..._ArgTypes>
1825_LIBCPP_NO_CFI
1826void
1827__packaged_task_function<_Rp(_ArgTypes...)>::swap(__packaged_task_function& __f) _NOEXCEPT
1828{
1829    if (__f_ == (__base*)&__buf_ && __f.__f_ == (__base*)&__f.__buf_)
1830    {
1831        typename aligned_storage<sizeof(__buf_)>::type __tempbuf;
1832        __base* __t = (__base*)&__tempbuf;
1833        __f_->__move_to(__t);
1834        __f_->destroy();
1835        __f_ = nullptr;
1836        __f.__f_->__move_to((__base*)&__buf_);
1837        __f.__f_->destroy();
1838        __f.__f_ = nullptr;
1839        __f_ = (__base*)&__buf_;
1840        __t->__move_to((__base*)&__f.__buf_);
1841        __t->destroy();
1842        __f.__f_ = (__base*)&__f.__buf_;
1843    }
1844    else if (__f_ == (__base*)&__buf_)
1845    {
1846        __f_->__move_to((__base*)&__f.__buf_);
1847        __f_->destroy();
1848        __f_ = __f.__f_;
1849        __f.__f_ = (__base*)&__f.__buf_;
1850    }
1851    else if (__f.__f_ == (__base*)&__f.__buf_)
1852    {
1853        __f.__f_->__move_to((__base*)&__buf_);
1854        __f.__f_->destroy();
1855        __f.__f_ = __f_;
1856        __f_ = (__base*)&__buf_;
1857    }
1858    else
1859        _VSTD::swap(__f_, __f.__f_);
1860}
1861
1862template<class _Rp, class ..._ArgTypes>
1863inline
1864_Rp
1865__packaged_task_function<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __arg) const
1866{
1867    return (*__f_)(_VSTD::forward<_ArgTypes>(__arg)...);
1868}
1869
1870template<class _Rp, class ..._ArgTypes>
1871class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE packaged_task<_Rp(_ArgTypes...)>
1872{
1873public:
1874    typedef _Rp result_type; // extension
1875
1876private:
1877    __packaged_task_function<result_type(_ArgTypes...)> __f_;
1878    promise<result_type>                                __p_;
1879
1880public:
1881    // construction and destruction
1882    _LIBCPP_INLINE_VISIBILITY
1883    packaged_task() _NOEXCEPT : __p_(nullptr) {}
1884    template <class _Fp,
1885              class = typename enable_if
1886              <
1887                  !is_same<
1888                      typename __uncvref<_Fp>::type,
1889                      packaged_task
1890                      >::value
1891                  >::type
1892             >
1893        _LIBCPP_INLINE_VISIBILITY
1894        explicit packaged_task(_Fp&& __f) : __f_(_VSTD::forward<_Fp>(__f)) {}
1895    template <class _Fp, class _Allocator,
1896              class = typename enable_if
1897              <
1898                  !is_same<
1899                      typename __uncvref<_Fp>::type,
1900                      packaged_task
1901                      >::value
1902                  >::type
1903              >
1904        _LIBCPP_INLINE_VISIBILITY
1905        packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
1906             : __f_(allocator_arg, __a, _VSTD::forward<_Fp>(__f)),
1907               __p_(allocator_arg, __a) {}
1908    // ~packaged_task() = default;
1909
1910    // no copy
1911    packaged_task(const packaged_task&) = delete;
1912    packaged_task& operator=(const packaged_task&) = delete;
1913
1914    // move support
1915    _LIBCPP_INLINE_VISIBILITY
1916    packaged_task(packaged_task&& __other) _NOEXCEPT
1917        : __f_(_VSTD::move(__other.__f_)), __p_(_VSTD::move(__other.__p_)) {}
1918    _LIBCPP_INLINE_VISIBILITY
1919    packaged_task& operator=(packaged_task&& __other) _NOEXCEPT
1920    {
1921        __f_ = _VSTD::move(__other.__f_);
1922        __p_ = _VSTD::move(__other.__p_);
1923        return *this;
1924    }
1925    _LIBCPP_INLINE_VISIBILITY
1926    void swap(packaged_task& __other) _NOEXCEPT
1927    {
1928        __f_.swap(__other.__f_);
1929        __p_.swap(__other.__p_);
1930    }
1931
1932    _LIBCPP_INLINE_VISIBILITY
1933    bool valid() const _NOEXCEPT {return __p_.__state_ != nullptr;}
1934
1935    // result retrieval
1936    _LIBCPP_INLINE_VISIBILITY
1937    future<result_type> get_future() {return __p_.get_future();}
1938
1939    // execution
1940    void operator()(_ArgTypes... __args);
1941    void make_ready_at_thread_exit(_ArgTypes... __args);
1942
1943    void reset();
1944};
1945
1946template<class _Rp, class ..._ArgTypes>
1947void
1948packaged_task<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __args)
1949{
1950    if (__p_.__state_ == nullptr)
1951        __throw_future_error(future_errc::no_state);
1952    if (__p_.__state_->__has_value())
1953        __throw_future_error(future_errc::promise_already_satisfied);
1954#ifndef _LIBCPP_NO_EXCEPTIONS
1955    try
1956    {
1957#endif  // _LIBCPP_NO_EXCEPTIONS
1958        __p_.set_value(__f_(_VSTD::forward<_ArgTypes>(__args)...));
1959#ifndef _LIBCPP_NO_EXCEPTIONS
1960    }
1961    catch (...)
1962    {
1963        __p_.set_exception(current_exception());
1964    }
1965#endif  // _LIBCPP_NO_EXCEPTIONS
1966}
1967
1968template<class _Rp, class ..._ArgTypes>
1969void
1970packaged_task<_Rp(_ArgTypes...)>::make_ready_at_thread_exit(_ArgTypes... __args)
1971{
1972    if (__p_.__state_ == nullptr)
1973        __throw_future_error(future_errc::no_state);
1974    if (__p_.__state_->__has_value())
1975        __throw_future_error(future_errc::promise_already_satisfied);
1976#ifndef _LIBCPP_NO_EXCEPTIONS
1977    try
1978    {
1979#endif  // _LIBCPP_NO_EXCEPTIONS
1980        __p_.set_value_at_thread_exit(__f_(_VSTD::forward<_ArgTypes>(__args)...));
1981#ifndef _LIBCPP_NO_EXCEPTIONS
1982    }
1983    catch (...)
1984    {
1985        __p_.set_exception_at_thread_exit(current_exception());
1986    }
1987#endif  // _LIBCPP_NO_EXCEPTIONS
1988}
1989
1990template<class _Rp, class ..._ArgTypes>
1991void
1992packaged_task<_Rp(_ArgTypes...)>::reset()
1993{
1994    if (!valid())
1995        __throw_future_error(future_errc::no_state);
1996    __p_ = promise<result_type>();
1997}
1998
1999template<class ..._ArgTypes>
2000class _LIBCPP_TEMPLATE_VIS _LIBCPP_AVAILABILITY_FUTURE packaged_task<void(_ArgTypes...)>
2001{
2002public:
2003    typedef void result_type; // extension
2004
2005private:
2006    __packaged_task_function<result_type(_ArgTypes...)> __f_;
2007    promise<result_type>                                __p_;
2008
2009public:
2010    // construction and destruction
2011    _LIBCPP_INLINE_VISIBILITY
2012    packaged_task() _NOEXCEPT : __p_(nullptr) {}
2013    template <class _Fp,
2014              class = typename enable_if
2015              <
2016                  !is_same<
2017                      typename __uncvref<_Fp>::type,
2018                      packaged_task
2019                      >::value
2020                  >::type
2021              >
2022        _LIBCPP_INLINE_VISIBILITY
2023        explicit packaged_task(_Fp&& __f) : __f_(_VSTD::forward<_Fp>(__f)) {}
2024    template <class _Fp, class _Allocator,
2025              class = typename enable_if
2026              <
2027                  !is_same<
2028                      typename __uncvref<_Fp>::type,
2029                      packaged_task
2030                      >::value
2031                  >::type
2032              >
2033        _LIBCPP_INLINE_VISIBILITY
2034        packaged_task(allocator_arg_t, const _Allocator& __a, _Fp&& __f)
2035             : __f_(allocator_arg, __a, _VSTD::forward<_Fp>(__f)),
2036               __p_(allocator_arg, __a) {}
2037    // ~packaged_task() = default;
2038
2039    // no copy
2040    packaged_task(const packaged_task&) = delete;
2041    packaged_task& operator=(const packaged_task&) = delete;
2042
2043    // move support
2044    _LIBCPP_INLINE_VISIBILITY
2045    packaged_task(packaged_task&& __other) _NOEXCEPT
2046        : __f_(_VSTD::move(__other.__f_)), __p_(_VSTD::move(__other.__p_)) {}
2047    _LIBCPP_INLINE_VISIBILITY
2048    packaged_task& operator=(packaged_task&& __other) _NOEXCEPT
2049    {
2050        __f_ = _VSTD::move(__other.__f_);
2051        __p_ = _VSTD::move(__other.__p_);
2052        return *this;
2053    }
2054    _LIBCPP_INLINE_VISIBILITY
2055    void swap(packaged_task& __other) _NOEXCEPT
2056    {
2057        __f_.swap(__other.__f_);
2058        __p_.swap(__other.__p_);
2059    }
2060
2061    _LIBCPP_INLINE_VISIBILITY
2062    bool valid() const _NOEXCEPT {return __p_.__state_ != nullptr;}
2063
2064    // result retrieval
2065    _LIBCPP_INLINE_VISIBILITY
2066    future<result_type> get_future() {return __p_.get_future();}
2067
2068    // execution
2069    void operator()(_ArgTypes... __args);
2070    void make_ready_at_thread_exit(_ArgTypes... __args);
2071
2072    void reset();
2073};
2074
2075template<class ..._ArgTypes>
2076void
2077packaged_task<void(_ArgTypes...)>::operator()(_ArgTypes... __args)
2078{
2079    if (__p_.__state_ == nullptr)
2080        __throw_future_error(future_errc::no_state);
2081    if (__p_.__state_->__has_value())
2082        __throw_future_error(future_errc::promise_already_satisfied);
2083#ifndef _LIBCPP_NO_EXCEPTIONS
2084    try
2085    {
2086#endif  // _LIBCPP_NO_EXCEPTIONS
2087        __f_(_VSTD::forward<_ArgTypes>(__args)...);
2088        __p_.set_value();
2089#ifndef _LIBCPP_NO_EXCEPTIONS
2090    }
2091    catch (...)
2092    {
2093        __p_.set_exception(current_exception());
2094    }
2095#endif  // _LIBCPP_NO_EXCEPTIONS
2096}
2097
2098template<class ..._ArgTypes>
2099void
2100packaged_task<void(_ArgTypes...)>::make_ready_at_thread_exit(_ArgTypes... __args)
2101{
2102    if (__p_.__state_ == nullptr)
2103        __throw_future_error(future_errc::no_state);
2104    if (__p_.__state_->__has_value())
2105        __throw_future_error(future_errc::promise_already_satisfied);
2106#ifndef _LIBCPP_NO_EXCEPTIONS
2107    try
2108    {
2109#endif  // _LIBCPP_NO_EXCEPTIONS
2110        __f_(_VSTD::forward<_ArgTypes>(__args)...);
2111        __p_.set_value_at_thread_exit();
2112#ifndef _LIBCPP_NO_EXCEPTIONS
2113    }
2114    catch (...)
2115    {
2116        __p_.set_exception_at_thread_exit(current_exception());
2117    }
2118#endif  // _LIBCPP_NO_EXCEPTIONS
2119}
2120
2121template<class ..._ArgTypes>
2122void
2123packaged_task<void(_ArgTypes...)>::reset()
2124{
2125    if (!valid())
2126        __throw_future_error(future_errc::no_state);
2127    __p_ = promise<result_type>();
2128}
2129
2130template <class _Callable>
2131inline _LIBCPP_INLINE_VISIBILITY
2132void
2133swap(packaged_task<_Callable>& __x, packaged_task<_Callable>& __y) _NOEXCEPT
2134{
2135    __x.swap(__y);
2136}
2137
2138template <class _Callable, class _Alloc>
2139struct _LIBCPP_TEMPLATE_VIS uses_allocator<packaged_task<_Callable>, _Alloc>
2140    : public true_type {};
2141
2142template <class _Rp, class _Fp>
2143_LIBCPP_INLINE_VISIBILITY future<_Rp>
2144__make_deferred_assoc_state(_Fp&& __f)
2145{
2146    unique_ptr<__deferred_assoc_state<_Rp, _Fp>, __release_shared_count>
2147        __h(new __deferred_assoc_state<_Rp, _Fp>(_VSTD::forward<_Fp>(__f)));
2148    return future<_Rp>(__h.get());
2149}
2150
2151template <class _Rp, class _Fp>
2152_LIBCPP_INLINE_VISIBILITY future<_Rp>
2153__make_async_assoc_state(_Fp&& __f)
2154{
2155    unique_ptr<__async_assoc_state<_Rp, _Fp>, __release_shared_count>
2156        __h(new __async_assoc_state<_Rp, _Fp>(_VSTD::forward<_Fp>(__f)));
2157    _VSTD::thread(&__async_assoc_state<_Rp, _Fp>::__execute, __h.get()).detach();
2158    return future<_Rp>(__h.get());
2159}
2160
2161template <class _Fp, class... _Args>
2162class _LIBCPP_HIDDEN __async_func
2163{
2164    tuple<_Fp, _Args...> __f_;
2165
2166public:
2167    typedef typename __invoke_of<_Fp, _Args...>::type _Rp;
2168
2169    _LIBCPP_INLINE_VISIBILITY
2170    explicit __async_func(_Fp&& __f, _Args&&... __args)
2171        : __f_(_VSTD::move(__f), _VSTD::move(__args)...) {}
2172
2173    _LIBCPP_INLINE_VISIBILITY
2174    __async_func(__async_func&& __f) : __f_(_VSTD::move(__f.__f_)) {}
2175
2176    _Rp operator()()
2177    {
2178        typedef typename __make_tuple_indices<1+sizeof...(_Args), 1>::type _Index;
2179        return __execute(_Index());
2180    }
2181private:
2182    template <size_t ..._Indices>
2183    _Rp
2184    __execute(__tuple_indices<_Indices...>)
2185    {
2186        return __invoke(_VSTD::move(_VSTD::get<0>(__f_)), _VSTD::move(_VSTD::get<_Indices>(__f_))...);
2187    }
2188};
2189
2190inline _LIBCPP_INLINE_VISIBILITY bool __does_policy_contain(launch __policy, launch __value )
2191{ return (int(__policy) & int(__value)) != 0; }
2192
2193template <class _Fp, class... _Args>
2194_LIBCPP_NODISCARD_AFTER_CXX17
2195future<typename __invoke_of<typename decay<_Fp>::type, typename decay<_Args>::type...>::type>
2196async(launch __policy, _Fp&& __f, _Args&&... __args)
2197{
2198    typedef __async_func<typename decay<_Fp>::type, typename decay<_Args>::type...> _BF;
2199    typedef typename _BF::_Rp _Rp;
2200
2201#ifndef _LIBCPP_NO_EXCEPTIONS
2202    try
2203    {
2204#endif
2205        if (__does_policy_contain(__policy, launch::async))
2206        return _VSTD::__make_async_assoc_state<_Rp>(_BF(__decay_copy(_VSTD::forward<_Fp>(__f)),
2207                                                     __decay_copy(_VSTD::forward<_Args>(__args))...));
2208#ifndef _LIBCPP_NO_EXCEPTIONS
2209    }
2210    catch ( ... ) { if (__policy == launch::async) throw ; }
2211#endif
2212
2213    if (__does_policy_contain(__policy, launch::deferred))
2214        return _VSTD::__make_deferred_assoc_state<_Rp>(_BF(__decay_copy(_VSTD::forward<_Fp>(__f)),
2215                                                        __decay_copy(_VSTD::forward<_Args>(__args))...));
2216    return future<_Rp>{};
2217}
2218
2219template <class _Fp, class... _Args>
2220_LIBCPP_NODISCARD_AFTER_CXX17 inline _LIBCPP_INLINE_VISIBILITY
2221future<typename __invoke_of<typename decay<_Fp>::type, typename decay<_Args>::type...>::type>
2222async(_Fp&& __f, _Args&&... __args)
2223{
2224    return _VSTD::async(launch::any, _VSTD::forward<_Fp>(__f),
2225                                    _VSTD::forward<_Args>(__args)...);
2226}
2227
2228#endif  // _LIBCPP_HAS_NO_VARIADICS
2229
2230// shared_future
2231
2232template <class _Rp>
2233class _LIBCPP_TEMPLATE_VIS shared_future
2234{
2235    __assoc_state<_Rp>* __state_;
2236
2237public:
2238    _LIBCPP_INLINE_VISIBILITY
2239    shared_future() _NOEXCEPT : __state_(nullptr) {}
2240    _LIBCPP_INLINE_VISIBILITY
2241    shared_future(const shared_future& __rhs)  _NOEXCEPT : __state_(__rhs.__state_)
2242        {if (__state_) __state_->__add_shared();}
2243    _LIBCPP_INLINE_VISIBILITY
2244    shared_future(future<_Rp>&& __f) _NOEXCEPT : __state_(__f.__state_)
2245        {__f.__state_ = nullptr;}
2246    _LIBCPP_INLINE_VISIBILITY
2247    shared_future(shared_future&& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
2248        {__rhs.__state_ = nullptr;}
2249    ~shared_future();
2250    shared_future& operator=(const shared_future& __rhs) _NOEXCEPT;
2251    _LIBCPP_INLINE_VISIBILITY
2252    shared_future& operator=(shared_future&& __rhs) _NOEXCEPT
2253        {
2254            shared_future(std::move(__rhs)).swap(*this);
2255            return *this;
2256        }
2257
2258    // retrieving the value
2259    _LIBCPP_INLINE_VISIBILITY
2260    const _Rp& get() const {return __state_->copy();}
2261
2262    _LIBCPP_INLINE_VISIBILITY
2263    void swap(shared_future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
2264
2265    // functions to check state
2266    _LIBCPP_INLINE_VISIBILITY
2267    bool valid() const _NOEXCEPT {return __state_ != nullptr;}
2268
2269    _LIBCPP_INLINE_VISIBILITY
2270    void wait() const {__state_->wait();}
2271    template <class _Rep, class _Period>
2272        _LIBCPP_INLINE_VISIBILITY
2273        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>
2277        _LIBCPP_INLINE_VISIBILITY
2278        future_status
2279        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
2280            {return __state_->wait_until(__abs_time);}
2281};
2282
2283template <class _Rp>
2284shared_future<_Rp>::~shared_future()
2285{
2286    if (__state_)
2287        __state_->__release_shared();
2288}
2289
2290template <class _Rp>
2291shared_future<_Rp>&
2292shared_future<_Rp>::operator=(const shared_future& __rhs) _NOEXCEPT
2293{
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
2302template <class _Rp>
2303class _LIBCPP_TEMPLATE_VIS shared_future<_Rp&>
2304{
2305    __assoc_state<_Rp&>* __state_;
2306
2307public:
2308    _LIBCPP_INLINE_VISIBILITY
2309    shared_future() _NOEXCEPT : __state_(nullptr) {}
2310    _LIBCPP_INLINE_VISIBILITY
2311    shared_future(const shared_future& __rhs) : __state_(__rhs.__state_)
2312        {if (__state_) __state_->__add_shared();}
2313    _LIBCPP_INLINE_VISIBILITY
2314    shared_future(future<_Rp&>&& __f) _NOEXCEPT : __state_(__f.__state_)
2315        {__f.__state_ = nullptr;}
2316    _LIBCPP_INLINE_VISIBILITY
2317    shared_future(shared_future&& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
2318        {__rhs.__state_ = nullptr;}
2319    ~shared_future();
2320    shared_future& operator=(const shared_future& __rhs);
2321    _LIBCPP_INLINE_VISIBILITY
2322    shared_future& operator=(shared_future&& __rhs) _NOEXCEPT
2323        {
2324            shared_future(std::move(__rhs)).swap(*this);
2325            return *this;
2326        }
2327
2328    // retrieving the value
2329    _LIBCPP_INLINE_VISIBILITY
2330    _Rp& get() const {return __state_->copy();}
2331
2332    _LIBCPP_INLINE_VISIBILITY
2333    void swap(shared_future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
2334
2335    // functions to check state
2336    _LIBCPP_INLINE_VISIBILITY
2337    bool valid() const _NOEXCEPT {return __state_ != nullptr;}
2338
2339    _LIBCPP_INLINE_VISIBILITY
2340    void wait() const {__state_->wait();}
2341    template <class _Rep, class _Period>
2342        _LIBCPP_INLINE_VISIBILITY
2343        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>
2347        _LIBCPP_INLINE_VISIBILITY
2348        future_status
2349        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
2350            {return __state_->wait_until(__abs_time);}
2351};
2352
2353template <class _Rp>
2354shared_future<_Rp&>::~shared_future()
2355{
2356    if (__state_)
2357        __state_->__release_shared();
2358}
2359
2360template <class _Rp>
2361shared_future<_Rp&>&
2362shared_future<_Rp&>::operator=(const shared_future& __rhs)
2363{
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 <>
2373class _LIBCPP_TYPE_VIS _LIBCPP_AVAILABILITY_FUTURE shared_future<void>
2374{
2375    __assoc_sub_state* __state_;
2376
2377public:
2378    _LIBCPP_INLINE_VISIBILITY
2379    shared_future() _NOEXCEPT : __state_(nullptr) {}
2380    _LIBCPP_INLINE_VISIBILITY
2381    shared_future(const shared_future& __rhs) : __state_(__rhs.__state_)
2382        {if (__state_) __state_->__add_shared();}
2383    _LIBCPP_INLINE_VISIBILITY
2384    shared_future(future<void>&& __f) _NOEXCEPT : __state_(__f.__state_)
2385        {__f.__state_ = nullptr;}
2386    _LIBCPP_INLINE_VISIBILITY
2387    shared_future(shared_future&& __rhs) _NOEXCEPT : __state_(__rhs.__state_)
2388        {__rhs.__state_ = nullptr;}
2389    ~shared_future();
2390    shared_future& operator=(const shared_future& __rhs);
2391    _LIBCPP_INLINE_VISIBILITY
2392    shared_future& operator=(shared_future&& __rhs) _NOEXCEPT
2393        {
2394            shared_future(std::move(__rhs)).swap(*this);
2395            return *this;
2396        }
2397
2398    // retrieving the value
2399    _LIBCPP_INLINE_VISIBILITY
2400    void get() const {__state_->copy();}
2401
2402    _LIBCPP_INLINE_VISIBILITY
2403    void swap(shared_future& __rhs) _NOEXCEPT {_VSTD::swap(__state_, __rhs.__state_);}
2404
2405    // functions to check state
2406    _LIBCPP_INLINE_VISIBILITY
2407    bool valid() const _NOEXCEPT {return __state_ != nullptr;}
2408
2409    _LIBCPP_INLINE_VISIBILITY
2410    void wait() const {__state_->wait();}
2411    template <class _Rep, class _Period>
2412        _LIBCPP_INLINE_VISIBILITY
2413        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>
2417        _LIBCPP_INLINE_VISIBILITY
2418        future_status
2419        wait_until(const chrono::time_point<_Clock, _Duration>& __abs_time) const
2420            {return __state_->wait_until(__abs_time);}
2421};
2422
2423template <class _Rp>
2424inline _LIBCPP_INLINE_VISIBILITY
2425void
2426swap(shared_future<_Rp>& __x, shared_future<_Rp>& __y) _NOEXCEPT
2427{
2428    __x.swap(__y);
2429}
2430
2431template <class _Rp>
2432inline
2433shared_future<_Rp>
2434future<_Rp>::share() _NOEXCEPT
2435{
2436    return shared_future<_Rp>(_VSTD::move(*this));
2437}
2438
2439template <class _Rp>
2440inline
2441shared_future<_Rp&>
2442future<_Rp&>::share() _NOEXCEPT
2443{
2444    return shared_future<_Rp&>(_VSTD::move(*this));
2445}
2446
2447inline
2448shared_future<void>
2449future<void>::share() _NOEXCEPT
2450{
2451    return shared_future<void>(_VSTD::move(*this));
2452}
2453
2454_LIBCPP_END_NAMESPACE_STD
2455
2456#endif // !_LIBCPP_HAS_NO_THREADS
2457
2458#endif  // _LIBCPP_FUTURE
2459