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