|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r84468 - in branches/release: boost/thread boost/thread/detail libs/thread libs/thread/test/sync/futures/packaged_task
From: vicente.botet_at_[hidden]
Date: 2013-05-24 17:27:54
Author: viboes
Date: 2013-05-24 17:27:53 EDT (Fri, 24 May 2013)
New Revision: 84468
URL: http://svn.boost.org/trac/boost/changeset/84468
Log:
Thread: merge 84414 to fix #8596.
Properties modified:
branches/release/boost/thread/ (props changed)
branches/release/libs/thread/ (props changed)
Text files modified:
branches/release/boost/thread/detail/config.hpp | 6
branches/release/boost/thread/future.hpp | 77 ++++++++----------
branches/release/libs/thread/test/sync/futures/packaged_task/func_ctor_pass.cpp | 161 +++++++++++++++++++++++++++++++++++++--
3 files changed, 187 insertions(+), 57 deletions(-)
Modified: branches/release/boost/thread/detail/config.hpp
==============================================================================
--- branches/release/boost/thread/detail/config.hpp (original)
+++ branches/release/boost/thread/detail/config.hpp 2013-05-24 17:27:53 EDT (Fri, 24 May 2013)
@@ -13,8 +13,6 @@
#include <boost/thread/detail/platform.hpp>
//#define BOOST_THREAD_DONT_PROVIDE_INTERRUPTIONS
-
-
// ATTRIBUTE_MAY_ALIAS
#if defined(__GNUC__) && (__GNUC__ * 100 + __GNUC_MINOR__) > 302 \
@@ -95,9 +93,9 @@
#endif
/// RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR
-#if defined BOOST_NO_CXX11_RVALUE_REFERENCES || defined BOOST_MSVC
+//#if defined BOOST_NO_CXX11_RVALUE_REFERENCES || defined BOOST_MSVC
#define BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR
-#endif
+//#endif
// Default version
#if !defined BOOST_THREAD_VERSION
Modified: branches/release/boost/thread/future.hpp
==============================================================================
--- branches/release/boost/thread/future.hpp (original)
+++ branches/release/boost/thread/future.hpp 2013-05-24 17:27:53 EDT (Fri, 24 May 2013)
@@ -2275,18 +2275,12 @@
task_object(task_object&);
public:
F f;
-#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
- task_object(BOOST_THREAD_RV_REF(F) f_):
- f(boost::forward<F>(f_))
- {}
-#else
task_object(F const& f_):
f(f_)
{}
task_object(BOOST_THREAD_RV_REF(F) f_):
- f(boost::move(f_)) // TODO forward
+ f(boost::move(f_))
{}
-#endif
#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
void do_apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)
@@ -2837,12 +2831,11 @@
#endif
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
template <class F>
- explicit packaged_task(BOOST_THREAD_RV_REF(F) f
+ explicit packaged_task(BOOST_THREAD_FWD_REF(F) f
, typename disable_if<is_same<typename decay<F>::type, packaged_task>, dummy* >::type=0
)
{
- //typedef typename remove_cv<typename remove_reference<F>::type>::type FR;
- typedef F FR;
+ typedef typename remove_cv<typename remove_reference<F>::type>::type FR;
#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
typedef detail::task_object<FR,R(ArgTypes...)> task_object_type;
@@ -2921,10 +2914,9 @@
#if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
template <class F, class Allocator>
- packaged_task(boost::allocator_arg_t, Allocator a, BOOST_THREAD_RV_REF(F) f)
+ packaged_task(boost::allocator_arg_t, Allocator a, BOOST_THREAD_FWD_REF(F) f)
{
- //typedef typename remove_cv<typename remove_reference<F>::type>::type FR;
- typedef F FR;
+ typedef typename remove_cv<typename remove_reference<F>::type>::type FR;
#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
typedef detail::task_object<FR,R(ArgTypes...)> task_object_type;
@@ -3150,11 +3142,6 @@
// future<R> async(launch policy, F&&, ArgTypes&&...);
////////////////////////////////
- ////////////////////////////////
- // template <class F, class... ArgTypes>
- // future<R> async(F&&, ArgTypes&&...);
- ////////////////////////////////
-
#if defined BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR
#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
@@ -3163,8 +3150,9 @@
BOOST_THREAD_FUTURE<R>
async(launch policy, R(*f)(BOOST_THREAD_FWD_REF(ArgTypes)...), BOOST_THREAD_FWD_REF(ArgTypes)... args)
{
- //typedef packaged_task<R(BOOST_THREAD_FWD_REF(ArgTypes)...)> packaged_task_type;
- typedef packaged_task<R(ArgTypes...)> packaged_task_type;
+ typedef R(*F)(BOOST_THREAD_FWD_REF(ArgTypes)...);
+ typedef detail::async_func<typename decay<F>::type, typename decay<ArgTypes>::type...> BF;
+ typedef typename BF::result_type Rp;
#else
template <class R>
BOOST_THREAD_FUTURE<R>
@@ -3181,37 +3169,44 @@
#endif
if (int(policy) & int(launch::async))
{
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ return BOOST_THREAD_MAKE_RV_REF(boost::detail::make_future_async_object<Rp>(
+ BF(
+ thread_detail::decay_copy(boost::forward<F>(f))
+ , thread_detail::decay_copy(boost::forward<ArgTypes>(args))...
+ )
+ ));
+#else
packaged_task_type pt( f );
BOOST_THREAD_FUTURE<R> ret = BOOST_THREAD_MAKE_RV_REF(pt.get_future());
ret.set_async();
-#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
- boost::thread( boost::move(pt), boost::forward<ArgTypes>(args)... ).detach();
-#else
boost::thread( boost::move(pt) ).detach();
-#endif
return ::boost::move(ret);
+#endif
}
else if (int(policy) & int(launch::deferred))
{
- packaged_task_type pt( f );
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ return BOOST_THREAD_MAKE_RV_REF(boost::detail::make_future_deferred_object<Rp>(
+ BF(
+ thread_detail::decay_copy(boost::forward<F>(f))
+ , thread_detail::decay_copy(boost::forward<ArgTypes>(args))...
+ )
+ ));
+#else
+ std::terminate();
+ BOOST_THREAD_FUTURE<R> ret;
+ return ::boost::move(ret);
- BOOST_THREAD_FUTURE<R> ret = pt.get_future();
- ret.set_deferred();
- return ::boost::move(ret);
+#endif
} else {
- //BOOST_THREAD_LOG << "ERROR async "<< int(policy) << BOOST_THREAD_END_LOG;
+ std::terminate();
BOOST_THREAD_FUTURE<R> ret;
return ::boost::move(ret);
}
}
-// template <class R>
-// BOOST_THREAD_FUTURE<R>
-// async(R(*f)())
-// {
-// return BOOST_THREAD_MAKE_RV_REF(async(launch(launch::any), f));
-// }
#endif
#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
@@ -3227,7 +3222,6 @@
typedef typename boost::result_of<typename decay<F>::type(
typename decay<ArgTypes>::type...
)>::type R;
- typedef packaged_task<R(ArgTypes...)> packaged_task_type;
typedef detail::async_func<typename decay<F>::type, typename decay<ArgTypes>::type...> BF;
typedef typename BF::result_type Rp;
@@ -3265,11 +3259,11 @@
BOOST_THREAD_FUTURE<R> ret = pt.get_future();
ret.set_async();
-#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
- boost::thread( boost::move(pt), boost::forward<ArgTypes>(args)... ).detach(); // todo forward
-#else
+//#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+// boost::thread( boost::move(pt), boost::forward<ArgTypes>(args)... ).detach(); // todo forward
+//#else
boost::thread( boost::move(pt) ).detach();
-#endif
+//#endif
return ::boost::move(ret);
#endif
}
@@ -3283,6 +3277,7 @@
)
));
#else
+ std::terminate();
BOOST_THREAD_FUTURE<R> ret;
return ::boost::move(ret);
// return boost::detail::make_future_deferred_object<Rp>(
@@ -3293,7 +3288,7 @@
#endif
} else {
- //BOOST_THREAD_LOG << "ERROR async "<< int(policy) << BOOST_THREAD_END_LOG;
+ std::terminate();
BOOST_THREAD_FUTURE<R> ret;
return ::boost::move(ret);
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/func_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/func_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/func_ctor_pass.cpp 2013-05-24 17:27:53 EDT (Fri, 24 May 2013)
@@ -54,24 +54,43 @@
class A
{
+public:
long data_;
-public:
- BOOST_THREAD_COPYABLE_AND_MOVABLE(A)
static int n_moves;
static int n_copies;
+ BOOST_THREAD_COPYABLE_AND_MOVABLE(A)
+ static void reset()
+ {
+ n_moves=0;
+ n_copies=0;
+ }
explicit A(long i) : data_(i)
{
}
A(BOOST_THREAD_RV_REF(A) a) : data_(BOOST_THREAD_RV(a).data_)
{
- ++n_moves; BOOST_THREAD_RV(a).data_ = -1;
+ BOOST_THREAD_RV(a).data_ = -1;
+ ++n_moves;
+ }
+ A& operator=(BOOST_THREAD_RV_REF(A) a)
+ {
+ data_ = BOOST_THREAD_RV(a).data_;
+ BOOST_THREAD_RV(a).data_ = -1;
+ ++n_moves;
+ return *this;
}
A(const A& a) : data_(a.data_)
{
++n_copies;
}
+ A& operator=(A const& a)
+ {
+ data_ = a.data_;
+ ++n_copies;
+ return *this;
+ }
~A()
{
}
@@ -85,6 +104,78 @@
int A::n_moves = 0;
int A::n_copies = 0;
+class M
+{
+
+public:
+ long data_;
+ static int n_moves;
+
+ BOOST_THREAD_MOVABLE_ONLY(M)
+ static void reset() {
+ n_moves=0;
+ }
+ explicit M(long i) : data_(i)
+ {
+ }
+ M(BOOST_THREAD_RV_REF(M) a) : data_(BOOST_THREAD_RV(a).data_)
+ {
+ BOOST_THREAD_RV(a).data_ = -1;
+ ++n_moves;
+ }
+ M& operator=(BOOST_THREAD_RV_REF(M) a)
+ {
+ data_ = BOOST_THREAD_RV(a).data_;
+ BOOST_THREAD_RV(a).data_ = -1;
+ ++n_moves;
+ return *this;
+ }
+ ~M()
+ {
+ }
+
+ long operator()() const
+ { return data_;}
+ long operator()(long i, long j) const
+ { return data_ + i + j;}
+};
+
+int M::n_moves = 0;
+
+class C
+{
+public:
+ long data_;
+
+ static int n_copies;
+ static void reset()
+ {
+ n_copies=0;
+ }
+
+ explicit C(long i) : data_(i)
+ {
+ }
+ C(const C& a) : data_(a.data_)
+ {
+ ++n_copies;
+ }
+ C& operator=(C const& a)
+ {
+ data_ = a.data_;
+ ++n_copies;
+ return *this;
+ }
+ ~C()
+ {
+ }
+
+ long operator()() const
+ { return data_;}
+ long operator()(long i, long j) const
+ { return data_ + i + j;}
+};
+int C::n_copies = 0;
int main()
{
@@ -99,11 +190,10 @@
#endif
BOOST_TEST(f.get() == BOOST_THREAD_DETAIL_SIGNATURE_2_RES);
BOOST_TEST(A::n_copies == 0);
- BOOST_TEST(A::n_moves > 0);
+ BOOST_TEST_EQ(A::n_moves, 1);
}
- A::n_copies = 0;
- A::n_moves = 0;
{
+ A::reset();
A a(5);
boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(a);
BOOST_TEST(p.valid());
@@ -111,13 +201,12 @@
//p(3, 'a');
p();
BOOST_TEST(f.get() == 5.0);
- //BOOST_TEST(A::n_copies > 0);
- //BOOST_TEST(A::n_moves > 0);
+ BOOST_TEST_EQ(A::n_copies, 1);
+ BOOST_TEST_EQ(A::n_moves, 0);
}
- A::n_copies = 0;
- A::n_moves = 0;
{
+ A::reset();
const A a(5);
boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(a);
BOOST_TEST(p.valid());
@@ -125,8 +214,56 @@
//p(3, 'a');
p();
BOOST_TEST(f.get() == 5.0);
- //BOOST_TEST(A::n_copies > 0);
- //BOOST_TEST(A::n_moves > 0);
+ BOOST_TEST_EQ(A::n_copies, 1);
+ BOOST_TEST_EQ(A::n_moves, 0);
+ }
+ {
+ M::reset();
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p(BOOST_THREAD_MAKE_RV_REF(M(5)));
+ BOOST_TEST(p.valid());
+ boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+#else
+ p();
+#endif
+ BOOST_TEST(f.get() == BOOST_THREAD_DETAIL_SIGNATURE_2_RES);
+ BOOST_TEST_EQ(M::n_moves, 1);
+ }
+ {
+ M::reset();
+ M a(5);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(boost::move(a));
+ BOOST_TEST(p.valid());
+ boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
+ //p(3, 'a');
+ p();
+ BOOST_TEST(f.get() == 5.0);
+ BOOST_TEST_EQ(M::n_moves, 1);
+ }
+
+ {
+ C::reset();
+ C a(5);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(a);
+ BOOST_TEST(p.valid());
+ boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
+ //p(3, 'a');
+ p();
+ BOOST_TEST(f.get() == 5.0);
+ BOOST_TEST_EQ(C::n_copies, 1);
+ }
+
+ {
+ C::reset();
+ const C a(5);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(a);
+ BOOST_TEST(p.valid());
+ boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
+ //p(3, 'a');
+ p();
+ BOOST_TEST(f.get() == 5.0);
+ BOOST_TEST_EQ(C::n_copies, 1);
}
{
boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(fct);
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk