diff --git a/include/boost/thread/future.hpp b/include/boost/thread/future.hpp index 7252465f7..7736156c3 100644 --- a/include/boost/thread/future.hpp +++ b/include/boost/thread/future.hpp @@ -1399,18 +1399,18 @@ namespace boost template BOOST_THREAD_FUTURE - make_future_async_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + make_future_async_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); template BOOST_THREAD_FUTURE - make_future_deferred_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + make_future_deferred_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); #endif #if defined BOOST_THREAD_PROVIDES_FUTURE_UNWRAP template struct future_unwrap_shared_state; template inline BOOST_THREAD_FUTURE - make_future_unwrap_shared_state(boost::unique_lock &lock, F& f); + make_future_unwrap_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f); #endif } @@ -1431,18 +1431,18 @@ namespace boost template friend BOOST_THREAD_FUTURE - detail::make_future_async_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + detail::make_future_async_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); template friend BOOST_THREAD_FUTURE - detail::make_future_deferred_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + detail::make_future_deferred_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); #endif #if defined BOOST_THREAD_PROVIDES_FUTURE_UNWRAP template friend struct detail::future_unwrap_shared_state; template friend BOOST_THREAD_FUTURE - detail::make_future_unwrap_shared_state(boost::unique_lock &lock, F& f); + detail::make_future_unwrap_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f); #endif #if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK template friend class packaged_task; // todo check if this works in windows @@ -1470,7 +1470,7 @@ namespace boost public: BOOST_THREAD_MOVABLE_ONLY(BOOST_THREAD_FUTURE) typedef future_state::state state; - typedef R value_type; + typedef R value_type; // EXTENSION BOOST_CONSTEXPR BOOST_THREAD_FUTURE() {} @@ -1480,7 +1480,7 @@ namespace boost base_type(boost::move(static_cast(BOOST_THREAD_RV(other)))) { } - inline BOOST_THREAD_FUTURE(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE >) other); + inline BOOST_THREAD_FUTURE(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE >) other); // EXTENSION BOOST_THREAD_FUTURE& operator=(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE) other) BOOST_NOEXCEPT { @@ -1546,7 +1546,7 @@ namespace boost template typename disable_if< is_void, move_dest_type>::type - get_or(R2 const& v) + get_or(R2 const& v) // EXTENSION { if(!this->future_) { @@ -1578,18 +1578,18 @@ namespace boost // inline BOOST_THREAD_FUTURE then(launch policy, RF(*func)(BOOST_THREAD_FUTURE&)); //#endif template - inline BOOST_THREAD_FUTURE::type> - then(BOOST_THREAD_FWD_REF(F) func); + inline BOOST_THREAD_FUTURE::type> + then(BOOST_THREAD_FWD_REF(F) func); // EXTENSION template - inline BOOST_THREAD_FUTURE::type> - then(launch policy, BOOST_THREAD_FWD_REF(F) func); + inline BOOST_THREAD_FUTURE::type> + then(launch policy, BOOST_THREAD_FWD_REF(F) func); // EXTENSION template inline typename disable_if< is_void, BOOST_THREAD_FUTURE >::type - fallback_to(BOOST_THREAD_RV_REF(R2) v); + fallback_to(BOOST_THREAD_RV_REF(R2) v); // EXTENSION template inline typename disable_if< is_void, BOOST_THREAD_FUTURE >::type - fallback_to(R2 const& v); + fallback_to(R2 const& v); // EXTENSION #endif @@ -1626,18 +1626,18 @@ namespace boost template friend BOOST_THREAD_FUTURE - detail::make_future_async_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + detail::make_future_async_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); template friend BOOST_THREAD_FUTURE - detail::make_future_deferred_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + detail::make_future_deferred_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); #endif #if defined BOOST_THREAD_PROVIDES_FUTURE_UNWRAP template friend struct detail::future_unwrap_shared_state; template friend BOOST_THREAD_FUTURE - detail::make_future_unwrap_shared_state(boost::unique_lock &lock, F& f); + detail::make_future_unwrap_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f); #endif #if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK template friend class packaged_task; // todo check if this works in windows @@ -1665,7 +1665,7 @@ namespace boost public: BOOST_THREAD_MOVABLE_ONLY(BOOST_THREAD_FUTURE) typedef future_state::state state; - typedef R value_type; + typedef R value_type; // EXTENSION BOOST_CONSTEXPR BOOST_THREAD_FUTURE() {} @@ -1716,7 +1716,7 @@ namespace boost #endif return fut_->get(); } - move_dest_type get_or(BOOST_THREAD_RV_REF(R) v) + move_dest_type get_or(BOOST_THREAD_RV_REF(R) v) // EXTENSION { if(!this->future_) { @@ -1731,7 +1731,7 @@ namespace boost else return boost::move(v); } - move_dest_type get_or(R const& v) + move_dest_type get_or(R const& v) // EXTENSION { if(!this->future_) { @@ -1759,17 +1759,17 @@ namespace boost // inline BOOST_THREAD_FUTURE then(launch policy, RF(*func)(BOOST_THREAD_FUTURE&)); //#endif template - inline BOOST_THREAD_FUTURE::type> - then(BOOST_THREAD_FWD_REF(F) func); + inline BOOST_THREAD_FUTURE::type> + then(BOOST_THREAD_FWD_REF(F) func); // EXTENSION template - inline BOOST_THREAD_FUTURE::type> - then(launch policy, BOOST_THREAD_FWD_REF(F) func); + inline BOOST_THREAD_FUTURE::type> + then(launch policy, BOOST_THREAD_FWD_REF(F) func); // EXTENSION #endif #if defined BOOST_THREAD_PROVIDES_FUTURE_UNWRAP inline BOOST_THREAD_FUTURE - unwrap(); + unwrap(); // EXTENSION #endif }; @@ -1792,11 +1792,11 @@ namespace boost template friend BOOST_THREAD_FUTURE - detail::make_future_async_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + detail::make_future_async_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); template friend BOOST_THREAD_FUTURE - detail::make_future_deferred_continuation_shared_state(boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c); + detail::make_future_deferred_continuation_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c); #endif #if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK template friend class packaged_task;// todo check if this works in windows @@ -1809,7 +1809,7 @@ namespace boost public: BOOST_THREAD_MOVABLE(shared_future) - typedef R value_type; + typedef R value_type; // EXTENSION shared_future(shared_future const& other): base_type(other) @@ -1867,7 +1867,7 @@ namespace boost template typename disable_if< is_void, typename detail::shared_state::shared_future_get_result_type>::type - get_or(BOOST_THREAD_RV_REF(R2) v) + get_or(BOOST_THREAD_RV_REF(R2) v) // EXTENSION { if(!this->future_) { @@ -1893,11 +1893,11 @@ namespace boost // inline BOOST_THREAD_FUTURE then(launch policy, RF(*func)(shared_future&)); //#endif template - inline BOOST_THREAD_FUTURE::type> - then(BOOST_THREAD_FWD_REF(F) func); + inline BOOST_THREAD_FUTURE::type> + then(BOOST_THREAD_FWD_REF(F) func); // EXTENSION template - inline BOOST_THREAD_FUTURE::type> - then(launch policy, BOOST_THREAD_FWD_REF(F) func); + inline BOOST_THREAD_FUTURE::type> + then(launch policy, BOOST_THREAD_FWD_REF(F) func); // EXTENSION #endif //#if defined BOOST_THREAD_PROVIDES_FUTURE_UNWRAP // inline @@ -3118,7 +3118,7 @@ namespace boost task = task_ptr(new task_shared_state_type(boost::forward(f))); #else typedef detail::task_shared_state task_shared_state_type; - task = task_ptr(new task_shared_state_type(boost::move(f))); // TODO forward + task = task_ptr(new task_shared_state_type(boost::move(f))); // TODO forward #endif #else typedef detail::task_shared_state task_shared_state_type; @@ -3714,9 +3714,9 @@ namespace boost public: future_async_continuation_shared_state( - F& f, BOOST_THREAD_FWD_REF(Fp) c + BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c ) : - parent(f.future_), + parent(boost::move(f)), continuation(boost::move(c)) { } @@ -3731,7 +3731,7 @@ namespace boost { try { - that->mark_finished_with_result(that->continuation(that->parent)); + that->mark_finished_with_result(that->continuation(boost::move(that->parent))); } #if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS catch(thread_interrupted& ) @@ -3754,10 +3754,9 @@ namespace boost public: future_async_continuation_shared_state( - F& f, BOOST_THREAD_FWD_REF(Fp) c + BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c ) : - parent(f.future_), - //continuation(boost::forward(c) + parent(boost::move(f)), continuation(boost::move(c)) { } @@ -3772,7 +3771,7 @@ namespace boost { try { - that->continuation(that->parent); + that->continuation(boost::move(that->parent)); that->mark_finished_with_result(); } #if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS @@ -3800,10 +3799,9 @@ namespace boost public: future_deferred_continuation_shared_state( - F& f, BOOST_THREAD_FWD_REF(Fp) c + BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c ) : - parent(f.future_), - //continuation(boost::forward(c) + parent(boost::move(f)), continuation(boost::move(c)) { this->set_deferred(); @@ -3817,7 +3815,7 @@ namespace boost virtual void execute(boost::unique_lock& lck) { try { - this->mark_finished_with_result_internal(continuation(parent), lck); + this->mark_finished_with_result_internal(continuation(boost::move(parent)), lck); } catch (...) { @@ -3834,9 +3832,9 @@ namespace boost public: future_deferred_continuation_shared_state( - F& f, BOOST_THREAD_FWD_REF(Fp) c + BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c ): - parent(f.future_), + parent(boost::move(f)), continuation(boost::move(c)) { this->set_deferred(); @@ -3849,7 +3847,7 @@ namespace boost virtual void execute(boost::unique_lock& lck) { try { - continuation(parent); + continuation(boost::move(parent)); this->mark_finished_with_result_internal(lck); } catch (...) @@ -3866,12 +3864,12 @@ namespace boost BOOST_THREAD_FUTURE make_future_deferred_continuation_shared_state( boost::unique_lock &lock, - F& f, BOOST_THREAD_FWD_REF(Fp) c + BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c ) { shared_ptr > - h(new future_deferred_continuation_shared_state(f, boost::forward(c))); - f.future_->set_continuation_ptr(h, lock); + h(new future_deferred_continuation_shared_state(boost::move(f), boost::forward(c))); + h->parent.future_->set_continuation_ptr(h, lock); return BOOST_THREAD_FUTURE(h); } @@ -3881,12 +3879,12 @@ namespace boost template BOOST_THREAD_FUTURE make_future_async_continuation_shared_state( - boost::unique_lock &lock, F& f, BOOST_THREAD_FWD_REF(Fp) c + boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_FWD_REF(Fp) c ) { shared_ptr > - h(new future_async_continuation_shared_state(f, boost::forward(c))); - f.future_->set_continuation_ptr(h, lock); + h(new future_async_continuation_shared_state(boost::move(f), boost::forward(c))); + h->parent.future_->set_continuation_ptr(h, lock); return BOOST_THREAD_FUTURE(h); } @@ -3900,31 +3898,31 @@ namespace boost template template - inline BOOST_THREAD_FUTURE&)>::type> + inline BOOST_THREAD_FUTURE)>::type> BOOST_THREAD_FUTURE::then(launch policy, BOOST_THREAD_FWD_REF(F) func) { - typedef typename boost::result_of&)>::type future_type; + typedef typename boost::result_of)>::type future_type; BOOST_THREAD_ASSERT_PRECONDITION(this->future_!=0, future_uninitialized()); boost::unique_lock lock(this->future_->mutex); if (int(policy) & int(launch::async)) { return BOOST_THREAD_MAKE_RV_REF((boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ))); } else if (int(policy) & int(launch::deferred)) { return BOOST_THREAD_MAKE_RV_REF((boost::detail::make_future_deferred_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ))); } else { //BOOST_THREAD_ASSERT_PRECONDITION(false && "invalid launch parameter", std::logic_error("invalid launch parameter")); return BOOST_THREAD_MAKE_RV_REF((boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ))); } @@ -3932,32 +3930,32 @@ namespace boost } template template - inline BOOST_THREAD_FUTURE&)>::type> + inline BOOST_THREAD_FUTURE)>::type> BOOST_THREAD_FUTURE::then(BOOST_THREAD_FWD_REF(F) func) { - typedef typename boost::result_of&)>::type future_type; + typedef typename boost::result_of)>::type future_type; BOOST_THREAD_ASSERT_PRECONDITION(this->future_!=0, future_uninitialized()); boost::unique_lock lock(this->future_->mutex); if (int(this->launch_policy()) & int(launch::async)) { return boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ); } else if (int(this->launch_policy()) & int(launch::deferred)) { this->future_->wait_internal(lock); return boost::detail::make_future_deferred_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ); } else { //BOOST_THREAD_ASSERT_PRECONDITION(false && "invalid launch parameter", std::logic_error("invalid launch parameter")); return boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ); } } @@ -4018,42 +4016,42 @@ namespace boost template template - inline BOOST_THREAD_FUTURE&)>::type> + inline BOOST_THREAD_FUTURE)>::type> shared_future::then(launch policy, BOOST_THREAD_FWD_REF(F) func) { - typedef typename boost::result_of&)>::type future_type; + typedef typename boost::result_of)>::type future_type; BOOST_THREAD_ASSERT_PRECONDITION(this->future_!=0, future_uninitialized()); boost::unique_lock lock(this->future_->mutex); if (int(policy) & int(launch::async)) { return BOOST_THREAD_MAKE_RV_REF((boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ))); } else if (int(policy) & int(launch::deferred)) { return BOOST_THREAD_MAKE_RV_REF((boost::detail::make_future_deferred_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ))); } else { //BOOST_THREAD_ASSERT_PRECONDITION(false && "invalid launch parameter", std::logic_error("invalid launch parameter")); return BOOST_THREAD_MAKE_RV_REF((boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ))); } } template template - inline BOOST_THREAD_FUTURE&)>::type> + inline BOOST_THREAD_FUTURE)>::type> shared_future::then(BOOST_THREAD_FWD_REF(F) func) { - typedef typename boost::result_of&)>::type future_type; + typedef typename boost::result_of)>::type future_type; BOOST_THREAD_ASSERT_PRECONDITION(this->future_!=0, future_uninitialized()); @@ -4061,21 +4059,21 @@ namespace boost if (int(this->launch_policy()) & int(launch::async)) { return boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ); } else if (int(this->launch_policy()) & int(launch::deferred)) { this->future_->wait_internal(lock); return boost::detail::make_future_deferred_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ); } else { //BOOST_THREAD_ASSERT_PRECONDITION(false && "invalid launch parameter", std::logic_error("invalid launch parameter")); return boost::detail::make_future_async_continuation_shared_state, future_type, F>( - lock, *this, boost::forward(func) + lock, boost::move(*this), boost::forward(func) ); } } @@ -4090,7 +4088,7 @@ namespace boost : value_(boost::move(v)) {} - T operator()(BOOST_THREAD_FUTURE& fut) + T operator()(BOOST_THREAD_FUTURE fut) { return fut.get_or(boost::move(value_)); @@ -4105,7 +4103,7 @@ namespace boost : value_(v) {} - T operator()(BOOST_THREAD_FUTURE& fut) + T operator()(BOOST_THREAD_FUTURE fut) { return fut.get_or(value_); @@ -4148,9 +4146,9 @@ namespace boost F parent; public: explicit future_unwrap_shared_state( - F& f + BOOST_THREAD_RV_REF(F) f ) : - parent(f.future_) + parent(boost::move(f)) { } virtual void wait(bool ) // todo see if rethrow must be used @@ -4168,13 +4166,13 @@ namespace boost template BOOST_THREAD_FUTURE - make_future_unwrap_shared_state(boost::unique_lock &lock, F& f) + make_future_unwrap_shared_state(boost::unique_lock &lock, BOOST_THREAD_RV_REF(F) f) { shared_ptr > //shared_ptr > //typename boost::detail::basic_future::future_ptr - h(new future_unwrap_shared_state(f)); - f.future_->set_continuation_ptr(h, lock); + h(new future_unwrap_shared_state(boost::move(f))); + h->parent.future_->set_continuation_ptr(h, lock); return BOOST_THREAD_FUTURE(h); } } @@ -4191,7 +4189,7 @@ namespace boost { BOOST_THREAD_ASSERT_PRECONDITION(this->future_!=0, future_uninitialized()); boost::unique_lock lock(this->future_->mutex); - return boost::detail::make_future_unwrap_shared_state >, R2>(lock, *this); + return boost::detail::make_future_unwrap_shared_state >, R2>(lock, boost::move(*this)); } #endif } diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index 2081b95a1..0904e3de3 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -782,7 +782,6 @@ rule thread-compile ( sources : reqs * : name ) #[ thread-run test_7720.cpp ] #[ thread-run test_7666.cpp ] #[ thread-run test_7755.cpp ] - #[ thread-run ../example/unwrap.cpp ] #[ thread-run ../example/perf_condition_variable.cpp ] #[ thread-run ../example/perf_shared_mutex.cpp ] #[ thread-run ../example/std_async_test.cpp ] diff --git a/test/sync/futures/future/then_pass.cpp b/test/sync/futures/future/then_pass.cpp index e3eb0c4c1..9fcfe51ff 100644 --- a/test/sync/futures/future/then_pass.cpp +++ b/test/sync/futures/future/then_pass.cpp @@ -29,7 +29,7 @@ int p1() return 1; } -int p2(boost::future& f) +int p2(boost::future f) { BOOST_THREAD_LOG << "p2 <" << &f << BOOST_THREAD_END_LOG; BOOST_TEST(f.valid()); @@ -39,7 +39,7 @@ int p2(boost::future& f) return 2 * i; } -void p3(boost::future& f) +void p3(boost::future f) { BOOST_THREAD_LOG << "p3 <" << &f << BOOST_THREAD_END_LOG; BOOST_TEST(f.valid()); @@ -57,6 +57,7 @@ int main() BOOST_TEST(f1.valid()); boost::future f2 = f1.then(&p2); BOOST_TEST(f2.valid()); + BOOST_TEST(! f1.valid()); try { BOOST_TEST(f2.get()==2); diff --git a/test/sync/futures/shared_future/then_pass.cpp b/test/sync/futures/shared_future/then_pass.cpp index 9044e1458..e1adde77d 100644 --- a/test/sync/futures/shared_future/then_pass.cpp +++ b/test/sync/futures/shared_future/then_pass.cpp @@ -28,7 +28,7 @@ int p1() return 1; } -int p2(boost::shared_future& f) +int p2(boost::shared_future f) { BOOST_THREAD_LOG << "p2 <" << &f << BOOST_THREAD_END_LOG; BOOST_TEST(f.valid()); @@ -38,7 +38,7 @@ int p2(boost::shared_future& f) return 2 * i; } -void p3(boost::shared_future& f) +void p3(boost::shared_future f) { BOOST_THREAD_LOG << "p3 <" << &f << BOOST_THREAD_END_LOG; BOOST_TEST(f.valid());