Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r76346 - in branches/release: boost/thread boost/thread/detail boost/thread/pthread boost/thread/win32 libs/thread/doc libs/thread/test
From: vicente.botet_at_[hidden]
Date: 2012-01-07 15:52:59


Author: viboes
Date: 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
New Revision: 76346
URL: http://svn.boost.org/trac/boost/changeset/76346

Log:
Thread: merge from trunk to fix #6141, #5594, #5040 and #5502.
Added:
   branches/release/libs/thread/test/test_2501.cpp (contents, props changed)
   branches/release/libs/thread/test/test_4521.cpp (contents, props changed)
   branches/release/libs/thread/test/test_4648.cpp (contents, props changed)
   branches/release/libs/thread/test/test_4882.cpp (contents, props changed)
   branches/release/libs/thread/test/test_5351.cpp (contents, props changed)
   branches/release/libs/thread/test/test_5502.cpp (contents, props changed)
   branches/release/libs/thread/test/test_5542_1.cpp (contents, props changed)
   branches/release/libs/thread/test/test_5542_2.cpp (contents, props changed)
   branches/release/libs/thread/test/test_5542_3.cpp (contents, props changed)
   branches/release/libs/thread/test/test_6130.cpp (contents, props changed)
   branches/release/libs/thread/test/test_6170.cpp
      - copied, changed from r76280, /trunk/libs/thread/test/test_6170.cpp
   branches/release/libs/thread/test/test_6174.cpp (contents, props changed)
Properties modified:
   branches/release/boost/thread/ (props changed)
   branches/release/libs/thread/test/ (props changed)
Text files modified:
   branches/release/boost/thread/detail/config.hpp | 9 +++++
   branches/release/boost/thread/detail/move.hpp | 16 +++++++---
   branches/release/boost/thread/detail/thread.hpp | 9 +++++
   branches/release/boost/thread/future.hpp | 61 +++++++++++++++++++++++++++++++++++++--
   branches/release/boost/thread/locks.hpp | 35 +++++++++++++++++++++-
   branches/release/boost/thread/pthread/shared_mutex.hpp | 26 ++++++++--------
   branches/release/boost/thread/win32/shared_mutex.hpp | 7 +++
   branches/release/libs/thread/doc/changes.qbk | 4 ++
   branches/release/libs/thread/test/Jamfile.v2 | 25 ++++++++++++++++
   branches/release/libs/thread/test/test_6170.cpp | 8 +++-
   branches/release/libs/thread/test/test_move_function.cpp | 25 +++++++++++++++-
   11 files changed, 196 insertions(+), 29 deletions(-)

Modified: branches/release/boost/thread/detail/config.hpp
==============================================================================
--- branches/release/boost/thread/detail/config.hpp (original)
+++ branches/release/boost/thread/detail/config.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -10,6 +10,15 @@
 #include <boost/config.hpp>
 #include <boost/detail/workaround.hpp>
 
+
+#if !defined BOOST_THREAD_VERSION
+#define BOOST_THREAD_VERSION 1
+#else
+#if BOOST_THREAD_VERSION!=1 && BOOST_THREAD_VERSION!=2
+#error "BOOST_THREAD_VERSION must be 1 or 2"
+#endif
+#endif
+
 #if BOOST_WORKAROUND(__BORLANDC__, < 0x600)
 # pragma warn -8008 // Condition always true/false
 # pragma warn -8080 // Identifier declared but never used

Modified: branches/release/boost/thread/detail/move.hpp
==============================================================================
--- branches/release/boost/thread/detail/move.hpp (original)
+++ branches/release/boost/thread/detail/move.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -6,15 +6,20 @@
 #ifndef BOOST_THREAD_MOVE_HPP
 #define BOOST_THREAD_MOVE_HPP
 
+#include <boost/thread/detail/config.hpp>
 #ifndef BOOST_NO_SFINAE
 #include <boost/utility/enable_if.hpp>
 #include <boost/type_traits/is_convertible.hpp>
+#include <boost/type_traits/remove_reference.hpp>
 #endif
 
+#include <boost/move/move.hpp>
+
 #include <boost/config/abi_prefix.hpp>
 
 namespace boost
 {
+
     namespace detail
     {
         template<typename T>
@@ -41,18 +46,19 @@
 
 #ifndef BOOST_NO_SFINAE
     template<typename T>
- typename enable_if<boost::is_convertible<T&,detail::thread_move_t<T> >, detail::thread_move_t<T> >::type move(T& t)
+ typename enable_if<boost::is_convertible<T&,boost::detail::thread_move_t<T> >, boost::detail::thread_move_t<T> >::type move(T& t)
     {
- return detail::thread_move_t<T>(t);
+ return boost::detail::thread_move_t<T>(t);
     }
 #endif
-
+
     template<typename T>
- detail::thread_move_t<T> move(detail::thread_move_t<T> t)
+ boost::detail::thread_move_t<T> move(boost::detail::thread_move_t<T> t)
     {
         return t;
     }
-
+
+
 }
 
 #include <boost/config/abi_suffix.hpp>

Modified: branches/release/boost/thread/detail/thread.hpp
==============================================================================
--- branches/release/boost/thread/detail/thread.hpp (original)
+++ branches/release/boost/thread/detail/thread.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -24,6 +24,7 @@
 #include <memory>
 #include <boost/utility/enable_if.hpp>
 #include <boost/type_traits/remove_reference.hpp>
+#include <boost/io/ios_state.hpp>
 
 #include <boost/config/abi_prefix.hpp>
 
@@ -444,6 +445,7 @@
         {
             if(x.thread_data)
             {
+ io::ios_flags_saver ifs( os );
                 return os<< std::hex << x.thread_data;
             }
             else
@@ -519,6 +521,13 @@
         void BOOST_THREAD_DECL add_thread_exit_function(thread_exit_function_base*);
     }
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <>
+ struct has_move_emulation_enabled_aux<thread>
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
     namespace this_thread
     {
         template<typename F>

Modified: branches/release/boost/thread/future.hpp
==============================================================================
--- branches/release/boost/thread/future.hpp (original)
+++ branches/release/boost/thread/future.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -413,13 +413,19 @@
 
             struct all_futures_lock
             {
- count_type count;
+#ifdef _MANAGED
+ typedef std::ptrdiff_t count_type_portable;
+#else
+ typedef count_type count_type_portable;
+#endif
+ count_type_portable count;
+
                 boost::scoped_array<boost::unique_lock<boost::mutex> > locks;
 
                 all_futures_lock(std::vector<registered_waiter>& futures):
                     count(futures.size()),locks(new boost::unique_lock<boost::mutex>[count])
                 {
- for(count_type i=0;i<count;++i)
+ for(count_type_portable i=0;i<count;++i)
                     {
 #if defined __DECCXX || defined __SUNPRO_CC
                         locks[i]=boost::unique_lock<boost::mutex>(futures[i].future->mutex).move();
@@ -436,7 +442,7 @@
 
                 void unlock()
                 {
- for(count_type i=0;i<count;++i)
+ for(count_type_portable i=0;i<count;++i)
                     {
                         locks[i].unlock();
                     }
@@ -748,6 +754,13 @@
 
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename T>
+ struct has_move_emulation_enabled_aux<unique_future<T> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
     template <typename R>
     class shared_future
     {
@@ -906,6 +919,13 @@
 
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename T>
+ struct has_move_emulation_enabled_aux<shared_future<T> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
     template <typename R>
     class promise
     {
@@ -1172,6 +1192,13 @@
 
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename T>
+ struct has_move_emulation_enabled_aux<promise<T> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
     namespace detail
     {
         template<typename R>
@@ -1220,9 +1247,15 @@
             task_object(F const& f_):
                 f(f_)
             {}
+#ifndef BOOST_NO_RVALUE_REFERENCES
+ task_object(F&& f_):
+ f(f_)
+ {}
+#else
             task_object(boost::detail::thread_move_t<F> f_):
                 f(f_)
             {}
+#endif
 
             void do_run()
             {
@@ -1245,9 +1278,15 @@
             task_object(F const& f_):
                 f(f_)
             {}
+#ifndef BOOST_NO_RVALUE_REFERENCES
+ task_object(F&& f_):
+ f(f_)
+ {}
+#else
             task_object(boost::detail::thread_move_t<F> f_):
                 f(f_)
             {}
+#endif
 
             void do_run()
             {
@@ -1289,10 +1328,17 @@
             task(new detail::task_object<R,R(*)()>(f)),future_obtained(false)
         {}
 
+#ifndef BOOST_NO_RVALUE_REFERENCES
+ template <class F>
+ explicit packaged_task(F&& f):
+ task(new detail::task_object<R,F>(f)),future_obtained(false)
+ {}
+#else
         template <class F>
         explicit packaged_task(boost::detail::thread_move_t<F> f):
             task(new detail::task_object<R,F>(f)),future_obtained(false)
         {}
+#endif
 
 // template <class F, class Allocator>
 // explicit packaged_task(F const& f, Allocator a);
@@ -1341,7 +1387,7 @@
         }
 #endif
 
- void swap(packaged_task& other)
+ void swap(packaged_task& other)
         {
             task.swap(other.task);
             std::swap(future_obtained,other.future_obtained);
@@ -1384,6 +1430,13 @@
 
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename T>
+ struct has_move_emulation_enabled_aux<packaged_task<T> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
 }
 
 

Modified: branches/release/boost/thread/locks.hpp
==============================================================================
--- branches/release/boost/thread/locks.hpp (original)
+++ branches/release/boost/thread/locks.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -518,6 +518,13 @@
     }
 #endif
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename Mutex>
+ struct has_move_emulation_enabled_aux<unique_lock<Mutex> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
     template<typename Mutex>
     class shared_lock
     {
@@ -553,7 +560,9 @@
         {
             timed_lock(target_time);
         }
+#ifndef BOOST_NO_RVALUE_REFERENCES
 
+#else
         shared_lock(detail::thread_move_t<shared_lock<Mutex> > other):
             m(other->m),is_locked(other->is_locked)
         {
@@ -614,6 +623,7 @@
             swap(temp);
             return *this;
         }
+#endif
 
 #ifndef BOOST_NO_RVALUE_REFERENCES
         void swap(shared_lock&& other)
@@ -709,6 +719,14 @@
 
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename Mutex>
+ struct has_move_emulation_enabled_aux<shared_lock<Mutex> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
+
 #ifndef BOOST_NO_RVALUE_REFERENCES
     template<typename Mutex>
     void swap(shared_lock<Mutex>&& lhs,shared_lock<Mutex>&& rhs)
@@ -758,7 +776,7 @@
         {
             try_lock();
         }
-#ifdef BOOST_HAS_RVALUE_REFS
+#ifndef BOOST_NO_RVALUE_REFERENCES
         upgrade_lock(upgrade_lock<Mutex>&& other):
             m(other.m),is_locked(other.is_locked)
         {
@@ -893,6 +911,12 @@
         friend class unique_lock<Mutex>;
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename Mutex>
+ struct has_move_emulation_enabled_aux<upgrade_lock<Mutex> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
 
 #ifndef BOOST_NO_RVALUE_REFERENCES
     template<typename Mutex>
@@ -938,7 +962,7 @@
             }
         }
 
-#ifdef BOOST_HAS_RVALUE_REFS
+#ifndef BOOST_NO_RVALUE_REFERENCES
         upgrade_to_unique_lock(upgrade_to_unique_lock<Mutex>&& other):
             source(other.source),exclusive(move(other.exclusive))
         {
@@ -985,6 +1009,13 @@
         }
     };
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+ template <typename Mutex>
+ struct has_move_emulation_enabled_aux<upgrade_to_unique_lock<Mutex> >
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+#endif
+
     namespace detail
     {
         template<typename Mutex>

Modified: branches/release/boost/thread/pthread/shared_mutex.hpp
==============================================================================
--- branches/release/boost/thread/pthread/shared_mutex.hpp (original)
+++ branches/release/boost/thread/pthread/shared_mutex.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -27,7 +27,7 @@
             bool upgrade;
             bool exclusive_waiting_blocked;
         };
-
+
 
 
         state_data state;
@@ -41,7 +41,7 @@
             exclusive_cond.notify_one();
             shared_cond.notify_all();
         }
-
+
 
     public:
         shared_mutex()
@@ -58,7 +58,7 @@
         {
             boost::this_thread::disable_interruption do_not_disturb;
             boost::mutex::scoped_lock lk(state_change);
-
+
             while(state.exclusive || state.exclusive_waiting_blocked)
             {
                 shared_cond.wait(lk);
@@ -69,7 +69,7 @@
         bool try_lock_shared()
         {
             boost::mutex::scoped_lock lk(state_change);
-
+
             if(state.exclusive || state.exclusive_waiting_blocked)
             {
                 return false;
@@ -85,7 +85,7 @@
         {
             boost::this_thread::disable_interruption do_not_disturb;
             boost::mutex::scoped_lock lk(state_change);
-
+
             while(state.exclusive || state.exclusive_waiting_blocked)
             {
                 if(!shared_cond.timed_wait(lk,timeout))
@@ -107,7 +107,7 @@
         {
             boost::mutex::scoped_lock lk(state_change);
             bool const last_reader=!--state.shared_count;
-
+
             if(last_reader)
             {
                 if(state.upgrade)
@@ -128,7 +128,7 @@
         {
             boost::this_thread::disable_interruption do_not_disturb;
             boost::mutex::scoped_lock lk(state_change);
-
+
             while(state.shared_count || state.exclusive)
             {
                 state.exclusive_waiting_blocked=true;
@@ -150,7 +150,7 @@
                     if(state.shared_count || state.exclusive)
                     {
                         state.exclusive_waiting_blocked=false;
- exclusive_cond.notify_one();
+ release_waiters();
                         return false;
                     }
                     break;
@@ -169,7 +169,7 @@
         bool try_lock()
         {
             boost::mutex::scoped_lock lk(state_change);
-
+
             if(state.shared_count || state.exclusive)
             {
                 return false;
@@ -179,7 +179,7 @@
                 state.exclusive=true;
                 return true;
             }
-
+
         }
 
         void unlock()
@@ -248,7 +248,7 @@
             boost::mutex::scoped_lock lk(state_change);
             state.upgrade=false;
             bool const last_reader=!--state.shared_count;
-
+
             if(last_reader)
             {
                 state.exclusive_waiting_blocked=false;
@@ -278,7 +278,7 @@
             state.exclusive_waiting_blocked=false;
             release_waiters();
         }
-
+
         void unlock_and_lock_shared()
         {
             boost::mutex::scoped_lock lk(state_change);
@@ -287,7 +287,7 @@
             state.exclusive_waiting_blocked=false;
             release_waiters();
         }
-
+
         void unlock_upgrade_and_lock_shared()
         {
             boost::mutex::scoped_lock lk(state_change);

Modified: branches/release/boost/thread/win32/shared_mutex.hpp
==============================================================================
--- branches/release/boost/thread/win32/shared_mutex.hpp (original)
+++ branches/release/boost/thread/win32/shared_mutex.hpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -337,7 +337,12 @@
                 {
                     return true;
                 }
- unsigned long const wait_res=detail::win32::WaitForMultipleObjects(2,semaphores,true,::boost::detail::get_milliseconds_until(wait_until));
+ #ifndef UNDER_CE
+ const bool wait_all = true;
+ #else
+ const bool wait_all = false;
+ #endif
+ unsigned long const wait_res=detail::win32::WaitForMultipleObjects(2,semaphores,wait_all,::boost::detail::get_milliseconds_until(wait_until));
                 if(wait_res==detail::win32::timeout)
                 {
                     for(;;)

Modified: branches/release/libs/thread/doc/changes.qbk
==============================================================================
--- branches/release/libs/thread/doc/changes.qbk (original)
+++ branches/release/libs/thread/doc/changes.qbk 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -24,7 +24,10 @@
 * [@http://svn.boost.org/trac/boost/ticket/4480 #4480] OpenVMS patches for compiler issues workarounds.
 * [@http://svn.boost.org/trac/boost/ticket/4819 #4819] boost.thread's documentation misprints.
 
+* [@http://svn.boost.org/trac/boost/ticket/5040 #5040] future.hpp in boost::thread does not compile with /clr.
 * [@http://svn.boost.org/trac/boost/ticket/5423 #5423] thread issues with C++0x.
+* [@http://svn.boost.org/trac/boost/ticket/5502 #5502] race condition between shared_mutex timed_lock and lock_shared.
+* [@http://svn.boost.org/trac/boost/ticket/5594 #5594] boost::shared_mutex not fully compatible with Windows CE.
 * [@http://svn.boost.org/trac/boost/ticket/5617 #5617] boost::thread::id copy ctor.
 * [@http://svn.boost.org/trac/boost/ticket/5739 #5739] set-but-not-used warnings with gcc-4.6.
 * [@http://svn.boost.org/trac/boost/ticket/5826 #5826] threads.cpp: resource leak on threads creation failure.
@@ -32,6 +35,7 @@
 * [@http://svn.boost.org/trac/boost/ticket/5859 #5859] win32 shared_mutex constructor leaks on exceptions.
 
 * [@http://svn.boost.org/trac/boost/ticket/6100 #6100] Compute hardware_concurrency() using get_nprocs() on GLIBC systems.
+* [@http://svn.boost.org/trac/boost/ticket/6141 #6141] Compilation error when boost.thread and boost.move are used together.
 * [@http://svn.boost.org/trac/boost/ticket/6168 #6168] recursive_mutex is using wrong config symbol (possible typo).
 * [@http://svn.boost.org/trac/boost/ticket/6175 #6175] Compile error with SunStudio.
 * [@http://svn.boost.org/trac/boost/ticket/6200 #6200] patch to have condition_variable and mutex error better handle EINTR.

Modified: branches/release/libs/thread/test/Jamfile.v2
==============================================================================
--- branches/release/libs/thread/test/Jamfile.v2 (original)
+++ branches/release/libs/thread/test/Jamfile.v2 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -62,4 +62,29 @@
           [ compile-fail no_implicit_move_from_lvalue_thread.cpp ]
           [ compile-fail no_implicit_assign_from_lvalue_thread.cpp ]
     ;
+
+
+ #explicit tickets ;
+ test-suite tickets
+ :
+ [ thread-run test_6170.cpp ]
+ ;
+
+
+ explicit oth_tickets ;
+ test-suite oth_tickets
+ :
+ [ thread-run test_2501.cpp ]
+ [ thread-run test_4521.cpp ]
+ [ thread-run test_4648.cpp ]
+ [ thread-run test_4882.cpp ]
+ [ thread-run test_5351.cpp ]
+ [ thread-run test_5502.cpp ]
+ [ thread-run test_5542_1.cpp ]
+ [ thread-run test_5542_2.cpp ]
+ [ thread-run test_5542_3.cpp ]
+ [ thread-run test_6130.cpp ]
+ [ thread-run test_6174.cpp ]
+ ;
+
 }

Added: branches/release/libs/thread/test/test_2501.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_2501.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,10 @@
+#include <boost/thread/shared_mutex.hpp>
+
+int main() {
+
+ boost::shared_mutex mtx; boost::upgrade_lock<boost::shared_mutex> lk(mtx);
+
+ boost::upgrade_to_unique_lock<boost::shared_mutex> lk2(lk);
+
+ return 0;
+}

Added: branches/release/libs/thread/test/test_4521.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_4521.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,21 @@
+#include <boost/thread.hpp>
+
+int calculate_the_answer_to_life_the_universe_and_everything()
+{
+ return 42;
+}
+
+int main() {
+boost::packaged_task<int> pt(calculate_the_answer_to_life_the_universe_and_everything);
+boost::unique_future<int> fi=pt.get_future();
+
+boost::thread task(boost::move(pt)); // launch task on a thread
+
+fi.wait(); // wait for it to finish
+
+//assert(fi.is_ready());
+//assert(fi.has_value());
+//assert(!fi.has_exception());
+//assert(fi.get_state()==boost::future_state::ready);
+//assert(fi.get()==42);
+}

Added: branches/release/libs/thread/test/test_4648.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_4648.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,42 @@
+#include <iostream>
+#include <boost/thread.hpp>
+#include <boost/current_function.hpp>
+
+class boostThreadLocksTest
+{
+public:
+ boost::shared_mutex myMutex;
+ //boost::upgrade_lock<boost::shared_mutex> myLock;
+ static int firstFunction(boostThreadLocksTest *pBoostThreadLocksTest);
+ static int secondFunction(boostThreadLocksTest *pBoostThreadLocksTest,
+ boost::upgrade_lock<boost::shared_mutex>& upgr);
+ boostThreadLocksTest()
+ :myMutex()
+ //, myLock(myMutex,boost::defer_lock_t())
+ {};
+};
+
+int boostThreadLocksTest::firstFunction(boostThreadLocksTest *pBoostThreadLocksTest)
+{
+ std::cout<<"Entering "<<boost::this_thread::get_id()<<" "<<"firstFunction"<<std::endl;
+ boost::upgrade_lock<boost::shared_mutex> myLock(pBoostThreadLocksTest->myMutex);
+ pBoostThreadLocksTest->secondFunction(pBoostThreadLocksTest, myLock);
+ std::cout<<"Returned From Call "<<boost::this_thread::get_id()<<" "<<"firstFunction"<<std::endl;
+ std::cout<<"Returning from "<<boost::this_thread::get_id()<<" "<<"firstFunction"<<std::endl;
+ return(0);
+}
+int boostThreadLocksTest::secondFunction(boostThreadLocksTest *pBoostThreadLocksTest, boost::upgrade_lock<boost::shared_mutex>& upgr) {
+ std::cout<<"Before Exclusive Locking "<<boost::this_thread::get_id()<<" "<<"secondFunction"<<std::endl;
+ boost::upgrade_to_unique_lock<boost::shared_mutex> localUniqueLock(upgr);
+ std::cout<<"After Exclusive Locking "<<boost::this_thread::get_id()<<" "<<"secondFunction"<<std::endl;
+ return(0);
+}
+int main() {
+ boostThreadLocksTest myObject;
+ boost::thread_group myThreadGroup;
+ myThreadGroup.create_thread(boost::bind(boostThreadLocksTest::firstFunction,&myObject));
+ myThreadGroup.create_thread(boost::bind(boostThreadLocksTest::firstFunction,&myObject));
+ myThreadGroup.create_thread(boost::bind(boostThreadLocksTest::firstFunction,&myObject));
+ myThreadGroup.join_all();
+ return 0;
+}

Added: branches/release/libs/thread/test/test_4882.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_4882.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,50 @@
+#include <boost/thread/thread.hpp>
+#include <boost/thread/shared_mutex.hpp>
+
+#include <iostream>
+
+boost::shared_mutex mutex;
+
+void thread()
+{
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ try
+ {
+ for (int i =0; i<10; ++i)
+ {
+ boost::system_time timeout = boost::get_system_time() + boost::posix_time::milliseconds(50);
+
+ if (mutex.timed_lock(timeout))
+ {
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ boost::this_thread::sleep(boost::posix_time::milliseconds(10));
+ mutex.unlock();
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ }
+ }
+ }
+ catch (boost::lock_error& le)
+ {
+ std::cerr << "lock_error exception\n";
+ }
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+}
+
+int main()
+{
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ const int nrThreads = 20;
+ boost::thread* threads[nrThreads];
+
+ for (int i = 0; i < nrThreads; ++i)
+ threads[i] = new boost::thread(&thread);
+
+ for (int i = 0; i < nrThreads; ++i)
+ {
+ threads[i]->join();
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ delete threads[i];
+ }
+ std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ return 0;
+}

Added: branches/release/libs/thread/test/test_5351.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_5351.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,45 @@
+#include <iostream>
+#include <boost/thread.hpp>
+#include <boost/date_time/posix_time/posix_time_types.hpp>
+#include <boost/thread/future.hpp>
+
+using namespace boost::posix_time;
+using namespace boost;
+
+int foo()
+{
+ this_thread::sleep(seconds(10));
+ return 0;
+}
+
+
+int main(int argc, char** argv)
+{
+ boost::packaged_task<int> pt(&foo);
+ boost::unique_future<int> fi = pt.get_future();
+ boost::thread task(boost::move(pt)); // launch task on a thread
+
+ task.interrupt();
+
+ try
+ {
+ int v = fi.get();
+ }
+ catch (boost::thread_interrupted& exc)
+ {
+ std::cout << "OK: " << std::endl;
+ return 0;
+ }
+ catch (boost::exception& exc)
+ {
+ std::cout << __LINE__ << " ERROR: " << boost::diagnostic_information(exc) << std::endl;
+ return 1;
+ }
+ catch (...)
+ {
+ std::cout << __LINE__ << " ERROR: " << std::endl;
+ return 2;
+ }
+ std::cout << __LINE__ << " ERROR: " << std::endl;
+ return 3;
+}

Added: branches/release/libs/thread/test/test_5502.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_5502.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,86 @@
+// bm.cpp
+
+// g++ test.cpp -lboost_thread-mt && ./a.out
+
+// the ration of XXX and YYY determines
+// if this works or deadlocks
+int XXX = 20;
+int YYY = 10;
+
+#include <boost/thread.hpp>
+#include <boost/thread/shared_mutex.hpp>
+
+#include <unistd.h>
+#include <iostream>
+#include <boost/detail/lightweight_test.hpp>
+
+using namespace std;
+
+void sleepmillis(useconds_t miliis)
+{
+ usleep(miliis * 1000);
+}
+
+void worker1(boost::shared_mutex * lk, int * x)
+{
+ (*x)++; // 1
+ cout << "lock b try " << *x << endl;
+ while (1)
+ {
+ if (lk->timed_lock(boost::posix_time::milliseconds(XXX))) break;
+ sleepmillis(YYY);
+ }
+ cout << "lock b got " << *x << endl;
+ (*x)++; // 2
+ lk->unlock();
+}
+
+void worker2(boost::shared_mutex * lk, int * x)
+{
+ cout << "lock c try" << endl;
+ lk->lock_shared();
+ (*x)++;
+ cout << "lock c got" << endl;
+ lk->unlock_shared();
+ cout << "lock c unlocked" << endl;
+ (*x)++;
+}
+
+int main()
+{
+
+ // create
+ boost::shared_mutex* lk = new boost::shared_mutex();
+
+ // read lock
+ cout << "lock a" << endl;
+ lk->lock_shared();
+
+ int x1 = 0;
+ boost::thread t1(boost::bind(worker1, lk, &x1));
+ while (!x1)
+ ;
+ BOOST_TEST(x1 == 1);
+ sleepmillis(500);
+ BOOST_TEST(x1 == 1);
+
+ int x2 = 0;
+ boost::thread t2(boost::bind(worker2, lk, &x2));
+ t2.join();
+ BOOST_TEST(x2 == 2);
+
+ lk->unlock_shared();
+ cout << "unlock a" << endl;
+
+ for (int i = 0; i < 2000; i++)
+ {
+ if (x1 == 2) break;
+ sleepmillis(10);
+ }
+
+ BOOST_TEST(x1 == 2);
+ t1.join();
+ delete lk;
+
+ return 0;
+}

Added: branches/release/libs/thread/test/test_5542_1.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_5542_1.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,62 @@
+#include <iostream>
+#include <boost/thread.hpp>
+
+class Worker
+{
+public:
+
+ Worker()
+ {
+ // the thread is not-a-thread until we call start()
+ }
+
+ void start(int N)
+ {
+ std::cout << "start\n";
+ m_Thread = boost::thread(&Worker::processQueue, this, N);
+ std::cout << "started\n";
+ }
+
+ void join()
+ {
+ m_Thread.join();
+ }
+
+ void processQueue(unsigned N)
+ {
+ float ms = N * 1e3;
+ boost::posix_time::milliseconds workTime(ms);
+
+ std::cout << "Worker: started, will work for "
+ << ms << "ms"
+ << std::endl;
+
+ // We're busy, honest!
+ boost::this_thread::sleep(workTime);
+
+ std::cout << "Worker: completed" << std::endl;
+ }
+
+private:
+
+ boost::thread m_Thread;
+};
+
+int main(int argc, char* argv[])
+{
+ std::cout << "main: startup" << std::endl;
+
+ Worker worker;
+
+ std::cout << "main: create worker" << std::endl;
+
+ worker.start(3);
+
+ std::cout << "main: waiting for thread" << std::endl;
+
+ worker.join();
+
+ std::cout << "main: done" << std::endl;
+
+ return 0;
+}

Added: branches/release/libs/thread/test/test_5542_2.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_5542_2.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,11 @@
+#include <boost/thread.hpp>
+
+void run_thread() {
+ return;
+}
+
+int main() {
+ boost::thread t(run_thread);
+ return 0;
+}
+

Added: branches/release/libs/thread/test/test_5542_3.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_5542_3.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,30 @@
+#include <iostream>
+#include <boost/thread.hpp>
+#include <boost/date_time.hpp>
+
+void workerFunc()
+{
+ boost::posix_time::seconds workTime(3);
+
+ std::cout << "Worker: running" << std::endl;
+
+ // Pretend to do something useful...
+ boost::this_thread::sleep(workTime);
+
+ std::cout << "Worker: finished" << std::endl;
+}
+
+int main(int argc, char* argv[])
+{
+ std::cout << "main: startup" << std::endl;
+
+ boost::thread workerThread(workerFunc);
+
+ std::cout << "main: waiting for thread" << std::endl;
+
+ workerThread.join();
+
+ std::cout << "main: done" << std::endl;
+
+ return 0;
+}

Added: branches/release/libs/thread/test/test_6130.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_6130.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,22 @@
+#include <boost/thread.hpp>
+#include <assert.h>
+#include <iostream>
+#include <stdlib.h>
+#include <unistd.h>
+
+boost::mutex mtx;
+boost::condition_variable cv;
+
+int main()
+{
+ for (int i=0; i<3; ++i) {
+ const time_t wait_time = ::time(0)+1;
+
+ boost::mutex::scoped_lock lk(mtx);
+ const bool res = cv.timed_wait(lk, boost::posix_time::from_time_t(wait_time));
+ const time_t end_time = ::time(0);
+ assert(end_time >= wait_time);
+ std::cerr << end_time - wait_time << " OK\n";
+ }
+ return 0;
+}

Copied: branches/release/libs/thread/test/test_6170.cpp (from r76280, /trunk/libs/thread/test/test_6170.cpp)
==============================================================================
--- /trunk/libs/thread/test/test_6170.cpp (original)
+++ branches/release/libs/thread/test/test_6170.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -9,8 +9,6 @@
 typedef upgrade_lock<shared_mutex> auto_upgrade_lock;
 typedef upgrade_to_unique_lock<shared_mutex> auto_upgrade_unique_lock;
 
-void testUpgrade(void);
-
 void testUpgrade(void)
 {
         shared_mutex mtx;
@@ -20,3 +18,9 @@
         auto_upgrade_unique_lock writeLock(lock);
         // Do some write-only stuff with the upgraded lock
 }
+
+int main()
+{
+ testUpgrade();
+ return 0;
+}
\ No newline at end of file

Added: branches/release/libs/thread/test/test_6174.cpp
==============================================================================
--- (empty file)
+++ branches/release/libs/thread/test/test_6174.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -0,0 +1,35 @@
+
+
+#include <boost/thread.hpp>
+#include <boost/config.hpp>
+
+#ifndef BOOST_NO_RVALUE_REFERENCES
+struct MovableButNonCopyable {
+#ifndef BOOST_NO_DEFAULTED_FUNCTIONS
+ MovableButNonCopyable() = default;
+ MovableButNonCopyable(MovableButNonCopyable const&) = delete;
+ MovableButNonCopyable& operator=(MovableButNonCopyable const&) = delete;
+ MovableButNonCopyable(MovableButNonCopyable&&) = default;
+ MovableButNonCopyable& operator=(MovableButNonCopyable&&) = default;
+#else
+ MovableButNonCopyable() {};
+ MovableButNonCopyable(MovableButNonCopyable&&) {};
+ MovableButNonCopyable& operator=(MovableButNonCopyable&&) {
+ return *this;
+ };
+private:
+ MovableButNonCopyable(MovableButNonCopyable const&);
+ MovableButNonCopyable& operator=(MovableButNonCopyable const&);
+#endif
+};
+int main()
+{
+ boost::packaged_task<MovableButNonCopyable>(MovableButNonCopyable());
+ return 0;
+}
+#else
+int main()
+{
+ return 0;
+}
+#endif

Modified: branches/release/libs/thread/test/test_move_function.cpp
==============================================================================
--- branches/release/libs/thread/test/test_move_function.cpp (original)
+++ branches/release/libs/thread/test/test_move_function.cpp 2012-01-07 15:52:57 EST (Sat, 07 Jan 2012)
@@ -1,6 +1,6 @@
 // Copyright (C) 2007-8 Anthony Williams
 //
-// Distributed under the Boost Software License, Version 1.0. (See accompanying
+// Distributed under the Boost Software License, Version 1.0. (See accompanying
 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
 #include <boost/thread/thread.hpp>
 #include <boost/test/unit_test.hpp>
@@ -89,10 +89,17 @@
     }
 
     bool move_called=false;
-
+
     struct nc:
         public boost::shared_ptr<int>
     {
+#ifndef BOOST_NO_RVALUE_REFERENCES
+ nc() {}
+ nc(nc&&)
+ {
+ move_called=true;
+ }
+#endif
         nc move()
         {
             move_called=true;
@@ -101,10 +108,24 @@
     };
 }
 
+#ifdef BOOST_NO_RVALUE_REFERENCES
+namespace boost
+{
+ template <>
+ struct has_move_emulation_enabled_aux<user_test_ns::nc>
+ : BOOST_MOVE_BOOST_NS::integral_constant<bool, true>
+ {};
+}
+#endif
+
 void test_move_for_user_defined_type_unaffected()
 {
     user_test_ns::nc src;
+#ifndef BOOST_NO_RVALUE_REFERENCES
+ user_test_ns::nc dest=boost::move(src);
+#else
     user_test_ns::nc dest=move(src);
+#endif
     BOOST_CHECK(user_test_ns::move_called);
 }
 


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