|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r81667 - in branches/release: boost/thread boost/thread/detail boost/thread/pthread boost/thread/v2 boost/thread/win32 libs/thread libs/thread/build libs/thread/doc libs/thread/example libs/thread/src/pthread libs/thread/src/win32 libs/thread/test libs/thread/test/sync/conditions/null_condition libs/thread/test/sync/futures/async libs/thread/test/sync/futures/future libs/thread/test/sync/futures/packaged_task libs/thread/test/sync/futures/promise libs/thread/test/sync/futures/shared_future libs/thread/test/sync/mutual_exclusion/locks/externaly_locked libs/thread/test/sync/mutual_exclusion/locks/lock_guard libs/thread/test/sync/mutual_exclusion/locks/nested_strict_lock libs/thread/test/sync/mutual_exclusion/locks/reverse_lock libs/thread/test/sync/mutual_exclusion/locks/shared_lock libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs libs/thread/test/sync/mutual_exclusion/locks/shared_lock_guard libs/thread/test/sync/mutual_exclusion/locks/strict_lock libs/thread/test/sync/mutual_exclusion/locks/unique_lock libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs libs/thread/test/sync/mutual_exclusion/null_mutex libs/thread/test/sync/mutual_exclusion/synchronized_value libs/thread/test/sync/mutual_exclusion/timed_mutex libs/thread/test/threads/container libs/thread/test/threads/scoped_thread libs/thread/test/threads/thread/assign libs/thread/test/threads/thread/constr libs/thread/test/threads/thread_guard libs/thread/test/tss
From: vicente.botet_at_[hidden]
Date: 2012-12-02 04:23:03
Author: viboes
Date: 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
New Revision: 81667
URL: http://svn.boost.org/trac/boost/changeset/81667
Log:
Thread: merge from trunk 1.53
Added:
branches/release/boost/thread/detail/async_func.hpp
- copied unchanged from r81201, /trunk/boost/thread/detail/async_func.hpp
branches/release/boost/thread/detail/invoke.hpp
- copied unchanged from r81201, /trunk/boost/thread/detail/invoke.hpp
branches/release/boost/thread/detail/is_convertible.hpp
- copied, changed from r81443, /trunk/boost/thread/detail/is_convertible.hpp
branches/release/boost/thread/detail/log.hpp
- copied unchanged from r81650, /trunk/boost/thread/detail/log.hpp
branches/release/boost/thread/detail/make_tuple_indices.hpp
- copied unchanged from r81201, /trunk/boost/thread/detail/make_tuple_indices.hpp
branches/release/boost/thread/externally_locked.hpp
- copied, changed from r81093, /trunk/boost/thread/externally_locked.hpp
branches/release/boost/thread/externally_locked_stream.hpp
- copied unchanged from r81143, /trunk/boost/thread/externally_locked_stream.hpp
branches/release/boost/thread/is_locked_by_this_thread.hpp
- copied unchanged from r81093, /trunk/boost/thread/is_locked_by_this_thread.hpp
branches/release/boost/thread/lock_algorithms.hpp
- copied unchanged from r81093, /trunk/boost/thread/lock_algorithms.hpp
branches/release/boost/thread/lock_concepts.hpp
- copied, changed from r81093, /trunk/boost/thread/lock_concepts.hpp
branches/release/boost/thread/lock_factories.hpp
- copied unchanged from r81650, /trunk/boost/thread/lock_factories.hpp
branches/release/boost/thread/lock_guard.hpp
- copied, changed from r81093, /trunk/boost/thread/lock_guard.hpp
branches/release/boost/thread/lock_options.hpp
- copied unchanged from r81093, /trunk/boost/thread/lock_options.hpp
branches/release/boost/thread/lock_traits.hpp
- copied unchanged from r81093, /trunk/boost/thread/lock_traits.hpp
branches/release/boost/thread/lock_types.hpp
- copied, changed from r81093, /trunk/boost/thread/lock_types.hpp
branches/release/boost/thread/lockable_adapter.hpp
- copied unchanged from r81143, /trunk/boost/thread/lockable_adapter.hpp
branches/release/boost/thread/lockable_concepts.hpp
- copied, changed from r81093, /trunk/boost/thread/lockable_concepts.hpp
branches/release/boost/thread/lockable_traits.hpp
- copied, changed from r81093, /trunk/boost/thread/lockable_traits.hpp
branches/release/boost/thread/null_mutex.hpp
- copied unchanged from r81093, /trunk/boost/thread/null_mutex.hpp
branches/release/boost/thread/poly_lockable.hpp
- copied unchanged from r81143, /trunk/boost/thread/poly_lockable.hpp
branches/release/boost/thread/poly_lockable_adapter.hpp
- copied unchanged from r81143, /trunk/boost/thread/poly_lockable_adapter.hpp
branches/release/boost/thread/poly_shared_lockable.hpp
- copied unchanged from r81143, /trunk/boost/thread/poly_shared_lockable.hpp
branches/release/boost/thread/poly_shared_lockable_adapter.hpp
- copied unchanged from r81143, /trunk/boost/thread/poly_shared_lockable_adapter.hpp
branches/release/boost/thread/scoped_thread.hpp
- copied, changed from r81093, /trunk/boost/thread/scoped_thread.hpp
branches/release/boost/thread/strict_lock.hpp
- copied, changed from r81093, /trunk/boost/thread/strict_lock.hpp
branches/release/boost/thread/synchronized_value.hpp
- copied, changed from r81093, /trunk/boost/thread/synchronized_value.hpp
branches/release/boost/thread/testable_mutex.hpp
- copied unchanged from r81093, /trunk/boost/thread/testable_mutex.hpp
branches/release/boost/thread/thread_functors.hpp
- copied unchanged from r81093, /trunk/boost/thread/thread_functors.hpp
branches/release/boost/thread/thread_guard.hpp
- copied unchanged from r81093, /trunk/boost/thread/thread_guard.hpp
branches/release/libs/thread/doc/scoped_thread.qbk
- copied unchanged from r81093, /trunk/libs/thread/doc/scoped_thread.qbk
branches/release/libs/thread/example/ba_externallly_locked.cpp
- copied, changed from r81093, /trunk/libs/thread/example/ba_externallly_locked.cpp
branches/release/libs/thread/example/future_then.cpp
- copied, changed from r81030, /trunk/libs/thread/example/future_then.cpp
branches/release/libs/thread/example/make_future.cpp
- copied, changed from r80756, /trunk/libs/thread/example/make_future.cpp
branches/release/libs/thread/example/not_interleaved.cpp
- copied unchanged from r81143, /trunk/libs/thread/example/not_interleaved.cpp
branches/release/libs/thread/example/scoped_thread.cpp
- copied, changed from r81093, /trunk/libs/thread/example/scoped_thread.cpp
branches/release/libs/thread/example/strict_lock.cpp
- copied, changed from r81093, /trunk/libs/thread/example/strict_lock.cpp
branches/release/libs/thread/example/synchronized_person.cpp
- copied unchanged from r81650, /trunk/libs/thread/example/synchronized_person.cpp
branches/release/libs/thread/example/synchronized_value.cpp
- copied, changed from r81093, /trunk/libs/thread/example/synchronized_value.cpp
branches/release/libs/thread/example/thread_guard.cpp
- copied, changed from r81093, /trunk/libs/thread/example/thread_guard.cpp
branches/release/libs/thread/test/sync/conditions/null_condition/
- copied from r81093, /trunk/libs/thread/test/sync/conditions/null_condition/
branches/release/libs/thread/test/sync/futures/future/then_pass.cpp
- copied, changed from r81143, /trunk/libs/thread/test/sync/futures/future/then_pass.cpp
branches/release/libs/thread/test/sync/futures/packaged_task/make_ready_at_thread_exit_pass.cpp
- copied unchanged from r81443, /trunk/libs/thread/test/sync/futures/packaged_task/make_ready_at_thread_exit_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_exception_at_thread_exit_pass.cpp
- copied unchanged from r81201, /trunk/libs/thread/test/sync/futures/promise/set_exception_at_thread_exit_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_exception_pass.cpp
- copied unchanged from r80756, /trunk/libs/thread/test/sync/futures/promise/set_exception_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_lvalue_at_thread_exit_pass.cpp
- copied unchanged from r81201, /trunk/libs/thread/test/sync/futures/promise/set_lvalue_at_thread_exit_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_lvalue_pass.cpp
- copied unchanged from r80756, /trunk/libs/thread/test/sync/futures/promise/set_lvalue_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_rvalue_at_thread_exit_pass.cpp
- copied unchanged from r81201, /trunk/libs/thread/test/sync/futures/promise/set_rvalue_at_thread_exit_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp
- copied, changed from r80756, /trunk/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_value_at_thread_exit_const_pass.cpp
- copied unchanged from r81201, /trunk/libs/thread/test/sync/futures/promise/set_value_at_thread_exit_const_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_value_at_thread_exit_void_pass.cpp
- copied unchanged from r81201, /trunk/libs/thread/test/sync/futures/promise/set_value_at_thread_exit_void_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_value_const_pass.cpp
- copied unchanged from r80756, /trunk/libs/thread/test/sync/futures/promise/set_value_const_pass.cpp
branches/release/libs/thread/test/sync/futures/promise/set_value_void_pass.cpp
- copied unchanged from r80756, /trunk/libs/thread/test/sync/futures/promise/set_value_void_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/copy_assign_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/copy_assign_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/copy_ctor_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/copy_ctor_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/default_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/default_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/dtor_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/dtor_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/get_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/get_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/move_assign_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/move_assign_pass.cpp
branches/release/libs/thread/test/sync/futures/shared_future/move_ctor_pass.cpp
- copied unchanged from r81143, /trunk/libs/thread/test/sync/futures/shared_future/move_ctor_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/externaly_locked/
- copied from r81093, /trunk/libs/thread/test/sync/mutual_exclusion/locks/externaly_locked/
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/make_lock_guard_adopt_lock_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/make_lock_guard_adopt_lock_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/make_lock_guard_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/make_lock_guard_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/nested_strict_lock/
- copied from r81093, /trunk/libs/thread/test/sync/mutual_exclusion/locks/nested_strict_lock/
branches/release/libs/thread/test/sync/mutual_exclusion/locks/strict_lock/
- copied from r81093, /trunk/libs/thread/test/sync/mutual_exclusion/locks/strict_lock/
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_adopt_lock_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_adopt_lock_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_defer_lock_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_defer_lock_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_mutex_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_mutex_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_try_to_lock_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_try_to_lock_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_locks_mutex_pass.cpp
- copied unchanged from r81650, /trunk/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/make_unique_locks_mutex_pass.cpp
branches/release/libs/thread/test/sync/mutual_exclusion/null_mutex/
- copied from r81093, /trunk/libs/thread/test/sync/mutual_exclusion/null_mutex/
branches/release/libs/thread/test/sync/mutual_exclusion/synchronized_value/
- copied from r81093, /trunk/libs/thread/test/sync/mutual_exclusion/synchronized_value/
branches/release/libs/thread/test/test_7571.cpp
- copied, changed from r81143, /trunk/libs/thread/test/test_7571.cpp
branches/release/libs/thread/test/test_7665.cpp
- copied, changed from r81443, /trunk/libs/thread/test/test_7665.cpp
branches/release/libs/thread/test/test_7666.cpp
- copied unchanged from r81443, /trunk/libs/thread/test/test_7666.cpp
branches/release/libs/thread/test/threads/scoped_thread/
- copied from r81093, /trunk/libs/thread/test/threads/scoped_thread/
branches/release/libs/thread/test/threads/thread_guard/
- copied from r81093, /trunk/libs/thread/test/threads/thread_guard/
branches/release/libs/thread/test/tss/
- copied from r81093, /trunk/libs/thread/test/tss/
Properties modified:
branches/release/boost/thread/ (props changed)
branches/release/libs/thread/ (props changed)
Text files modified:
branches/release/boost/thread/barrier.hpp | 3
branches/release/boost/thread/condition.hpp | 7
branches/release/boost/thread/detail/config.hpp | 206 +++
branches/release/boost/thread/detail/is_convertible.hpp | 17
branches/release/boost/thread/detail/move.hpp | 47
branches/release/boost/thread/detail/thread.hpp | 267 ++++
branches/release/boost/thread/detail/thread_group.hpp | 64
branches/release/boost/thread/detail/thread_interruption.hpp | 5
branches/release/boost/thread/exceptions.hpp | 2
branches/release/boost/thread/externally_locked.hpp | 84
branches/release/boost/thread/future.hpp | 2215 +++++++++++++++++++++++++++++++++------
branches/release/boost/thread/lock_concepts.hpp | 60
branches/release/boost/thread/lock_guard.hpp | 63 +
branches/release/boost/thread/lock_types.hpp | 99
branches/release/boost/thread/lockable_concepts.hpp | 30
branches/release/boost/thread/lockable_traits.hpp | 217 ++-
branches/release/boost/thread/locks.hpp | 1821 --------------------------------
branches/release/boost/thread/mutex.hpp | 34
branches/release/boost/thread/pthread/condition_variable.hpp | 47
branches/release/boost/thread/pthread/condition_variable_fwd.hpp | 44
branches/release/boost/thread/pthread/mutex.hpp | 77
branches/release/boost/thread/pthread/recursive_mutex.hpp | 24
branches/release/boost/thread/pthread/shared_mutex.hpp | 86 +
branches/release/boost/thread/pthread/thread_data.hpp | 89
branches/release/boost/thread/pthread/timespec.hpp | 106 +
branches/release/boost/thread/recursive_mutex.hpp | 45
branches/release/boost/thread/reverse_lock.hpp | 5
branches/release/boost/thread/scoped_thread.hpp | 5
branches/release/boost/thread/shared_lock_guard.hpp | 3
branches/release/boost/thread/shared_mutex.hpp | 22
branches/release/boost/thread/strict_lock.hpp | 23
branches/release/boost/thread/synchronized_value.hpp | 74 +
branches/release/boost/thread/thread.hpp | 2
branches/release/boost/thread/v2/thread.hpp | 50
branches/release/boost/thread/win32/basic_recursive_mutex.hpp | 4
branches/release/boost/thread/win32/basic_timed_mutex.hpp | 6
branches/release/boost/thread/win32/condition_variable.hpp | 11
branches/release/boost/thread/win32/mutex.hpp | 9
branches/release/boost/thread/win32/once.hpp | 12
branches/release/boost/thread/win32/recursive_mutex.hpp | 9
branches/release/boost/thread/win32/shared_mutex.hpp | 3
branches/release/boost/thread/win32/thread_data.hpp | 33
branches/release/boost/thread/win32/thread_heap_alloc.hpp | 101 -
branches/release/boost/thread/win32/thread_primitives.hpp | 2
branches/release/boost/thread/xtime.hpp | 3
branches/release/libs/thread/build/Jamfile.v2 | 16
branches/release/libs/thread/doc/changes.qbk | 79 +
branches/release/libs/thread/doc/compliance.qbk | 19
branches/release/libs/thread/doc/configuration.qbk | 228 +++
branches/release/libs/thread/doc/future_ref.qbk | 603 ++++++++--
branches/release/libs/thread/doc/futures.qbk | 279 +++++
branches/release/libs/thread/doc/mutex_concepts.qbk | 406 ++++++
branches/release/libs/thread/doc/mutexes.qbk | 4
branches/release/libs/thread/doc/shared_mutex_ref.qbk | 84 +
branches/release/libs/thread/doc/sync_tutorial.qbk | 27
branches/release/libs/thread/doc/thread.qbk | 17
branches/release/libs/thread/doc/thread_ref.qbk | 290 +++-
branches/release/libs/thread/example/ba_externallly_locked.cpp | 79
branches/release/libs/thread/example/condition.cpp | 14
branches/release/libs/thread/example/future_then.cpp | 47
branches/release/libs/thread/example/make_future.cpp | 6
branches/release/libs/thread/example/monitor.cpp | 10
branches/release/libs/thread/example/mutex.cpp | 6
branches/release/libs/thread/example/recursive_mutex.cpp | 6
branches/release/libs/thread/example/scoped_thread.cpp | 14
branches/release/libs/thread/example/shared_monitor.cpp | 1
branches/release/libs/thread/example/shared_mutex.cpp | 1
branches/release/libs/thread/example/starvephil.cpp | 26
branches/release/libs/thread/example/strict_lock.cpp | 2
branches/release/libs/thread/example/synchronized_value.cpp | 6
branches/release/libs/thread/example/tennis.cpp | 6
branches/release/libs/thread/example/thread.cpp | 2
branches/release/libs/thread/example/thread_group.cpp | 49
branches/release/libs/thread/example/thread_guard.cpp | 4
branches/release/libs/thread/example/xtime.cpp | 2
branches/release/libs/thread/src/pthread/thread.cpp | 213 ++-
branches/release/libs/thread/src/pthread/timeconv.inl | 21
branches/release/libs/thread/src/win32/thread.cpp | 162 +-
branches/release/libs/thread/test/Jamfile.v2 | 109 +
branches/release/libs/thread/test/condition_test_common.hpp | 24
branches/release/libs/thread/test/shared_mutex_locking_thread.hpp | 40
branches/release/libs/thread/test/sync/futures/async/async_pass.cpp | 248 +++
branches/release/libs/thread/test/sync/futures/future/dtor_pass.cpp | 4
branches/release/libs/thread/test/sync/futures/future/get_pass.cpp | 174 ++-
branches/release/libs/thread/test/sync/futures/future/move_assign_pass.cpp | 4
branches/release/libs/thread/test/sync/futures/future/move_ctor_pass.cpp | 4
branches/release/libs/thread/test/sync/futures/future/then_pass.cpp | 18
branches/release/libs/thread/test/sync/futures/packaged_task/alloc_ctor_pass.cpp | 32
branches/release/libs/thread/test/sync/futures/packaged_task/copy_assign_fail.cpp | 12
branches/release/libs/thread/test/sync/futures/packaged_task/copy_ctor_fail.cpp | 12
branches/release/libs/thread/test/sync/futures/packaged_task/default_ctor_pass.cpp | 10
branches/release/libs/thread/test/sync/futures/packaged_task/dtor_pass.cpp | 55
branches/release/libs/thread/test/sync/futures/packaged_task/func_ctor_pass.cpp | 51
branches/release/libs/thread/test/sync/futures/packaged_task/get_future_pass.cpp | 13
branches/release/libs/thread/test/sync/futures/packaged_task/member_swap_pass.cpp | 15
branches/release/libs/thread/test/sync/futures/packaged_task/move_assign_pass.cpp | 15
branches/release/libs/thread/test/sync/futures/packaged_task/move_ctor_pass.cpp | 15
branches/release/libs/thread/test/sync/futures/packaged_task/non_member_swap_pass.cpp | 15
branches/release/libs/thread/test/sync/futures/packaged_task/operator_pass.cpp | 140 ++
branches/release/libs/thread/test/sync/futures/packaged_task/reset_pass.cpp | 12
branches/release/libs/thread/test/sync/futures/packaged_task/types_pass.cpp | 2
branches/release/libs/thread/test/sync/futures/packaged_task/use_allocator_pass.cpp | 9
branches/release/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/adopt_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_assign_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_ctor_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/default_pass.cpp | 4
branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/types_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_assign_fail.cpp | 4
branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_ctor_fail.cpp | 4
branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/types_pass.cpp | 3
branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/unique_lock_ctor_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/adopt_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_assign_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_ctor_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/default_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/defer_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/duration_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_assign_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_unique_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_upgrade_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/mutex_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/time_point_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/try_to_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_for_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_until_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/unlock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/member_swap_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/non_member_swap_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/release_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/mutex_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/op_bool_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/owns_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/types_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock_guard/types_pass.cpp | 1
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/adopt_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_assign_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_ctor_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/default_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/defer_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/duration_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_assign_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_for_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_try_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_until_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_for_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_try_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_until_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/mutex_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/time_point_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/try_to_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_for_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_until_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/unlock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/member_swap_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/non_member_swap_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/release_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/mutex_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_bool_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_int_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/owns_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/types_pass.cpp | 1
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/adopt_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_assign_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_ctor_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/default_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/defer_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/duration_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_assign_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_for_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_try_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_until_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_unique_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/mutex_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/time_point_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/try_to_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_for_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_until_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/unlock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/member_swap_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/non_member_swap_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/release_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/mutex_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/op_bool_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/owns_lock_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/types_pass.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/assign_fail.cpp | 2
branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/copy_fail.cpp | 2
branches/release/libs/thread/test/test_2309.cpp | 9
branches/release/libs/thread/test/test_2741.cpp | 2
branches/release/libs/thread/test/test_3628.cpp | 12
branches/release/libs/thread/test/test_4521.cpp | 2
branches/release/libs/thread/test/test_4882.cpp | 39
branches/release/libs/thread/test/test_5351.cpp | 2
branches/release/libs/thread/test/test_5542_1.cpp | 2
branches/release/libs/thread/test/test_5542_2.cpp | 2
branches/release/libs/thread/test/test_5542_3.cpp | 2
branches/release/libs/thread/test/test_5891.cpp | 2
branches/release/libs/thread/test/test_6130.cpp | 4
branches/release/libs/thread/test/test_6174.cpp | 5
branches/release/libs/thread/test/test_7328.cpp | 8
branches/release/libs/thread/test/test_7571.cpp | 2
branches/release/libs/thread/test/test_7665.cpp | 17
branches/release/libs/thread/test/test_barrier.cpp | 4
branches/release/libs/thread/test/test_condition.cpp | 9
branches/release/libs/thread/test/test_condition_notify_all.cpp | 16
branches/release/libs/thread/test/test_condition_notify_one.cpp | 16
branches/release/libs/thread/test/test_condition_timed_wait_times_out.cpp | 18
branches/release/libs/thread/test/test_futures.cpp | 4
branches/release/libs/thread/test/test_generic_locks.cpp | 14
branches/release/libs/thread/test/test_lock_concept.cpp | 11
branches/release/libs/thread/test/test_ml.cpp | 2
branches/release/libs/thread/test/test_move_function.cpp | 7
branches/release/libs/thread/test/test_mutex.cpp | 5
branches/release/libs/thread/test/test_once.cpp | 15
branches/release/libs/thread/test/test_shared_mutex.cpp | 27
branches/release/libs/thread/test/test_shared_mutex_part_2.cpp | 24
branches/release/libs/thread/test/test_shared_mutex_timed_locks.cpp | 14
branches/release/libs/thread/test/test_shared_mutex_timed_locks_chrono.cpp | 14
branches/release/libs/thread/test/test_thread.cpp | 15
branches/release/libs/thread/test/test_thread_launching.cpp | 3
branches/release/libs/thread/test/test_thread_mf.cpp | 1
branches/release/libs/thread/test/test_tss.cpp | 9
branches/release/libs/thread/test/test_xtime.cpp | 4
branches/release/libs/thread/test/threads/container/thread_ptr_list_pass.cpp | 2
branches/release/libs/thread/test/threads/container/thread_vector_pass.cpp | 10
branches/release/libs/thread/test/threads/thread/assign/move_pass.cpp | 1
branches/release/libs/thread/test/threads/thread/constr/FrvalueArgs_pass.cpp | 7
branches/release/libs/thread/test/threads/thread/constr/Frvalue_pass.cpp | 5
branches/release/libs/thread/test/util.inl | 6
240 files changed, 6649 insertions(+), 3819 deletions(-)
Modified: branches/release/boost/thread/barrier.hpp
==============================================================================
--- branches/release/boost/thread/barrier.hpp (original)
+++ branches/release/boost/thread/barrier.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -12,6 +12,7 @@
#include <boost/throw_exception.hpp>
#include <boost/thread/mutex.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/condition_variable.hpp>
#include <string>
#include <stdexcept>
@@ -33,7 +34,7 @@
bool wait()
{
- boost::mutex::scoped_lock lock(m_mutex);
+ boost::unique_lock<boost::mutex> lock(m_mutex);
unsigned int gen = m_generation;
if (--m_count == 0)
Modified: branches/release/boost/thread/condition.hpp
==============================================================================
--- branches/release/boost/thread/condition.hpp (original)
+++ branches/release/boost/thread/condition.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -1,11 +1,15 @@
#ifndef BOOST_THREAD_CONDITION_HPP
#define BOOST_THREAD_CONDITION_HPP
-// (C) Copyright 2007 Anthony Williams
+// (C) Copyright 2007 Anthony Williams
//
// 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/detail/config.hpp>
+
+#if defined BOOST_THREAD_PROVIDES_CONDITION
+
#include <boost/thread/condition_variable.hpp>
namespace boost
@@ -14,3 +18,4 @@
}
#endif
+#endif
Modified: branches/release/boost/thread/detail/config.hpp
==============================================================================
--- branches/release/boost/thread/detail/config.hpp (original)
+++ branches/release/boost/thread/detail/config.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -15,104 +15,153 @@
#include <boost/config.hpp>
#include <boost/detail/workaround.hpp>
+#include <boost/thread/detail/platform.hpp>
-#ifdef BOOST_NO_NOEXCEPT
+#if ! defined BOOST_THREAD_NOEXCEPT_OR_THROW
+#ifdef BOOST_NO_CXX11_NOEXCEPT
# define BOOST_THREAD_NOEXCEPT_OR_THROW throw()
#else
# define BOOST_THREAD_NOEXCEPT_OR_THROW noexcept
#endif
+#endif
+
+#if defined BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED
+#define BOOST_THREAD_ASSERT_PRECONDITION(EXPR, EX) \
+ if (EXPR) {} else boost::throw_exception(EX)
+#define BOOST_THREAD_VERIFY_PRECONDITION(EXPR, EX) \
+ if (EXPR) {} else boost::throw_exception(EX)
+#define BOOST_THREAD_THROW_ELSE_RETURN(EX, RET) \
+ boost::throw_exception(EX)
+#else
+#define BOOST_THREAD_ASSERT_PRECONDITION(EXPR, EX)
+#define BOOST_THREAD_VERIFY_PRECONDITION(EXPR, EX) \
+ (void)(EXPR)
+#define BOOST_THREAD_THROW_ELSE_RETURN(EX, RET) \
+ return (RET)
+#endif
// This compiler doesn't support Boost.Chrono
-#if defined __IBMCPP__ && (__IBMCPP__ < 1100) && ! defined BOOST_THREAD_DONT_USE_CHRONO
+#if defined __IBMCPP__ && (__IBMCPP__ < 1100) \
+ && ! defined BOOST_THREAD_DONT_USE_CHRONO
#define BOOST_THREAD_DONT_USE_CHRONO
+#if ! defined BOOST_THREAD_USE_DATE
+#define BOOST_THREAD_USE_DATE
+#endif
#endif
// This compiler doesn't support Boost.Move
-#if BOOST_WORKAROUND(__SUNPRO_CC, < 0x5100) && ! defined BOOST_THREAD_DONT_USE_MOVE
+#if BOOST_WORKAROUND(__SUNPRO_CC, < 0x5100) \
+ && ! defined BOOST_THREAD_DONT_USE_MOVE
#define BOOST_THREAD_DONT_USE_MOVE
#endif
// This compiler doesn't support Boost.Container Allocators files
-#if defined __SUNPRO_CC && ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS
+#if defined __SUNPRO_CC \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS
#define BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS
#endif
-#if defined _WIN32_WCE && _WIN32_WCE==0x501 && ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS
+#if defined _WIN32_WCE && _WIN32_WCE==0x501 \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS
#define BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS
#endif
-#if ! defined BOOST_THREAD_DONT_PROVIDE_BASIC_THREAD_ID && ! defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
+/// BASIC_THREAD_ID
+// todo to be removed for 1.54
+#if ! defined BOOST_THREAD_DONT_PROVIDE_BASIC_THREAD_ID \
+ && ! defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
#define BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
#endif
+/// RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR
+#if defined BOOST_NO_CXX11_RVALUE_REFERENCES || defined BOOST_MSVC
+#define BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR
+#endif
+
// Default version is 2
#if !defined BOOST_THREAD_VERSION
#define BOOST_THREAD_VERSION 2
#else
-#if BOOST_THREAD_VERSION!=2 && BOOST_THREAD_VERSION!=3
-#error "BOOST_THREAD_VERSION must be 2 or 3"
+#if BOOST_THREAD_VERSION!=2 && BOOST_THREAD_VERSION!=3 && BOOST_THREAD_VERSION!=4
+#error "BOOST_THREAD_VERSION must be 2, 3 or 4"
#endif
#endif
+// CHRONO
// Uses Boost.Chrono by default if not stated the opposite defining BOOST_THREAD_DONT_USE_CHRONO
-#if ! defined BOOST_THREAD_DONT_USE_CHRONO && ! defined BOOST_THREAD_USES_CHRONO
+#if ! defined BOOST_THREAD_DONT_USE_CHRONO \
+ && ! defined BOOST_THREAD_USES_CHRONO
#define BOOST_THREAD_USES_CHRONO
#endif
-// Don't provided by default in version 1.
-#if defined BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
-#define BOOST_THREAD_EXPLICIT_LOCK_CONVERSION explicit
-#else
-#define BOOST_THREAD_EXPLICIT_LOCK_CONVERSION
-#endif
-
-
#if BOOST_THREAD_VERSION==2
-#if ! defined BOOST_THREAD_DONT_PROVIDE_PROMISE_LAZY && ! defined BOOST_THREAD_PROMISE_LAZY
-#define BOOST_THREAD_PROMISE_LAZY
+
+// PROVIDE_PROMISE_LAZY
+#if ! defined BOOST_THREAD_DONT_PROVIDE_PROMISE_LAZY \
+ && ! defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
+#define BOOST_THREAD_PROVIDES_PROMISE_LAZY
#endif
-#if ! defined BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0
-#define BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
+
+// PROVIDE_THREAD_EQ
+#if ! defined BOOST_THREAD_DONT_PROVIDE_THREAD_EQ \
+ && ! defined BOOST_THREAD_PROVIDES_THREAD_EQ
+#define BOOST_THREAD_PROVIDES_THREAD_EQ
#endif
+
#endif
-#if BOOST_THREAD_VERSION==3
+#if BOOST_THREAD_VERSION>=3
+
+// ONCE_CXX11
+// fixme BOOST_THREAD_PROVIDES_ONCE_CXX11 doesn't works when thread.cpp is compiled BOOST_THREAD_VERSION 3
#if ! defined BOOST_THREAD_DONT_PROVIDE_ONCE_CXX11 \
&& ! defined BOOST_THREAD_PROVIDES_ONCE_CXX11
-#define BOOST_THREAD_PROVIDES_ONCE_CXX11
+#define BOOST_THREAD_DONT_PROVIDE_ONCE_CXX11
#endif
+
+// THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE
#if ! defined BOOST_THREAD_DONT_PROVIDE_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE \
&& ! defined BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE
#define BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE
#endif
+
+// THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE
#if ! defined BOOST_THREAD_DONT_PROVIDE_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE \
&& ! defined BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE
#define BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE
#endif
+
+// PROVIDE_FUTURE
#if ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE \
&& ! defined BOOST_THREAD_PROVIDES_FUTURE
#define BOOST_THREAD_PROVIDES_FUTURE
#endif
+
+// FUTURE_CTOR_ALLOCATORS
#if ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS \
&& ! defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
#define BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
#endif
+
+// SHARED_MUTEX_UPWARDS_CONVERSIONS
#if ! defined BOOST_THREAD_DONT_PROVIDE_SHARED_MUTEX_UPWARDS_CONVERSIONS \
&& ! defined BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
#define BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
#endif
+
+// PROVIDE_EXPLICIT_LOCK_CONVERSION
#if ! defined BOOST_THREAD_DONT_PROVIDE_EXPLICIT_LOCK_CONVERSION \
&& ! defined BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#endif
+
+// GENERIC_SHARED_MUTEX_ON_WIN
#if ! defined BOOST_THREAD_DONT_PROVIDE_GENERIC_SHARED_MUTEX_ON_WIN \
&& ! defined BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
#endif
-#if ! defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 \
- && ! defined BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_
-#define BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0
-#endif
+
+// USE_MOVE
#if ! defined BOOST_THREAD_DONT_USE_MOVE \
&& ! defined BOOST_THREAD_USES_MOVE
#define BOOST_THREAD_USES_MOVE
@@ -120,6 +169,93 @@
#endif
+// deprecated since version 4
+#if BOOST_THREAD_VERSION < 4
+
+// NESTED_LOCKS
+#if ! defined BOOST_THREAD_PROVIDES_NESTED_LOCKS \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_NESTED_LOCKS
+#define BOOST_THREAD_PROVIDES_NESTED_LOCKS
+#endif
+
+// CONDITION
+#if ! defined BOOST_THREAD_PROVIDES_CONDITION \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_CONDITION
+#define BOOST_THREAD_PROVIDES_CONDITION
+#endif
+
+// USE_DATETIME
+#if ! defined BOOST_THREAD_DONT_USE_DATETIME \
+ && ! defined BOOST_THREAD_USES_DATETIME
+#define BOOST_THREAD_USES_DATETIME
+#endif
+#endif
+
+#if BOOST_THREAD_VERSION>=4
+
+// SIGNATURE_PACKAGED_TASK
+#if ! defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_SIGNATURE_PACKAGED_TASK
+#define BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#endif
+
+// VARIADIC_THREAD
+#if ! defined BOOST_THREAD_PROVIDES_VARIADIC_THREAD \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_VARIADIC_THREAD
+
+#if ! defined(BOOST_NO_SFINAE_EXPR) && \
+ ! defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) && \
+ ! defined(BOOST_NO_CXX11_DECLTYPE) && \
+ ! defined(BOOST_NO_CXX11_DECLTYPE_N3276) && \
+ ! defined(BOOST_NO_CXX11_AUTO) && \
+ ! defined(BOOST_NO_CXX11_RVALUE_REFERENCES) && \
+ ! defined(BOOST_NO_CXX11_HDR_TUPLE)
+
+#define BOOST_THREAD_PROVIDES_VARIADIC_THREAD
+#endif
+#endif
+
+// FUTURE_CONTINUATION
+#if ! defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_CONTINUATION
+#define BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+#endif
+
+// FUTURE_INVALID_AFTER_GET
+#if ! defined BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_FUTURE_INVALID_AFTER_GET
+#define BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
+#endif
+
+// NESTED_LOCKS
+#if ! defined BOOST_THREAD_PROVIDES_NESTED_LOCKS \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_NESTED_LOCKS
+#define BOOST_THREAD_DONT_PROVIDE_NESTED_LOCKS
+#endif
+
+// CONDITION
+#if ! defined BOOST_THREAD_PROVIDES_CONDITION \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_CONDITION
+#define BOOST_THREAD_DONT_PROVIDE_CONDITION
+#endif
+
+#endif // BOOST_THREAD_VERSION>=4
+
+// INTERRUPTIONS
+#if ! defined BOOST_THREAD_PROVIDES_INTERRUPTIONS \
+ && ! defined BOOST_THREAD_DONT_PROVIDE_INTERRUPTIONS
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+#endif
+
+// CORRELATIONS
+
+// EXPLICIT_LOCK_CONVERSION.
+#if defined BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
+#define BOOST_THREAD_EXPLICIT_LOCK_CONVERSION explicit
+#else
+#define BOOST_THREAD_EXPLICIT_LOCK_CONVERSION
+#endif
+
// BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN is defined if BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
#if defined BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS \
&& ! defined BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
@@ -128,9 +264,12 @@
// BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 defined by default up to Boost 1.52
// BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0 defined by default up to Boost 1.55
-#if ! defined BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0 \
-&& ! defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
-#define BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
+#if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
+
+#if ! defined BOOST_THREAD_PROVIDES_THREAD_EQ
+#define BOOST_THREAD_PROVIDES_THREAD_EQ
+#endif
+
#endif
#if BOOST_WORKAROUND(__BORLANDC__, < 0x600)
@@ -142,6 +281,13 @@
#include <boost/thread/detail/platform.hpp>
+#if defined(BOOST_THREAD_PLATFORM_WIN32)
+#else
+ # if defined(BOOST_HAS_PTHREAD_DELAY_NP) || defined(BOOST_HAS_NANOSLEEP)
+ # define BOOST_THREAD_SLEEP_FOR_IS_STEADY
+ # endif
+#endif
+
// provided for backwards compatibility, since this
// macro was used for several releases by mistake.
#if defined(BOOST_THREAD_DYN_DLL) && ! defined BOOST_THREAD_DYN_LINK
Copied: branches/release/boost/thread/detail/is_convertible.hpp (from r81443, /trunk/boost/thread/detail/is_convertible.hpp)
==============================================================================
--- /trunk/boost/thread/detail/is_convertible.hpp (original)
+++ branches/release/boost/thread/detail/is_convertible.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -12,6 +12,7 @@
#define BOOST_THREAD_DETAIL_IS_CONVERTIBLE_HPP
#include <boost/type_traits/is_convertible.hpp>
+#include <boost/thread/detail/move.hpp>
namespace boost
{
@@ -20,9 +21,25 @@
template <typename T1, typename T2>
struct is_convertible : boost::is_convertible<T1,T2> {};
+#if defined BOOST_NO_CXX11_RVALUE_REFERENCES
+
+#if defined(BOOST_INTEL_CXX_VERSION) && (BOOST_INTEL_CXX_VERSION <= 1001)
+
+#if defined BOOST_THREAD_USES_MOVE
+ template <typename T1, typename T2>
+ struct is_convertible<
+ rv<T1> &,
+ rv<rv<T2> > &
+ > : false_type {};
+#endif
+
+#elif defined __GNUC__ && (__GNUC__ < 4 || ( __GNUC__ == 4 && __GNUC_MINOR__ <= 4 ))
+
template <typename T1, typename T2>
struct is_convertible<T1&, T2&> : boost::is_convertible<T1, T2> {};
+#endif
+#endif
}
} // namespace boost
Modified: branches/release/boost/thread/detail/move.hpp
==============================================================================
--- branches/release/boost/thread/detail/move.hpp (original)
+++ branches/release/boost/thread/detail/move.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,7 +17,7 @@
#endif
#include <boost/thread/detail/delete.hpp>
-#include <boost/move/move.hpp>
+#include <boost/move/utility.hpp>
#include <boost/config/abi_prefix.hpp>
namespace boost
@@ -26,7 +26,7 @@
namespace detail
{
template <typename T>
- struct has_move_emulation_enabled_aux_dummy_specialization;
+ struct enable_move_utility_emulation_dummy_specialization;
template<typename T>
struct thread_move_t
{
@@ -49,6 +49,7 @@
};
}
+#if !defined BOOST_THREAD_USES_MOVE
#ifndef BOOST_NO_SFINAE
template<typename T>
@@ -63,11 +64,14 @@
{
return t;
}
+
+#endif //#if !defined BOOST_THREAD_USES_MOVE
}
#if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
#define BOOST_THREAD_RV_REF(TYPE) BOOST_RV_REF(TYPE)
+#define BOOST_THREAD_RV_REF_2_TEMPL_ARGS(TYPE) BOOST_RV_REF_2_TEMPL_ARGS(TYPE)
#define BOOST_THREAD_RV_REF_BEG BOOST_RV_REF_BEG
#define BOOST_THREAD_RV_REF_END BOOST_RV_REF_END
#define BOOST_THREAD_RV(V) V
@@ -77,16 +81,17 @@
#define BOOST_THREAD_DCL_MOVABLE_BEG(T) \
namespace detail { \
template <typename T> \
- struct has_move_emulation_enabled_aux_dummy_specialization<
+ struct enable_move_utility_emulation_dummy_specialization<
#define BOOST_THREAD_DCL_MOVABLE_END > \
- : integral_constant<bool, true> \
+ : integral_constant<bool, false> \
{}; \
}
#elif ! defined BOOST_NO_CXX11_RVALUE_REFERENCES && defined BOOST_MSVC
#define BOOST_THREAD_RV_REF(TYPE) BOOST_RV_REF(TYPE)
+#define BOOST_THREAD_RV_REF_2_TEMPL_ARGS(TYPE) BOOST_RV_REF_2_TEMPL_ARGS(TYPE)
#define BOOST_THREAD_RV_REF_BEG BOOST_RV_REF_BEG
#define BOOST_THREAD_RV_REF_END BOOST_RV_REF_END
#define BOOST_THREAD_RV(V) V
@@ -96,10 +101,10 @@
#define BOOST_THREAD_DCL_MOVABLE_BEG(T) \
namespace detail { \
template <typename T> \
- struct has_move_emulation_enabled_aux_dummy_specialization<
+ struct enable_move_utility_emulation_dummy_specialization<
#define BOOST_THREAD_DCL_MOVABLE_END > \
- : integral_constant<bool, true> \
+ : integral_constant<bool, false> \
{}; \
}
@@ -107,6 +112,7 @@
#if defined BOOST_THREAD_USES_MOVE
#define BOOST_THREAD_RV_REF(TYPE) BOOST_RV_REF(TYPE)
+#define BOOST_THREAD_RV_REF_2_TEMPL_ARGS(TYPE) BOOST_RV_REF_2_TEMPL_ARGS(TYPE)
#define BOOST_THREAD_RV_REF_BEG BOOST_RV_REF_BEG
#define BOOST_THREAD_RV_REF_END BOOST_RV_REF_END
#define BOOST_THREAD_RV(V) V
@@ -115,10 +121,10 @@
#define BOOST_THREAD_DCL_MOVABLE_BEG(T) \
namespace detail { \
template <typename T> \
- struct has_move_emulation_enabled_aux_dummy_specialization<
+ struct enable_move_utility_emulation_dummy_specialization<
#define BOOST_THREAD_DCL_MOVABLE_END > \
- : integral_constant<bool, true> \
+ : integral_constant<bool, false> \
{}; \
}
@@ -132,17 +138,19 @@
#define BOOST_THREAD_DCL_MOVABLE(TYPE) \
template <> \
-struct has_move_emulation_enabled_aux< TYPE > \
- : BOOST_MOVE_BOOST_NS::integral_constant<bool, true> \
-{};
+struct enable_move_utility_emulation< TYPE > \
+{ \
+ static const bool value = false; \
+};
#define BOOST_THREAD_DCL_MOVABLE_BEG(T) \
template <typename T> \
-struct has_move_emulation_enabled_aux<
+struct enable_move_utility_emulation<
#define BOOST_THREAD_DCL_MOVABLE_END > \
- : BOOST_MOVE_BOOST_NS::integral_constant<bool, true> \
-{};
+{ \
+ static const bool value = false; \
+};
#endif
@@ -227,19 +235,26 @@
-#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
namespace boost
{ namespace thread_detail
{
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
template <class T>
typename decay<T>::type
decay_copy(T&& t)
{
return boost::forward<T>(t);
}
+#else
+ template <class T>
+ typename decay<T>::type
+ decay_copy(BOOST_THREAD_FWD_REF(T) t)
+ {
+ return boost::forward<T>(t);
}
-}
#endif
+ }
+}
#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-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,18 +3,24 @@
// 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)
-// (C) Copyright 2007-10 Anthony Williams
-// (C) Copyright 20011-12 Vicente J. Botet Escriba
+// (C) Copyright 2007-2010 Anthony Williams
+// (C) Copyright 20011-2012 Vicente J. Botet Escriba
#include <boost/thread/detail/config.hpp>
+
#include <boost/thread/exceptions.hpp>
#ifndef BOOST_NO_IOSTREAM
#include <ostream>
#endif
#include <boost/thread/detail/move.hpp>
#include <boost/thread/mutex.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/thread/xtime.hpp>
+#endif
#include <boost/thread/detail/thread_heap_alloc.hpp>
+#include <boost/thread/detail/make_tuple_indices.hpp>
+#include <boost/thread/detail/invoke.hpp>
+#include <boost/thread/detail/is_convertible.hpp>
#include <boost/assert.hpp>
#include <list>
#include <algorithm>
@@ -23,8 +29,6 @@
#include <boost/bind.hpp>
#include <stdlib.h>
#include <memory>
-//#include <vector>
-//#include <utility>
#include <boost/utility/enable_if.hpp>
#include <boost/type_traits/remove_reference.hpp>
#include <boost/io/ios_state.hpp>
@@ -36,6 +40,9 @@
#include <boost/chrono/ceil.hpp>
#endif
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+#include <tuple>
+#endif
#include <boost/config/abi_prefix.hpp>
#ifdef BOOST_MSVC
@@ -48,6 +55,38 @@
namespace detail
{
+
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+
+ template<typename F, class ...ArgTypes>
+ class thread_data:
+ public detail::thread_data_base
+ {
+ public:
+ BOOST_THREAD_NO_COPYABLE(thread_data)
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
+ thread_data(BOOST_THREAD_RV_REF(F) f_, BOOST_THREAD_RV_REF(ArgTypes)... args_):
+ fp(boost::forward<F>(f_), boost::forward<ArgTypes>(args_)...)
+ {}
+#endif
+ template <std::size_t ...Indices>
+ void run2(tuple_indices<Indices...>)
+ {
+
+ invoke(std::move(std::get<0>(fp)), std::move(std::get<Indices>(fp))...);
+ }
+ void run()
+ {
+ typedef typename make_tuple_indices<std::tuple_size<std::tuple<F, ArgTypes...> >::value, 1>::type index_type;
+
+ run2(index_type());
+ }
+
+ private:
+ std::tuple<typename decay<F>::type, typename decay<ArgTypes>::type...> fp;
+ };
+#else // defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+
template<typename F>
class thread_data:
public detail::thread_data_base
@@ -115,6 +154,7 @@
f();
}
};
+#endif
}
class BOOST_THREAD_DECL thread
@@ -125,24 +165,55 @@
BOOST_THREAD_MOVABLE_ONLY(thread)
private:
+ struct dummy;
+
void release_handle();
detail::thread_data_ptr thread_info;
- void start_thread();
- void start_thread(const attributes& attr);
+ private:
+ bool start_thread_noexcept();
+ bool start_thread_noexcept(const attributes& attr);
+ public:
+ void start_thread()
+ {
+ if (!start_thread_noexcept())
+ {
+ boost::throw_exception(thread_resource_error());
+ }
+ }
+ void start_thread(const attributes& attr)
+ {
+ if (!start_thread_noexcept(attr))
+ {
+ boost::throw_exception(thread_resource_error());
+ }
+ }
explicit thread(detail::thread_data_ptr data);
detail::thread_data_ptr get_thread_info BOOST_PREVENT_MACRO_SUBSTITUTION () const;
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename F, class ...ArgTypes>
+ static inline detail::thread_data_ptr make_thread_info(BOOST_THREAD_RV_REF(F) f, BOOST_THREAD_RV_REF(ArgTypes)... args)
+ {
+ return detail::thread_data_ptr(detail::heap_new<
+ detail::thread_data<typename boost::remove_reference<F>::type, ArgTypes...>
+ >(
+ boost::forward<F>(f), boost::forward<ArgTypes>(args)...
+ )
+ );
+ }
+#else
template<typename F>
static inline detail::thread_data_ptr make_thread_info(BOOST_THREAD_RV_REF(F) f)
{
return detail::thread_data_ptr(detail::heap_new<detail::thread_data<typename boost::remove_reference<F>::type> >(
boost::forward<F>(f)));
}
+#endif
static inline detail::thread_data_ptr make_thread_info(void (*f)())
{
return detail::thread_data_ptr(detail::heap_new<detail::thread_data<void(*)()> >(
@@ -150,7 +221,12 @@
}
#else
template<typename F>
- static inline detail::thread_data_ptr make_thread_info(F f)
+ static inline detail::thread_data_ptr make_thread_info(F f
+ , typename disable_if_c<
+ //boost::thread_detail::is_convertible<F&,BOOST_THREAD_RV_REF(F)>::value ||
+ is_same<typename decay<F>::type, thread>::value,
+ dummy* >::type=0
+ )
{
return detail::thread_data_ptr(detail::heap_new<detail::thread_data<F> >(f));
}
@@ -161,7 +237,6 @@
}
#endif
- struct dummy;
public:
#if 0 // This should not be needed anymore. Use instead BOOST_THREAD_MAKE_RV_REF.
#if BOOST_WORKAROUND(__SUNPRO_CC, < 0x5100)
@@ -171,6 +246,7 @@
thread() BOOST_NOEXCEPT;
~thread()
{
+
#if defined BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE
if (joinable()) {
std::terminate();
@@ -184,7 +260,7 @@
class F
>
explicit thread(BOOST_THREAD_RV_REF(F) f
- , typename disable_if<is_same<typename decay<F>::type, thread>, dummy* >::type=0
+ //, typename disable_if<is_same<typename decay<F>::type, thread>, dummy* >::type=0
):
thread_info(make_thread_info(thread_detail::decay_copy(boost::forward<F>(f))))
{
@@ -193,7 +269,7 @@
template <
class F
>
- thread(attributes& attrs, BOOST_THREAD_RV_REF(F) f):
+ thread(attributes const& attrs, BOOST_THREAD_RV_REF(F) f):
thread_info(make_thread_info(thread_detail::decay_copy(boost::forward<F>(f))))
{
start_thread(attrs);
@@ -208,7 +284,7 @@
start_thread();
}
template <class F>
- thread(attributes& attrs, F f):
+ thread(attributes const& attrs, F f):
thread_info(make_thread_info(f))
{
start_thread(attrs);
@@ -216,15 +292,19 @@
#else
template <class F>
explicit thread(F f
- // todo Disable also if Or is_same<typename decay<F>::type, thread>
- , typename disable_if<boost::is_convertible<F&,BOOST_THREAD_RV_REF(F) >, dummy* >::type=0):
+ , typename disable_if_c<
+ boost::thread_detail::is_convertible<F&,BOOST_THREAD_RV_REF(F)>::value
+ //|| is_same<typename decay<F>::type, thread>::value
+ , dummy* >::type=0
+ ):
thread_info(make_thread_info(f))
{
start_thread();
}
template <class F>
- thread(attributes& attrs, F f
- , typename disable_if<boost::is_convertible<F&,BOOST_THREAD_RV_REF(F) >, dummy* >::type=0):
+ thread(attributes const& attrs, F f
+ , typename disable_if<boost::thread_detail::is_convertible<F&,BOOST_THREAD_RV_REF(F) >, dummy* >::type=0
+ ):
thread_info(make_thread_info(f))
{
start_thread(attrs);
@@ -234,14 +314,22 @@
explicit thread(BOOST_THREAD_RV_REF(F) f
, typename disable_if<is_same<typename decay<F>::type, thread>, dummy* >::type=0
):
- thread_info(make_thread_info(f))
+#ifdef BOOST_THREAD_USES_MOVE
+ thread_info(make_thread_info(boost::move<F>(f))) // todo : Add forward
+#else
+ thread_info(make_thread_info(f)) // todo : Add forward
+#endif
{
start_thread();
}
template <class F>
- thread(attributes& attrs, BOOST_THREAD_RV_REF(F) f):
- thread_info(make_thread_info(f))
+ thread(attributes const& attrs, BOOST_THREAD_RV_REF(F) f):
+#ifdef BOOST_THREAD_USES_MOVE
+ thread_info(make_thread_info(boost::move<F>(f))) // todo : Add forward
+#else
+ thread_info(make_thread_info(f)) // todo : Add forward
+#endif
{
start_thread(attrs);
}
@@ -272,8 +360,32 @@
return *this;
}
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template <class F, class Arg, class ...Args>
+ thread(F&& f, Arg&& arg, Args&&... args) :
+ thread_info(make_thread_info(
+ thread_detail::decay_copy(boost::forward<F>(f)),
+ thread_detail::decay_copy(boost::forward<Arg>(arg)),
+ thread_detail::decay_copy(boost::forward<Args>(args))...)
+ )
+
+ {
+ start_thread();
+ }
+ template <class F, class Arg, class ...Args>
+ thread(attributes const& attrs, F&& f, Arg&& arg, Args&&... args) :
+ thread_info(make_thread_info(
+ thread_detail::decay_copy(boost::forward<F>(f)),
+ thread_detail::decay_copy(boost::forward<Arg>(arg)),
+ thread_detail::decay_copy(boost::forward<Args>(args))...)
+ )
+
+ {
+ start_thread(attrs);
+ }
+#else
template <class F,class A1>
- thread(F f,A1 a1,typename disable_if<boost::is_convertible<F&,thread_attributes >, dummy* >::type=0):
+ thread(F f,A1 a1,typename disable_if<boost::thread_detail::is_convertible<F&,thread_attributes >, dummy* >::type=0):
thread_info(make_thread_info(boost::bind(boost::type<void>(),f,a1)))
{
start_thread();
@@ -333,18 +445,26 @@
{
start_thread();
}
-
+#endif
void swap(thread& x) BOOST_NOEXCEPT
{
thread_info.swap(x.thread_info);
}
class BOOST_SYMBOL_VISIBLE id;
+#ifdef BOOST_THREAD_PLATFORM_PTHREAD
+ inline id get_id() const BOOST_NOEXCEPT;
+#else
id get_id() const BOOST_NOEXCEPT;
+#endif
bool joinable() const BOOST_NOEXCEPT;
- void join();
+ private:
+ bool join_noexcept();
+ public:
+ inline void join();
+
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_join_for(const chrono::duration<Rep, Period>& rel_time)
@@ -368,10 +488,15 @@
}
#endif
#if defined(BOOST_THREAD_PLATFORM_WIN32)
- bool timed_join(const system_time& abs_time);
private:
- bool do_try_join_until(uintmax_t milli);
+ bool do_try_join_until_noexcept(uintmax_t milli, bool& res);
+ inline bool do_try_join_until(uintmax_t milli);
public:
+ bool timed_join(const system_time& abs_time);
+ //{
+ // return do_try_join_until(get_milliseconds_until(wait_until));
+ //}
+
#ifdef BOOST_THREAD_USES_CHRONO
bool try_join_until(const chrono::time_point<chrono::system_clock, chrono::nanoseconds>& tp)
{
@@ -382,35 +507,37 @@
#else
+ private:
+ bool do_try_join_until_noexcept(struct timespec const &timeout, bool& res);
+ inline bool do_try_join_until(struct timespec const &timeout);
+ public:
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_join(const system_time& abs_time)
{
- struct timespec const ts=detail::get_timespec(abs_time);
+ struct timespec const ts=detail::to_timespec(abs_time);
return do_try_join_until(ts);
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
bool try_join_until(const chrono::time_point<chrono::system_clock, chrono::nanoseconds>& tp)
{
using namespace chrono;
nanoseconds d = tp.time_since_epoch();
- timespec ts;
- seconds s = duration_cast<seconds>(d);
- ts.tv_sec = static_cast<long>(s.count());
- ts.tv_nsec = static_cast<long>((d - s).count());
+ timespec ts = boost::detail::to_timespec(d);
return do_try_join_until(ts);
}
#endif
- private:
- bool do_try_join_until(struct timespec const &timeout);
- public:
#endif
+ public:
+#if defined BOOST_THREAD_USES_DATETIME
template<typename TimeDuration>
inline bool timed_join(TimeDuration const& rel_time)
{
return timed_join(get_system_time()+rel_time);
}
-
+#endif
void detach();
static unsigned hardware_concurrency() BOOST_NOEXCEPT;
@@ -419,12 +546,13 @@
typedef detail::thread_data_base::native_handle_type native_handle_type;
native_handle_type native_handle();
-#if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
+#if defined BOOST_THREAD_PROVIDES_THREAD_EQ
// Use thread::id when comparisions are needed
// backwards compatibility
bool operator==(const thread& other) const;
bool operator!=(const thread& other) const;
#endif
+#if defined BOOST_THREAD_USES_DATETIME
static inline void yield() BOOST_NOEXCEPT
{
this_thread::yield();
@@ -434,10 +562,13 @@
{
this_thread::sleep(xt);
}
+#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
// extensions
void interrupt();
bool interruption_requested() const BOOST_NOEXCEPT;
+#endif
};
inline void swap(thread& lhs,thread& rhs) BOOST_NOEXCEPT
@@ -456,16 +587,24 @@
namespace this_thread
{
+#ifdef BOOST_THREAD_PLATFORM_PTHREAD
+ inline thread::id get_id() BOOST_NOEXCEPT;
+#else
thread::id BOOST_THREAD_DECL get_id() BOOST_NOEXCEPT;
+#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void BOOST_THREAD_DECL interruption_point();
bool BOOST_THREAD_DECL interruption_enabled() BOOST_NOEXCEPT;
bool BOOST_THREAD_DECL interruption_requested() BOOST_NOEXCEPT;
+#endif
+#if defined BOOST_THREAD_USES_DATETIME
inline BOOST_SYMBOL_VISIBLE void sleep(xtime const& abs_time)
{
sleep(system_time(abs_time));
}
+#endif
}
class BOOST_SYMBOL_VISIBLE thread::id
@@ -501,12 +640,8 @@
public:
id() BOOST_NOEXCEPT:
#if defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
-#if defined(BOOST_THREAD_PLATFORM_WIN32)
thread_data(0)
#else
- thread_data(0)
-#endif
-#else
thread_data()
#endif
{}
@@ -583,6 +718,62 @@
#endif
};
+#ifdef BOOST_THREAD_PLATFORM_PTHREAD
+ thread::id thread::get_id() const BOOST_NOEXCEPT
+ {
+ #if defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
+ return const_cast<thread*>(this)->native_handle();
+ #else
+ detail::thread_data_ptr const local_thread_info=(get_thread_info)();
+ return (local_thread_info? id(local_thread_info) id());
+ #endif
+ }
+
+ namespace this_thread
+ {
+ thread::id get_id() BOOST_NOEXCEPT
+ {
+ #if defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
+ return pthread_self();
+ #else
+ boost::detail::thread_data_base* const thread_info=get_or_make_current_thread_data();
+ return (thread_info?thread::id(thread_info->shared_from_this()):thread::id());
+ #endif
+ }
+ }
+#endif
+ void thread::join() {
+ BOOST_THREAD_ASSERT_PRECONDITION( this_thread::get_id() != get_id(),
+ thread_resource_error(system::errc::resource_deadlock_would_occur, "boost thread: trying joining itself")
+ );
+ BOOST_THREAD_VERIFY_PRECONDITION( join_noexcept(),
+ thread_resource_error(system::errc::invalid_argument, "boost thread: thread not joinable")
+ );
+ }
+
+#ifdef BOOST_THREAD_PLATFORM_PTHREAD
+ bool thread::do_try_join_until(struct timespec const &timeout)
+#else
+ bool thread::do_try_join_until(uintmax_t timeout)
+#endif
+ {
+ BOOST_THREAD_ASSERT_PRECONDITION( this_thread::get_id() != get_id(),
+ thread_resource_error(system::errc::resource_deadlock_would_occur, "boost thread: trying joining itself")
+ );
+ bool res;
+ if (do_try_join_until_noexcept(timeout, res))
+ {
+ return res;
+ }
+ else
+ {
+ BOOST_THREAD_THROW_ELSE_RETURN(
+ thread_resource_error(system::errc::invalid_argument, "boost thread: thread not joinable"),
+ false
+ );
+ }
+ }
+
#if !defined(BOOST_NO_IOSTREAM) && defined(BOOST_NO_MEMBER_TEMPLATE_FRIENDS)
template<class charT, class traits>
BOOST_SYMBOL_VISIBLE
@@ -593,7 +784,7 @@
}
#endif
-#if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
+#if defined BOOST_THREAD_PROVIDES_THREAD_EQ
inline bool thread::operator==(const thread& other) const
{
return get_id()==other.get_id();
Modified: branches/release/boost/thread/detail/thread_group.hpp
==============================================================================
--- branches/release/boost/thread/detail/thread_group.hpp (original)
+++ branches/release/boost/thread/detail/thread_group.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,6 +8,7 @@
#include <list>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/mutex.hpp>
+#include <boost/thread/lock_guard.hpp>
#include <boost/config/abi_prefix.hpp>
@@ -22,7 +23,7 @@
{
private:
thread_group(thread_group const&);
- thread_group& operator=(thread_group const&);
+ thread_group& operator=(thread_group const&);
public:
thread_group() {}
~thread_group()
@@ -35,6 +36,41 @@
}
}
+ bool is_this_thread_in()
+ {
+ thread::id id = this_thread::get_id();
+ boost::shared_lock<shared_mutex> guard(m);
+ for(std::list<thread*>::iterator it=threads.begin(),end=threads.end();
+ it!=end;
+ ++it)
+ {
+ if ((*it)->get_id() == id)
+ return true;
+ }
+ return false;
+ }
+
+ bool is_thread_in(thread* thrd)
+ {
+ if(thrd)
+ {
+ thread::id id = thrd->get_id();
+ boost::shared_lock<shared_mutex> guard(m);
+ for(std::list<thread*>::iterator it=threads.begin(),end=threads.end();
+ it!=end;
+ ++it)
+ {
+ if ((*it)->get_id() == id)
+ return true;
+ }
+ return false;
+ }
+ else
+ {
+ return false;
+ }
+ }
+
template<typename F>
thread* create_thread(F threadfunc)
{
@@ -43,16 +79,20 @@
threads.push_back(new_thread.get());
return new_thread.release();
}
-
+
void add_thread(thread* thrd)
{
if(thrd)
{
+ BOOST_THREAD_ASSERT_PRECONDITION( ! is_thread_in(thrd) ,
+ thread_resource_error(system::errc::resource_deadlock_would_occur, "boost::thread_group: trying to add a duplicated thread")
+ );
+
boost::lock_guard<shared_mutex> guard(m);
threads.push_back(thrd);
}
}
-
+
void remove_thread(thread* thrd)
{
boost::lock_guard<shared_mutex> guard(m);
@@ -62,23 +102,28 @@
threads.erase(it);
}
}
-
+
void join_all()
{
+ BOOST_THREAD_ASSERT_PRECONDITION( ! is_this_thread_in() ,
+ thread_resource_error(system::errc::resource_deadlock_would_occur, "boost::thread_group: trying joining itself")
+ );
boost::shared_lock<shared_mutex> guard(m);
-
+
for(std::list<thread*>::iterator it=threads.begin(),end=threads.end();
it!=end;
++it)
{
+ if ((*it)->joinable())
(*it)->join();
}
}
-
+
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void interrupt_all()
{
boost::shared_lock<shared_mutex> guard(m);
-
+
for(std::list<thread*>::iterator it=threads.begin(),end=threads.end();
it!=end;
++it)
@@ -86,13 +131,14 @@
(*it)->interrupt();
}
}
-
+#endif
+
size_t size() const
{
boost::shared_lock<shared_mutex> guard(m);
return threads.size();
}
-
+
private:
std::list<thread*> threads;
mutable shared_mutex m;
Modified: branches/release/boost/thread/detail/thread_interruption.hpp
==============================================================================
--- branches/release/boost/thread/detail/thread_interruption.hpp (original)
+++ branches/release/boost/thread/detail/thread_interruption.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -9,6 +9,8 @@
#include <boost/thread/detail/config.hpp>
#include <boost/thread/detail/delete.hpp>
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
namespace boost
{
namespace this_thread
@@ -33,4 +35,5 @@
}
}
-#endif
+#endif // BOOST_THREAD_PROVIDES_INTERRUPTIONS
+#endif // header
Modified: branches/release/boost/thread/exceptions.hpp
==============================================================================
--- branches/release/boost/thread/exceptions.hpp (original)
+++ branches/release/boost/thread/exceptions.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -28,8 +28,10 @@
namespace boost
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
class BOOST_SYMBOL_VISIBLE thread_interrupted
{};
+#endif
class BOOST_SYMBOL_VISIBLE thread_exception:
public system::system_error
Copied: branches/release/boost/thread/externally_locked.hpp (from r81093, /trunk/boost/thread/externally_locked.hpp)
==============================================================================
--- /trunk/boost/thread/externally_locked.hpp (original)
+++ branches/release/boost/thread/externally_locked.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -87,19 +87,13 @@
*/
T& get(strict_lock<mutex_type>& lk)
{
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return obj_;
}
const T& get(strict_lock<mutex_type>& lk) const
{
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return obj_;
}
@@ -107,10 +101,7 @@
T& get(nested_strict_lock<Lock>& lk)
{
BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return obj_;
}
@@ -118,10 +109,7 @@
const T& get(nested_strict_lock<Lock>& lk) const
{
BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return obj_;
}
@@ -138,12 +126,9 @@
BOOST_STATIC_ASSERT( (is_strict_lock<Lock>::value)); /*< lk is a strict lock "sur parolle" >*/
BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_OWNERSHIP /*< define BOOST_THREAD_EXTERNALLY_LOCKED_NO_CHECK_OWNERSHIP if you don't want to check lock ownership >*/
- if (!lk.own_lock()) throw lock_error(); /*< run time check throw if no locked >*/
-#endif
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME
- if (lk.mutex()!=mtx_) throw lock_error();
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(), lock_error() ); /*< run time check throw if no locked >*/
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
+
return obj_;
}
@@ -220,43 +205,31 @@
*
* Throws: lock_error if BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME is not defined and the lk parameter doesn't satisfy the preconditions
*/
- T& get(strict_lock<mutex_type>& lk)
+ T& get(strict_lock<mutex_type> const& lk)
{
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return *obj_;
}
- const T& get(strict_lock<mutex_type>& lk) const
+ const T& get(strict_lock<mutex_type> const& lk) const
{
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return *obj_;
}
template <class Lock>
- T& get(nested_strict_lock<Lock>& lk)
+ T& get(nested_strict_lock<Lock> const& lk)
{
BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (lk.mutex()!=mtx_) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return *obj_;
}
template <class Lock>
- const T& get(nested_strict_lock<Lock>& lk) const
+ const T& get(nested_strict_lock<Lock> const& lk) const
{
BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME /*< define BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME if you don't want to check lk check the same mtx >*/
- if (!lk.is_locking(&mtx_)) throw lock_error(); /*< run time check throw if not locks the same >*/
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return *obj_;
}
@@ -267,21 +240,32 @@
* Throws: lock_error if BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME is not defined and the lk parameter doesn't satisfy the preconditions
*/
template <class Lock>
- T& get(Lock& lk)
+ T& get(Lock const& lk)
{
BOOST_CONCEPT_ASSERT(( StrictLock<Lock> ));
BOOST_STATIC_ASSERT( (is_strict_lock<Lock>::value)); /*< lk is a strict lock "sur parolle" >*/
BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
-
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_OWNERSHIP /*< define BOOST_THREAD_EXTERNALLY_LOCKED_NO_CHECK_OWNERSHIP if you don't want to check lock ownership >*/
- if (!lk.own_lock()) throw lock_error(); /*< run time check throw if no locked >*/
-#endif
-#ifndef BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME
- if (lk.mutex()!=mtx_) throw lock_error();
-#endif
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(), lock_error() ); /*< run time check throw if no locked >*/
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
return *obj_;
}
+ /**
+ * Requires: The lk parameter must be locking the associated mtx.
+ * Returns: The address of the cloaked object..
+ *
+ * Throws: lock_error if BOOST_THREAD_EXTERNALLY_LOCKED_DONT_CHECK_SAME is not defined and the lk parameter doesn't satisfy the preconditions
+ */
+ template <class Lock>
+ T const& get(Lock const& lk) const
+ {
+ BOOST_CONCEPT_ASSERT(( StrictLock<Lock> ));
+ BOOST_STATIC_ASSERT( (is_strict_lock<Lock>::value)); /*< lk is a strict lock "sur parolle" >*/
+ BOOST_STATIC_ASSERT( (is_same<mutex_type, typename Lock::mutex_type>::value)); /*< that locks the same type >*/
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(), lock_error() ); /*< run time check throw if no locked >*/
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.owns_lock(mtx_), lock_error() ); /*< run time check throw if not locks the same >*/
+ return *obj_;
+ }
mutex_type* mutex()
{
return mtx_;
Modified: branches/release/boost/thread/future.hpp
==============================================================================
--- branches/release/boost/thread/future.hpp (original)
+++ branches/release/boost/thread/future.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,14 +18,17 @@
#include <boost/detail/scoped_enum_emulation.hpp>
#include <stdexcept>
#include <boost/thread/detail/move.hpp>
+#include <boost/thread/detail/async_func.hpp>
#include <boost/thread/thread_time.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/condition_variable.hpp>
+#include <boost/thread/lock_algorithms.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/exception_ptr.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/scoped_ptr.hpp>
#include <boost/type_traits/is_fundamental.hpp>
-#include <boost/type_traits/is_convertible.hpp>
+#include <boost/thread/detail/is_convertible.hpp>
#include <boost/type_traits/remove_reference.hpp>
#include <boost/type_traits/remove_cv.hpp>
#include <boost/mpl/if.hpp>
@@ -36,10 +39,12 @@
#include <boost/bind.hpp>
#include <boost/ref.hpp>
#include <boost/scoped_array.hpp>
+#include <boost/enable_shared_from_this.hpp>
#include <boost/utility/enable_if.hpp>
#include <list>
#include <boost/next_prior.hpp>
#include <vector>
+
#include <boost/system/error_code.hpp>
#ifdef BOOST_THREAD_USES_CHRONO
#include <boost/chrono/system_clocks.hpp>
@@ -58,14 +63,14 @@
#define BOOST_THREAD_FUTURE unique_future
#endif
-
namespace boost
{
+
//enum class future_errc
BOOST_SCOPED_ENUM_DECLARE_BEGIN(future_errc)
{
- broken_promise,
+ broken_promise = 1,
future_already_retrieved,
promise_already_satisfied,
no_state
@@ -205,29 +210,92 @@
namespace future_state
{
- enum state { uninitialized, waiting, ready, moved };
+ enum state { uninitialized, waiting, ready, moved, deferred };
}
namespace detail
{
- struct future_object_base
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ struct future_continuation_base
+ {
+ future_continuation_base() {}
+ virtual ~future_continuation_base() {}
+
+ virtual void do_continuation(boost::unique_lock<boost::mutex>& ) {};
+ private:
+ future_continuation_base(future_continuation_base const&);
+ future_continuation_base& operator=(future_continuation_base const&);
+ };
+
+ template <typename F, typename R, typename C>
+ struct future_continuation;
+
+#endif
+
+ struct relocker
+ {
+ boost::unique_lock<boost::mutex>& lock_;
+ bool unlocked_;
+
+ relocker(boost::unique_lock<boost::mutex>& lk):
+ lock_(lk)
+ {
+ lock_.unlock();
+ unlocked_=true;
+ }
+ ~relocker()
+ {
+ if (unlocked_) {
+ lock_.lock();
+ }
+ }
+ void lock() {
+ if (unlocked_) {
+ lock_.lock();
+ unlocked_=false;
+ }
+ }
+ private:
+ relocker& operator=(relocker const&);
+ };
+
+ struct future_object_base : enable_shared_from_this<future_object_base>
{
+
boost::exception_ptr exception;
bool done;
+ bool is_deferred_;
+ launch policy_;
+ bool is_constructed;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
bool thread_was_interrupted;
+#endif
boost::mutex mutex;
boost::condition_variable waiters;
typedef std::list<boost::condition_variable_any*> waiter_list;
waiter_list external_waiters;
boost::function<void()> callback;
-
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ shared_ptr<future_continuation_base> continuation_ptr;
+#endif
future_object_base():
done(false),
- thread_was_interrupted(false)
+ is_deferred_(false),
+ policy_(launch::any),
+ is_constructed(false)
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ , thread_was_interrupted(false)
+#endif
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ , continuation_ptr()
+#endif
{}
virtual ~future_object_base()
{}
+ void set_deferred() {is_deferred_ = true;}
+ void set_launch_policy(launch policy) {policy_ = policy;}
+
waiter_list::iterator register_external_waiter(boost::condition_variable_any& cv)
{
boost::unique_lock<boost::mutex> lock(mutex);
@@ -241,7 +309,28 @@
external_waiters.erase(it);
}
- void mark_finished_internal()
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ void do_continuation(boost::unique_lock<boost::mutex>& lock)
+ {
+ if (continuation_ptr) {
+ continuation_ptr->do_continuation(lock);
+ }
+ }
+#else
+ void do_continuation(boost::unique_lock<boost::mutex>&)
+ {
+ }
+#endif
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ void set_continuation_ptr(future_continuation_base* continuation, boost::unique_lock<boost::mutex>& lock)
+ {
+ continuation_ptr.reset(continuation);
+ if (done) {
+ do_continuation(lock);
+ }
+ }
+#endif
+ void mark_finished_internal(boost::unique_lock<boost::mutex>& lock)
{
done=true;
waiters.notify_all();
@@ -250,24 +339,13 @@
{
(*it)->notify_all();
}
+ do_continuation(lock);
}
-
- struct relocker
+ void make_ready()
{
- boost::unique_lock<boost::mutex>& lock;
-
- relocker(boost::unique_lock<boost::mutex>& lock_):
- lock(lock_)
- {
- lock.unlock();
- }
- ~relocker()
- {
- lock.lock();
- }
- private:
- relocker& operator=(relocker const&);
- };
+ boost::unique_lock<boost::mutex> lock(mutex);
+ mark_finished_internal(lock);
+ }
void do_callback(boost::unique_lock<boost::mutex>& lock)
{
@@ -280,27 +358,49 @@
}
- void wait(bool rethrow=true)
+ void wait_internal(boost::unique_lock<boost::mutex> &lock, bool rethrow=true)
{
- boost::unique_lock<boost::mutex> lock(mutex);
- do_callback(lock);
- while(!done)
- {
- waiters.wait(lock);
- }
- if(rethrow && thread_was_interrupted)
+ do_callback(lock);
+ //if (!done) // fixme why this doesn't works?
+ {
+ if (is_deferred_)
{
- throw boost::thread_interrupted();
+ is_deferred_=false;
+ execute(lock);
+ //lock.unlock();
}
- if(rethrow && exception)
+ else
{
- boost::rethrow_exception(exception);
+ while(!done)
+ {
+ waiters.wait(lock);
+ }
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ if(rethrow && thread_was_interrupted)
+ {
+ throw boost::thread_interrupted();
+ }
+#endif
+ if(rethrow && exception)
+ {
+ boost::rethrow_exception(exception);
+ }
}
+ }
+ }
+ void wait(bool rethrow=true)
+ {
+ boost::unique_lock<boost::mutex> lock(mutex);
+ wait_internal(lock, rethrow);
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_wait_until(boost::system_time const& target_time)
{
boost::unique_lock<boost::mutex> lock(mutex);
+ if (is_deferred_)
+ return false;
+
do_callback(lock);
while(!done)
{
@@ -312,7 +412,7 @@
}
return true;
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Clock, class Duration>
@@ -320,6 +420,8 @@
wait_until(const chrono::time_point<Clock, Duration>& abs_time)
{
boost::unique_lock<boost::mutex> lock(mutex);
+ if (is_deferred_)
+ return future_status::deferred;
do_callback(lock);
while(!done)
{
@@ -332,31 +434,83 @@
return future_status::ready;
}
#endif
- void mark_exceptional_finish_internal(boost::exception_ptr const& e)
+ void mark_exceptional_finish_internal(boost::exception_ptr const& e, boost::unique_lock<boost::mutex>& lock)
{
exception=e;
- mark_finished_internal();
+ mark_finished_internal(lock);
}
void mark_exceptional_finish()
{
- boost::lock_guard<boost::mutex> lock(mutex);
- mark_exceptional_finish_internal(boost::current_exception());
+ boost::unique_lock<boost::mutex> lock(mutex);
+ mark_exceptional_finish_internal(boost::current_exception(), lock);
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void mark_interrupted_finish()
{
- boost::lock_guard<boost::mutex> lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
thread_was_interrupted=true;
- mark_finished_internal();
+ mark_finished_internal(lock);
+ }
+ void set_interrupted_at_thread_exit()
+ {
+ unique_lock<boost::mutex> lk(mutex);
+ thread_was_interrupted=true;
+ if (has_value(lk))
+ {
+ throw_exception(promise_already_satisfied());
+ }
+ get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
+ }
+#endif
+ void set_exception_at_thread_exit(exception_ptr e)
+ {
+ unique_lock<boost::mutex> lk(mutex);
+ if (has_value(lk))
+ {
+ throw_exception(promise_already_satisfied());
+ }
+ exception=e;
+ get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
}
bool has_value()
{
boost::lock_guard<boost::mutex> lock(mutex);
- return done && !(exception || thread_was_interrupted);
+ return done && !(exception
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ || thread_was_interrupted
+#endif
+ );
+ }
+ bool has_value(unique_lock<boost::mutex>& )
+ {
+ return done && !(exception
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ || thread_was_interrupted
+#endif
+ );
}
bool has_exception()
{
boost::lock_guard<boost::mutex> lock(mutex);
- return done && (exception || thread_was_interrupted);
+ return done && (exception
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ || thread_was_interrupted
+#endif
+ );
+ }
+ bool has_exception(unique_lock<boost::mutex>&)
+ {
+ return done && (exception
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ || thread_was_interrupted
+#endif
+ );
+ }
+ void is_deferred() {is_deferred_ = true;}
+
+ launch launch_policy() const BOOST_NOEXCEPT
+ {
+ return policy_;
}
template<typename F,typename U>
@@ -364,6 +518,7 @@
{
callback=boost::bind(f,boost::ref(*u));
}
+ virtual void execute(boost::unique_lock<boost::mutex>&) {}
private:
future_object_base(future_object_base const&);
@@ -385,8 +540,8 @@
typedef typename boost::mpl::if_<boost::has_move_emulation_enabled<T>,BOOST_THREAD_RV_REF(T),T>::type move_dest_type;
#else
typedef T& source_reference_type;
- typedef typename boost::mpl::if_<boost::is_convertible<T&,BOOST_THREAD_RV_REF(T) >,BOOST_THREAD_RV_REF(T),T const&>::type rvalue_source_type;
- typedef typename boost::mpl::if_<boost::is_convertible<T&,BOOST_THREAD_RV_REF(T) >,BOOST_THREAD_RV_REF(T),T>::type move_dest_type;
+ typedef typename boost::mpl::if_<boost::thread_detail::is_convertible<T&,BOOST_THREAD_RV_REF(T) >,BOOST_THREAD_RV_REF(T),T const&>::type rvalue_source_type;
+ typedef typename boost::mpl::if_<boost::thread_detail::is_convertible<T&,BOOST_THREAD_RV_REF(T) >,BOOST_THREAD_RV_REF(T),T>::type move_dest_type;
#endif
typedef const T& shared_future_get_result_type;
@@ -447,6 +602,7 @@
};
+ // Used to create stand-alone futures
template<typename T>
struct future_object:
detail::future_object_base
@@ -463,30 +619,35 @@
result(0)
{}
- void mark_finished_with_result_internal(source_reference_type result_)
+ ~future_object()
+ {
+ }
+
+ void mark_finished_with_result_internal(source_reference_type result_, boost::unique_lock<boost::mutex>& lock)
{
future_traits<T>::init(result,result_);
- mark_finished_internal();
+ mark_finished_internal(lock);
}
- void mark_finished_with_result_internal(rvalue_source_type result_)
+ void mark_finished_with_result_internal(rvalue_source_type result_, boost::unique_lock<boost::mutex>& lock)
{
future_traits<T>::init(result,static_cast<rvalue_source_type>(result_));
- mark_finished_internal();
+ mark_finished_internal(lock);
}
void mark_finished_with_result(source_reference_type result_)
{
- boost::lock_guard<boost::mutex> lock(mutex);
- mark_finished_with_result_internal(result_);
+ boost::unique_lock<boost::mutex> lock(mutex);
+ mark_finished_with_result_internal(result_, lock);
}
void mark_finished_with_result(rvalue_source_type result_)
{
- boost::lock_guard<boost::mutex> lock(mutex);
- mark_finished_with_result_internal(static_cast<rvalue_source_type>(result_));
+ boost::unique_lock<boost::mutex> lock(mutex);
+ mark_finished_with_result_internal(static_cast<rvalue_source_type>(result_), lock);
}
+
move_dest_type get()
{
wait();
@@ -499,6 +660,110 @@
return static_cast<shared_future_get_result_type>(*result);
}
+ // todo move this to detail::future_object_base
+ future_state::state get_state()
+ {
+ boost::lock_guard<boost::mutex> guard(mutex);
+ if(!done)
+ {
+ return future_state::waiting;
+ }
+ else
+ {
+ return future_state::ready;
+ }
+ }
+
+
+ void set_value_at_thread_exit(const T & result_)
+ {
+ unique_lock<boost::mutex> lk(this->mutex);
+ if (this->has_value(lk))
+ {
+ throw_exception(promise_already_satisfied());
+ }
+ future_traits<T>::init(result,result_);
+ this->is_constructed = true;
+ get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
+ }
+ void set_value_at_thread_exit(BOOST_THREAD_RV_REF(T) result_)
+ {
+ unique_lock<boost::mutex> lk(this->mutex);
+ if (this->has_value(lk))
+ throw_exception(promise_already_satisfied());
+ result.reset(new T(boost::move(result_)));
+ //future_traits<T>::init(result,static_cast<rvalue_source_type>(result_));
+ this->is_constructed = true;
+ get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
+ }
+
+
+ private:
+ future_object(future_object const&);
+ future_object& operator=(future_object const&);
+ };
+
+ template<typename T>
+ struct future_object<T&>:
+ detail::future_object_base
+ {
+ typedef typename future_traits<T>::storage_type storage_type;
+ typedef typename future_traits<T>::source_reference_type source_reference_type;
+ typedef typename future_traits<T>::rvalue_source_type rvalue_source_type;
+ typedef typename future_traits<T>::move_dest_type move_dest_type;
+ typedef typename future_traits<T>::shared_future_get_result_type shared_future_get_result_type;
+
+ T* result;
+
+ future_object():
+ result(0)
+ {}
+
+ ~future_object()
+ {
+ }
+
+ void mark_finished_with_result_internal(T& result_, boost::unique_lock<boost::mutex>& lock)
+ {
+ //future_traits<T>::init(result,result_);
+ result= &result_;
+ mark_finished_internal(lock);
+ }
+
+// void mark_finished_with_result_internal(rvalue_source_type result_, boost::unique_lock<boost::mutex>& lock)
+// {
+// future_traits<T>::init(result,static_cast<rvalue_source_type>(result_));
+// mark_finished_internal(lock);
+// }
+
+ void mark_finished_with_result(T& result_)
+ {
+ boost::unique_lock<boost::mutex> lock(mutex);
+ mark_finished_with_result_internal(result_, lock);
+ }
+
+// void mark_finished_with_result(rvalue_source_type result_)
+// {
+// boost::unique_lock<boost::mutex> lock(mutex);
+// mark_finished_with_result_internal(static_cast<rvalue_source_type>(result_), lock);
+// }
+
+
+ T& get()
+ {
+ wait();
+ //return static_cast<T&>(*result);
+ return *result;
+ }
+
+ T& get_sh()
+ {
+ wait();
+ //return static_cast<shared_future_get_result_type>(*result);
+ return *result;
+ }
+
+ // todo move this to detail::future_object_base
future_state::state get_state()
{
boost::lock_guard<boost::mutex> guard(mutex);
@@ -512,6 +777,27 @@
}
}
+ void set_value_at_thread_exit(T& result_)
+ {
+ unique_lock<boost::mutex> lk(this->mutex);
+ if (this->has_value(lk))
+ throw_exception(promise_already_satisfied());
+ //future_traits<T>::init(result,result_);
+ result= &result_;
+ this->is_constructed = true;
+ get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
+ }
+// void set_value_at_thread_exit(rvalue_source_type result_)
+// {
+// unique_lock<boost::mutex> lk(this->mutex);
+// if (this->has_value())
+// throw_exception(promise_already_satisfied());
+// future_traits<T>::init(result,static_cast<rvalue_source_type>(result_));
+// this->is_constructed = true;
+// get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
+// }
+
+
private:
future_object(future_object const&);
future_object& operator=(future_object const&);
@@ -526,25 +812,26 @@
future_object()
{}
- void mark_finished_with_result_internal()
+ void mark_finished_with_result_internal(boost::unique_lock<boost::mutex>& lock)
{
- mark_finished_internal();
+ mark_finished_internal(lock);
}
void mark_finished_with_result()
{
- boost::lock_guard<boost::mutex> lock(mutex);
- mark_finished_with_result_internal();
+ boost::unique_lock<boost::mutex> lock(mutex);
+ mark_finished_with_result_internal(lock);
}
void get()
{
- wait();
+ this->wait();
}
void get_sh()
{
wait();
}
+ // todo move this to detail::future_object_base
future_state::state get_state()
{
boost::lock_guard<boost::mutex> guard(mutex);
@@ -557,11 +844,176 @@
return future_state::ready;
}
}
+ void set_value_at_thread_exit()
+ {
+ unique_lock<boost::mutex> lk(this->mutex);
+ if (this->has_value(lk))
+ {
+ throw_exception(promise_already_satisfied());
+ }
+ this->is_constructed = true;
+ get_current_thread_data()->make_ready_at_thread_exit(shared_from_this());
+ }
private:
future_object(future_object const&);
future_object& operator=(future_object const&);
};
+ /// future_async_object
+ template<typename Rp, typename Fp>
+ struct future_async_object: future_object<Rp>
+ {
+ typedef future_object<Rp> base_type;
+ boost::thread thr_;
+
+ public:
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ explicit future_async_object(Fp&& f)
+ :
+ #else
+ explicit future_async_object(BOOST_THREAD_FWD_REF(Fp) f)
+ :
+ #endif
+ thr_(&future_async_object::run, this, boost::forward<Fp>(f))
+ {
+ }
+
+ ~future_async_object()
+ {
+ thr_.join();
+ }
+
+#if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ static void run(future_async_object* that, Fp&& f)
+#else
+ static void run(future_async_object* that, BOOST_THREAD_FWD_REF(Fp) f)
+#endif
+ {
+ try
+ {
+ that->mark_finished_with_result(f());
+ }
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ catch(thread_interrupted& )
+ {
+ that->mark_interrupted_finish();
+ }
+#endif
+ catch(...)
+ {
+ that->mark_exceptional_finish();
+ }
+ }
+ };
+
+ template<typename Fp>
+ struct future_async_object<void, Fp>: public future_object<void>
+ {
+ typedef future_object<void> base_type;
+ boost::thread thr_;
+
+ public:
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ explicit future_async_object(Fp&& f)
+ :
+ #else
+ explicit future_async_object(BOOST_THREAD_FWD_REF(Fp) f)
+ :
+ #endif
+ thr_(&future_async_object::run, this, boost::forward<Fp>(f))
+ {
+ }
+
+ ~future_async_object()
+ {
+ thr_.join();
+ }
+
+#if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ static void run(future_async_object* that, Fp&& f)
+#else
+ static void run(future_async_object* that, BOOST_THREAD_FWD_REF(Fp) f)
+#endif
+ {
+ try
+ {
+ f();
+ that->mark_finished_with_result();
+ }
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ catch(thread_interrupted& )
+ {
+ that->mark_interrupted_finish();
+ }
+#endif
+ catch(...)
+ {
+ that->mark_exceptional_finish();
+ }
+ }
+ };
+ /// future_deferred_object
+ template<typename Rp, typename Fp>
+ struct future_deferred_object: future_object<Rp>
+ {
+ typedef future_object<Rp> base_type;
+ Fp func_;
+
+ public:
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ explicit future_deferred_object(Fp&& f)
+ : func_(boost::forward<Fp>(f))
+ #else
+ explicit future_deferred_object(Fp f)
+ : func_(f)
+ #endif
+ {
+ this->set_deferred();
+ }
+
+ virtual void execute(boost::unique_lock<boost::mutex>& lck) {
+ try
+ {
+ this->mark_finished_with_result_internal(func_(), lck);
+ }
+ catch (...)
+ {
+ this->mark_exceptional_finish_internal(current_exception(), lck);
+ }
+ }
+ };
+
+ template<typename Fp>
+ struct future_deferred_object<void,Fp>: future_object<void>
+ {
+ typedef future_object<void> base_type;
+ Fp func_;
+
+ public:
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ explicit future_deferred_object(Fp&& f)
+ : func_(boost::forward<Fp>(f))
+ #else
+ explicit future_deferred_object(Fp f)
+ : func_(f)
+ #endif
+ {
+ this->set_deferred();
+ }
+
+ virtual void execute(boost::unique_lock<boost::mutex>& lck) {
+ try
+ {
+ func_();
+ this->mark_finished_with_result_internal(lck);
+ }
+ catch (...)
+ {
+ this->mark_exceptional_finish_internal(current_exception(), lck);
+ }
+ }
+ };
+
// template<typename T, typename Allocator>
// struct future_object_alloc: public future_object<T>
// {
@@ -589,18 +1041,17 @@
count_type index_):
future_(a_future),wait_iterator(wait_iterator_),index(index_)
{}
-
};
struct all_futures_lock
{
#ifdef _MANAGED
- typedef std::ptrdiff_t count_type_portable;
+ typedef std::ptrdiff_t count_type_portable;
#else
- typedef count_type count_type_portable;
+ typedef count_type count_type_portable;
#endif
- count_type_portable count;
- boost::scoped_array<boost::unique_lock<boost::mutex> > locks;
+ 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])
@@ -610,7 +1061,7 @@
#if defined __DECCXX || defined __SUNPRO_CC || defined __hpux
locks[i]=boost::unique_lock<boost::mutex>(futures[i].future_->mutex).move();
#else
- locks[i]=boost::unique_lock<boost::mutex>(futures[i].future_->mutex);
+ locks[i]=boost::unique_lock<boost::mutex>(futures[i].future_->mutex); // TODO shouldn't be moved explicitly
#endif
}
}
@@ -805,70 +1256,53 @@
template <typename R>
class packaged_task;
- template <typename R>
- class BOOST_THREAD_FUTURE
+ namespace detail
{
- private:
+ /// Common implementation for all the futures independently of the return type
+ class base_future
+ {
+ //BOOST_THREAD_MOVABLE(base_future)
+
+ };
+ /// Common implementation for future and shared_future.
+ template <typename R>
+ class basic_future : public base_future
+ {
+ protected:
typedef boost::shared_ptr<detail::future_object<R> > future_ptr;
future_ptr future_;
- friend class shared_future<R>;
- friend class promise<R>;
- friend class packaged_task<R>;
- friend class detail::future_waiter;
-
- typedef typename detail::future_traits<R>::move_dest_type move_dest_type;
-
- BOOST_THREAD_FUTURE(future_ptr a_future):
- future_(a_future)
- {}
+ basic_future(future_ptr a_future):
+ future_(a_future)
+ {
+ }
+ // Copy construction from a shared_future
+ explicit basic_future(const shared_future<R>&) BOOST_NOEXCEPT;
- public:
- BOOST_THREAD_MOVABLE_ONLY(BOOST_THREAD_FUTURE)
+ public:
typedef future_state::state state;
- BOOST_THREAD_FUTURE()
- {}
-
- ~BOOST_THREAD_FUTURE()
- {}
+ BOOST_THREAD_MOVABLE(basic_future)
+ basic_future(): future_() {}
+ ~basic_future() {}
- BOOST_THREAD_FUTURE(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE) other) BOOST_NOEXCEPT:
- future_(BOOST_THREAD_RV(other).future_)
+ basic_future(BOOST_THREAD_RV_REF(basic_future) other) BOOST_NOEXCEPT:
+ future_(BOOST_THREAD_RV(other).future_)
{
BOOST_THREAD_RV(other).future_.reset();
}
-
- BOOST_THREAD_FUTURE& operator=(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE) other) BOOST_NOEXCEPT
+ basic_future& operator=(BOOST_THREAD_RV_REF(basic_future) other) BOOST_NOEXCEPT
{
future_=BOOST_THREAD_RV(other).future_;
BOOST_THREAD_RV(other).future_.reset();
return *this;
}
-
- shared_future<R> share()
- {
- return shared_future<R>(::boost::move(*this));
- }
-
- void swap(BOOST_THREAD_FUTURE& other)
- {
- future_.swap(other.future_);
- }
-
- // retrieving the value
- move_dest_type get()
+ void swap(basic_future& that) BOOST_NOEXCEPT
{
- if(!future_)
- {
- boost::throw_exception(future_uninitialized());
- }
-
- return future_->get();
+ future_.swap(that.future_);
}
-
// functions to check state, and wait for ready
state get_state() const BOOST_NOEXCEPT
{
@@ -894,6 +1328,12 @@
return future_ && future_->has_value();
}
+ launch launch_policy() const BOOST_NOEXCEPT
+ {
+ if ( future_ ) return future_->launch_policy();
+ else return launch(launch::any);
+ }
+
bool valid() const BOOST_NOEXCEPT
{
return future_ != 0;
@@ -909,6 +1349,7 @@
future_->wait(false);
}
+#if defined BOOST_THREAD_USES_DATETIME
template<typename Duration>
bool timed_wait(Duration const& rel_time) const
{
@@ -923,6 +1364,7 @@
}
return future_->timed_wait_until(abs_time);
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
future_status
@@ -942,30 +1384,166 @@
return future_->wait_until(abs_time);
}
#endif
+
+ };
+
+ } // detail
+ BOOST_THREAD_DCL_MOVABLE_BEG(R) detail::basic_future<R> BOOST_THREAD_DCL_MOVABLE_END
+
+ namespace detail
+ {
+ template <class Rp, class Fp>
+ BOOST_THREAD_FUTURE<Rp>
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ make_future_async_object(Fp&& f);
+ #else
+ make_future_async_object(BOOST_THREAD_FWD_REF(Fp) f);
+ #endif
+
+ template <class Rp, class Fp>
+ BOOST_THREAD_FUTURE<Rp>
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ make_future_deferred_object(Fp&& f);
+ #else
+ make_future_deferred_object(BOOST_THREAD_FWD_REF(Fp) f);
+ #endif
+ }
+
+ template <typename R>
+ class BOOST_THREAD_FUTURE : public detail::basic_future<R>
+ {
+ private:
+ typedef detail::basic_future<R> base_type;
+ typedef typename base_type::future_ptr future_ptr;
+
+ friend class shared_future<R>;
+ friend class promise<R>;
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ template <typename, typename, typename>
+ friend struct detail::future_continuation;
+#endif
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ template <class> friend class packaged_task; // todo check if this works in windows
+#else
+ friend class packaged_task<R>;
+#endif
+ friend class detail::future_waiter;
+
+ template <class Rp, class Fp>
+ friend BOOST_THREAD_FUTURE<Rp>
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ detail::make_future_async_object(Fp&& f);
+ #else
+ detail::make_future_async_object(BOOST_THREAD_FWD_REF(Fp) f);
+ #endif
+
+ template <class Rp, class Fp>
+ friend BOOST_THREAD_FUTURE<Rp>
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ detail::make_future_deferred_object(Fp&& f);
+ #else
+ detail::make_future_deferred_object(BOOST_THREAD_FWD_REF(Fp) f);
+ #endif
+
+ typedef typename detail::future_traits<R>::move_dest_type move_dest_type;
+
+ BOOST_THREAD_FUTURE(future_ptr a_future):
+ base_type(a_future)
+ {
+ }
+
+ public:
+ BOOST_THREAD_MOVABLE_ONLY(BOOST_THREAD_FUTURE)
+ typedef future_state::state state;
+
+ BOOST_THREAD_FUTURE() {}
+
+ ~BOOST_THREAD_FUTURE() {}
+
+ BOOST_THREAD_FUTURE(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE) other) BOOST_NOEXCEPT:
+ base_type(boost::move(static_cast<base_type&>(BOOST_THREAD_RV(other))))
+ {
+ }
+
+ BOOST_THREAD_FUTURE& operator=(BOOST_THREAD_RV_REF(BOOST_THREAD_FUTURE) other) BOOST_NOEXCEPT
+ {
+ base_type::operator=(boost::move(static_cast<base_type&>(BOOST_THREAD_RV(other))));
+ return *this;
+ }
+
+ shared_future<R> share()
+ {
+ return shared_future<R>(::boost::move(*this));
+ }
+
+ void swap(BOOST_THREAD_FUTURE& other)
+ {
+ static_cast<base_type*>(this)->swap(other);
+ }
+
+ // retrieving the value
+ move_dest_type get()
+ {
+ if(!this->future_)
+ {
+ boost::throw_exception(future_uninitialized());
+ }
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
+ future_ptr fut_=this->future_;
+ this->future_.reset();
+ return fut_->get();
+#else
+ return this->future_->get();
+#endif
+ }
+
+
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+
+// template<typename F>
+// auto then(F&& func) -> BOOST_THREAD_FUTURE<decltype(func(*this))>;
+
+#if defined(BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR)
+ template<typename RF>
+ inline BOOST_THREAD_FUTURE<RF> then(RF(*func)(BOOST_THREAD_FUTURE&));
+ template<typename RF>
+ inline BOOST_THREAD_FUTURE<RF> then(launch policy, RF(*func)(BOOST_THREAD_FUTURE&));
+#endif
+ template<typename F>
+ inline BOOST_THREAD_FUTURE<typename boost::result_of<F(BOOST_THREAD_FUTURE&)>::type>
+ then(BOOST_THREAD_RV_REF(F) func);
+ template<typename F>
+ inline BOOST_THREAD_FUTURE<typename boost::result_of<F(BOOST_THREAD_FUTURE&)>::type>
+ then(launch policy, BOOST_THREAD_RV_REF(F) func);
+#endif
};
BOOST_THREAD_DCL_MOVABLE_BEG(T) BOOST_THREAD_FUTURE<T> BOOST_THREAD_DCL_MOVABLE_END
template <typename R>
- class shared_future
+ class shared_future : public detail::basic_future<R>
{
- typedef boost::shared_ptr<detail::future_object<R> > future_ptr;
- future_ptr future_;
+ typedef detail::basic_future<R> base_type;
+ typedef typename base_type::future_ptr future_ptr;
friend class detail::future_waiter;
friend class promise<R>;
- friend class packaged_task<R>;
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ template <class> friend class packaged_task;// todo check if this works in windows
+#else
+ friend class packaged_task<R>;
+#endif
shared_future(future_ptr a_future):
- future_(a_future)
+ base_type(a_future)
{}
public:
BOOST_THREAD_MOVABLE(shared_future)
shared_future(shared_future const& other):
- future_(other.future_)
+ base_type(other)
{}
typedef future_state::state state;
@@ -978,125 +1556,63 @@
shared_future& operator=(shared_future const& other)
{
- future_=other.future_;
+ shared_future(other).swap(*this);
return *this;
}
shared_future(BOOST_THREAD_RV_REF(shared_future) other) BOOST_NOEXCEPT :
- future_(BOOST_THREAD_RV(other).future_)
+ base_type(boost::move(static_cast<base_type&>(BOOST_THREAD_RV(other))))
{
BOOST_THREAD_RV(other).future_.reset();
}
- shared_future(BOOST_THREAD_RV_REF_BEG BOOST_THREAD_FUTURE<R> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT :
- future_(BOOST_THREAD_RV(other).future_)
+ shared_future(BOOST_THREAD_RV_REF( BOOST_THREAD_FUTURE<R> ) other) BOOST_NOEXCEPT :
+ base_type(boost::move(static_cast<base_type&>(BOOST_THREAD_RV(other))))
{
- BOOST_THREAD_RV(other).future_.reset();
}
+
shared_future& operator=(BOOST_THREAD_RV_REF(shared_future) other) BOOST_NOEXCEPT
{
- future_.swap(BOOST_THREAD_RV(other).future_);
- BOOST_THREAD_RV(other).future_.reset();
+ base_type::operator=(boost::move(static_cast<base_type&>(BOOST_THREAD_RV(other))));
return *this;
}
- shared_future& operator=(BOOST_THREAD_RV_REF_BEG BOOST_THREAD_FUTURE<R> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT
+ shared_future& operator=(BOOST_THREAD_RV_REF( BOOST_THREAD_FUTURE<R> ) other) BOOST_NOEXCEPT
{
- future_.swap(BOOST_THREAD_RV(other).future_);
- BOOST_THREAD_RV(other).future_.reset();
+ base_type::operator=(boost::move(static_cast<base_type&>(BOOST_THREAD_RV(other))));
+ //shared_future(boost::move(other)).swap(*this);
+ //this->future_.swap(BOOST_THREAD_RV(other).future_);
+ //BOOST_THREAD_RV(other).future_.reset();
return *this;
}
void swap(shared_future& other) BOOST_NOEXCEPT
{
- future_.swap(other.future_);
+ static_cast<base_type*>(this)->swap(other);
}
// retrieving the value
typename detail::future_object<R>::shared_future_get_result_type get()
{
- if(!future_)
- {
- boost::throw_exception(future_uninitialized());
- }
-
- return future_->get_sh();
- }
-
- // functions to check state, and wait for ready
- state get_state() const BOOST_NOEXCEPT
- {
- if(!future_)
- {
- return future_state::uninitialized;
- }
- return future_->get_state();
- }
-
- bool valid() const BOOST_NOEXCEPT
- {
- return future_ != 0;
- }
-
- bool is_ready() const BOOST_NOEXCEPT
- {
- return get_state()==future_state::ready;
- }
-
- bool has_exception() const BOOST_NOEXCEPT
- {
- return future_ && future_->has_exception();
- }
-
- bool has_value() const BOOST_NOEXCEPT
- {
- return future_ && future_->has_value();
- }
-
- void wait() const
- {
- if(!future_)
+ if(!this->future_)
{
boost::throw_exception(future_uninitialized());
}
- future_->wait(false);
- }
-
- template<typename Duration>
- bool timed_wait(Duration const& rel_time) const
- {
- return timed_wait_until(boost::get_system_time()+rel_time);
- }
- bool timed_wait_until(boost::system_time const& abs_time) const
- {
- if(!future_)
- {
- boost::throw_exception(future_uninitialized());
- }
- return future_->timed_wait_until(abs_time);
+ return this->future_->get_sh();
}
-#ifdef BOOST_THREAD_USES_CHRONO
-
- template <class Rep, class Period>
- future_status
- wait_for(const chrono::duration<Rep, Period>& rel_time) const
- {
- return wait_until(chrono::steady_clock::now() + rel_time);
- }
- template <class Clock, class Duration>
- future_status
- wait_until(const chrono::time_point<Clock, Duration>& abs_time) const
- {
- if(!future_)
- {
- boost::throw_exception(future_uninitialized());
- }
- return future_->wait_until(abs_time);
- }
-#endif
};
BOOST_THREAD_DCL_MOVABLE_BEG(T) shared_future<T> BOOST_THREAD_DCL_MOVABLE_END
+ namespace detail
+ {
+ /// Copy construction from a shared_future
+ template <typename R>
+ inline basic_future<R>::basic_future(const shared_future<R>& other) BOOST_NOEXCEPT
+ : future_(other.future_)
+ {
+ }
+ }
+
template <typename R>
class promise
{
@@ -1107,7 +1623,7 @@
void lazy_init()
{
-#if defined BOOST_THREAD_PROMISE_LAZY
+#if defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
if(!atomic_load(&future_))
{
future_ptr blank;
@@ -1131,7 +1647,7 @@
}
#endif
promise():
-#if defined BOOST_THREAD_PROMISE_LAZY
+#if defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
future_(),
#else
future_(new detail::future_object<R>()),
@@ -1143,11 +1659,11 @@
{
if(future_)
{
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(!future_->done)
{
- future_->mark_exceptional_finish_internal(boost::copy_exception(broken_promise()));
+ future_->mark_exceptional_finish_internal(boost::copy_exception(broken_promise()), lock);
}
}
}
@@ -1193,41 +1709,63 @@
void set_value(typename detail::future_traits<R>::source_reference_type r)
{
lazy_init();
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(future_->done)
{
boost::throw_exception(promise_already_satisfied());
}
- future_->mark_finished_with_result_internal(r);
+ future_->mark_finished_with_result_internal(r, lock);
}
// void set_value(R && r);
void set_value(typename detail::future_traits<R>::rvalue_source_type r)
{
lazy_init();
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(future_->done)
{
boost::throw_exception(promise_already_satisfied());
}
- future_->mark_finished_with_result_internal(static_cast<typename detail::future_traits<R>::rvalue_source_type>(r));
+ future_->mark_finished_with_result_internal(static_cast<typename detail::future_traits<R>::rvalue_source_type>(r), lock);
}
void set_exception(boost::exception_ptr p)
{
lazy_init();
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(future_->done)
{
boost::throw_exception(promise_already_satisfied());
}
- future_->mark_exceptional_finish_internal(p);
+ future_->mark_exceptional_finish_internal(p, lock);
}
// setting the result with deferred notification
- //void set_value_at_thread_exit(const R& r); // NOT YET IMPLEMENTED
- //void set_value_at_thread_exit(see below); // NOT YET IMPLEMENTED
- //void set_exception_at_thread_exit(exception_ptr p); // NOT YET IMPLEMENTED
+ void set_value_at_thread_exit(const R& r)
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_value_at_thread_exit(r);
+ }
+
+ void set_value_at_thread_exit(BOOST_THREAD_RV_REF(R) r)
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_value_at_thread_exit(boost::move(r));
+ }
+ void set_exception_at_thread_exit(exception_ptr e)
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_exception_at_thread_exit(e);
+ }
template<typename F>
void set_wait_callback(F f)
@@ -1238,44 +1776,44 @@
};
- template <>
- class promise<void>
+ template <typename R>
+ class promise<R&>
{
- typedef boost::shared_ptr<detail::future_object<void> > future_ptr;
+ typedef boost::shared_ptr<detail::future_object<R&> > future_ptr;
future_ptr future_;
bool future_obtained;
void lazy_init()
{
-#if defined BOOST_THREAD_PROMISE_LAZY
+#if defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
if(!atomic_load(&future_))
{
future_ptr blank;
- atomic_compare_exchange(&future_,&blank,future_ptr(new detail::future_object<void>));
+ atomic_compare_exchange(&future_,&blank,future_ptr(new detail::future_object<R&>));
}
#endif
}
+
public:
BOOST_THREAD_MOVABLE_ONLY(promise)
-
#if defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
template <class Allocator>
promise(boost::allocator_arg_t, Allocator a)
{
- typedef typename Allocator::template rebind<detail::future_object<void> >::other A2;
+ typedef typename Allocator::template rebind<detail::future_object<R&> >::other A2;
A2 a2(a);
typedef thread_detail::allocator_destructor<A2> D;
- future_ = future_ptr(::new(a2.allocate(1)) detail::future_object<void>(), D(a2, 1) );
+ future_ = future_ptr(::new(a2.allocate(1)) detail::future_object<R&>(), D(a2, 1) );
future_obtained = false;
}
#endif
promise():
-#if defined BOOST_THREAD_PROMISE_LAZY
+#if defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
future_(),
#else
- future_(new detail::future_object<void>),
+ future_(new detail::future_object<R&>()),
#endif
future_obtained(false)
{}
@@ -1284,11 +1822,11 @@
{
if(future_)
{
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(!future_->done)
{
- future_->mark_exceptional_finish_internal(boost::copy_exception(broken_promise()));
+ future_->mark_exceptional_finish_internal(boost::copy_exception(broken_promise()), lock);
}
}
}
@@ -1297,11 +1835,9 @@
promise(BOOST_THREAD_RV_REF(promise) rhs) BOOST_NOEXCEPT :
future_(BOOST_THREAD_RV(rhs).future_),future_obtained(BOOST_THREAD_RV(rhs).future_obtained)
{
- // we need to release the future as shared_ptr doesn't implements move semantics
BOOST_THREAD_RV(rhs).future_.reset();
BOOST_THREAD_RV(rhs).future_obtained=false;
}
-
promise & operator=(BOOST_THREAD_RV_REF(promise) rhs) BOOST_NOEXCEPT
{
future_=BOOST_THREAD_RV(rhs).future_;
@@ -1318,42 +1854,60 @@
}
// Result retrieval
- BOOST_THREAD_FUTURE<void> get_future()
+ BOOST_THREAD_FUTURE<R&> get_future()
{
lazy_init();
-
if (future_.get()==0)
{
boost::throw_exception(promise_moved());
}
- if(future_obtained)
+ if (future_obtained)
{
boost::throw_exception(future_already_retrieved());
}
future_obtained=true;
- return BOOST_THREAD_FUTURE<void>(future_);
+ return BOOST_THREAD_FUTURE<R&>(future_);
}
- void set_value()
+ void set_value(R& r)
{
lazy_init();
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(future_->done)
{
boost::throw_exception(promise_already_satisfied());
}
- future_->mark_finished_with_result_internal();
+ future_->mark_finished_with_result_internal(r, lock);
}
void set_exception(boost::exception_ptr p)
{
lazy_init();
- boost::lock_guard<boost::mutex> lock(future_->mutex);
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
if(future_->done)
{
boost::throw_exception(promise_already_satisfied());
}
- future_->mark_exceptional_finish_internal(p);
+ future_->mark_exceptional_finish_internal(p, lock);
+ }
+
+ // setting the result with deferred notification
+ void set_value_at_thread_exit(R& r)
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_value_at_thread_exit(r);
+ }
+
+ void set_exception_at_thread_exit(exception_ptr e)
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_exception_at_thread_exit(e);
}
template<typename F>
@@ -1364,23 +1918,180 @@
}
};
-
-#if defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
- namespace container
+ template <>
+ class promise<void>
{
- template <class R, class Alloc>
- struct uses_allocator<promise<R> , Alloc> : true_type
- {
- };
- }
-#endif
+ typedef boost::shared_ptr<detail::future_object<void> > future_ptr;
- BOOST_THREAD_DCL_MOVABLE_BEG(T) promise<T> BOOST_THREAD_DCL_MOVABLE_END
+ future_ptr future_;
+ bool future_obtained;
- namespace detail
- {
- template<typename R>
- struct task_base:
+ void lazy_init()
+ {
+#if defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
+ if(!atomic_load(&future_))
+ {
+ future_ptr blank;
+ atomic_compare_exchange(&future_,&blank,future_ptr(new detail::future_object<void>));
+ }
+#endif
+ }
+ public:
+ BOOST_THREAD_MOVABLE_ONLY(promise)
+
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
+ template <class Allocator>
+ promise(boost::allocator_arg_t, Allocator a)
+ {
+ typedef typename Allocator::template rebind<detail::future_object<void> >::other A2;
+ A2 a2(a);
+ typedef thread_detail::allocator_destructor<A2> D;
+
+ future_ = future_ptr(::new(a2.allocate(1)) detail::future_object<void>(), D(a2, 1) );
+ future_obtained = false;
+ }
+#endif
+ promise():
+#if defined BOOST_THREAD_PROVIDES_PROMISE_LAZY
+ future_(),
+#else
+ future_(new detail::future_object<void>),
+#endif
+ future_obtained(false)
+ {}
+
+ ~promise()
+ {
+ if(future_)
+ {
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
+
+ if(!future_->done)
+ {
+ future_->mark_exceptional_finish_internal(boost::copy_exception(broken_promise()), lock);
+ }
+ }
+ }
+
+ // Assignment
+ promise(BOOST_THREAD_RV_REF(promise) rhs) BOOST_NOEXCEPT :
+ future_(BOOST_THREAD_RV(rhs).future_),future_obtained(BOOST_THREAD_RV(rhs).future_obtained)
+ {
+ // we need to release the future as shared_ptr doesn't implements move semantics
+ BOOST_THREAD_RV(rhs).future_.reset();
+ BOOST_THREAD_RV(rhs).future_obtained=false;
+ }
+
+ promise & operator=(BOOST_THREAD_RV_REF(promise) rhs) BOOST_NOEXCEPT
+ {
+ future_=BOOST_THREAD_RV(rhs).future_;
+ future_obtained=BOOST_THREAD_RV(rhs).future_obtained;
+ BOOST_THREAD_RV(rhs).future_.reset();
+ BOOST_THREAD_RV(rhs).future_obtained=false;
+ return *this;
+ }
+
+ void swap(promise& other)
+ {
+ future_.swap(other.future_);
+ std::swap(future_obtained,other.future_obtained);
+ }
+
+ // Result retrieval
+ BOOST_THREAD_FUTURE<void> get_future()
+ {
+ lazy_init();
+
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ if(future_obtained)
+ {
+ boost::throw_exception(future_already_retrieved());
+ }
+ future_obtained=true;
+ return BOOST_THREAD_FUTURE<void>(future_);
+ }
+
+ void set_value()
+ {
+ lazy_init();
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
+ if(future_->done)
+ {
+ boost::throw_exception(promise_already_satisfied());
+ }
+ future_->mark_finished_with_result_internal(lock);
+ }
+
+ void set_exception(boost::exception_ptr p)
+ {
+ lazy_init();
+ boost::unique_lock<boost::mutex> lock(future_->mutex);
+ if(future_->done)
+ {
+ boost::throw_exception(promise_already_satisfied());
+ }
+ future_->mark_exceptional_finish_internal(p,lock);
+ }
+
+ // setting the result with deferred notification
+ void set_value_at_thread_exit()
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_value_at_thread_exit();
+ }
+
+ void set_exception_at_thread_exit(exception_ptr e)
+ {
+ if (future_.get()==0)
+ {
+ boost::throw_exception(promise_moved());
+ }
+ future_->set_exception_at_thread_exit(e);
+ }
+
+ template<typename F>
+ void set_wait_callback(F f)
+ {
+ lazy_init();
+ future_->set_wait_callback(f,this);
+ }
+
+ };
+
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
+ namespace container
+ {
+ template <class R, class Alloc>
+ struct uses_allocator<promise<R> , Alloc> : true_type
+ {
+ };
+ }
+#endif
+
+ BOOST_THREAD_DCL_MOVABLE_BEG(T) promise<T> BOOST_THREAD_DCL_MOVABLE_END
+
+ namespace detail
+ {
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ template<typename R>
+ struct task_base;
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename R, typename ...ArgTypes>
+ struct task_base<R(ArgTypes...)>:
+#else
+ template<typename R>
+ struct task_base<R()>:
+#endif
+#else
+ template<typename R>
+ struct task_base:
+#endif
detail::future_object<R>
{
bool started;
@@ -1393,7 +2104,13 @@
{
started=false;
}
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ virtual void do_run(BOOST_THREAD_RV_REF(ArgTypes) ... args)=0;
+ void run(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+#else
+ virtual void do_run()=0;
void run()
+#endif
{
{
boost::lock_guard<boost::mutex> lk(this->mutex);
@@ -1403,56 +2120,131 @@
}
started=true;
}
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ do_run(boost::forward<ArgTypes>(args)...);
+#else
do_run();
+#endif
+ }
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ virtual void do_apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)=0;
+ void apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+#else
+ virtual void do_apply()=0;
+ void apply()
+#endif
+ {
+ {
+ boost::lock_guard<boost::mutex> lk(this->mutex);
+ if(started)
+ {
+ boost::throw_exception(task_already_started());
+ }
+ started=true;
+ }
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ do_apply(boost::forward<ArgTypes>(args)...);
+#else
+ do_apply();
+#endif
}
void owner_destroyed()
{
- boost::lock_guard<boost::mutex> lk(this->mutex);
+ boost::unique_lock<boost::mutex> lk(this->mutex);
if(!started)
{
started=true;
- this->mark_exceptional_finish_internal(boost::copy_exception(boost::broken_promise()));
+ this->mark_exceptional_finish_internal(boost::copy_exception(boost::broken_promise()), lk);
}
}
-
- virtual void do_run()=0;
};
-
-
-
- template<typename R,typename F>
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ template<typename F, typename R>
+ struct task_object;
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename F, typename R, typename ...ArgTypes>
+ struct task_object<F, R(ArgTypes...)>:
+ task_base<R(ArgTypes...)>
+#else
+ template<typename F, typename R>
+ struct task_object<F, R()>:
+ task_base<R()>
+#endif
+#else
+ template<typename F, typename R>
struct task_object:
task_base<R>
+#endif
{
private:
task_object(task_object&);
public:
F f;
- task_object(F const& f_):
- 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_))
+ f(boost::move(f_)) // TODO forward
{}
#endif
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ this->set_value_at_thread_exit(f(boost::forward<ArgTypes>(args)...));
+ }
+#else
+ void do_apply()
+ {
+ try
+ {
+ this->set_value_at_thread_exit(f());
+ }
+#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ catch(thread_interrupted& )
+ {
+ this->set_interrupted_at_thread_exit();
+ }
+#endif
+ catch(...)
+ {
+ this->set_exception_at_thread_exit(current_exception());
+ }
+ }
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_run(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ this->mark_finished_with_result(f(boost::forward<ArgTypes>(args)...));
+ }
+#else
void do_run()
{
try
{
this->mark_finished_with_result(f());
}
+#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
catch(thread_interrupted& )
{
this->mark_interrupted_finish();
}
+#endif
catch(...)
{
this->mark_exceptional_finish();
@@ -1460,9 +2252,23 @@
}
};
- template<typename R>
- struct task_object<R,R (*)()>:
- task_base<R>
+#if defined(BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR)
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename R, typename ...ArgTypes>
+ struct task_object<R (*)(ArgTypes...), R(ArgTypes...)>:
+ task_base<R(ArgTypes...)>
+#else
+ template<typename R>
+ struct task_object<R (*)(), R()>:
+ task_base<R()>
+#endif
+#else
+ template<typename R>
+ struct task_object<R (*)(), R> :
+ task_base<R>
+#endif
{
private:
task_object(task_object&);
@@ -1471,84 +2277,225 @@
task_object(R (*f_)()):
f(f_)
{}
+
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ this->set_value_at_thread_exit(f(boost::forward<ArgTypes>(args)...));
+ }
+#else
+ void do_apply()
+ {
+ try
+ {
+ this->set_value_at_thread_exit(f());
+ }
+#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ catch(thread_interrupted& )
+ {
+ this->set_interrupted_at_thread_exit();
+ }
+#endif
+ catch(...)
+ {
+ this->set_exception_at_thread_exit(current_exception());
+ }
+ }
+
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_run(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ this->mark_finished_with_result(f(boost::forward<ArgTypes>(args)...));
+ }
+#else
void do_run()
{
try
{
this->mark_finished_with_result(f());
}
+#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
catch(thread_interrupted& )
{
this->mark_interrupted_finish();
}
+#endif
catch(...)
{
this->mark_exceptional_finish();
}
}
};
+#endif
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename F, typename ...ArgTypes>
+ struct task_object<F, void(ArgTypes...)>:
+ task_base<void(ArgTypes...)>
+#else
template<typename F>
- struct task_object<void,F>:
- task_base<void>
+ struct task_object<F, void()>:
+ task_base<void()>
+#endif
+#else
+ template<typename F>
+ struct task_object<F,void>:
+ task_base<void>
+#endif
{
private:
task_object(task_object&);
public:
F f;
- task_object(F const& f_):
- 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_))
+ f(boost::move(f_)) // TODO forward
+ {}
+#endif
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ f(boost::forward<ArgTypes>(args)...);
+#else
+ void do_apply()
+ {
+ try
+ {
+ f();
+#endif
+ this->set_value_at_thread_exit();
+ }
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ catch(thread_interrupted& )
+ {
+ this->set_interrupted_at_thread_exit();
+ }
+#endif
+ catch(...)
+ {
+ this->set_exception_at_thread_exit(current_exception());
+ }
+ }
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_run(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ f(boost::forward<ArgTypes>(args)...);
+#else
+ void do_run()
+ {
+ try
+ {
+ f();
+#endif
+ this->mark_finished_with_result();
+ }
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ catch(thread_interrupted& )
+ {
+ this->mark_interrupted_finish();
+ }
+#endif
+ catch(...)
+ {
+ this->mark_exceptional_finish();
+ }
+ }
+ };
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename ...ArgTypes>
+ struct task_object<void (*)(ArgTypes...), void(ArgTypes...)>:
+ task_base<void(ArgTypes...)>
+#else
+ template<>
+ struct task_object<void (*)(), void()>:
+ task_base<void()>
+#endif
+#else
+ template<>
+ struct task_object<void (*)(),void>:
+ task_base<void>
+#endif
+ {
+ private:
+ task_object(task_object&);
+ public:
+ void (*f)();
+ task_object(void (*f_)()):
+ f(f_)
{}
-#endif
- void do_run()
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_apply(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ f(boost::forward<ArgTypes>(args)...);
+#else
+ void do_apply()
{
try
{
f();
- this->mark_finished_with_result();
+#endif
+ this->set_value_at_thread_exit();
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
catch(thread_interrupted& )
{
- this->mark_interrupted_finish();
+ this->set_interrupted_at_thread_exit();
}
+#endif
catch(...)
{
- this->mark_exceptional_finish();
+ this->set_exception_at_thread_exit(current_exception());
}
}
- };
- template<>
- struct task_object<void,void (*)()>:
- task_base<void>
- {
- private:
- task_object(task_object&);
- public:
- void (*f)();
- task_object(void (*f_)()):
- f(f_)
- {}
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void do_run(BOOST_THREAD_RV_REF(ArgTypes) ... args)
+ {
+ try
+ {
+ f(boost::forward<ArgTypes>(args)...);
+#else
void do_run()
{
try
{
f();
+#endif
this->mark_finished_with_result();
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
catch(thread_interrupted& )
{
this->mark_interrupted_finish();
}
+#endif
catch(...)
{
this->mark_exceptional_finish();
@@ -1558,12 +2505,30 @@
}
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template<typename R, typename ...ArgTypes>
+ class packaged_task<R(ArgTypes...)>
+ {
+ typedef boost::shared_ptr<detail::task_base<R(ArgTypes...)> > task_ptr;
+ boost::shared_ptr<detail::task_base<R(ArgTypes...)> > task;
+ #else
+ template<typename R>
+ class packaged_task<R()>
+ {
+ typedef boost::shared_ptr<detail::task_base<R()> > task_ptr;
+ boost::shared_ptr<detail::task_base<R()> > task;
+ #endif
+#else
template<typename R>
class packaged_task
{
- typedef boost::shared_ptr<detail::task_base<R> > task_ptr;
- boost::shared_ptr<detail::task_base<R> > task;
+ typedef boost::shared_ptr<detail::task_base<R> > task_ptr;
+ boost::shared_ptr<detail::task_base<R> > task;
+#endif
bool future_obtained;
+ struct dummy;
public:
typedef R result_type;
@@ -1574,73 +2539,186 @@
{}
// construction and destruction
+#if defined(BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR)
- explicit packaged_task(R(*f)()):
- task(new detail::task_object<R,R(*)()>(f)),future_obtained(false)
- {}
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ explicit packaged_task(R(*f)(), BOOST_THREAD_FWD_REF(ArgTypes)... args)
+ {
+ typedef R(*FR)(BOOST_THREAD_FWD_REF(ArgTypes)...);
+ typedef detail::task_object<FR,R(ArgTypes...)> task_object_type;
+ task= task_ptr(new task_object_type(f, boost::forward<ArgTypes>(args)...));
+ future_obtained=false;
+ }
+ #else
+ explicit packaged_task(R(*f)())
+ {
+ typedef R(*FR)();
+ typedef detail::task_object<FR,R()> task_object_type;
+ task= task_ptr(new task_object_type(f));
+ future_obtained=false;
+ }
+ #endif
+#else
+ explicit packaged_task(R(*f)())
+ {
+ typedef R(*FR)();
+ typedef detail::task_object<FR,R> task_object_type;
+ task= task_ptr(new task_object_type(f));
+ future_obtained=false;
+ }
+#endif
+#endif
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
template <class F>
- explicit packaged_task(BOOST_THREAD_RV_REF(F) f):
- task(new detail::task_object<R,
- typename remove_cv<typename remove_reference<F>::type>::type
- >(boost::forward<F>(f))),future_obtained(false)
- {}
+ explicit packaged_task(BOOST_THREAD_RV_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;
+#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;
+ #else
+ typedef detail::task_object<FR,R()> task_object_type;
+ #endif
+#else
+ typedef detail::task_object<FR,R> task_object_type;
+#endif
+ task = task_ptr(new task_object_type(boost::forward<F>(f)));
+ future_obtained = false;
+
+ }
+
#else
template <class F>
- explicit packaged_task(F const& f):
- task(new detail::task_object<R,F>(f)),future_obtained(false)
- {}
+ explicit packaged_task(F const& f
+ , typename disable_if<is_same<typename decay<F>::type, packaged_task>, dummy* >::type=0
+ )
+ {
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ typedef detail::task_object<F,R(ArgTypes...)> task_object_type;
+ #else
+ typedef detail::task_object<F,R()> task_object_type;
+ #endif
+#else
+ typedef detail::task_object<F,R> task_object_type;
+#endif
+ task = task_ptr(new task_object_type(f));
+ future_obtained=false;
+ }
template <class F>
- explicit packaged_task(BOOST_THREAD_RV_REF(F) f):
- task(new detail::task_object<R,F>(boost::move(f))),future_obtained(false)
- {}
+ explicit packaged_task(BOOST_THREAD_RV_REF(F) f)
+ {
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ typedef detail::task_object<F,R(ArgTypes...)> task_object_type;
+ task = task_ptr(new task_object_type(boost::forward<F>(f)));
+#else
+ typedef detail::task_object<F,R()> task_object_type;
+ task = task_ptr(new task_object_type(boost::move<F>(f))); // TODO forward
+#endif
+#else
+ typedef detail::task_object<F,R> task_object_type;
+ task = task_ptr(new task_object_type(boost::forward<F>(f)));
+#endif
+ future_obtained=false;
+
+ }
#endif
#if defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
+#if defined(BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR)
template <class Allocator>
packaged_task(boost::allocator_arg_t, Allocator a, R(*f)())
{
typedef R(*FR)();
- typedef typename Allocator::template rebind<detail::task_object<R,FR> >::other A2;
+#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;
+ #else
+ typedef detail::task_object<FR,R()> task_object_type;
+ #endif
+#else
+ typedef detail::task_object<FR,R> task_object_type;
+#endif
+ typedef typename Allocator::template rebind<task_object_type>::other A2;
A2 a2(a);
typedef thread_detail::allocator_destructor<A2> D;
- task = task_ptr(::new(a2.allocate(1)) detail::task_object<R,FR>(f), D(a2, 1) );
+ task = task_ptr(::new(a2.allocate(1)) task_object_type(f), D(a2, 1) );
future_obtained = false;
}
-#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
+#endif // BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR
+
+#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)
{
- typedef typename remove_cv<typename remove_reference<F>::type>::type FR;
- typedef typename Allocator::template rebind<detail::task_object<R,FR> >::other A2;
+ //typedef typename remove_cv<typename remove_reference<F>::type>::type FR;
+ typedef F 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;
+ #else
+ typedef detail::task_object<FR,R()> task_object_type;
+ #endif
+#else
+ typedef detail::task_object<FR,R> task_object_type;
+#endif
+ typedef typename Allocator::template rebind<task_object_type>::other A2;
A2 a2(a);
typedef thread_detail::allocator_destructor<A2> D;
- task = task_ptr(::new(a2.allocate(1)) detail::task_object<R,FR>(boost::forward<F>(f)), D(a2, 1) );
+ task = task_ptr(::new(a2.allocate(1)) task_object_type(boost::forward<F>(f)), D(a2, 1) );
future_obtained = false;
}
-#else
+#else // ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
template <class F, class Allocator>
packaged_task(boost::allocator_arg_t, Allocator a, const F& f)
{
- typedef typename Allocator::template rebind<detail::task_object<R,F> >::other A2;
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ typedef detail::task_object<F,R(ArgTypes...)> task_object_type;
+ #else
+ typedef detail::task_object<F,R()> task_object_type;
+ #endif
+#else
+ typedef detail::task_object<F,R> task_object_type;
+#endif
+ typedef typename Allocator::template rebind<task_object_type>::other A2;
A2 a2(a);
typedef thread_detail::allocator_destructor<A2> D;
- task = task_ptr(::new(a2.allocate(1)) detail::task_object<R,F>(f), D(a2, 1) );
+ task = task_ptr(::new(a2.allocate(1)) task_object_type(f), D(a2, 1) );
future_obtained = false;
}
template <class F, class Allocator>
packaged_task(boost::allocator_arg_t, Allocator a, BOOST_THREAD_RV_REF(F) f)
{
- typedef typename Allocator::template rebind<detail::task_object<R,F> >::other A2;
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ typedef detail::task_object<F,R(ArgTypes...)> task_object_type;
+ #else
+ typedef detail::task_object<F,R()> task_object_type;
+ #endif
+#else
+ typedef detail::task_object<F,R> task_object_type;
+#endif
+ typedef typename Allocator::template rebind<task_object_type>::other A2;
A2 a2(a);
typedef thread_detail::allocator_destructor<A2> D;
- task = task_ptr(::new(a2.allocate(1)) detail::task_object<R,F>(boost::move(f)), D(a2, 1) );
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ task = task_ptr(::new(a2.allocate(1)) task_object_type(boost::forward<F>(f)), D(a2, 1) );
+#else
+ task = task_ptr(::new(a2.allocate(1)) task_object_type(boost::move(f)), D(a2, 1) ); // TODO forward
+#endif
future_obtained = false;
}
+
#endif //BOOST_NO_CXX11_RVALUE_REFERENCES
#endif // BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
@@ -1661,6 +2739,8 @@
}
packaged_task& operator=(BOOST_THREAD_RV_REF(packaged_task) other) BOOST_NOEXCEPT
{
+
+ // todo use forward
packaged_task temp(static_cast<BOOST_THREAD_RV_REF(packaged_task)>(other));
swap(temp);
return *this;
@@ -1687,6 +2767,7 @@
// result retrieval
BOOST_THREAD_FUTURE<R> get_future()
{
+
if(!task)
{
boost::throw_exception(task_moved());
@@ -1700,12 +2781,34 @@
{
boost::throw_exception(future_already_retrieved());
}
- return BOOST_THREAD_FUTURE<R>();
+ //return BOOST_THREAD_FUTURE<R>();
}
// execution
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ void operator()(BOOST_THREAD_RV_REF(ArgTypes)... args)
+ {
+ if(!task)
+ {
+ boost::throw_exception(task_moved());
+ }
+ task->run(boost::forward<ArgTypes>(args)...);
+ }
+ void make_ready_at_thread_exit(ArgTypes... args)
+ {
+ if(!task)
+ {
+ boost::throw_exception(task_moved());
+ }
+ if (task->has_value())
+ {
+ boost::throw_exception(promise_already_satisfied());
+ }
+ task->apply(boost::forward<ArgTypes>(args)...);
+ }
+#else
void operator()()
{
if(!task)
@@ -1714,7 +2817,17 @@
}
task->run();
}
-
+ void make_ready_at_thread_exit()
+ {
+ if(!task)
+ {
+ boost::throw_exception(task_moved());
+ }
+ if (task->has_value())
+ boost::throw_exception(promise_already_satisfied());
+ task->apply();
+ }
+#endif
template<typename F>
void set_wait_callback(F f)
{
@@ -1734,22 +2847,86 @@
BOOST_THREAD_DCL_MOVABLE_BEG(T) packaged_task<T> BOOST_THREAD_DCL_MOVABLE_END
+ namespace detail
+ {
+ ////////////////////////////////
+ // make_future_deferred_object
+ ////////////////////////////////
+ template <class Rp, class Fp>
+ BOOST_THREAD_FUTURE<Rp>
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ make_future_deferred_object(Fp&& f)
+ #else
+ make_future_deferred_object(BOOST_THREAD_FWD_REF(Fp) f)
+ #endif
+ {
+ shared_ptr<future_deferred_object<Rp, Fp> >
+ h(new future_deferred_object<Rp, Fp>(boost::forward<Fp>(f)));
+ return BOOST_THREAD_FUTURE<Rp>(h);
+ }
+
+ ////////////////////////////////
+ // make_future_async_object
+ ////////////////////////////////
+ template <class Rp, class Fp>
+ BOOST_THREAD_FUTURE<Rp>
+ #if ! defined BOOST_NO_CXX11_RVALUE_REFERENCES
+ make_future_async_object(Fp&& f)
+ #else
+ make_future_async_object(BOOST_THREAD_FWD_REF(Fp) f)
+ #endif
+ {
+ shared_ptr<future_async_object<Rp, Fp> >
+ h(new future_async_object<Rp, Fp>(boost::forward<Fp>(f)));
+ return BOOST_THREAD_FUTURE<Rp>(h);
+ }
+
+ }
+
+ ////////////////////////////////
+ // 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
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ template <class R, class... ArgTypes>
+ 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;
+ #else
+ template <class R>
+ BOOST_THREAD_FUTURE<R>
+ async(launch policy, R(*f)())
+ {
+ typedef packaged_task<R()> packaged_task_type;
+ #endif
+#else
template <class R>
BOOST_THREAD_FUTURE<R>
async(launch policy, R(*f)())
{
- if (int(policy) & int(launch::async))
+ typedef packaged_task<R> packaged_task_type;
+#endif
+ if (int(policy) & int(launch::async))
{
- packaged_task<R> pt( f );
+ packaged_task_type pt( f );
BOOST_THREAD_FUTURE<R> ret = pt.get_future();
+#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);
}
else if (int(policy) & int(launch::deferred))
{
- packaged_task<R> pt( f );
+ packaged_task_type pt( f );
BOOST_THREAD_FUTURE<R> ret = pt.get_future();
return ::boost::move(ret);
@@ -1763,28 +2940,92 @@
BOOST_THREAD_FUTURE<R>
async(R(*f)())
{
- return async(launch::any, f);
+ return BOOST_THREAD_MAKE_RV_REF(async(launch(launch::any), f));
}
-#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
- template <class F>
- BOOST_THREAD_FUTURE<typename boost::result_of<typename decay<F>::type()>::type>
- async(launch policy, BOOST_THREAD_FWD_REF(F) f)
- {
- typedef typename boost::result_of<typename decay<F>::type()>::type R;
+#endif
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+ #if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+
+ template <class F, class ...ArgTypes>
+ BOOST_THREAD_FUTURE<typename boost::result_of<typename decay<F>::type(
+ typename decay<ArgTypes>::type...
+ )>::type>
+ async(launch policy, BOOST_THREAD_FWD_REF(F) f, BOOST_THREAD_FWD_REF(ArgTypes)... args)
+ {
+
+ 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;
+
+ #else
+ template <class F>
+ BOOST_THREAD_FUTURE<typename boost::result_of<typename decay<F>::type()>::type>
+ async(launch policy, BOOST_THREAD_FWD_REF(F) f)
+ {
+ typedef typename boost::result_of<typename decay<F>::type()>::type R;
+ typedef packaged_task<R()> packaged_task_type;
+
+ typedef detail::async_func<typename decay<F>::type> BF;
+ typedef typename BF::result_type Rp;
+
+ #endif
+#else
+ template <class F>
+ BOOST_THREAD_FUTURE<typename boost::result_of<typename decay<F>::type()>::type>
+ async(launch policy, BOOST_THREAD_FWD_REF(F) f)
+ {
+ typedef typename boost::result_of<typename decay<F>::type()>::type R;
+ typedef packaged_task<R> packaged_task_type;
+
+ typedef detail::async_func<typename decay<F>::type> BF;
+ typedef typename BF::result_type Rp;
+#endif
+
if (int(policy) & int(launch::async))
{
- packaged_task<R> pt( boost::forward<F>(f) );
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ return 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( boost::forward<F>(f) );
BOOST_THREAD_FUTURE<R> ret = pt.get_future();
+#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
return ::boost::move(ret);
+#endif
}
else if (int(policy) & int(launch::deferred))
{
- packaged_task<R> pt( boost::forward<F>(f) );
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ return 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
+ BOOST_THREAD_FUTURE<R> ret;
+ return ::boost::move(ret);
+// return boost::detail::make_future_deferred_object<Rp>(
+// BF(
+// thread_detail::decay_copy(boost::forward<F>(f))
+// )
+// );
+#endif
- BOOST_THREAD_FUTURE<R> ret = pt.get_future();
- return ::boost::move(ret);
} else {
BOOST_THREAD_FUTURE<R> ret;
return ::boost::move(ret);
@@ -1794,72 +3035,272 @@
BOOST_THREAD_FUTURE<typename boost::result_of<F()>::type>
async(BOOST_THREAD_RV_REF(F) f)
{
- return async(launch::any, boost::forward<F>(f));
+ return async(launch(launch::any), boost::forward<F>(f));
}
-#else
-// template <class F>
-// BOOST_THREAD_FUTURE<typename boost::result_of<typename decay<F>::type()>::type>
-// async(launch policy, F const& f)
-// {
-// typedef typename boost::result_of<typename decay<F>::type()>::type R;
-// if (int(policy) & int(launch::async))
-// {
-// packaged_task<R> pt( f );
-//
-// BOOST_THREAD_FUTURE<R> ret = pt.get_future();
-// boost::thread( boost::move(pt) ).detach();
-// return ::boost::move(ret);
-// }
-// else if (int(policy) & int(launch::deferred))
-// {
-// packaged_task<R> pt( f );
-//
-// BOOST_THREAD_FUTURE<R> ret = pt.get_future();
-// return ::boost::move(ret);
-// } else {
-// BOOST_THREAD_FUTURE<R> ret;
-// return ::boost::move(ret);
-// }
-// }
-// template <class F>
-// BOOST_THREAD_FUTURE<typename boost::result_of<F()>::type>
-// async(F const& f)
-// {
-// return async(launch::any, f);
-// }
- template <class F>
- BOOST_THREAD_FUTURE<typename boost::result_of<typename decay<F>::type()>::type>
- async(launch policy, BOOST_THREAD_FWD_REF(F) f)
- {
- typedef typename boost::result_of<typename decay<F>::type()>::type R;
- if (int(policy) & int(launch::async))
- {
- packaged_task<R> pt( boost::forward<F>(f) );
+ ////////////////////////////////
+ // make_future
+ ////////////////////////////////
+ template <typename T>
+ BOOST_THREAD_FUTURE<typename decay<T>::type> make_future(BOOST_THREAD_FWD_REF(T) value)
+ {
+ typedef typename decay<T>::type future_type;
+ promise<future_type> p;
+ p.set_value(boost::forward<T>(value));
+ return p.get_future();
+ }
- BOOST_THREAD_FUTURE<R> ret = pt.get_future();
- boost::thread( boost::move(pt) ).detach();
- return ::boost::move(ret);
- }
- else if (int(policy) & int(launch::deferred))
+
+ inline BOOST_THREAD_FUTURE<void> make_future()
+ {
+ promise<void> p;
+ return p.get_future();
+
+ }
+
+ ////////////////////////////////
+ // make_shared_future
+ ////////////////////////////////
+ template <typename T>
+ shared_future<typename decay<T>::type> make_shared_future(BOOST_THREAD_FWD_REF(T) value)
+ {
+ typedef typename decay<T>::type future_type;
+ promise<future_type> p;
+ p.set_value(boost::forward<T>(value));
+ return p.get_future().share();
+ }
+
+
+ inline shared_future<void> make_shared_future()
+ {
+ promise<void> p;
+ return p.get_future().share();
+
+ }
+
+ ////////////////////////////////
+ // detail::future_continuation
+ ////////////////////////////////
+#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
+ namespace detail
+ {
+ template <typename F, typename R, typename C>
+ struct future_continuation : future_continuation_base
+ {
+ F& parent;
+ C continuation;
+ launch policy_;
+ promise<R> next;
+
+ future_continuation(F& f, BOOST_THREAD_FWD_REF(C) c) :
+ parent(f),
+ continuation(boost::forward<C>(c)),
+ policy_(f.launch_policy()),
+ next()
+ {}
+ future_continuation(F& f, BOOST_THREAD_FWD_REF(C) c, launch policy) :
+ parent(f),
+ continuation(boost::forward<C>(c)),
+ policy_(policy),
+ next()
+ {}
+ ~future_continuation()
+ {}
+
+ void do_continuation(boost::unique_lock<boost::mutex>& lk)
{
- packaged_task<R> pt( boost::forward<F>(f) );
+ try
+ {
+ lk.unlock();
+ // fixme what to do depending on inherits_launch_policy_ and policy_?
+// if (int(policy_) & int(launch::deferred))
+ {
+ R val = continuation(parent);
+ next.set_value(boost::move(val));
+ }
+// else
+// {
+// BOOST_THREAD_FUTURE<R> f = async(policy_, continuation, boost::ref(parent));
+// R val = f.get();
+// next.set_value(boost::move(val));
+// }
+ }
+ catch (...)
+ {
+ next.set_exception(boost::current_exception());
+ }
+ }
+ private:
- BOOST_THREAD_FUTURE<R> ret = pt.get_future();
- return ::boost::move(ret);
- } else {
- BOOST_THREAD_FUTURE<R> ret;
- return ::boost::move(ret);
+ future_continuation(future_continuation const&);
+ future_continuation& operator=(future_continuation const&);
+ };
+#if defined(BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR)
+ template <typename F, typename R, typename CR>
+ struct future_continuation<F,R,CR(*)(F&)> : future_continuation_base
+ {
+ F& parent;
+ CR(*continuation)(F&) ;
+ launch policy_;
+ promise<R> next;
+
+ future_continuation(F& f, CR(*c)(F&)) :
+ parent(f),
+ continuation(c),
+ policy_(f.launch_policy()),
+ next()
+ {}
+ future_continuation(F& f, CR(*c)(F&), launch policy) :
+ parent(f),
+ continuation(c),
+ policy_(policy),
+ next()
+ {}
+ ~future_continuation()
+ {}
+
+ void do_continuation(boost::unique_lock<boost::mutex>& lk)
+ {
+ try
+ {
+ lk.unlock();
+ // fixme what to do depending on inherits_launch_policy_ and policy_?
+// if (int(policy_) & int(launch::deferred))
+ {
+ R val = continuation(parent);
+ next.set_value(boost::move(val));
+ }
+// else
+// {
+// BOOST_THREAD_FUTURE<R> f = async(policy_, continuation, boost::ref(parent));
+// R val = f.get();
+// next.set_value(boost::move(val));
+// }
+ }
+ catch (...)
+ {
+ next.set_exception(boost::current_exception());
+ }
}
+ private:
+
+ future_continuation(future_continuation const&);
+ future_continuation& operator=(future_continuation const&);
+ };
+#endif
+ }
+
+ ////////////////////////////////
+ // template<typename F>
+ // auto future<R>::then(F&& func) -> BOOST_THREAD_FUTURE<decltype(func(*this))>;
+ ////////////////////////////////
+
+ template <typename R>
+ template <typename F>
+ inline BOOST_THREAD_FUTURE<typename boost::result_of<F(BOOST_THREAD_FUTURE<R>&)>::type>
+ BOOST_THREAD_FUTURE<R>::then(launch policy, BOOST_THREAD_RV_REF(F) func)
+ {
+
+ typedef typename boost::result_of<F(BOOST_THREAD_FUTURE<R>&)>::type future_type;
+
+ if (this->future_)
+ {
+ boost::unique_lock<boost::mutex> lock(this->future_->mutex);
+ detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, F > *ptr =
+ new detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, F>(*this, boost::forward<F>(func), policy);
+ if (ptr==0)
+ {
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+ this->future_->set_continuation_ptr(ptr, lock);
+ return ptr->next.get_future();
}
- template <class F>
- BOOST_THREAD_FUTURE<typename boost::result_of<F()>::type>
- async(BOOST_THREAD_FWD_REF(F) f)
+ else
+ {
+ // fixme what to do when the future has no associated state?
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+
+ }
+ template <typename R>
+ template <typename F>
+ inline BOOST_THREAD_FUTURE<typename boost::result_of<F(BOOST_THREAD_FUTURE<R>&)>::type>
+ BOOST_THREAD_FUTURE<R>::then(BOOST_THREAD_RV_REF(F) func)
+ {
+
+ typedef typename boost::result_of<F(BOOST_THREAD_FUTURE<R>&)>::type future_type;
+
+ if (this->future_)
+ {
+ boost::unique_lock<boost::mutex> lock(this->future_->mutex);
+ detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, F > *ptr =
+ new detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, F>(*this, boost::forward<F>(func));
+ if (ptr==0)
+ {
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+ this->future_->set_continuation_ptr(ptr, lock);
+ return ptr->next.get_future();
+ } else {
+ // fixme what to do when the future has no associated state?
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+
+ }
+#if defined(BOOST_THREAD_RVALUE_REFERENCES_DONT_MATCH_FUNTION_PTR)
+ template <typename R>
+ template<typename RF>
+ BOOST_THREAD_FUTURE<RF>
+ BOOST_THREAD_FUTURE<R>::then(RF(*func)(BOOST_THREAD_FUTURE<R>&))
+ {
+
+ typedef RF future_type;
+
+ if (this->future_)
+ {
+ boost::unique_lock<boost::mutex> lock(this->future_->mutex);
+ detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, RF(*)(BOOST_THREAD_FUTURE&) > *ptr =
+ new detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, RF(*)(BOOST_THREAD_FUTURE&)>(*this, func);
+ if (ptr==0)
+ {
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+ this->future_->set_continuation_ptr(ptr, lock);
+ return ptr->next.get_future();
+ } else {
+ // fixme what to do when the future has no associated state?
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+
+ }
+ template <typename R>
+ template<typename RF>
+ BOOST_THREAD_FUTURE<RF>
+ BOOST_THREAD_FUTURE<R>::then(launch policy, RF(*func)(BOOST_THREAD_FUTURE<R>&))
+ {
+
+ typedef RF future_type;
+
+ if (this->future_)
{
- return async(launch::any, boost::forward<F>(f));
+ boost::unique_lock<boost::mutex> lock(this->future_->mutex);
+ detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, RF(*)(BOOST_THREAD_FUTURE&) > *ptr =
+ new detail::future_continuation<BOOST_THREAD_FUTURE<R>, future_type, RF(*)(BOOST_THREAD_FUTURE&)>(*this, func, policy);
+ if (ptr==0)
+ {
+ return BOOST_THREAD_FUTURE<future_type>();
+ }
+ this->future_->set_continuation_ptr(ptr, lock);
+ return ptr->next.get_future();
+ } else {
+ // fixme what to do when the future has no associated state?
+ return BOOST_THREAD_FUTURE<future_type>();
}
+ }
+#endif
+
#endif
}
Copied: branches/release/boost/thread/lock_concepts.hpp (from r81093, /trunk/boost/thread/lock_concepts.hpp)
==============================================================================
--- /trunk/boost/thread/lock_concepts.hpp (original)
+++ branches/release/boost/thread/lock_concepts.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -10,6 +10,7 @@
#include <boost/thread/lock_options.hpp>
#include <boost/thread/lockable_concepts.hpp>
#include <boost/thread/exceptions.hpp>
+#include <boost/thread/detail/move.hpp>
#include <boost/chrono/chrono.hpp>
#include <boost/concept_check.hpp>
@@ -37,7 +38,7 @@
Lk l2(mtx, defer_lock);
Lk l3(mtx, adopt_lock);
Lk l4(( Lk()));
- // BUG Lk l5(( boost::move(l1)));
+ Lk l5(( boost::move(l2)));
cvt_mutex_ptr(l1.mutex());
if (l1.owns_lock()) return;
if (l1) return;
@@ -48,7 +49,12 @@
l2.release();
}
- mutex_type mtx;
+ BasicLock() :
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ BasicLock operator=(BasicLock const&);
+ mutex_type& mtx;
}
;
@@ -64,7 +70,12 @@
Lk l1(mtx, try_to_lock);
if (l1.try_lock()) return;
}
- mutex_type mtx;
+ Lock() :
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ Lock operator=(Lock const&);
+ mutex_type& mtx;
};
template <typename Lk>
@@ -76,12 +87,17 @@
BOOST_CONCEPT_USAGE(TimedLock)
{
- Lk l1(mtx, t);
+ const Lk l1(mtx, t);
Lk l2(mtx, d);
if (l1.try_lock_until(t)) return;
if (l1.try_lock_for(d)) return;
}
- mutex_type mtx;
+ TimedLock() :
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ TimedLock operator=(TimedLock const&);
+ mutex_type& mtx;
boost::chrono::system_clock::time_point t;
boost::chrono::system_clock::duration d;
};
@@ -96,7 +112,12 @@
{
}
- mutex_type mtx;
+ UniqueLock() :
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ UniqueLock operator=(UniqueLock const&);
+ mutex_type& mtx;
};
template <typename Lk>
@@ -108,7 +129,12 @@
BOOST_CONCEPT_USAGE(SharedLock)
{
}
- mutex_type mtx;
+ SharedLock() :
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ SharedLock operator=(SharedLock const&);
+ mutex_type& mtx;
};
@@ -121,7 +147,12 @@
BOOST_CONCEPT_USAGE(UpgradeLock)
{
}
- mutex_type mtx;
+ UpgradeLock() :
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ UpgradeLock operator=(UpgradeLock const&);
+ mutex_type& mtx;
};
/**
@@ -147,10 +178,17 @@
BOOST_CONCEPT_USAGE( StrictLock)
{
- if (l1.is_locking(&mtx)) return;
+ if (l1.owns_lock(&mtx)) return;
}
- const Lk &l1;
- mutex_type mtx;
+ StrictLock() :
+ l1(*static_cast<Lk*>(0)),
+ mtx(*static_cast<mutex_type*>(0))
+ {}
+ private:
+ StrictLock operator=(StrictLock const&);
+
+ Lk const& l1;
+ mutex_type const& mtx;
};
Copied: branches/release/boost/thread/lock_guard.hpp (from r81093, /trunk/boost/thread/lock_guard.hpp)
==============================================================================
--- /trunk/boost/thread/lock_guard.hpp (original)
+++ branches/release/boost/thread/lock_guard.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,16 +8,43 @@
#define BOOST_THREAD_LOCK_GUARD_HPP
#include <boost/thread/detail/delete.hpp>
+#include <boost/thread/detail/move.hpp>
#include <boost/thread/lock_options.hpp>
#if ! defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
#include <boost/thread/is_locked_by_this_thread.hpp>
#endif
-
+#include <boost/assert.hpp>
+#include <iostream>
+#if ! defined BOOST_NO_CXX11_HDR_INITIALIZER_LIST
+#include <initializer_list>
+#endif
#include <boost/config/abi_prefix.hpp>
namespace boost
{
+#if ! defined BOOST_NO_CXX11_HDR_INITIALIZER_LIST
+ namespace thread_detail
+ {
+ template <typename Mutex>
+ struct lockable_wrapper
+ {
+ Mutex* m;
+ explicit lockable_wrapper(Mutex& m_) :
+ m(&m_)
+ {}
+ };
+ template <typename Mutex>
+ struct lockable_adopt_wrapper
+ {
+ Mutex* m;
+ explicit lockable_adopt_wrapper(Mutex& m_) :
+ m(&m_)
+ {}
+ };
+ }
+#endif
+
template <typename Mutex>
class lock_guard
{
@@ -26,13 +53,14 @@
public:
typedef Mutex mutex_type;
- BOOST_THREAD_NO_COPYABLE( lock_guard)
+ BOOST_THREAD_NO_COPYABLE( lock_guard )
explicit lock_guard(Mutex& m_) :
m(m_)
{
m.lock();
}
+
lock_guard(Mutex& m_, adopt_lock_t) :
m(m_)
{
@@ -40,13 +68,44 @@
BOOST_ASSERT(is_locked_by_this_thread(m));
#endif
}
+
+#if ! defined BOOST_NO_CXX11_HDR_INITIALIZER_LIST
+ lock_guard(std::initializer_list<thread_detail::lockable_wrapper<Mutex> > l_) :
+ m(*(const_cast<thread_detail::lockable_wrapper<Mutex>*>(l_.begin())->m))
+ {
+ m.lock();
+ }
+
+ lock_guard(std::initializer_list<thread_detail::lockable_adopt_wrapper<Mutex> > l_) :
+ m(*(const_cast<thread_detail::lockable_adopt_wrapper<Mutex>*>(l_.begin())->m))
+ {
+#if ! defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
+ BOOST_ASSERT(is_locked_by_this_thread(m));
+#endif
+ }
+
+#endif
~lock_guard()
{
m.unlock();
}
};
+
+#if ! defined BOOST_NO_CXX11_HDR_INITIALIZER_LIST
+ template <typename Lockable>
+ lock_guard<Lockable> make_lock_guard(Lockable& mtx)
+ {
+ return { thread_detail::lockable_wrapper<Lockable>(mtx) };
+ }
+ template <typename Lockable>
+ lock_guard<Lockable> make_lock_guard(Lockable& mtx, adopt_lock_t)
+ {
+ return { thread_detail::lockable_adopt_wrapper<Lockable>(mtx) };
+ }
+#endif
}
+
#include <boost/config/abi_suffix.hpp>
#endif
Copied: branches/release/boost/thread/lock_types.hpp (from r81093, /trunk/boost/thread/lock_types.hpp)
==============================================================================
--- /trunk/boost/thread/lock_types.hpp (original)
+++ branches/release/boost/thread/lock_types.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -46,64 +46,55 @@
}
#ifdef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
- template<typename T>
- struct is_mutex_type<unique_lock<T> >
+ namespace sync
{
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- template<typename T>
- struct is_mutex_type<shared_lock<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- template<typename T>
- struct is_mutex_type<upgrade_lock<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- template<typename T>
- struct is_mutex_type<detail::try_lock_wrapper<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
+ template<typename T>
+ struct is_basic_lockable<unique_lock<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<typename T>
+ struct is_lockable<unique_lock<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
- class mutex;
- class timed_mutex;
- class recursive_mutex;
- class recursive_timed_mutex;
- class shared_mutex;
+ template<typename T>
+ struct is_basic_lockable<shared_lock<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<typename T>
+ struct is_lockable<shared_lock<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
- template<>
- struct is_mutex_type<mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<timed_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<recursive_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<recursive_timed_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<shared_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
+ template<typename T>
+ struct is_basic_lockable<upgrade_lock<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<typename T>
+ struct is_lockable<upgrade_lock<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<typename T>
+ struct is_basic_lockable<detail::try_lock_wrapper<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<typename T>
+ struct is_lockable<detail::try_lock_wrapper<T> >
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ }
#endif
+
template <typename Mutex>
class unique_lock
{
@@ -178,7 +169,9 @@
{
BOOST_THREAD_RV(other).is_locked=false;
BOOST_THREAD_RV(other).m=0;
- }BOOST_THREAD_EXPLICIT_LOCK_CONVERSION unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other);
+ }
+
+ BOOST_THREAD_EXPLICIT_LOCK_CONVERSION unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other);
#ifndef BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
unique_lock& operator=(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT
Copied: branches/release/boost/thread/lockable_concepts.hpp (from r81093, /trunk/boost/thread/lockable_concepts.hpp)
==============================================================================
--- /trunk/boost/thread/lockable_concepts.hpp (original)
+++ branches/release/boost/thread/lockable_concepts.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -28,8 +28,11 @@
l.lock();
l.unlock();
}
+ BasicLockable() : l(*static_cast<Mutex*>(0)) {}
private:
- Mutex l;
+ BasicLockable operator=(BasicLockable const&);
+
+ Mutex& l;
}
;
//]
@@ -48,8 +51,10 @@
{
if (l.try_lock()) return;
}
+ Lockable() : l(*static_cast<Mutex*>(0)) {}
private:
- Mutex l;
+ Lockable operator=(Lockable const&);
+ Mutex& l;
};
//]
@@ -69,9 +74,12 @@
if (l.try_lock_until(t)) return;
if (l.try_lock_for(d)) return;
}
+ TimedLockable() : l(*static_cast<Mutex*>(0)) {}
+ private:
+ TimedLockable operator=(TimedLockable const&);
Mutex& l;
- chrono::system_clock::time_point& t;
- chrono::system_clock::duration& d;
+ chrono::system_clock::time_point t;
+ chrono::system_clock::duration d;
};
//]
@@ -94,9 +102,12 @@
if (l.try_lock_shared_until(t)) return;
if (l.try_lock_shared_for(d)) return;
}
+ SharedLockable() : l(*static_cast<Mutex*>(0)) {}
+ private:
+ SharedLockable operator=(SharedLockable const&);
Mutex& l;
- chrono::system_clock::time_point& t;
- chrono::system_clock::duration& d;
+ chrono::system_clock::time_point t;
+ chrono::system_clock::duration d;
};
//]
@@ -133,9 +144,12 @@
if (l.try_unlock_upgrade_and_lock_for(d)) return;
l.unlock_upgrade_and_lock_shared();
}
+ UpgradeLockable() : l(*static_cast<Mutex*>(0)) {}
+ private:
+ UpgradeLockable operator=(UpgradeLockable const&);
Mutex& l;
- chrono::system_clock::time_point& t;
- chrono::system_clock::duration& d;
+ chrono::system_clock::time_point t;
+ chrono::system_clock::duration d;
};
//]
Copied: branches/release/boost/thread/lockable_traits.hpp (from r81093, /trunk/boost/thread/lockable_traits.hpp)
==============================================================================
--- /trunk/boost/thread/lockable_traits.hpp (original)
+++ branches/release/boost/thread/lockable_traits.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,32 +8,27 @@
#define BOOST_THREAD_LOCKABLE_TRAITS_HPP
#include <boost/thread/detail/config.hpp>
-#include <boost/thread/detail/move.hpp>
-#include <boost/thread/exceptions.hpp>
-//#include <boost/thread/testable_mutex.hpp>
-#include <boost/thread/thread_time.hpp>
#include <boost/assert.hpp>
-#ifdef BOOST_THREAD_USES_CHRONO
-#include <boost/chrono/time_point.hpp>
-#include <boost/chrono/duration.hpp>
-#endif
#include <boost/detail/workaround.hpp>
#include <boost/type_traits/is_class.hpp>
-#include <algorithm>
-#include <iterator>
-
#include <boost/config/abi_prefix.hpp>
+// todo make use of integral_constant, true_type and false_type
+
namespace boost
{
+ namespace sync
+ {
#if defined(BOOST_NO_SFINAE) || \
BOOST_WORKAROUND(__IBMCPP__, BOOST_TESTED_AT(600)) || \
BOOST_WORKAROUND(__SUNPRO_CC, BOOST_TESTED_AT(0x590))
+#if ! defined BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
#define BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
#endif
+#endif
#ifndef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
namespace detail
@@ -72,101 +67,135 @@
bool, value=sizeof(has_member<derived>(0))==sizeof(true_type)); \
}
- BOOST_THREAD_DEFINE_HAS_MEMBER_CALLED(lock);
- BOOST_THREAD_DEFINE_HAS_MEMBER_CALLED(unlock);
- BOOST_THREAD_DEFINE_HAS_MEMBER_CALLED(try_lock);
-
- template<typename T,bool=has_member_called_lock<T>::value >
- struct has_member_lock
- {
- BOOST_STATIC_CONSTANT(bool, value=false);
- };
-
- template<typename T>
- struct has_member_lock<T,true>
- {
- typedef char true_type;
- struct false_type
- {
- true_type dummy[2];
- };
-
- template<typename U,typename V>
- static true_type has_member(V (U::*)());
- template<typename U>
- static false_type has_member(U);
-
- BOOST_STATIC_CONSTANT(
- bool,value=sizeof(has_member_lock<T>::has_member(&T::lock))==sizeof(true_type));
- };
-
- template<typename T,bool=has_member_called_unlock<T>::value >
- struct has_member_unlock
- {
- BOOST_STATIC_CONSTANT(bool, value=false);
- };
-
- template<typename T>
- struct has_member_unlock<T,true>
- {
- typedef char true_type;
- struct false_type
- {
- true_type dummy[2];
- };
-
- template<typename U,typename V>
- static true_type has_member(V (U::*)());
- template<typename U>
- static false_type has_member(U);
-
- BOOST_STATIC_CONSTANT(
- bool,value=sizeof(has_member_unlock<T>::has_member(&T::unlock))==sizeof(true_type));
- };
-
- template<typename T,bool=has_member_called_try_lock<T>::value >
- struct has_member_try_lock
- {
- BOOST_STATIC_CONSTANT(bool, value=false);
- };
-
- template<typename T>
- struct has_member_try_lock<T,true>
- {
- typedef char true_type;
- struct false_type
- {
- true_type dummy[2];
- };
-
- template<typename U>
- static true_type has_member(bool (U::*)());
- template<typename U>
- static false_type has_member(U);
-
- BOOST_STATIC_CONSTANT(
- bool,value=sizeof(has_member_try_lock<T>::has_member(&T::try_lock))==sizeof(true_type));
- };
+ BOOST_THREAD_DEFINE_HAS_MEMBER_CALLED(lock)
+; BOOST_THREAD_DEFINE_HAS_MEMBER_CALLED(unlock);
+ BOOST_THREAD_DEFINE_HAS_MEMBER_CALLED(try_lock);
+
+ template<typename T,bool=has_member_called_lock<T>::value >
+ struct has_member_lock
+ {
+ BOOST_STATIC_CONSTANT(bool, value=false);
+ };
+
+ template<typename T>
+ struct has_member_lock<T,true>
+ {
+ typedef char true_type;
+ struct false_type
+ {
+ true_type dummy[2];
+ };
+
+ template<typename U,typename V>
+ static true_type has_member(V (U::*)());
+ template<typename U>
+ static false_type has_member(U);
+
+ BOOST_STATIC_CONSTANT(
+ bool,value=sizeof(has_member_lock<T>::has_member(&T::lock))==sizeof(true_type));
+ };
+
+ template<typename T,bool=has_member_called_unlock<T>::value >
+ struct has_member_unlock
+ {
+ BOOST_STATIC_CONSTANT(bool, value=false);
+ };
+
+ template<typename T>
+ struct has_member_unlock<T,true>
+ {
+ typedef char true_type;
+ struct false_type
+ {
+ true_type dummy[2];
+ };
+
+ template<typename U,typename V>
+ static true_type has_member(V (U::*)());
+ template<typename U>
+ static false_type has_member(U);
+
+ BOOST_STATIC_CONSTANT(
+ bool,value=sizeof(has_member_unlock<T>::has_member(&T::unlock))==sizeof(true_type));
+ };
+
+ template<typename T,bool=has_member_called_try_lock<T>::value >
+ struct has_member_try_lock
+ {
+ BOOST_STATIC_CONSTANT(bool, value=false);
+ };
+
+ template<typename T>
+ struct has_member_try_lock<T,true>
+ {
+ typedef char true_type;
+ struct false_type
+ {
+ true_type dummy[2];
+ };
+
+ template<typename U>
+ static true_type has_member(bool (U::*)());
+ template<typename U>
+ static false_type has_member(U);
+
+ BOOST_STATIC_CONSTANT(
+ bool,value=sizeof(has_member_try_lock<T>::has_member(&T::try_lock))==sizeof(true_type));
+ };
}
-
template<typename T>
- struct is_mutex_type
+ struct is_basic_lockable
{
- BOOST_STATIC_CONSTANT(bool, value = detail::has_member_lock<T>::value &&
- detail::has_member_unlock<T>::value &&
- detail::has_member_try_lock<T>::value);
-
+ BOOST_STATIC_CONSTANT(bool, value = detail::has_member_lock<T>::value &&
+ detail::has_member_unlock<T>::value);
};
+ template<typename T>
+ struct is_lockable
+ {
+ BOOST_STATIC_CONSTANT(bool, value =
+ is_basic_lockable<T>::value &&
+ detail::has_member_try_lock<T>::value);
+ };
+
#else
template<typename T>
- struct is_mutex_type
+ struct is_basic_lockable
+ {
+ BOOST_STATIC_CONSTANT(bool, value = false);
+ };
+ template<typename T>
+ struct is_lockable
{
- BOOST_STATIC_CONSTANT(bool, value = false);
+ BOOST_STATIC_CONSTANT(bool, value = false);
};
#endif
+ template<typename T>
+ struct is_recursive_mutex_sur_parolle
+ {
+ BOOST_STATIC_CONSTANT(bool, value = false);
+ };
+ template<typename T>
+ struct is_recursive_basic_lockable
+ {
+ BOOST_STATIC_CONSTANT(bool, value = is_basic_lockable<T>::value &&
+ is_recursive_mutex_sur_parolle<T>::value);
+ };
+ template<typename T>
+ struct is_recursive_lockable
+ {
+ BOOST_STATIC_CONSTANT(bool, value = is_lockable<T>::value &&
+ is_recursive_mutex_sur_parolle<T>::value);
+ };
+ }
+ template<typename T>
+ struct is_mutex_type
+ {
+ BOOST_STATIC_CONSTANT(bool, value = sync::is_lockable<T>::value);
+ };
+
}
#include <boost/config/abi_suffix.hpp>
Modified: branches/release/boost/thread/locks.hpp
==============================================================================
--- branches/release/boost/thread/locks.hpp (original)
+++ branches/release/boost/thread/locks.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,1822 +6,11 @@
#ifndef BOOST_THREAD_LOCKS_HPP
#define BOOST_THREAD_LOCKS_HPP
-#include <boost/thread/detail/config.hpp>
-#include <boost/thread/exceptions.hpp>
-#include <boost/thread/detail/move.hpp>
-#include <algorithm>
-#include <iterator>
-#include <boost/thread/thread_time.hpp>
-#include <boost/detail/workaround.hpp>
-#include <boost/type_traits/is_class.hpp>
-#ifdef BOOST_THREAD_USES_CHRONO
-#include <boost/chrono/time_point.hpp>
-#include <boost/chrono/duration.hpp>
-#endif
-
-#include <boost/config/abi_prefix.hpp>
-
-namespace boost
-{
- struct xtime;
-
-#if defined(BOOST_NO_SFINAE) || \
- BOOST_WORKAROUND(__IBMCPP__, BOOST_TESTED_AT(600)) || \
- BOOST_WORKAROUND(__SUNPRO_CC, BOOST_TESTED_AT(0x590))
-#define BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
-#endif
-
-#ifndef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
- namespace detail
- {
-#define BOOST_DEFINE_HAS_MEMBER_CALLED(member_name) \
- template<typename T, bool=boost::is_class<T>::value> \
- struct has_member_called_##member_name \
- { \
- BOOST_STATIC_CONSTANT(bool, value=false); \
- }; \
- \
- template<typename T> \
- struct has_member_called_##member_name<T,true> \
- { \
- typedef char true_type; \
- struct false_type \
- { \
- true_type dummy[2]; \
- }; \
- \
- struct fallback { int member_name; }; \
- struct derived: \
- T, fallback \
- { \
- derived(); \
- }; \
- \
- template<int fallback::*> struct tester; \
- \
- template<typename U> \
- static false_type has_member(tester<&U::member_name>*); \
- template<typename U> \
- static true_type has_member(...); \
- \
- BOOST_STATIC_CONSTANT( \
- bool, value=sizeof(has_member<derived>(0))==sizeof(true_type)); \
- }
-
- BOOST_DEFINE_HAS_MEMBER_CALLED(lock);
- BOOST_DEFINE_HAS_MEMBER_CALLED(unlock);
- BOOST_DEFINE_HAS_MEMBER_CALLED(try_lock);
-
- template<typename T,bool=has_member_called_lock<T>::value >
- struct has_member_lock
- {
- BOOST_STATIC_CONSTANT(bool, value=false);
- };
-
- template<typename T>
- struct has_member_lock<T,true>
- {
- typedef char true_type;
- struct false_type
- {
- true_type dummy[2];
- };
-
- template<typename U,typename V>
- static true_type has_member(V (U::*)());
- template<typename U>
- static false_type has_member(U);
-
- BOOST_STATIC_CONSTANT(
- bool,value=sizeof(has_member_lock<T>::has_member(&T::lock))==sizeof(true_type));
- };
-
- template<typename T,bool=has_member_called_unlock<T>::value >
- struct has_member_unlock
- {
- BOOST_STATIC_CONSTANT(bool, value=false);
- };
-
- template<typename T>
- struct has_member_unlock<T,true>
- {
- typedef char true_type;
- struct false_type
- {
- true_type dummy[2];
- };
-
- template<typename U,typename V>
- static true_type has_member(V (U::*)());
- template<typename U>
- static false_type has_member(U);
-
- BOOST_STATIC_CONSTANT(
- bool,value=sizeof(has_member_unlock<T>::has_member(&T::unlock))==sizeof(true_type));
- };
-
- template<typename T,bool=has_member_called_try_lock<T>::value >
- struct has_member_try_lock
- {
- BOOST_STATIC_CONSTANT(bool, value=false);
- };
-
- template<typename T>
- struct has_member_try_lock<T,true>
- {
- typedef char true_type;
- struct false_type
- {
- true_type dummy[2];
- };
-
- template<typename U>
- static true_type has_member(bool (U::*)());
- template<typename U>
- static false_type has_member(U);
-
- BOOST_STATIC_CONSTANT(
- bool,value=sizeof(has_member_try_lock<T>::has_member(&T::try_lock))==sizeof(true_type));
- };
-
- }
-
-
- template<typename T>
- struct is_mutex_type
- {
- BOOST_STATIC_CONSTANT(bool, value = detail::has_member_lock<T>::value &&
- detail::has_member_unlock<T>::value &&
- detail::has_member_try_lock<T>::value);
-
- };
-#else
- template<typename T>
- struct is_mutex_type
- {
- BOOST_STATIC_CONSTANT(bool, value = false);
- };
-#endif
-
- struct defer_lock_t
- {};
- struct try_to_lock_t
- {};
- struct adopt_lock_t
- {};
-
- BOOST_CONSTEXPR_OR_CONST defer_lock_t defer_lock={};
- BOOST_CONSTEXPR_OR_CONST try_to_lock_t try_to_lock={};
- BOOST_CONSTEXPR_OR_CONST adopt_lock_t adopt_lock={};
-
- template<typename Mutex>
- class shared_lock;
-
- template<typename Mutex>
- class upgrade_lock;
-
- template<typename Mutex>
- class unique_lock;
-
- namespace detail
- {
- template<typename Mutex>
- class try_lock_wrapper;
- }
-
-#ifdef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
- template<typename T>
- struct is_mutex_type<unique_lock<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- template<typename T>
- struct is_mutex_type<shared_lock<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- template<typename T>
- struct is_mutex_type<upgrade_lock<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- template<typename T>
- struct is_mutex_type<detail::try_lock_wrapper<T> >
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
- class mutex;
- class timed_mutex;
- class recursive_mutex;
- class recursive_timed_mutex;
- class shared_mutex;
-
- template<>
- struct is_mutex_type<mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<timed_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<recursive_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<recursive_timed_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
- template<>
- struct is_mutex_type<shared_mutex>
- {
- BOOST_STATIC_CONSTANT(bool, value = true);
- };
-
-#endif
-
- template<typename Mutex>
- class lock_guard
- {
- private:
- Mutex& m;
-
- public:
- typedef Mutex mutex_type;
- BOOST_THREAD_NO_COPYABLE(lock_guard)
-
- explicit lock_guard(Mutex& m_):
- m(m_)
- {
- m.lock();
- }
- lock_guard(Mutex& m_,adopt_lock_t):
- m(m_)
- {}
- ~lock_guard()
- {
- m.unlock();
- }
- };
-
- template<typename Mutex>
- class unique_lock
- {
- private:
- Mutex* m;
- bool is_locked;
-
- private:
- explicit unique_lock(upgrade_lock<Mutex>&);
- unique_lock& operator=(upgrade_lock<Mutex>& other);
- public:
- typedef Mutex mutex_type;
- BOOST_THREAD_MOVABLE_ONLY(unique_lock)
-
-#if 0 // This should not be needed anymore. Use instead BOOST_THREAD_MAKE_RV_REF.
-#if BOOST_WORKAROUND(__SUNPRO_CC, < 0x5100)
- unique_lock(const volatile unique_lock&);
-#endif
-#endif
- unique_lock() BOOST_NOEXCEPT :
- m(0),is_locked(false)
- {}
-
- explicit unique_lock(Mutex& m_):
- m(&m_),is_locked(false)
- {
- lock();
- }
- unique_lock(Mutex& m_,adopt_lock_t):
- m(&m_),is_locked(true)
- {}
- unique_lock(Mutex& m_,defer_lock_t) BOOST_NOEXCEPT:
- m(&m_),is_locked(false)
- {}
- unique_lock(Mutex& m_,try_to_lock_t):
- m(&m_),is_locked(false)
- {
- try_lock();
- }
- template<typename TimeDuration>
- unique_lock(Mutex& m_,TimeDuration const& target_time):
- m(&m_),is_locked(false)
- {
- timed_lock(target_time);
- }
- unique_lock(Mutex& m_,system_time const& target_time):
- m(&m_),is_locked(false)
- {
- timed_lock(target_time);
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Clock, class Duration>
- unique_lock(Mutex& mtx, const chrono::time_point<Clock, Duration>& t)
- : m(&mtx), is_locked(mtx.try_lock_until(t))
- {
- }
- template <class Rep, class Period>
- unique_lock(Mutex& mtx, const chrono::duration<Rep, Period>& d)
- : m(&mtx), is_locked(mtx.try_lock_for(d))
- {
- }
-#endif
-
- unique_lock(BOOST_THREAD_RV_REF(unique_lock) other) BOOST_NOEXCEPT:
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- BOOST_THREAD_RV(other).is_locked=false;
- BOOST_THREAD_RV(other).m=0;
- }
- BOOST_THREAD_EXPLICIT_LOCK_CONVERSION unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other);
-
-#ifndef BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
- unique_lock& operator=(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT
- {
- unique_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-#endif
-
- unique_lock& operator=(BOOST_THREAD_RV_REF(unique_lock) other) BOOST_NOEXCEPT
- {
- unique_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-#if 0 // This should not be needed anymore. Use instead BOOST_THREAD_MAKE_RV_REF.
-#if BOOST_WORKAROUND(__SUNPRO_CC, < 0x5100)
- unique_lock& operator=(unique_lock<Mutex> other)
- {
- swap(other);
- return *this;
- }
-#endif // BOOST_WORKAROUND
-#endif
-
- // Conversion from upgrade locking
- unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<mutex_type> BOOST_THREAD_RV_REF_END ul, try_to_lock_t)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(ul).owns_lock()) {
- if (BOOST_THREAD_RV(ul).mutex()->try_unlock_upgrade_and_lock())
- {
- m = BOOST_THREAD_RV(ul).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(ul).release();
- }
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Clock, class Duration>
- unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<mutex_type> BOOST_THREAD_RV_REF_END ul,
- const chrono::time_point<Clock, Duration>& abs_time)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(ul).owns_lock()) {
- if (BOOST_THREAD_RV(ul).mutex()->try_unlock_upgrade_and_lock_until(abs_time))
- {
- m = BOOST_THREAD_RV(ul).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(ul).release();
- }
- }
-
- template <class Rep, class Period>
- unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<mutex_type> BOOST_THREAD_RV_REF_END ul,
- const chrono::duration<Rep, Period>& rel_time)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(ul).owns_lock()) {
- if (BOOST_THREAD_RV(ul).mutex()->try_unlock_upgrade_and_lock_for(rel_time))
- {
- m = BOOST_THREAD_RV(ul).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(ul).release();
- }
- }
-#endif
-
-#ifdef BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
- // Conversion from shared locking
- unique_lock(BOOST_THREAD_RV_REF_BEG shared_lock<mutex_type> BOOST_THREAD_RV_REF_END sl, try_to_lock_t)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(sl).owns_lock()) {
- if (BOOST_THREAD_RV(sl).mutex()->try_unlock_shared_and_lock())
- {
- m = BOOST_THREAD_RV(sl).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(sl).release();
- }
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Clock, class Duration>
- unique_lock(BOOST_THREAD_RV_REF_BEG shared_lock<mutex_type> BOOST_THREAD_RV_REF_END sl,
- const chrono::time_point<Clock, Duration>& abs_time)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(sl).owns_lock()) {
- if (BOOST_THREAD_RV(sl).mutex()->try_unlock_shared_and_lock_until(abs_time))
- {
- m = BOOST_THREAD_RV(sl).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(sl).release();
- }
- }
-
- template <class Rep, class Period>
- unique_lock(BOOST_THREAD_RV_REF_BEG shared_lock<mutex_type> BOOST_THREAD_RV_REF_END sl,
- const chrono::duration<Rep, Period>& rel_time)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(sl).owns_lock()) {
- if (BOOST_THREAD_RV(sl).mutex()->try_unlock_shared_and_lock_for(rel_time))
- {
- m = BOOST_THREAD_RV(sl).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(sl).release();
- }
- }
-#endif // BOOST_THREAD_USES_CHRONO
-#endif // BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
-
-
- void swap(unique_lock& other) BOOST_NOEXCEPT
- {
- std::swap(m,other.m);
- std::swap(is_locked,other.is_locked);
- }
-
- ~unique_lock()
- {
- if(owns_lock())
- {
- m->unlock();
- }
- }
- void lock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- m->lock();
- is_locked=true;
- }
- bool try_lock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- is_locked=m->try_lock();
- return is_locked;
- }
- template<typename TimeDuration>
- bool timed_lock(TimeDuration const& relative_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- is_locked=m->timed_lock(relative_time);
- return is_locked;
- }
-
- bool timed_lock(::boost::system_time const& absolute_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- is_locked=m->timed_lock(absolute_time);
- return is_locked;
- }
- bool timed_lock(::boost::xtime const& absolute_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- is_locked=m->timed_lock(absolute_time);
- return is_locked;
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
-
- template <class Rep, class Period>
- bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- is_locked=m->try_lock_for(rel_time);
- return is_locked;
- }
- template <class Clock, class Duration>
- bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost unique_lock owns already the mutex"));
- }
- is_locked=m->try_lock_until(abs_time);
- return is_locked;
- }
-#endif
-
- void unlock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock has no mutex"));
- }
- if(!owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost unique_lock doesn't own the mutex"));
- }
- m->unlock();
- is_locked=false;
- }
-
-#if defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
- typedef void (unique_lock::*bool_type)();
- operator bool_type() const BOOST_NOEXCEPT
- {
- return is_locked?&unique_lock::lock:0;
- }
- bool operator!() const BOOST_NOEXCEPT
- {
- return !owns_lock();
- }
-#else
- explicit operator bool() const BOOST_NOEXCEPT
- {
- return owns_lock();
- }
-#endif
- bool owns_lock() const BOOST_NOEXCEPT
- {
- return is_locked;
- }
-
- Mutex* mutex() const BOOST_NOEXCEPT
- {
- return m;
- }
-
- Mutex* release() BOOST_NOEXCEPT
- {
- Mutex* const res=m;
- m=0;
- is_locked=false;
- return res;
- }
-
- friend class shared_lock<Mutex>;
- friend class upgrade_lock<Mutex>;
- };
-
- template<typename Mutex>
- void swap(unique_lock<Mutex>& lhs,unique_lock<Mutex>& rhs) BOOST_NOEXCEPT
- {
- lhs.swap(rhs);
- }
-
- BOOST_THREAD_DCL_MOVABLE_BEG(Mutex) unique_lock<Mutex> BOOST_THREAD_DCL_MOVABLE_END
-
- template<typename Mutex>
- class shared_lock
- {
- protected:
- Mutex* m;
- bool is_locked;
-
- public:
- typedef Mutex mutex_type;
- BOOST_THREAD_MOVABLE_ONLY(shared_lock)
-
- shared_lock() BOOST_NOEXCEPT:
- m(0),is_locked(false)
- {}
-
- explicit shared_lock(Mutex& m_):
- m(&m_),is_locked(false)
- {
- lock();
- }
- shared_lock(Mutex& m_,adopt_lock_t):
- m(&m_),is_locked(true)
- {}
- shared_lock(Mutex& m_,defer_lock_t) BOOST_NOEXCEPT:
- m(&m_),is_locked(false)
- {}
- shared_lock(Mutex& m_,try_to_lock_t):
- m(&m_),is_locked(false)
- {
- try_lock();
- }
- shared_lock(Mutex& m_,system_time const& target_time):
- m(&m_),is_locked(false)
- {
- timed_lock(target_time);
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Clock, class Duration>
- shared_lock(Mutex& mtx, const chrono::time_point<Clock, Duration>& t)
- : m(&mtx), is_locked(mtx.try_lock_shared_until(t))
- {
- }
- template <class Rep, class Period>
- shared_lock(Mutex& mtx, const chrono::duration<Rep, Period>& d)
- : m(&mtx), is_locked(mtx.try_lock_shared_for(d))
- {
- }
-#endif
-
- shared_lock(BOOST_THREAD_RV_REF_BEG shared_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT:
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- BOOST_THREAD_RV(other).is_locked=false;
- BOOST_THREAD_RV(other).m=0;
- }
-
- BOOST_THREAD_EXPLICIT_LOCK_CONVERSION shared_lock(BOOST_THREAD_RV_REF_BEG unique_lock<Mutex> BOOST_THREAD_RV_REF_END other):
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- if(is_locked)
- {
- m->unlock_and_lock_shared();
- }
- BOOST_THREAD_RV(other).is_locked=false;
- BOOST_THREAD_RV(other).m=0;
- }
-
- BOOST_THREAD_EXPLICIT_LOCK_CONVERSION shared_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other):
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- if(is_locked)
- {
- m->unlock_upgrade_and_lock_shared();
- }
- BOOST_THREAD_RV(other).is_locked=false;
- BOOST_THREAD_RV(other).m=0;
- }
-
-
- shared_lock& operator=(BOOST_THREAD_RV_REF_BEG shared_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT
- {
- shared_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-#ifndef BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
- shared_lock& operator=(BOOST_THREAD_RV_REF_BEG unique_lock<Mutex> BOOST_THREAD_RV_REF_END other)
- {
- shared_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-
- shared_lock& operator=(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other)
- {
- shared_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-#endif
-
- void swap(shared_lock& other) BOOST_NOEXCEPT
- {
- std::swap(m,other.m);
- std::swap(is_locked,other.is_locked);
- }
-
- Mutex* mutex() const BOOST_NOEXCEPT
- {
- return m;
- }
-
- Mutex* release() BOOST_NOEXCEPT
- {
- Mutex* const res=m;
- m=0;
- is_locked=false;
- return res;
- }
-
- ~shared_lock()
- {
- if(owns_lock())
- {
- m->unlock_shared();
- }
- }
- void lock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- m->lock_shared();
- is_locked=true;
- }
- bool try_lock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->try_lock_shared();
- return is_locked;
- }
- bool timed_lock(boost::system_time const& target_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->timed_lock_shared(target_time);
- return is_locked;
- }
- template<typename Duration>
- bool timed_lock(Duration const& target_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->timed_lock_shared(target_time);
- return is_locked;
- }
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Rep, class Period>
- bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->try_lock_shared_for(rel_time);
- return is_locked;
- }
- template <class Clock, class Duration>
- bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->try_lock_shared_until(abs_time);
- return is_locked;
- }
-#endif
- void unlock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(!owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock doesn't own the mutex"));
- }
- m->unlock_shared();
- is_locked=false;
- }
-
-#if defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
- typedef void (shared_lock<Mutex>::*bool_type)();
- operator bool_type() const BOOST_NOEXCEPT
- {
- return is_locked?&shared_lock::lock:0;
- }
- bool operator!() const BOOST_NOEXCEPT
- {
- return !owns_lock();
- }
-#else
- explicit operator bool() const BOOST_NOEXCEPT
- {
- return owns_lock();
- }
-#endif
- bool owns_lock() const BOOST_NOEXCEPT
- {
- return is_locked;
- }
-
- };
-
- BOOST_THREAD_DCL_MOVABLE_BEG(Mutex) shared_lock<Mutex> BOOST_THREAD_DCL_MOVABLE_END
-
- template<typename Mutex>
- void swap(shared_lock<Mutex>& lhs,shared_lock<Mutex>& rhs) BOOST_NOEXCEPT
- {
- lhs.swap(rhs);
- }
-
- template<typename Mutex>
- class upgrade_lock
- {
- protected:
- Mutex* m;
- bool is_locked;
-
- public:
- typedef Mutex mutex_type;
- BOOST_THREAD_MOVABLE_ONLY(upgrade_lock)
-
- upgrade_lock() BOOST_NOEXCEPT:
- m(0),is_locked(false)
- {}
-
- explicit upgrade_lock(Mutex& m_):
- m(&m_),is_locked(false)
- {
- lock();
- }
- upgrade_lock(Mutex& m_,adopt_lock_t):
- m(&m_),is_locked(true)
- {}
- upgrade_lock(Mutex& m_,defer_lock_t) BOOST_NOEXCEPT:
- m(&m_),is_locked(false)
- {}
- upgrade_lock(Mutex& m_,try_to_lock_t):
- m(&m_),is_locked(false)
- {
- try_lock();
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Clock, class Duration>
- upgrade_lock(Mutex& mtx, const chrono::time_point<Clock, Duration>& t)
- : m(&mtx), is_locked(mtx.try_lock_upgrade_until(t))
- {
- }
- template <class Rep, class Period>
- upgrade_lock(Mutex& mtx, const chrono::duration<Rep, Period>& d)
- : m(&mtx), is_locked(mtx.try_lock_upgrade_for(d))
- {
- }
-#endif
-
- upgrade_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT:
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- BOOST_THREAD_RV(other).is_locked=false;
- BOOST_THREAD_RV(other).m=0;
- }
-
- BOOST_THREAD_EXPLICIT_LOCK_CONVERSION upgrade_lock(BOOST_THREAD_RV_REF_BEG unique_lock<Mutex> BOOST_THREAD_RV_REF_END other):
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- if(is_locked)
- {
- m->unlock_and_lock_upgrade();
- }
- BOOST_THREAD_RV(other).is_locked=false;
- BOOST_THREAD_RV(other).m=0;
- }
-
- upgrade_lock& operator=(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT
- {
- upgrade_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-
-#ifndef BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
- upgrade_lock& operator=(BOOST_THREAD_RV_REF_BEG unique_lock<Mutex> BOOST_THREAD_RV_REF_END other)
- {
- upgrade_lock temp(::boost::move(other));
- swap(temp);
- return *this;
- }
-#endif
-
-#ifdef BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
- // Conversion from shared locking
- upgrade_lock(BOOST_THREAD_RV_REF_BEG shared_lock<mutex_type> BOOST_THREAD_RV_REF_END sl, try_to_lock_t)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(sl).owns_lock()) {
- if (BOOST_THREAD_RV(sl).mutex()->try_unlock_shared_and_lock_upgrade())
- {
- m = BOOST_THREAD_RV(sl).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(sl).release();
- }
- }
-
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Clock, class Duration>
- upgrade_lock(BOOST_THREAD_RV_REF_BEG shared_lock<mutex_type> BOOST_THREAD_RV_REF_END sl,
- const chrono::time_point<Clock, Duration>& abs_time)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(sl).owns_lock()) {
- if (BOOST_THREAD_RV(sl).mutex()->try_unlock_shared_and_lock_upgrade_until(abs_time))
- {
- m = BOOST_THREAD_RV(sl).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(sl).release();
- }
- }
-
- template <class Rep, class Period>
- upgrade_lock(BOOST_THREAD_RV_REF_BEG shared_lock<mutex_type> BOOST_THREAD_RV_REF_END sl,
- const chrono::duration<Rep, Period>& rel_time)
- : m(0),is_locked(false)
- {
- if (BOOST_THREAD_RV(sl).owns_lock()) {
- if (BOOST_THREAD_RV(sl).mutex()->try_unlock_shared_and_lock_upgrade_for(rel_time))
- {
- m = BOOST_THREAD_RV(sl).release();
- is_locked = true;
- }
- }
- else
- {
- m = BOOST_THREAD_RV(sl).release();
- }
- }
-#endif // BOOST_THREAD_USES_CHRONO
-#endif // BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
-
- void swap(upgrade_lock& other) BOOST_NOEXCEPT
- {
- std::swap(m,other.m);
- std::swap(is_locked,other.is_locked);
- }
- Mutex* mutex() const BOOST_NOEXCEPT
- {
- return m;
- }
-
- Mutex* release() BOOST_NOEXCEPT
- {
- Mutex* const res=m;
- m=0;
- is_locked=false;
- return res;
- }
- ~upgrade_lock()
- {
- if(owns_lock())
- {
- m->unlock_upgrade();
- }
- }
- void lock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost upgrade_lock owns already the mutex"));
- }
- m->lock_upgrade();
- is_locked=true;
- }
- bool try_lock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost upgrade_lock owns already the mutex"));
- }
- is_locked=m->try_lock_upgrade();
- return is_locked;
- }
- void unlock()
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(!owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost upgrade_lock doesn't own the mutex"));
- }
- m->unlock_upgrade();
- is_locked=false;
- }
-#ifdef BOOST_THREAD_USES_CHRONO
- template <class Rep, class Period>
- bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->try_lock_upgrade_for(rel_time);
- return is_locked;
- }
- template <class Clock, class Duration>
- bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time)
- {
- if(m==0)
- {
- boost::throw_exception(boost::lock_error(system::errc::operation_not_permitted, "boost shared_lock has no mutex"));
- }
- if(owns_lock())
- {
- boost::throw_exception(boost::lock_error(system::errc::resource_deadlock_would_occur, "boost shared_lock owns already the mutex"));
- }
- is_locked=m->try_lock_upgrade_until(abs_time);
- return is_locked;
- }
-#endif
-#if defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
- typedef void (upgrade_lock::*bool_type)();
- operator bool_type() const BOOST_NOEXCEPT
- {
- return is_locked?&upgrade_lock::lock:0;
- }
- bool operator!() const BOOST_NOEXCEPT
- {
- return !owns_lock();
- }
-#else
- explicit operator bool() const BOOST_NOEXCEPT
- {
- return owns_lock();
- }
-#endif
- bool owns_lock() const BOOST_NOEXCEPT
- {
- return is_locked;
- }
- friend class shared_lock<Mutex>;
- friend class unique_lock<Mutex>;
- };
-
- template<typename Mutex>
- void swap(upgrade_lock<Mutex>& lhs,upgrade_lock<Mutex>& rhs) BOOST_NOEXCEPT
- {
- lhs.swap(rhs);
- }
-
- BOOST_THREAD_DCL_MOVABLE_BEG(Mutex) upgrade_lock<Mutex> BOOST_THREAD_DCL_MOVABLE_END
-
- template<typename Mutex>
- unique_lock<Mutex>::unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_lock<Mutex> BOOST_THREAD_RV_REF_END other):
- m(BOOST_THREAD_RV(other).m),is_locked(BOOST_THREAD_RV(other).is_locked)
- {
- if(is_locked)
- {
- m->unlock_upgrade_and_lock();
- }
- BOOST_THREAD_RV(other).release();
- }
-
- template <class Mutex>
- class upgrade_to_unique_lock
- {
- private:
- upgrade_lock<Mutex>* source;
- unique_lock<Mutex> exclusive;
-
- public:
- typedef Mutex mutex_type;
- BOOST_THREAD_MOVABLE_ONLY(upgrade_to_unique_lock)
-
- explicit upgrade_to_unique_lock(upgrade_lock<Mutex>& m_):
- source(&m_),exclusive(::boost::move(*source))
- {}
- ~upgrade_to_unique_lock()
- {
- if(source)
- {
- *source=BOOST_THREAD_MAKE_RV_REF(upgrade_lock<Mutex>(::boost::move(exclusive)));
- }
- }
-
- upgrade_to_unique_lock(BOOST_THREAD_RV_REF_BEG upgrade_to_unique_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT:
- source(BOOST_THREAD_RV(other).source),exclusive(::boost::move(BOOST_THREAD_RV(other).exclusive))
- {
- BOOST_THREAD_RV(other).source=0;
- }
-
- upgrade_to_unique_lock& operator=(BOOST_THREAD_RV_REF_BEG upgrade_to_unique_lock<Mutex> BOOST_THREAD_RV_REF_END other) BOOST_NOEXCEPT
- {
- upgrade_to_unique_lock temp(other);
- swap(temp);
- return *this;
- }
-
- void swap(upgrade_to_unique_lock& other) BOOST_NOEXCEPT
- {
- std::swap(source,other.source);
- exclusive.swap(other.exclusive);
- }
-
-#if defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
- typedef void (upgrade_to_unique_lock::*bool_type)(upgrade_to_unique_lock&);
- operator bool_type() const BOOST_NOEXCEPT
- {
- return exclusive.owns_lock()?&upgrade_to_unique_lock::swap:0;
- }
- bool operator!() const BOOST_NOEXCEPT
- {
- return !owns_lock();
- }
-#else
- explicit operator bool() const BOOST_NOEXCEPT
- {
- return owns_lock();
- }
-#endif
-
- bool owns_lock() const BOOST_NOEXCEPT
- {
- return exclusive.owns_lock();
- }
- };
-
- BOOST_THREAD_DCL_MOVABLE_BEG(Mutex) upgrade_to_unique_lock<Mutex> BOOST_THREAD_DCL_MOVABLE_END
-
- namespace detail
- {
- template<typename Mutex>
- class try_lock_wrapper:
- private unique_lock<Mutex>
- {
- typedef unique_lock<Mutex> base;
- public:
- BOOST_THREAD_MOVABLE_ONLY(try_lock_wrapper)
-
- try_lock_wrapper()
- {}
-
- explicit try_lock_wrapper(Mutex& m):
- base(m,try_to_lock)
- {}
-
- try_lock_wrapper(Mutex& m_,adopt_lock_t):
- base(m_,adopt_lock)
- {}
- try_lock_wrapper(Mutex& m_,defer_lock_t):
- base(m_,defer_lock)
- {}
- try_lock_wrapper(Mutex& m_,try_to_lock_t):
- base(m_,try_to_lock)
- {}
-#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
- try_lock_wrapper(BOOST_THREAD_RV_REF(try_lock_wrapper) other):
- base(::boost::move(other))
- {}
-
-#elif defined BOOST_THREAD_USES_MOVE
- try_lock_wrapper(BOOST_THREAD_RV_REF(try_lock_wrapper) other):
- base(::boost::move(static_cast<base&>(other)))
- {}
-
-#else
- try_lock_wrapper(BOOST_THREAD_RV_REF(try_lock_wrapper) other):
- base(BOOST_THREAD_RV_REF(base)(*other))
- {}
-#endif
- try_lock_wrapper& operator=(BOOST_THREAD_RV_REF_BEG try_lock_wrapper<Mutex> BOOST_THREAD_RV_REF_END other)
- {
- try_lock_wrapper temp(other);
- swap(temp);
- return *this;
- }
- void swap(try_lock_wrapper& other)
- {
- base::swap(other);
- }
- void lock()
- {
- base::lock();
- }
- bool try_lock()
- {
- return base::try_lock();
- }
- void unlock()
- {
- base::unlock();
- }
- bool owns_lock() const
- {
- return base::owns_lock();
- }
- Mutex* mutex() const
- {
- return base::mutex();
- }
- Mutex* release()
- {
- return base::release();
- }
-
-#if defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
- typedef typename base::bool_type bool_type;
- operator bool_type() const
- {
- return base::operator bool_type();
- }
- bool operator!() const
- {
- return !this->owns_lock();
- }
-#else
- explicit operator bool() const
- {
- return owns_lock();
- }
-#endif
- };
-
- template<typename Mutex>
- void swap(try_lock_wrapper<Mutex>& lhs,try_lock_wrapper<Mutex>& rhs)
- {
- lhs.swap(rhs);
- }
-
- template<typename MutexType1,typename MutexType2>
- unsigned try_lock_internal(MutexType1& m1,MutexType2& m2)
- {
- boost::unique_lock<MutexType1> l1(m1,boost::try_to_lock);
- if(!l1)
- {
- return 1;
- }
- if(!m2.try_lock())
- {
- return 2;
- }
- l1.release();
- return 0;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3>
- unsigned try_lock_internal(MutexType1& m1,MutexType2& m2,MutexType3& m3)
- {
- boost::unique_lock<MutexType1> l1(m1,boost::try_to_lock);
- if(!l1)
- {
- return 1;
- }
- if(unsigned const failed_lock=try_lock_internal(m2,m3))
- {
- return failed_lock+1;
- }
- l1.release();
- return 0;
- }
-
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,
- typename MutexType4>
- unsigned try_lock_internal(MutexType1& m1,MutexType2& m2,MutexType3& m3,
- MutexType4& m4)
- {
- boost::unique_lock<MutexType1> l1(m1,boost::try_to_lock);
- if(!l1)
- {
- return 1;
- }
- if(unsigned const failed_lock=try_lock_internal(m2,m3,m4))
- {
- return failed_lock+1;
- }
- l1.release();
- return 0;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,
- typename MutexType4,typename MutexType5>
- unsigned try_lock_internal(MutexType1& m1,MutexType2& m2,MutexType3& m3,
- MutexType4& m4,MutexType5& m5)
- {
- boost::unique_lock<MutexType1> l1(m1,boost::try_to_lock);
- if(!l1)
- {
- return 1;
- }
- if(unsigned const failed_lock=try_lock_internal(m2,m3,m4,m5))
- {
- return failed_lock+1;
- }
- l1.release();
- return 0;
- }
-
-
- template<typename MutexType1,typename MutexType2>
- unsigned lock_helper(MutexType1& m1,MutexType2& m2)
- {
- boost::unique_lock<MutexType1> l1(m1);
- if(!m2.try_lock())
- {
- return 1;
- }
- l1.release();
- return 0;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3>
- unsigned lock_helper(MutexType1& m1,MutexType2& m2,MutexType3& m3)
- {
- boost::unique_lock<MutexType1> l1(m1);
- if(unsigned const failed_lock=try_lock_internal(m2,m3))
- {
- return failed_lock;
- }
- l1.release();
- return 0;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,
- typename MutexType4>
- unsigned lock_helper(MutexType1& m1,MutexType2& m2,MutexType3& m3,
- MutexType4& m4)
- {
- boost::unique_lock<MutexType1> l1(m1);
- if(unsigned const failed_lock=try_lock_internal(m2,m3,m4))
- {
- return failed_lock;
- }
- l1.release();
- return 0;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,
- typename MutexType4,typename MutexType5>
- unsigned lock_helper(MutexType1& m1,MutexType2& m2,MutexType3& m3,
- MutexType4& m4,MutexType5& m5)
- {
- boost::unique_lock<MutexType1> l1(m1);
- if(unsigned const failed_lock=try_lock_internal(m2,m3,m4,m5))
- {
- return failed_lock;
- }
- l1.release();
- return 0;
- }
- }
-
- namespace detail
- {
- template<bool x>
- struct is_mutex_type_wrapper
- {};
-
- template<typename MutexType1,typename MutexType2>
- void lock_impl(MutexType1& m1,MutexType2& m2,is_mutex_type_wrapper<true>)
- {
- unsigned const lock_count=2;
- unsigned lock_first=0;
- for(;;)
- {
- switch(lock_first)
- {
- case 0:
- lock_first=detail::lock_helper(m1,m2);
- if(!lock_first)
- return;
- break;
- case 1:
- lock_first=detail::lock_helper(m2,m1);
- if(!lock_first)
- return;
- lock_first=(lock_first+1)%lock_count;
- break;
- }
- }
- }
-
- template<typename Iterator>
- void lock_impl(Iterator begin,Iterator end,is_mutex_type_wrapper<false>);
- }
-
-
- template<typename MutexType1,typename MutexType2>
- void lock(MutexType1& m1,MutexType2& m2)
- {
- detail::lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2>
- void lock(const MutexType1& m1,MutexType2& m2)
- {
- detail::lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2>
- void lock(MutexType1& m1,const MutexType2& m2)
- {
- detail::lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2>
- void lock(const MutexType1& m1,const MutexType2& m2)
- {
- detail::lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3>
- void lock(MutexType1& m1,MutexType2& m2,MutexType3& m3)
- {
- unsigned const lock_count=3;
- unsigned lock_first=0;
- for(;;)
- {
- switch(lock_first)
- {
- case 0:
- lock_first=detail::lock_helper(m1,m2,m3);
- if(!lock_first)
- return;
- break;
- case 1:
- lock_first=detail::lock_helper(m2,m3,m1);
- if(!lock_first)
- return;
- lock_first=(lock_first+1)%lock_count;
- break;
- case 2:
- lock_first=detail::lock_helper(m3,m1,m2);
- if(!lock_first)
- return;
- lock_first=(lock_first+2)%lock_count;
- break;
- }
- }
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,
- typename MutexType4>
- void lock(MutexType1& m1,MutexType2& m2,MutexType3& m3,
- MutexType4& m4)
- {
- unsigned const lock_count=4;
- unsigned lock_first=0;
- for(;;)
- {
- switch(lock_first)
- {
- case 0:
- lock_first=detail::lock_helper(m1,m2,m3,m4);
- if(!lock_first)
- return;
- break;
- case 1:
- lock_first=detail::lock_helper(m2,m3,m4,m1);
- if(!lock_first)
- return;
- lock_first=(lock_first+1)%lock_count;
- break;
- case 2:
- lock_first=detail::lock_helper(m3,m4,m1,m2);
- if(!lock_first)
- return;
- lock_first=(lock_first+2)%lock_count;
- break;
- case 3:
- lock_first=detail::lock_helper(m4,m1,m2,m3);
- if(!lock_first)
- return;
- lock_first=(lock_first+3)%lock_count;
- break;
- }
- }
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,
- typename MutexType4,typename MutexType5>
- void lock(MutexType1& m1,MutexType2& m2,MutexType3& m3,
- MutexType4& m4,MutexType5& m5)
- {
- unsigned const lock_count=5;
- unsigned lock_first=0;
- for(;;)
- {
- switch(lock_first)
- {
- case 0:
- lock_first=detail::lock_helper(m1,m2,m3,m4,m5);
- if(!lock_first)
- return;
- break;
- case 1:
- lock_first=detail::lock_helper(m2,m3,m4,m5,m1);
- if(!lock_first)
- return;
- lock_first=(lock_first+1)%lock_count;
- break;
- case 2:
- lock_first=detail::lock_helper(m3,m4,m5,m1,m2);
- if(!lock_first)
- return;
- lock_first=(lock_first+2)%lock_count;
- break;
- case 3:
- lock_first=detail::lock_helper(m4,m5,m1,m2,m3);
- if(!lock_first)
- return;
- lock_first=(lock_first+3)%lock_count;
- break;
- case 4:
- lock_first=detail::lock_helper(m5,m1,m2,m3,m4);
- if(!lock_first)
- return;
- lock_first=(lock_first+4)%lock_count;
- break;
- }
- }
- }
-
- namespace detail
- {
- template<typename Mutex,bool x=is_mutex_type<Mutex>::value>
- struct try_lock_impl_return
- {
- typedef int type;
- };
-
- template<typename Iterator>
- struct try_lock_impl_return<Iterator,false>
- {
- typedef Iterator type;
- };
-
- template<typename MutexType1,typename MutexType2>
- int try_lock_impl(MutexType1& m1,MutexType2& m2,is_mutex_type_wrapper<true>)
- {
- return ((int)detail::try_lock_internal(m1,m2))-1;
- }
-
- template<typename Iterator>
- Iterator try_lock_impl(Iterator begin,Iterator end,is_mutex_type_wrapper<false>);
- }
-
- template<typename MutexType1,typename MutexType2>
- typename detail::try_lock_impl_return<MutexType1>::type try_lock(MutexType1& m1,MutexType2& m2)
- {
- return detail::try_lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2>
- typename detail::try_lock_impl_return<MutexType1>::type try_lock(const MutexType1& m1,MutexType2& m2)
- {
- return detail::try_lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2>
- typename detail::try_lock_impl_return<MutexType1>::type try_lock(MutexType1& m1,const MutexType2& m2)
- {
- return detail::try_lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2>
- typename detail::try_lock_impl_return<MutexType1>::type try_lock(const MutexType1& m1,const MutexType2& m2)
- {
- return detail::try_lock_impl(m1,m2,detail::is_mutex_type_wrapper<is_mutex_type<MutexType1>::value>());
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3>
- int try_lock(MutexType1& m1,MutexType2& m2,MutexType3& m3)
- {
- return ((int)detail::try_lock_internal(m1,m2,m3))-1;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,typename MutexType4>
- int try_lock(MutexType1& m1,MutexType2& m2,MutexType3& m3,MutexType4& m4)
- {
- return ((int)detail::try_lock_internal(m1,m2,m3,m4))-1;
- }
-
- template<typename MutexType1,typename MutexType2,typename MutexType3,typename MutexType4,typename MutexType5>
- int try_lock(MutexType1& m1,MutexType2& m2,MutexType3& m3,MutexType4& m4,MutexType5& m5)
- {
- return ((int)detail::try_lock_internal(m1,m2,m3,m4,m5))-1;
- }
-
-
- namespace detail
- {
- template<typename Iterator>
- struct range_lock_guard
- {
- Iterator begin;
- Iterator end;
-
- range_lock_guard(Iterator begin_,Iterator end_):
- begin(begin_),end(end_)
- {
- boost::lock(begin,end);
- }
-
- void release()
- {
- begin=end;
- }
-
- ~range_lock_guard()
- {
- for(;begin!=end;++begin)
- {
- begin->unlock();
- }
- }
- };
-
- template<typename Iterator>
- Iterator try_lock_impl(Iterator begin,Iterator end,is_mutex_type_wrapper<false>)
-
- {
- if(begin==end)
- {
- return end;
- }
- typedef typename std::iterator_traits<Iterator>::value_type lock_type;
- unique_lock<lock_type> guard(*begin,try_to_lock);
-
- if(!guard.owns_lock())
- {
- return begin;
- }
- Iterator const failed=boost::try_lock(++begin,end);
- if(failed==end)
- {
- guard.release();
- }
-
- return failed;
- }
- }
-
-
- namespace detail
- {
- template<typename Iterator>
- void lock_impl(Iterator begin,Iterator end,is_mutex_type_wrapper<false>)
- {
- typedef typename std::iterator_traits<Iterator>::value_type lock_type;
-
- if(begin==end)
- {
- return;
- }
- bool start_with_begin=true;
- Iterator second=begin;
- ++second;
- Iterator next=second;
-
- for(;;)
- {
- unique_lock<lock_type> begin_lock(*begin,defer_lock);
- if(start_with_begin)
- {
- begin_lock.lock();
- Iterator const failed_lock=boost::try_lock(next,end);
- if(failed_lock==end)
- {
- begin_lock.release();
- return;
- }
- start_with_begin=false;
- next=failed_lock;
- }
- else
- {
- detail::range_lock_guard<Iterator> guard(next,end);
- if(begin_lock.try_lock())
- {
- Iterator const failed_lock=boost::try_lock(second,next);
- if(failed_lock==next)
- {
- begin_lock.release();
- guard.release();
- return;
- }
- start_with_begin=false;
- next=failed_lock;
- }
- else
- {
- start_with_begin=true;
- next=second;
- }
- }
- }
- }
-
- }
-}
-#include <boost/config/abi_suffix.hpp>
+#include <boost/thread/lock_algorithms.hpp>
+#include <boost/thread/lock_types.hpp>
+#include <boost/thread/lock_guard.hpp>
+#include <boost/thread/lockable_traits.hpp>
+#include <boost/thread/lock_options.hpp>
#endif
Modified: branches/release/boost/thread/mutex.hpp
==============================================================================
--- branches/release/boost/thread/mutex.hpp (original)
+++ branches/release/boost/thread/mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,7 +3,7 @@
// mutex.hpp
//
-// (C) Copyright 2007 Anthony Williams
+// (C) Copyright 2007 Anthony Williams
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at
@@ -18,4 +18,36 @@
#error "Boost threads unavailable on this platform"
#endif
+#include <boost/thread/lockable_traits.hpp>
+
+
+namespace boost
+{
+ namespace sync
+ {
+#ifdef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
+ template<>
+ struct is_basic_lockable<mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_lockable<mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_basic_lockable<timed_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_lockable<timed_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+#endif
+ }
+}
+
#endif
Modified: branches/release/boost/thread/pthread/condition_variable.hpp
==============================================================================
--- branches/release/boost/thread/pthread/condition_variable.hpp (original)
+++ branches/release/boost/thread/pthread/condition_variable.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,11 +4,13 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
// (C) Copyright 2007-10 Anthony Williams
-// (C) Copyright 2011 Vicente J. Botet Escriba
+// (C) Copyright 2011-2012 Vicente J. Botet Escriba
#include <boost/thread/pthread/timespec.hpp>
#include <boost/thread/pthread/pthread_mutex_scoped_lock.hpp>
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
#include <boost/thread/pthread/thread_data.hpp>
+#endif
#include <boost/thread/pthread/condition_variable_fwd.hpp>
#ifdef BOOST_THREAD_USES_CHRONO
#include <boost/chrono/system_clocks.hpp>
@@ -20,10 +22,12 @@
namespace boost
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
namespace this_thread
{
void BOOST_THREAD_DECL interruption_point();
}
+#endif
namespace thread_cv_detail
{
@@ -56,34 +60,44 @@
int res=0;
{
thread_cv_detail::lock_on_exit<unique_lock<mutex> > guard;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
detail::interruption_checker check_for_interruption(&internal_mutex,&cond);
+#endif
guard.activate(m);
do {
res = pthread_cond_wait(&cond,&internal_mutex);
} while (res == EINTR);
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
this_thread::interruption_point();
+#endif
if(res)
{
boost::throw_exception(condition_error(res, "boost:: condition_variable constructor failed in pthread_cond_wait"));
}
}
- inline bool condition_variable::do_timed_wait(
+ inline bool condition_variable::do_wait_until(
unique_lock<mutex>& m,
struct timespec const &timeout)
{
if (!m.owns_lock())
- boost::throw_exception(condition_error(EPERM, "condition_variable do_timed_wait: mutex not locked"));
+ {
+ boost::throw_exception(condition_error(EPERM, "condition_variable do_wait_until: mutex not locked"));
+ }
thread_cv_detail::lock_on_exit<unique_lock<mutex> > guard;
int cond_res;
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
detail::interruption_checker check_for_interruption(&internal_mutex,&cond);
+#endif
guard.activate(m);
cond_res=pthread_cond_timedwait(&cond,&internal_mutex,&timeout);
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
this_thread::interruption_point();
+#endif
if(cond_res==ETIMEDOUT)
{
return false;
@@ -140,11 +154,15 @@
int res=0;
{
thread_cv_detail::lock_on_exit<lock_type> guard;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
detail::interruption_checker check_for_interruption(&internal_mutex,&cond);
+#endif
guard.activate(m);
res=pthread_cond_wait(&cond,&internal_mutex);
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
this_thread::interruption_point();
+#endif
if(res)
{
boost::throw_exception(condition_error(res, "condition_variable_any failed in pthread_cond_wait"));
@@ -157,11 +175,12 @@
while(!pred()) wait(m);
}
+#if defined BOOST_THREAD_USES_DATETIME
template<typename lock_type>
bool timed_wait(lock_type& m,boost::system_time const& wait_until)
{
- struct timespec const timeout=detail::get_timespec(wait_until);
- return do_timed_wait(m, timeout);
+ struct timespec const timeout=detail::to_timespec(wait_until);
+ return do_wait_until(m, timeout);
}
template<typename lock_type>
bool timed_wait(lock_type& m,xtime const& wait_until)
@@ -197,7 +216,7 @@
{
return timed_wait(m,get_system_time()+wait_duration,pred);
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class lock_type,class Duration>
cv_status
@@ -274,17 +293,15 @@
}
template <class lock_type>
- inline void wait_until(
+ cv_status wait_until(
lock_type& lk,
chrono::time_point<chrono::system_clock, chrono::nanoseconds> tp)
{
using namespace chrono;
nanoseconds d = tp.time_since_epoch();
- timespec ts;
- seconds s = duration_cast<seconds>(d);
- ts.tv_sec = static_cast<long>(s.count());
- ts.tv_nsec = static_cast<long>((d - s).count());
- do_timed_wait(lk, ts);
+ timespec ts = boost::detail::to_timespec(d);
+ if (do_wait_until(lk, ts)) return cv_status::no_timeout;
+ else return cv_status::timeout;
}
#endif
@@ -302,18 +319,22 @@
private: // used by boost::thread::try_join_until
template <class lock_type>
- inline bool do_timed_wait(
+ inline bool do_wait_until(
lock_type& m,
struct timespec const &timeout)
{
int res=0;
{
thread_cv_detail::lock_on_exit<lock_type> guard;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
detail::interruption_checker check_for_interruption(&internal_mutex,&cond);
+#endif
guard.activate(m);
res=pthread_cond_timedwait(&cond,&internal_mutex,&timeout);
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
this_thread::interruption_point();
+#endif
if(res==ETIMEDOUT)
{
return false;
Modified: branches/release/boost/thread/pthread/condition_variable_fwd.hpp
==============================================================================
--- branches/release/boost/thread/pthread/condition_variable_fwd.hpp (original)
+++ branches/release/boost/thread/pthread/condition_variable_fwd.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,15 +4,16 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
// (C) Copyright 2007-8 Anthony Williams
-// (C) Copyright 2011 Vicente J. Botet Escriba
+// (C) Copyright 2011-2012 Vicente J. Botet Escriba
#include <boost/assert.hpp>
#include <boost/throw_exception.hpp>
#include <pthread.h>
#include <boost/thread/cv_status.hpp>
#include <boost/thread/mutex.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/thread_time.hpp>
+#include <boost/thread/pthread/timespec.hpp>
#include <boost/thread/xtime.hpp>
#ifdef BOOST_THREAD_USES_CHRONO
#include <boost/chrono/system_clocks.hpp>
@@ -32,6 +33,20 @@
pthread_cond_t cond;
public:
+ //private: // used by boost::thread::try_join_until
+
+ inline bool do_wait_until(
+ unique_lock<mutex>& lock,
+ struct timespec const &timeout);
+
+ bool do_wait_for(
+ unique_lock<mutex>& lock,
+ struct timespec const &timeout)
+ {
+ return do_wait_until(lock, boost::detail::timespec_plus(timeout, boost::detail::timespec_now()));
+ }
+
+ public:
BOOST_THREAD_NO_COPYABLE(condition_variable)
condition_variable()
{
@@ -66,16 +81,17 @@
}
+#if defined BOOST_THREAD_USES_DATETIME
inline bool timed_wait(
unique_lock<mutex>& m,
boost::system_time const& wait_until)
{
#if defined BOOST_THREAD_WAIT_BUG
- struct timespec const timeout=detail::get_timespec(wait_until + BOOST_THREAD_WAIT_BUG);
- return do_timed_wait(m, timeout);
+ struct timespec const timeout=detail::to_timespec(wait_until + BOOST_THREAD_WAIT_BUG);
+ return do_wait_until(m, timeout);
#else
- struct timespec const timeout=detail::get_timespec(wait_until);
- return do_timed_wait(m, timeout);
+ struct timespec const timeout=detail::to_timespec(wait_until);
+ return do_wait_until(m, timeout);
#endif
}
bool timed_wait(
@@ -121,6 +137,7 @@
{
return timed_wait(m,get_system_time()+wait_duration,pred);
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
@@ -210,24 +227,17 @@
void notify_all() BOOST_NOEXCEPT;
#ifdef BOOST_THREAD_USES_CHRONO
- inline void wait_until(
+ inline cv_status wait_until(
unique_lock<mutex>& lk,
chrono::time_point<chrono::system_clock, chrono::nanoseconds> tp)
{
using namespace chrono;
nanoseconds d = tp.time_since_epoch();
- timespec ts;
- seconds s = duration_cast<seconds>(d);
- ts.tv_sec = static_cast<long>(s.count());
- ts.tv_nsec = static_cast<long>((d - s).count());
- do_timed_wait(lk, ts);
+ timespec ts = boost::detail::to_timespec(d);
+ if (do_wait_until(lk, ts)) return cv_status::no_timeout;
+ else return cv_status::timeout;
}
#endif
- //private: // used by boost::thread::try_join_until
-
- inline bool do_timed_wait(
- unique_lock<mutex>& lock,
- struct timespec const &timeout);
};
BOOST_THREAD_DECL void notify_all_at_thread_exit(condition_variable& cond, unique_lock<mutex> lk);
Modified: branches/release/boost/thread/pthread/mutex.hpp
==============================================================================
--- branches/release/boost/thread/pthread/mutex.hpp (original)
+++ branches/release/boost/thread/pthread/mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,10 +6,13 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#include <boost/thread/detail/config.hpp>
#include <pthread.h>
#include <boost/throw_exception.hpp>
#include <boost/thread/exceptions.hpp>
-#include <boost/thread/locks.hpp>
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
+#include <boost/thread/lock_types.hpp>
+#endif
#include <boost/thread/thread_time.hpp>
#include <boost/thread/xtime.hpp>
#include <boost/assert.hpp>
@@ -71,12 +74,15 @@
void unlock()
{
- int ret;
+ int res;
do
{
- ret = pthread_mutex_unlock(&m);
- } while (ret == EINTR);
- BOOST_VERIFY(!ret);
+ res = pthread_mutex_unlock(&m);
+ } while (res == EINTR);
+ if (res)
+ {
+ boost::throw_exception(lock_error(res,"boost: mutex unlock failed in pthread_mutex_lock"));
+ }
}
bool try_lock()
@@ -86,12 +92,8 @@
{
res = pthread_mutex_trylock(&m);
} while (res == EINTR);
- if(res && (res!=EBUSY))
+ if (res==EBUSY)
{
- // The following throw_exception has been replaced by an assertion and just return false,
- // as this is an internal error and the user can do nothing with the exception.
- //boost::throw_exception(lock_error(res,"boost: mutex try_lock failed in pthread_mutex_trylock"));
- BOOST_ASSERT_MSG(false ,"boost: mutex try_lock failed in pthread_mutex_trylock");
return false;
}
@@ -105,8 +107,10 @@
return &m;
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<mutex> scoped_lock;
typedef detail::try_lock_wrapper<mutex> scoped_try_lock;
+#endif
};
typedef mutex try_mutex;
@@ -146,6 +150,7 @@
#endif
}
+#if defined BOOST_THREAD_USES_DATETIME
template<typename TimeDuration>
bool timed_lock(TimeDuration const & relative_time)
{
@@ -155,23 +160,47 @@
{
return timed_lock(system_time(absolute_time));
}
-
+#endif
#ifdef BOOST_PTHREAD_HAS_TIMEDLOCK
void lock()
{
- BOOST_VERIFY(!pthread_mutex_lock(&m));
+ int res;
+ do
+ {
+ res = pthread_mutex_lock(&m);
+ } while (res == EINTR);
+ if (res)
+ {
+ boost::throw_exception(lock_error(res,"boost: mutex lock failed in pthread_mutex_lock"));
+ }
}
void unlock()
{
- BOOST_VERIFY(!pthread_mutex_unlock(&m));
+ int res;
+ do
+ {
+ res = pthread_mutex_unlock(&m);
+ } while (res == EINTR);
+ if (res)
+ {
+ boost::throw_exception(lock_error(res,"boost: mutex unlock failed in pthread_mutex_lock"));
+ }
}
bool try_lock()
{
- int const res=pthread_mutex_trylock(&m);
- BOOST_ASSERT(!res || res==EBUSY);
- return !res;
+ int res;
+ do
+ {
+ res = pthread_mutex_trylock(&m);
+ } while (res == EINTR);
+ if (res==EBUSY)
+ {
+ return false;
+ }
+
+ return !res;
}
@@ -232,12 +261,13 @@
public:
#endif
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock(system_time const & abs_time)
{
- struct timespec const ts=detail::get_timespec(abs_time);
+ struct timespec const ts=boost::detail::to_timespec(abs_time);
return do_try_lock_until(ts);
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
@@ -261,12 +291,9 @@
}
bool try_lock_until(const chrono::time_point<chrono::system_clock, chrono::nanoseconds>& tp)
{
- using namespace chrono;
- nanoseconds d = tp.time_since_epoch();
- timespec ts;
- seconds s = duration_cast<seconds>(d);
- ts.tv_sec = static_cast<long>(s.count());
- ts.tv_nsec = static_cast<long>((d - s).count());
+ //using namespace chrono;
+ chrono::nanoseconds d = tp.time_since_epoch();
+ timespec ts = boost::detail::to_timespec(d);
return do_try_lock_until(ts);
}
#endif
@@ -278,9 +305,11 @@
return &m;
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<timed_mutex> scoped_timed_lock;
typedef detail::try_lock_wrapper<timed_mutex> scoped_try_lock;
typedef scoped_timed_lock scoped_lock;
+#endif
};
}
Modified: branches/release/boost/thread/pthread/recursive_mutex.hpp
==============================================================================
--- branches/release/boost/thread/pthread/recursive_mutex.hpp (original)
+++ branches/release/boost/thread/pthread/recursive_mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -9,7 +9,9 @@
#include <pthread.h>
#include <boost/throw_exception.hpp>
#include <boost/thread/exceptions.hpp>
-#include <boost/thread/locks.hpp>
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
+#include <boost/thread/lock_types.hpp>
+#endif
#include <boost/thread/thread_time.hpp>
#include <boost/assert.hpp>
#ifndef _WIN32
@@ -167,8 +169,10 @@
#endif
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<recursive_mutex> scoped_lock;
typedef detail::try_lock_wrapper<recursive_mutex> scoped_try_lock;
+#endif
};
typedef recursive_mutex recursive_try_mutex;
@@ -232,11 +236,13 @@
#endif
}
+#if defined BOOST_THREAD_USES_DATETIME
template<typename TimeDuration>
bool timed_lock(TimeDuration const & relative_time)
{
return timed_lock(get_system_time()+relative_time);
}
+#endif
#ifdef BOOST_USE_PTHREAD_RECURSIVE_TIMEDLOCK
void lock()
@@ -334,12 +340,13 @@
#endif
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock(system_time const & abs_time)
{
- struct timespec const ts=detail::get_timespec(abs_time);
+ struct timespec const ts=detail::to_timespec(abs_time);
return do_try_lock_until(ts);
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
@@ -363,12 +370,9 @@
}
bool try_lock_until(const chrono::time_point<chrono::system_clock, chrono::nanoseconds>& tp)
{
- using namespace chrono;
- nanoseconds d = tp.time_since_epoch();
- timespec ts;
- seconds s = duration_cast<seconds>(d);
- ts.tv_sec = static_cast<long>(s.count());
- ts.tv_nsec = static_cast<long>((d - s).count());
+ //using namespace chrono;
+ chrono::nanoseconds d = tp.time_since_epoch();
+ timespec ts = boost::detail::to_timespec(d);
return do_try_lock_until(ts);
}
#endif
@@ -380,9 +384,11 @@
return &m;
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<recursive_timed_mutex> scoped_timed_lock;
typedef detail::try_lock_wrapper<recursive_timed_mutex> scoped_try_lock;
typedef scoped_timed_lock scoped_lock;
+#endif
};
}
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-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -12,7 +12,9 @@
#include <boost/static_assert.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/condition_variable.hpp>
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
#include <boost/thread/detail/thread_interruption.hpp>
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
#include <boost/chrono/system_clocks.hpp>
#include <boost/chrono/ceil.hpp>
@@ -63,8 +65,10 @@
void lock_shared()
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.exclusive || state.exclusive_waiting_blocked)
{
@@ -75,7 +79,7 @@
bool try_lock_shared()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
if(state.exclusive || state.exclusive_waiting_blocked)
{
@@ -88,10 +92,13 @@
}
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock_shared(system_time const& timeout)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.exclusive || state.exclusive_waiting_blocked)
{
@@ -109,6 +116,7 @@
{
return timed_lock_shared(get_system_time()+relative_time);
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_lock_shared_for(const chrono::duration<Rep, Period>& rel_time)
@@ -118,8 +126,10 @@
template <class Clock, class Duration>
bool try_lock_shared_until(const chrono::time_point<Clock, Duration>& abs_time)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.exclusive || state.exclusive_waiting_blocked)
{
@@ -134,7 +144,7 @@
#endif
void unlock_shared()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
bool const last_reader=!--state.shared_count;
if(last_reader)
@@ -155,8 +165,10 @@
void lock()
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.shared_count || state.exclusive)
{
@@ -166,10 +178,13 @@
state.exclusive=true;
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock(system_time const& timeout)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.shared_count || state.exclusive)
{
@@ -194,7 +209,7 @@
{
return timed_lock(get_system_time()+relative_time);
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
@@ -204,8 +219,10 @@
template <class Clock, class Duration>
bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.shared_count || state.exclusive)
{
@@ -228,7 +245,7 @@
bool try_lock()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
if(state.shared_count || state.exclusive)
{
@@ -244,7 +261,7 @@
void unlock()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
state.exclusive=false;
state.exclusive_waiting_blocked=false;
release_waiters();
@@ -252,8 +269,10 @@
void lock_upgrade()
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.exclusive || state.exclusive_waiting_blocked || state.upgrade)
{
shared_cond.wait(lk);
@@ -262,10 +281,13 @@
state.upgrade=true;
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock_upgrade(system_time const& timeout)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.exclusive || state.exclusive_waiting_blocked || state.upgrade)
{
if(!shared_cond.timed_wait(lk,timeout))
@@ -287,7 +309,7 @@
{
return timed_lock_upgrade(get_system_time()+relative_time);
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_lock_upgrade_for(const chrono::duration<Rep, Period>& rel_time)
@@ -297,8 +319,10 @@
template <class Clock, class Duration>
bool try_lock_upgrade_until(const chrono::time_point<Clock, Duration>& abs_time)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
while(state.exclusive || state.exclusive_waiting_blocked || state.upgrade)
{
if(cv_status::timeout == shared_cond.wait_until(lk,abs_time))
@@ -317,7 +341,7 @@
#endif
bool try_lock_upgrade()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
if(state.exclusive || state.exclusive_waiting_blocked || state.upgrade)
{
return false;
@@ -332,7 +356,7 @@
void unlock_upgrade()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
state.upgrade=false;
bool const last_reader=!--state.shared_count;
@@ -348,8 +372,10 @@
// Upgrade <-> Exclusive
void unlock_upgrade_and_lock()
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
--state.shared_count;
while(state.shared_count)
{
@@ -361,7 +387,7 @@
void unlock_and_lock_upgrade()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
state.exclusive=false;
state.upgrade=true;
++state.shared_count;
@@ -371,7 +397,7 @@
bool try_unlock_upgrade_and_lock()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
if( !state.exclusive
&& !state.exclusive_waiting_blocked
&& state.upgrade
@@ -398,8 +424,10 @@
try_unlock_upgrade_and_lock_until(
const chrono::time_point<Clock, Duration>& abs_time)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
if (state.shared_count != 1)
{
for (;;)
@@ -422,7 +450,7 @@
// Shared <-> Exclusive
void unlock_and_lock_shared()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
state.exclusive=false;
++state.shared_count;
state.exclusive_waiting_blocked=false;
@@ -432,7 +460,7 @@
#ifdef BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
bool try_unlock_shared_and_lock()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
if( !state.exclusive
&& !state.exclusive_waiting_blocked
&& !state.upgrade
@@ -458,8 +486,10 @@
try_unlock_shared_and_lock_until(
const chrono::time_point<Clock, Duration>& abs_time)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
if (state.shared_count != 1)
{
for (;;)
@@ -483,7 +513,7 @@
// Shared <-> Upgrade
void unlock_upgrade_and_lock_shared()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
state.upgrade=false;
state.exclusive_waiting_blocked=false;
release_waiters();
@@ -492,7 +522,7 @@
#ifdef BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSIONS
bool try_unlock_shared_and_lock_upgrade()
{
- boost::mutex::scoped_lock lk(state_change);
+ boost::unique_lock<boost::mutex> lk(state_change);
if( !state.exclusive
&& !state.exclusive_waiting_blocked
&& !state.upgrade
@@ -517,8 +547,10 @@
try_unlock_shared_and_lock_upgrade_until(
const chrono::time_point<Clock, Duration>& abs_time)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
boost::this_thread::disable_interruption do_not_disturb;
- boost::mutex::scoped_lock lk(state_change);
+#endif
+ boost::unique_lock<boost::mutex> lk(state_change);
if( state.exclusive
|| state.exclusive_waiting_blocked
|| state.upgrade
Modified: branches/release/boost/thread/pthread/thread_data.hpp
==============================================================================
--- branches/release/boost/thread/pthread/thread_data.hpp (original)
+++ branches/release/boost/thread/pthread/thread_data.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,7 +8,8 @@
#include <boost/thread/detail/config.hpp>
#include <boost/thread/exceptions.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_guard.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/pthread/condition_variable_fwd.hpp>
@@ -24,6 +25,10 @@
#include <vector>
#include <utility>
+#if defined(__ANDROID__)
+#include <asm/page.h> // http://code.google.com/p/android/issues/detail?id=39983
+#endif
+
#include <pthread.h>
#include <unistd.h>
@@ -77,6 +82,7 @@
namespace detail
{
+ struct future_object_base;
struct tss_cleanup_function;
struct thread_exit_callback_node;
struct tss_data_node
@@ -107,8 +113,10 @@
bool joined;
boost::detail::thread_exit_callback_node* thread_exit_callbacks;
std::map<void const*,boost::detail::tss_data_node> tss_data;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
bool interrupt_enabled;
bool interrupt_requested;
+#endif
pthread_mutex_t* cond_mutex;
pthread_cond_t* current_cond;
typedef std::vector<std::pair<condition_variable*, mutex*>
@@ -116,27 +124,40 @@
> notify_list_t;
notify_list_t notify;
+ typedef std::vector<shared_ptr<future_object_base> > async_states_t;
+ async_states_t async_states_;
+
thread_data_base():
done(false),join_started(false),joined(false),
thread_exit_callbacks(0),
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
interrupt_enabled(true),
interrupt_requested(false),
+#endif
current_cond(0),
- notify()
+ notify(),
+ async_states_()
{}
virtual ~thread_data_base();
typedef pthread_t native_handle_type;
virtual void run()=0;
- void notify_all_at_thread_exit(condition_variable* cv, mutex* m)
+ virtual void notify_all_at_thread_exit(condition_variable* cv, mutex* m)
{
notify.push_back(std::pair<condition_variable*, mutex*>(cv, m));
}
+
+ void make_ready_at_thread_exit(shared_ptr<future_object_base> as)
+ {
+ async_states_.push_back(as);
+ }
+
};
BOOST_THREAD_DECL thread_data_base* get_current_thread_data();
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
class interruption_checker
{
thread_data_base* const thread_info;
@@ -189,70 +210,46 @@
}
};
}
+#endif
namespace this_thread
{
+ namespace hiden
+ {
+ void BOOST_THREAD_DECL sleep_for(const timespec& ts);
+ void BOOST_THREAD_DECL sleep_until(const timespec& ts);
+ }
+
#ifdef BOOST_THREAD_USES_CHRONO
+#ifdef BOOST_THREAD_SLEEP_FOR_IS_STEADY
+
inline
void BOOST_SYMBOL_VISIBLE sleep_for(const chrono::nanoseconds& ns)
{
- using namespace chrono;
- boost::detail::thread_data_base* const thread_info=boost::detail::get_current_thread_data();
-
- if(thread_info)
- {
- unique_lock<mutex> lk(thread_info->sleep_mutex);
- while(cv_status::no_timeout==thread_info->sleep_condition.wait_for(lk,ns)) {}
- }
- else
- {
- if (ns >= nanoseconds::zero())
- {
-
- # if defined(BOOST_HAS_PTHREAD_DELAY_NP)
- timespec ts;
- ts.tv_sec = static_cast<long>(duration_cast<seconds>(ns).count());
- ts.tv_nsec = static_cast<long>((ns - seconds(ts.tv_sec)).count());
- BOOST_VERIFY(!pthread_delay_np(&ts));
- # elif defined(BOOST_HAS_NANOSLEEP)
- timespec ts;
- ts.tv_sec = static_cast<long>(duration_cast<seconds>(ns).count());
- ts.tv_nsec = static_cast<long>((ns - seconds(ts.tv_sec)).count());
- // nanosleep takes a timespec that is an offset, not
- // an absolute time.
- nanosleep(&ts, 0);
- # else
- mutex mx;
- mutex::scoped_lock lock(mx);
- condition_variable cond;
- cond.wait_for(lock, ns);
- # endif
- }
- }
+ return boost::this_thread::hiden::sleep_for(boost::detail::to_timespec(ns));
}
#endif
+#endif // BOOST_THREAD_USES_CHRONO
+
void BOOST_THREAD_DECL yield() BOOST_NOEXCEPT;
+#if defined BOOST_THREAD_USES_DATETIME
#ifdef __DECXXX
/// Workaround of DECCXX issue of incorrect template substitution
- template<typename TimeDuration>
- inline void sleep(TimeDuration const& rel_time)
+ template<>
+#endif
+ inline void sleep(system_time const& abs_time)
{
- this_thread::sleep(get_system_time()+rel_time);
+ return boost::this_thread::hiden::sleep_until(boost::detail::to_timespec(abs_time));
}
- template<>
- void BOOST_THREAD_DECL sleep(system_time const& abs_time);
-#else
- void BOOST_THREAD_DECL sleep(system_time const& abs_time);
-
template<typename TimeDuration>
inline BOOST_SYMBOL_VISIBLE void sleep(TimeDuration const& rel_time)
{
this_thread::sleep(get_system_time()+rel_time);
}
-#endif
- }
+#endif // BOOST_THREAD_USES_DATETIME
+ } // this_thread
}
#include <boost/config/abi_suffix.hpp>
Modified: branches/release/boost/thread/pthread/timespec.hpp
==============================================================================
--- branches/release/boost/thread/pthread/timespec.hpp (original)
+++ branches/release/boost/thread/pthread/timespec.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -1,34 +1,118 @@
#ifndef BOOST_THREAD_PTHREAD_TIMESPEC_HPP
#define BOOST_THREAD_PTHREAD_TIMESPEC_HPP
-// (C) Copyright 2007-8 Anthony Williams
+// (C) Copyright 2007-8 Anthony Williams
+// (C) Copyright 2012 Vicente J. Botet Escriba
//
// 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/detail/config.hpp>
#include <boost/thread/thread_time.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/date_time/posix_time/conversion.hpp>
+#endif
#include <pthread.h>
#ifndef _WIN32
#include <unistd.h>
#endif
+#ifdef BOOST_THREAD_USES_CHRONO
+#include <boost/chrono/duration.hpp>
+#endif
+
+#if defined(macintosh) || defined(__APPLE__) || defined(__APPLE_CC__)
+# define BOOST_THREAD_TIMESPEC_MAC_API
+#include <sys/time.h> //for gettimeofday and timeval
+#else
+#include <time.h> // for clock_gettime
+#endif
#include <boost/config/abi_prefix.hpp>
namespace boost
{
- namespace detail
+ namespace detail
+ {
+#if defined BOOST_THREAD_USES_DATETIME
+ inline struct timespec to_timespec(boost::system_time const& abs_time)
+ {
+ struct timespec timeout = { 0,0};
+ boost::posix_time::time_duration const time_since_epoch=abs_time-boost::posix_time::from_time_t(0);
+
+ timeout.tv_sec=time_since_epoch.total_seconds();
+ timeout.tv_nsec=(long)(time_since_epoch.fractional_seconds()*(1000000000l/time_since_epoch.ticks_per_second()));
+ return timeout;
+ }
+#endif
+#if defined BOOST_THREAD_USES_CHRONO
+ inline timespec to_timespec(chrono::nanoseconds const& ns)
+ {
+ struct timespec ts;
+ ts.tv_sec = static_cast<long>(chrono::duration_cast<chrono::seconds>(ns).count());
+ ts.tv_nsec = static_cast<long>((ns - chrono::duration_cast<chrono::seconds>(ns)).count());
+ return ts;
+ }
+
+#endif
+
+ inline timespec to_timespec(boost::intmax_t const& ns)
+ {
+ boost::intmax_t s = ns / 1000000000l;
+ struct timespec ts;
+ ts.tv_sec = static_cast<long> (s);
+ ts.tv_nsec = static_cast<long> (ns - s * 1000000000l);
+ return ts;
+ }
+ inline boost::intmax_t to_nanoseconds_int_max(timespec const& ts)
+ {
+ return static_cast<boost::intmax_t>(ts.tv_sec) * 1000000000l + ts.tv_nsec;
+ }
+ inline bool timespec_ge_zero(timespec const& ts)
+ {
+ return (ts.tv_sec >= 0) || (ts.tv_nsec >= 0);
+ }
+ inline timespec timespec_now()
+ {
+ timespec ts;
+
+#if defined(BOOST_THREAD_TIMESPEC_MAC_API)
+ timeval tv;
+ ::gettimeofday(&tv, 0);
+ ts.tv_sec = tv.tv_sec;
+ ts.tv_nsec = tv.tv_usec * 1000;
+#else
+ if ( ::clock_gettime( CLOCK_REALTIME, &ts ) )
+ {
+ BOOST_ASSERT(0 && "Boost::Thread - Internal Error");
+ }
+#endif
+ return ts;
+ }
+ inline timespec timespec_zero()
+ {
+ timespec ts;
+ ts.tv_sec = 0;
+ ts.tv_nsec = 0;
+ return ts;
+ }
+ inline timespec timespec_plus(timespec const& lhs, timespec const& rhs)
+ {
+ return to_timespec(to_nanoseconds_int_max(lhs) + to_nanoseconds_int_max(rhs));
+ }
+ inline timespec timespec_minus(timespec const& lhs, timespec const& rhs)
+ {
+ return to_timespec(to_nanoseconds_int_max(lhs) - to_nanoseconds_int_max(rhs));
+ }
+ inline bool timespec_gt(timespec const& lhs, timespec const& rhs)
+ {
+ return to_nanoseconds_int_max(lhs) > to_nanoseconds_int_max(rhs);
+ }
+ inline bool timespec_ge(timespec const& lhs, timespec const& rhs)
{
- inline struct timespec get_timespec(boost::system_time const& abs_time)
- {
- struct timespec timeout={0,0};
- boost::posix_time::time_duration const time_since_epoch=abs_time-boost::posix_time::from_time_t(0);
-
- timeout.tv_sec=time_since_epoch.total_seconds();
- timeout.tv_nsec=(long)(time_since_epoch.fractional_seconds()*(1000000000l/time_since_epoch.ticks_per_second()));
- return timeout;
- }
+ return to_nanoseconds_int_max(lhs) >= to_nanoseconds_int_max(rhs);
}
+
+ }
}
#include <boost/config/abi_suffix.hpp>
Modified: branches/release/boost/thread/recursive_mutex.hpp
==============================================================================
--- branches/release/boost/thread/recursive_mutex.hpp (original)
+++ branches/release/boost/thread/recursive_mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,7 +3,7 @@
// recursive_mutex.hpp
//
-// (C) Copyright 2007 Anthony Williams
+// (C) Copyright 2007 Anthony Williams
//
// Distributed under the Boost Software License, Version 1.0. (See
// accompanying file LICENSE_1_0.txt or copy at
@@ -18,4 +18,47 @@
#error "Boost threads unavailable on this platform"
#endif
+#include <boost/thread/lockable_traits.hpp>
+
+namespace boost
+{
+ namespace sync
+ {
+
+#ifdef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
+ template<>
+ struct is_basic_lockable<recursive_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_lockable<recursive_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_basic_lockable<recursive_timed_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_lockable<recursive_timed_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+#endif
+
+ template<>
+ struct is_recursive_mutex_sur_parolle<recursive_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_recursive_mutex_sur_parolle<recursive_timed_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+
+ }
+}
#endif
Modified: branches/release/boost/thread/reverse_lock.hpp
==============================================================================
--- branches/release/boost/thread/reverse_lock.hpp (original)
+++ branches/release/boost/thread/reverse_lock.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,7 +6,9 @@
#ifndef BOOST_THREAD_REVERSE_LOCK_HPP
#define BOOST_THREAD_REVERSE_LOCK_HPP
#include <boost/thread/detail/config.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/detail/move.hpp>
+#include <boost/thread/lockable_traits.hpp>
+#include <boost/thread/lock_options.hpp>
#include <boost/thread/detail/delete.hpp>
namespace boost
@@ -15,7 +17,6 @@
template<typename Lock>
class reverse_lock
{
-
public:
typedef typename Lock::mutex_type mutex_type;
BOOST_THREAD_NO_COPYABLE(reverse_lock)
Copied: branches/release/boost/thread/scoped_thread.hpp (from r81093, /trunk/boost/thread/scoped_thread.hpp)
==============================================================================
--- /trunk/boost/thread/scoped_thread.hpp (original)
+++ branches/release/boost/thread/scoped_thread.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -117,6 +117,11 @@
{
}
+// explicit operator thread()
+// {
+// return boost::move(t_);
+// }
+
/**
* Move constructor.
*/
Modified: branches/release/boost/thread/shared_lock_guard.hpp
==============================================================================
--- branches/release/boost/thread/shared_lock_guard.hpp (original)
+++ branches/release/boost/thread/shared_lock_guard.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,7 +6,8 @@
#ifndef BOOST_THREAD_SHARED_LOCK_GUARD_HPP
#define BOOST_THREAD_SHARED_LOCK_GUARD_HPP
#include <boost/thread/detail/config.hpp>
-#include <boost/thread/locks.hpp>
+//#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_options.hpp>
#include <boost/thread/detail/delete.hpp>
namespace boost
Modified: branches/release/boost/thread/shared_mutex.hpp
==============================================================================
--- branches/release/boost/thread/shared_mutex.hpp (original)
+++ branches/release/boost/thread/shared_mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -23,4 +23,26 @@
#error "Boost threads unavailable on this platform"
#endif
+#include <boost/thread/lockable_traits.hpp>
+
+namespace boost
+{
+ namespace sync
+ {
+#ifdef BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES
+ template<>
+ struct is_basic_lockable<shared_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+ template<>
+ struct is_lockable<shared_mutex>
+ {
+ BOOST_STATIC_CONSTANT(bool, value = true);
+ };
+#endif
+
+ }
+}
+
#endif
Copied: branches/release/boost/thread/strict_lock.hpp (from r81093, /trunk/boost/thread/strict_lock.hpp)
==============================================================================
--- /trunk/boost/thread/strict_lock.hpp (original)
+++ branches/release/boost/thread/strict_lock.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -62,6 +62,8 @@
// observers
+ private:
+
/**
* @return the owned mutex.
*/
@@ -69,11 +71,12 @@
{
return &mtx_;
}
+ public:
/**
* @return whether if this lock is locking that mutex.
*/
- bool is_locking(mutex_type* l) const BOOST_NOEXCEPT
+ bool owns_lock(mutex_type const* l) const BOOST_NOEXCEPT
{
return l == mutex();
} /*< strict locks specific function >*/
@@ -115,7 +118,7 @@
* __Requires: <c>lk.mutex() != null_ptr</c>
* __Effects: Stores the reference to the lock parameter and takes ownership on it.
* If the lock doesn't owns the mutex @mtx lock it.
- * __Postconditions: @c is_locking()
+ * __Postconditions: @c owns_lock()
* __StrongException
* __Throws:
*
@@ -127,12 +130,10 @@
nested_strict_lock(Lock& lk) :
lk_(lk) /*< Store reference to lk >*/
{
-#ifdef BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED /*< Define BOOST_THREAD_DONT_CHECK_PRECONDITIONS if you don't want to check lk ownership >*/
- if (lk.mutex() == 0)
- {
- throw_exception( lock_error() );
- }
-#endif
+ /*< Define BOOST_THREAD_DONT_CHECK_PRECONDITIONS if you don't want to check lk ownership >*/
+ BOOST_THREAD_ASSERT_PRECONDITION( lk.mutex() != 0,
+ lock_error()
+ );
if (!lk.owns_lock()) lk.lock(); /*< ensures it is locked >*/
tmp_lk_ = move(lk); /*< Move ownership to temporary lk >*/
}
@@ -148,7 +149,7 @@
}
// observers
-
+private:
/**
* return @c the owned mutex.
*/
@@ -156,11 +157,11 @@
{
return tmp_lk_.mutex();
}
-
+public:
/**
* @return whether if this lock is locking that mutex.
*/
- bool is_locking(mutex_type* l) const BOOST_NOEXCEPT
+ bool owns_lock(mutex_type const* l) const BOOST_NOEXCEPT
{
return l == mutex();
}
Copied: branches/release/boost/thread/synchronized_value.hpp (from r81093, /trunk/boost/thread/synchronized_value.hpp)
==============================================================================
--- /trunk/boost/thread/synchronized_value.hpp (original)
+++ branches/release/boost/thread/synchronized_value.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -13,6 +13,7 @@
#include <boost/thread/mutex.hpp>
#include <boost/thread/lock_types.hpp>
+#include <boost/thread/lock_guard.hpp>
#include <boost/config/abi_prefix.hpp>
@@ -31,64 +32,109 @@
T value_;
mutable lockable_type mtx_;
public:
+ synchronized_value()
+ : value_()
+ {
+ }
+
+ synchronized_value(T other)
+ : value_(other)
+ {
+ }
+
/**
*
*/
- struct strict_synchronizer
+ struct const_strict_synchronizer
{
- private:
+ protected:
friend class synchronized_value;
boost::unique_lock<lockable_type> lk_;
- T& value_;
+ T const& value_;
- explicit strict_synchronizer(synchronized_value& outer) :
+ explicit const_strict_synchronizer(synchronized_value const& outer) :
lk_(outer.mtx_), value_(outer.value_)
{
}
public:
- BOOST_THREAD_NO_COPYABLE( strict_synchronizer )
+ BOOST_THREAD_NO_COPYABLE( const_strict_synchronizer )
- strict_synchronizer(strict_synchronizer&& other)
+ const_strict_synchronizer(const_strict_synchronizer&& other)
: lk_(boost::move(other.lk_)),value_(other.value_)
{
}
- ~strict_synchronizer()
+ ~const_strict_synchronizer()
{
}
- T* operator->()
+ const T* operator->() const
{
return &value_;
}
- const T* operator->() const
+ const T& operator*() const
{
- return &value_;
+ return value_;
}
- T& operator*()
+ };
+
+ /**
+ *
+ */
+ struct strict_synchronizer : const_strict_synchronizer
+ {
+ protected:
+ friend class synchronized_value;
+
+ explicit strict_synchronizer(synchronized_value& outer) :
+ const_strict_synchronizer(const_cast<synchronized_value&>(outer))
{
- return value_;
}
+ public:
+ BOOST_THREAD_NO_COPYABLE( strict_synchronizer )
- const T& operator*() const
+ strict_synchronizer(strict_synchronizer&& other)
+ : const_strict_synchronizer(boost::move(other))
+ {
+ }
+
+ ~strict_synchronizer()
{
- return value_;
+ }
+
+ T* operator->()
+ {
+ return const_cast<T*>(&this->value_);
+ }
+
+ T& operator*()
+ {
+ return const_cast<T&>(this->value_);
}
};
+
strict_synchronizer operator->()
{
return BOOST_THREAD_MAKE_RV_REF(strict_synchronizer(*this));
}
+ const_strict_synchronizer operator->() const
+ {
+ return BOOST_THREAD_MAKE_RV_REF(const_strict_synchronizer(*this));
+ }
strict_synchronizer synchronize()
{
return BOOST_THREAD_MAKE_RV_REF(strict_synchronizer(*this));
}
+ const_strict_synchronizer synchronize() const
+ {
+ return BOOST_THREAD_MAKE_RV_REF(const_strict_synchronizer(*this));
+ }
/**
*
Modified: branches/release/boost/thread/thread.hpp
==============================================================================
--- branches/release/boost/thread/thread.hpp (original)
+++ branches/release/boost/thread/thread.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -20,7 +20,9 @@
#endif
#include <boost/thread/detail/thread.hpp>
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
#include <boost/thread/detail/thread_interruption.hpp>
+#endif
#include <boost/thread/detail/thread_group.hpp>
#include <boost/thread/v2/thread.hpp>
Modified: branches/release/boost/thread/v2/thread.hpp
==============================================================================
--- branches/release/boost/thread/v2/thread.hpp (original)
+++ branches/release/boost/thread/v2/thread.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -9,9 +9,10 @@
#include <boost/thread/detail/config.hpp>
#ifdef BOOST_THREAD_USES_CHRONO
#include <boost/chrono/system_clocks.hpp>
+#include <boost/chrono/ceil.hpp>
#endif
#include <boost/thread/condition_variable.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
namespace boost
{
@@ -20,15 +21,6 @@
#ifdef BOOST_THREAD_USES_CHRONO
- template <class Rep, class Period>
- void sleep_for(const chrono::duration<Rep, Period>& d)
- {
- using namespace chrono;
- nanoseconds ns = duration_cast<nanoseconds> (d);
- if (ns < d) ++ns;
- sleep_for(ns);
- }
-
template <class Clock, class Duration>
void sleep_until(const chrono::time_point<Clock, Duration>& t)
{
@@ -40,6 +32,28 @@
cv.wait_until(lk, t);
}
+#ifdef BOOST_THREAD_SLEEP_FOR_IS_STEADY
+
+ template <class Rep, class Period>
+ void sleep_for(const chrono::duration<Rep, Period>& d)
+ {
+ using namespace chrono;
+ if (d > duration<Rep, Period>::zero())
+ {
+ duration<long double> Max = nanoseconds::max();
+ nanoseconds ns;
+ if (d < Max)
+ {
+ ns = duration_cast<nanoseconds>(d);
+ if (ns < d)
+ ++ns;
+ }
+ else
+ ns = nanoseconds::max();
+ sleep_for(ns);
+ }
+ }
+
template <class Duration>
inline BOOST_SYMBOL_VISIBLE
void sleep_until(const chrono::time_point<chrono::steady_clock, Duration>& t)
@@ -47,6 +61,22 @@
using namespace chrono;
sleep_for(t - steady_clock::now());
}
+#else
+ template <class Rep, class Period>
+ void sleep_for(const chrono::duration<Rep, Period>& d)
+ {
+ using namespace chrono;
+ if (d > duration<Rep, Period>::zero())
+ {
+ steady_clock::time_point c_now = steady_clock::now();
+ do
+ {
+ sleep_until(system_clock::now() + ceil<nanoseconds>(d));
+ } while (steady_clock::now() - c_now < d );
+ }
+ }
+
+#endif
#endif
}
Modified: branches/release/boost/thread/win32/basic_recursive_mutex.hpp
==============================================================================
--- branches/release/boost/thread/win32/basic_recursive_mutex.hpp (original)
+++ branches/release/boost/thread/win32/basic_recursive_mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -58,6 +58,7 @@
recursion_count=1;
}
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock(::boost::system_time const& target)
{
long const current_thread_id=win32::GetCurrentThreadId();
@@ -68,6 +69,7 @@
{
return timed_lock(get_system_time()+timeout);
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
@@ -114,6 +116,7 @@
return false;
}
+#if defined BOOST_THREAD_USES_DATETIME
bool try_timed_lock(long current_thread_id,::boost::system_time const& target)
{
if(mutex.timed_lock(target))
@@ -124,6 +127,7 @@
}
return false;
}
+#endif
template <typename TP>
bool try_timed_lock_until(long current_thread_id,TP const& target)
{
Modified: branches/release/boost/thread/win32/basic_timed_mutex.hpp
==============================================================================
--- branches/release/boost/thread/win32/basic_timed_mutex.hpp (original)
+++ branches/release/boost/thread/win32/basic_timed_mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -14,7 +14,9 @@
#include <boost/thread/win32/thread_primitives.hpp>
#include <boost/thread/win32/interlocked_read.hpp>
#include <boost/thread/thread_time.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/thread/xtime.hpp>
+#endif
#include <boost/detail/interlocked.hpp>
#ifdef BOOST_THREAD_USES_CHRONO
#include <boost/chrono/system_clocks.hpp>
@@ -118,6 +120,7 @@
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_lock(::boost::system_time const& wait_until)
{
if(try_lock())
@@ -147,7 +150,6 @@
return true;
}
-
template<typename Duration>
bool timed_lock(Duration const& timeout)
{
@@ -158,7 +160,7 @@
{
return timed_lock(system_time(timeout));
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
bool try_lock_for(const chrono::duration<Rep, Period>& rel_time)
Modified: branches/release/boost/thread/win32/condition_variable.hpp
==============================================================================
--- branches/release/boost/thread/win32/condition_variable.hpp (original)
+++ branches/release/boost/thread/win32/condition_variable.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -11,9 +11,13 @@
#include <boost/thread/win32/thread_data.hpp>
#include <boost/thread/win32/interlocked_read.hpp>
#include <boost/thread/cv_status.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/thread/xtime.hpp>
+#endif
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread_time.hpp>
+#include <boost/thread/lock_guard.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/assert.hpp>
#include <boost/intrusive_ptr.hpp>
@@ -195,7 +199,7 @@
~entry_manager()
{
- if(! entry->is_notified())
+ //if(! entry->is_notified()) // several regression #7657
{
entry->remove_waiter();
}
@@ -321,6 +325,7 @@
}
+#if defined BOOST_THREAD_USES_DATETIME
bool timed_wait(unique_lock<mutex>& m,boost::system_time const& abs_time)
{
return do_wait(m,abs_time);
@@ -351,7 +356,7 @@
{
return do_wait(m,wait_duration.total_milliseconds(),pred);
}
-
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Clock, class Duration>
@@ -428,6 +433,7 @@
while(!pred()) wait(m);
}
+#if defined BOOST_THREAD_USES_DATETIME
template<typename lock_type>
bool timed_wait(lock_type& m,boost::system_time const& abs_time)
{
@@ -463,6 +469,7 @@
{
return do_wait(m,wait_duration.total_milliseconds(),pred);
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class lock_type, class Clock, class Duration>
Modified: branches/release/boost/thread/win32/mutex.hpp
==============================================================================
--- branches/release/boost/thread/win32/mutex.hpp (original)
+++ branches/release/boost/thread/win32/mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,7 +8,10 @@
#include <boost/thread/win32/basic_timed_mutex.hpp>
#include <boost/thread/exceptions.hpp>
-#include <boost/thread/locks.hpp>
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
+#include <boost/thread/lock_types.hpp>
+#endif
+#include <boost/thread/detail/delete.hpp>
#include <boost/config/abi_prefix.hpp>
@@ -33,8 +36,10 @@
destroy();
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<mutex> scoped_lock;
typedef detail::try_lock_wrapper<mutex> scoped_try_lock;
+#endif
};
typedef mutex try_mutex;
@@ -54,9 +59,11 @@
destroy();
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<timed_mutex> scoped_timed_lock;
typedef detail::try_lock_wrapper<timed_mutex> scoped_try_lock;
typedef scoped_timed_lock scoped_lock;
+#endif
};
}
Modified: branches/release/boost/thread/win32/once.hpp
==============================================================================
--- branches/release/boost/thread/win32/once.hpp (original)
+++ branches/release/boost/thread/win32/once.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,6 +18,7 @@
#include <boost/detail/interlocked.hpp>
#include <boost/thread/win32/thread_primitives.hpp>
#include <boost/thread/win32/interlocked_read.hpp>
+#include <boost/detail/no_exceptions_support.hpp>
#include <boost/config/abi_prefix.hpp>
@@ -157,9 +158,7 @@
status=BOOST_INTERLOCKED_COMPARE_EXCHANGE(&flag.status,running_value,0);
if(!status)
{
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
if(!event_handle)
{
@@ -187,8 +186,7 @@
}
break;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
BOOST_INTERLOCKED_EXCHANGE(&flag.status,0);
if(!event_handle)
@@ -199,9 +197,9 @@
{
::boost::detail::win32::SetEvent(event_handle);
}
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
if(!counted)
Modified: branches/release/boost/thread/win32/recursive_mutex.hpp
==============================================================================
--- branches/release/boost/thread/win32/recursive_mutex.hpp (original)
+++ branches/release/boost/thread/win32/recursive_mutex.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -12,7 +12,10 @@
#include <boost/thread/win32/basic_recursive_mutex.hpp>
#include <boost/thread/exceptions.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/detail/delete.hpp>
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
+#include <boost/thread/lock_types.hpp>
+#endif
#include <boost/config/abi_prefix.hpp>
@@ -32,8 +35,10 @@
::boost::detail::basic_recursive_mutex::destroy();
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<recursive_mutex> scoped_lock;
typedef detail::try_lock_wrapper<recursive_mutex> scoped_try_lock;
+#endif
};
typedef recursive_mutex recursive_try_mutex;
@@ -52,9 +57,11 @@
::boost::detail::basic_recursive_timed_mutex::destroy();
}
+#if defined BOOST_THREAD_PROVIDES_NESTED_LOCKS
typedef unique_lock<recursive_timed_mutex> scoped_timed_lock;
typedef detail::try_lock_wrapper<recursive_timed_mutex> scoped_try_lock;
typedef scoped_timed_lock scoped_lock;
+#endif
};
}
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-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -136,12 +136,12 @@
BOOST_VERIFY(timed_lock_shared(::boost::detail::get_system_time_sentinel()));
}
+#if defined BOOST_THREAD_USES_DATETIME
template<typename TimeDuration>
bool timed_lock_shared(TimeDuration const & relative_time)
{
return timed_lock_shared(get_system_time()+relative_time);
}
-
bool timed_lock_shared(boost::system_time const& wait_until)
{
for(;;)
@@ -220,6 +220,7 @@
BOOST_ASSERT(res==0);
}
}
+#endif
#ifdef BOOST_THREAD_USES_CHRONO
template <class Rep, class Period>
Modified: branches/release/boost/thread/win32/thread_data.hpp
==============================================================================
--- branches/release/boost/thread/win32/thread_data.hpp (original)
+++ branches/release/boost/thread/win32/thread_data.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -22,6 +22,11 @@
#include <boost/config/abi_prefix.hpp>
+#ifdef BOOST_MSVC
+#pragma warning(push)
+#pragma warning(disable:4251)
+#endif
+
namespace boost
{
class condition_variable;
@@ -67,6 +72,7 @@
namespace detail
{
+ struct future_object_base;
struct tss_cleanup_function;
struct thread_exit_callback_node;
struct tss_data_node
@@ -88,24 +94,35 @@
{
long count;
detail::win32::handle_manager thread_handle;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
detail::win32::handle_manager interruption_handle;
+#endif
boost::detail::thread_exit_callback_node* thread_exit_callbacks;
std::map<void const*,boost::detail::tss_data_node> tss_data;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
bool interruption_enabled;
+#endif
unsigned id;
typedef std::vector<std::pair<condition_variable*, mutex*>
//, hidden_allocator<std::pair<condition_variable*, mutex*> >
> notify_list_t;
notify_list_t notify;
+ typedef std::vector<shared_ptr<future_object_base> > async_states_t;
+ async_states_t async_states_;
thread_data_base():
count(0),thread_handle(detail::win32::invalid_handle_value),
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
interruption_handle(create_anonymous_event(detail::win32::manual_reset_event,detail::win32::event_initially_reset)),
+#endif
thread_exit_callbacks(0),tss_data(),
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
interruption_enabled(true),
+#endif
id(0),
- notify()
+ notify(),
+ async_states_()
{}
virtual ~thread_data_base();
@@ -122,11 +139,12 @@
}
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void interrupt()
{
BOOST_VERIFY(detail::win32::SetEvent(interruption_handle)!=0);
}
-
+#endif
typedef detail::win32::handle native_handle_type;
virtual void run()=0;
@@ -136,7 +154,13 @@
notify.push_back(std::pair<condition_variable*, mutex*>(cv, m));
}
+ void make_ready_at_thread_exit(shared_ptr<future_object_base> as)
+ {
+ async_states_.push_back(as);
+ }
+
};
+ BOOST_THREAD_DECL thread_data_base* get_current_thread_data();
typedef boost::intrusive_ptr<detail::thread_data_base> thread_data_ptr;
@@ -235,7 +259,6 @@
{
interruptible_wait(detail::win32::invalid_handle_value,abs_time);
}
-
template<typename TimeDuration>
inline BOOST_SYMBOL_VISIBLE void sleep(TimeDuration const& rel_time)
{
@@ -255,6 +278,10 @@
}
+#ifdef BOOST_MSVC
+#pragma warning(pop)
+#endif
+
#include <boost/config/abi_suffix.hpp>
#endif
Modified: branches/release/boost/thread/win32/thread_heap_alloc.hpp
==============================================================================
--- branches/release/boost/thread/win32/thread_heap_alloc.hpp (original)
+++ branches/release/boost/thread/win32/thread_heap_alloc.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,10 +5,12 @@
#ifndef THREAD_HEAP_ALLOC_HPP
#define THREAD_HEAP_ALLOC_HPP
#include <new>
+#include <boost/thread/detail/config.hpp>
#include <boost/thread/win32/thread_primitives.hpp>
#include <stdexcept>
#include <boost/assert.hpp>
#include <boost/throw_exception.hpp>
+#include <boost/detail/no_exceptions_support.hpp>
#if defined( BOOST_USE_WINDOWS_H )
# include <windows.h>
@@ -75,20 +77,17 @@
inline T* heap_new()
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T();
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
@@ -96,159 +95,135 @@
inline T* heap_new(A1&& a1)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(static_cast<A1&&>(a1));
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
template<typename T,typename A1,typename A2>
inline T* heap_new(A1&& a1,A2&& a2)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(static_cast<A1&&>(a1),static_cast<A2&&>(a2));
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
template<typename T,typename A1,typename A2,typename A3>
inline T* heap_new(A1&& a1,A2&& a2,A3&& a3)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(static_cast<A1&&>(a1),static_cast<A2&&>(a2),
static_cast<A3&&>(a3));
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
template<typename T,typename A1,typename A2,typename A3,typename A4>
inline T* heap_new(A1&& a1,A2&& a2,A3&& a3,A4&& a4)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(static_cast<A1&&>(a1),static_cast<A2&&>(a2),
static_cast<A3&&>(a3),static_cast<A4&&>(a4));
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
#else
template<typename T,typename A1>
inline T* heap_new_impl(A1 a1)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(a1);
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
template<typename T,typename A1,typename A2>
inline T* heap_new_impl(A1 a1,A2 a2)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(a1,a2);
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
template<typename T,typename A1,typename A2,typename A3>
inline T* heap_new_impl(A1 a1,A2 a2,A3 a3)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(a1,a2,a3);
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
template<typename T,typename A1,typename A2,typename A3,typename A4>
inline T* heap_new_impl(A1 a1,A2 a2,A3 a3,A4 a4)
{
void* const heap_memory=allocate_raw_heap_memory(sizeof(T));
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
T* const data=new (heap_memory) T(a1,a2,a3,a4);
return data;
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
free_raw_heap_memory(heap_memory);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
Modified: branches/release/boost/thread/win32/thread_primitives.hpp
==============================================================================
--- branches/release/boost/thread/win32/thread_primitives.hpp (original)
+++ branches/release/boost/thread/win32/thread_primitives.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -232,7 +232,7 @@
BOOST_VERIFY(ReleaseSemaphore(semaphore,count,0)!=0);
}
- class handle_manager
+ class BOOST_THREAD_DECL handle_manager
{
private:
handle handle_to_manage;
Modified: branches/release/boost/thread/xtime.hpp
==============================================================================
--- branches/release/boost/thread/xtime.hpp (original)
+++ branches/release/boost/thread/xtime.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -9,6 +9,7 @@
#define BOOST_XTIME_WEK070601_HPP
#include <boost/thread/detail/config.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/cstdint.hpp>
#include <boost/thread/thread_time.hpp>
@@ -88,5 +89,5 @@
} // namespace boost
#include <boost/config/abi_suffix.hpp>
-
+#endif
#endif //BOOST_XTIME_WEK070601_HPP
Modified: branches/release/libs/thread/build/Jamfile.v2
==============================================================================
--- branches/release/libs/thread/build/Jamfile.v2 (original)
+++ branches/release/libs/thread/build/Jamfile.v2 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -60,7 +60,7 @@
<toolset>darwin:<cxxflags>-Wextra
<toolset>darwin:<cxxflags>-pedantic
- <toolset>darwin:<cxxflags>-ansi
+ #<toolset>darwin:<cxxflags>-ansi
<toolset>darwin:<cxxflags>-fpermissive
<toolset>darwin:<cxxflags>-Wno-long-long
@@ -70,7 +70,7 @@
<toolset>clang:<cxxflags>-Wextra
<toolset>clang:<cxxflags>-pedantic
- <toolset>clang:<cxxflags>-ansi
+ #<toolset>clang:<cxxflags>-ansi
#<toolset>clang:<cxxflags>-fpermissive
<toolset>clang:<cxxflags>-Wno-long-long
@@ -91,6 +91,18 @@
<toolset>clang-3.0:<cxxflags>-Wno-delete-non-virtual-dtor
#<toolset>clang-3.0:<cxxflags>-Wno-unused-function
#<toolset>clang-3.0:<cxxflags>-Wno-unused-variable
+
+# Note: Some of the remarks from the Intel compiler are disabled
+# remark #193: zero used for undefined preprocessing identifier "XXX"
+# remark #304: access control not specified ("public" by default)
+# remark #593: variable "XXX" was set but never used
+# remark #1418: external function definition with no prior declaration
+# remark #2415: variable "XXX" of static storage duration was declared but never referenced
+
+ <toolset>intel:<cxxflags>-wd193,304,383,444
+ <toolset>intel:<cxxflags>-wd593,981
+ <toolset>intel:<cxxflags>-wd1418
+ <toolset>intel:<cxxflags>-wd2415
# : default-build <threading>multi
Modified: branches/release/libs/thread/doc/changes.qbk
==============================================================================
--- branches/release/libs/thread/doc/changes.qbk (original)
+++ branches/release/libs/thread/doc/changes.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,6 +8,66 @@
[section:changes History]
+[heading Version 4.0.0 - boost 1.53]
+
+Breaking changes:
+
+[warning
+BOOST_THREAD_VERSION==3 by default since Boost 1.53. So that all the deprecated features since 1.50 are not included by default. You can change this by setting the appropriated define (see Configuration section).
+]
+
+Deprecated features:
+
+[warning Deprecated features since boost 1.53 will be available only until boost 1.58.]
+
+* C++11 compliance: packaged_task<R> is deprecated, use instead packaged_task<R()>.
+See BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK and BOOST_THREAD_DONT_PROVIDE_SIGNATURE_PACKAGED_TASK
+
+* [@http://svn.boost.org/trac/boost/ticket/7537 #7537] deprecate Mutex::scoped_lock and scoped_try_lock and boost::condition
+
+New Features:
+
+* [@http://svn.boost.org/trac/boost/ticket/6270 #6270] c++11 compliance: Add thread constructor from movable callable and movable arguments
+Provided when BOOST_THREAD_PROVIDES_VARIADIC_THREAD is defined (Default value from Boost 1.55):
+See BOOST_THREAD_PROVIDES_VARIADIC_THREAD and BOOST_THREAD_DONT_PROVIDE_VARIADIC_THREAD.
+
+* [@http://svn.boost.org/trac/boost/ticket/7280 #7280] C++11 compliance: Add promise::...at_thread_exit functions
+
+* [@http://svn.boost.org/trac/boost/ticket/7281 #7281] C++11 compliance: Add ArgTypes to packaged_task template.
+Provided when BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK is defined (Default value from Boost 1.55).
+See BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK and BOOST_THREAD_DONT_PROVIDE_SIGNATURE_PACKAGED_TASK.
+
+* [@http://svn.boost.org/trac/boost/ticket/7282 #7282] C++11 compliance: Add packaged_task::make_ready_at_thread_exit function
+
+* [@http://svn.boost.org/trac/boost/ticket/7412 #7412] C++11 compliance: Add async from movable callable and movable arguments
+Provided when BOOST_THREAD_PROVIDES_VARIADIC_THREAD and BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK are defined (Default value from Boost 1.55):
+See BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK and BOOST_THREAD_DONT_PROVIDE_SIGNATURE_PACKAGED_TASK, BOOST_THREAD_PROVIDES_VARIADIC_THREAD and BOOST_THREAD_DONT_PROVIDE_VARIADIC_THREAD.
+
+* [@http://svn.boost.org/trac/boost/ticket/7413 #7413] C++11 compliance: Add async when the launch policy is deferred.
+* [@http://svn.boost.org/trac/boost/ticket/7414 #7414] C++11 compliance: future::get post-condition should be valid()==false.
+* [@http://svn.boost.org/trac/boost/ticket/7414 #7444] Async: Add make_future/make_shared_future.
+* [@http://svn.boost.org/trac/boost/ticket/7445 #7445] Async: Add future<>.then.
+* [@http://svn.boost.org/trac/boost/ticket/7449 #7449] Synchro: Add a synchronized value class.
+* [@http://svn.boost.org/trac/boost/ticket/7540 #7540] Threads: Add a helper class that join a thread on destruction.
+* [@http://svn.boost.org/trac/boost/ticket/7541 #7541] Threads: Add a thread wrapper class that joins on destruction.
+* [@http://svn.boost.org/trac/boost/ticket/7575 #7575] C++11 compliance: A future created by async should "join" in the destructor.
+* [@http://svn.boost.org/trac/boost/ticket/7587 #7587] Synchro: Add strict_lock and nested_strict_lock
+* [@http://svn.boost.org/trac/boost/ticket/7588 #7588] Synchro: Split the locks.hpp in several files to limit dependencies
+* [@http://svn.boost.org/trac/boost/ticket/7589 #7589] Synchro: Add polymorphic lockables
+* [@http://svn.boost.org/trac/boost/ticket/7590 #7590] Synchro: Add lockable concept checkers based on Boost.ConceptCheck
+* [@http://svn.boost.org/trac/boost/ticket/7591 #7591] Add lockable traits that can be used with enable_if
+* [@http://svn.boost.org/trac/boost/ticket/7592 #7592] Synchro: Add a null_mutex that is a no-op and that is a model of UpgardeLockable
+* [@http://svn.boost.org/trac/boost/ticket/7593 #7593] Synchro: Add a externally_locked class
+* [@http://svn.boost.org/trac/boost/ticket/7590 #7594] Threads: Allow to disable thread interruptions
+
+Fixed Bugs:
+
+* [@http://svn.boost.org/trac/boost/ticket/7657 #7657] Serious performance and memory consuption hit if condition_variable methods condition notify_one or notify_all is used repeatedly.
+* [@http://svn.boost.org/trac/boost/ticket/7668 #7668] thread_group::join_all() should check whether its threads are joinable.
+* [@http://svn.boost.org/trac/boost/ticket/7669 #7669] thread_group::join_all() should catch resource_deadlock_would_occur.
+* [@http://svn.boost.org/trac/boost/ticket/7672 #7672] lockable_traits.hpp syntax error: "defined" token misspelled.
+
+
[heading Version 3.1.0 - boost 1.52]
Deprecated Features:
@@ -58,6 +118,7 @@
* [@http://svn.boost.org/trac/boost/ticket/7438 #7438] Segmentation fault in test_once regression test in group.join_all();
* [@http://svn.boost.org/trac/boost/ticket/7461 #7461] detail::win32::ReleaseSemaphore may be called with count_to_release equal to 0
* [@http://svn.boost.org/trac/boost/ticket/7499 #7499] call_once doesn't call even once
+
[heading Version 3.0.1 - boost 1.51]
@@ -274,10 +335,22 @@
The following features will be included in next releases.
# Complete the C++11 missing features, in particular
+ * [@http://svn.boost.org/trac/boost/ticket/7413 #7413] c++11 compliance: Add async when the launch policy is deferred.
+ * [@http://svn.boost.org/trac/boost/ticket/7280 #7280] C++11 compliance: Add promise::...at_thread_exit functions.
+ * [@http://svn.boost.org/trac/boost/ticket/7282 #7282] C++11 compliance: Add packaged_task::make_ready_at_thread_exit function.
+ * [@http://svn.boost.org/trac/boost/ticket/7285 #7285] C++11 compliance: Allow to pass movable arguments for call_once.
+ * [@http://svn.boost.org/trac/boost/ticket/6227 #6227] C++11 compliance: Use of variadic templates on Generic Locking Algorithms on compilers providing them.
+
+
+# Add some of the extension proposed in [@http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3428.pdf A Standardized Representation of Asynchronous Operations], in particular
+
+ * [@http://svn.boost.org/trac/boost/ticket/7445 #7445] Async: Add future<>.then
+ * [@http://svn.boost.org/trac/boost/ticket/7446 #7446] Async: Add when_any
+ * [@http://svn.boost.org/trac/boost/ticket/7447 #7447] Async: Add when_all
+ * [@http://svn.boost.org/trac/boost/ticket/7448 #7448] Async: Add async taking a scheduler parameter
+
- * async with deferred and variadic rvalue reference args.
- * [@http://svn.boost.org/trac/boost/ticket/6227 #6227] Use of variadic templates on Generic Locking Algorithms on compilers providing them.
- * [@http://svn.boost.org/trac/boost/ticket/6270 #6270] Add thread constructor from movable callable and movable arguments following C++11.
+# Add a synchronized value class following the design in [@http://www.drdobbs.com/cpp/enforcing-correct-mutex-usage-with-synch/225200269 Enforcing Correct Mutex Usage with Synchronized Values]
Modified: branches/release/libs/thread/doc/compliance.qbk
==============================================================================
--- branches/release/libs/thread/doc/compliance.qbk (original)
+++ branches/release/libs/thread/doc/compliance.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -25,10 +25,10 @@
[[30.2.5.3] [Lockable requirements] [yes] [-] [-]]
[[30.2.5.4] [TimedLockable requirements] [Yes] [-] [-]]
[[30.2.6] [decay_copy] [-] [-] [-]]
- [[30.3] [Threads] [Partial] [-] [-]]
- [[30.3.1] [Class thread] [Partial] [move,variadic,terminate] [#6270]]
+ [[30.3] [Threads] [Yes] [-] [-]]
+ [[30.3.1] [Class thread] [Yes] [-] [-]]
[[30.3.1.1] [Class thread::id] [Yes] [-] [-]]
- [[30.3.1.2] [thread constructors] [Partial] [move,variadic] [#6270]]
+ [[30.3.1.2] [thread constructors] [Partial] [-] [-]]
[[30.3.1.3] [thread destructor] [Yes] [-] [-]]
[[30.3.1.4] [thread assignment] [Yes] [-] [-]]
[[30.3.1.5] [thread members] [Yes] [-] [-]]
@@ -45,7 +45,7 @@
[[30.4.1.3] [Timed mutex types] [Yes] [-] [-]]
[[30.4.1.3.1] [Class timed_mutex] [Yes] [-] [-]]
[[30.4.1.3.1] [Class recursive_timed_mutex] [Yes] [-] [-]]
- [[30.4.2] [Locks] [Partial] [variadic] [#6227]]
+ [[30.4.2] [Locks] [Yes] [-] [-]]
[[30.4.2.1] [Class template lock_guard] [Yes] [-] [-]]
[[30.4.2.2] [Class template unique_lock] [Yes] [-] [-]]
[[30.4.2.2.1] [unique_lock constructors, destructor, and assignment] [Yes] [-] [-]]
@@ -56,20 +56,19 @@
[[30.4.4] [Call once] [Partial] [call_once] [#7285]]
[[30.4.4.1] [Struct once_flag] [Yes] [-] [-]]
[[30.4.4.2] [Function call_once] [Partial] [interface] [#7285]]
- [[30.5] [Condition variables] [Partial] [notify_all_at_thread_exit] [#7283]]
- [[30.5 6-10] [Function notify_all_at_thread_exit] [No] [-] [#7283]]
+ [[30.5] [Condition variables] [Yes] [-] [-]]
[[30.5.1] [Class condition_variable] [Yes] [-] [-]]
[[30.5.2] [Class condition_variable_any] [Yes] [-] [-]]
- [[30.6] [Futures] [Partial] [async,at_thread_exit] [#4710,#7280]]
+ [[30.6] [Futures] [Partial] [noexcept] [#7279]]
[[30.6.1] [Overview] [Partial] [-] [-]]
[[30.6.2] [Error handling] [Yes] [-] [-]]
[[30.6.3] [Class future_error] [Partial] [noexcept] [#7279]]
[[30.6.4] [Shared state] [-] [-] [-]]
- [[30.6.5] [Class template promise] [Partial] [at_thread_exit] [#7280]]
+ [[30.6.5] [Class template promise] [Yes] [-] [-]]
[[30.6.6] [Class template future] [Yes] [-] [-]]
[[30.6.7] [Class template shared_future] [Yes] [-] [-]]
- [[30.6.8] [Function template async] [Partial] [deferred not implemented and only a copyable functor is allowed yet] [#4710]]
- [[30.6.9] [Class template packaged_task] [Partial] [args,make_ready_at_thread_exit] [#7281,#7282]]
+ [[30.6.8] [Function template async] [Yes] [-] [-]]
+ [[30.6.9] [Class template packaged_task] [Yes] [-] [-]]
]
[/
Modified: branches/release/libs/thread/doc/configuration.qbk
==============================================================================
--- branches/release/libs/thread/doc/configuration.qbk (original)
+++ branches/release/libs/thread/doc/configuration.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -9,30 +9,158 @@
[section:configuration Configuration]
-[section:chrono Boost.Chrono]
+[table Default Values for Configurable Features
+ [[Feature] [Anti-Feature] [V2] [V3] [V4] ]
+ [[USES_CHRONO] [DONT_USE_CHRONO] [YES] [YES] [YES] ]
+ [[PROVIDES_INTERRUPTIONS] [DONT_PROVIDE_INTERRUPTIONS] [YES] [YES] [YES] ]
+ [[THROW_IF_PRECONDITION_NOT_SATISFIED] [-] [NO] [NO] [NO] ]
+
+
+
+ [[PROVIDES_PROMISE_LAZY] [DONT_PROVIDE_PROMISE_LAZY] [YES] [NO] [NO] ]
+
+ [[PROVIDES_BASIC_THREAD_ID] [DONT_PROVIDE_BASIC_THREAD_ID] [NO] [YES] [YES] ]
+ [[PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN] [DONT_PROVIDE_GENERIC_SHARED_MUTEX_ON_WIN] [NO] [YES] [YES] ]
+
+ [[PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSION] [DONT_PROVIDE_SHARED_MUTEX_UPWARDS_CONVERSION] [NO] [YES] [YES] ]
+ [[PROVIDES_EXPLICIT_LOCK_CONVERSION] [DONT_PROVIDE_EXPLICIT_LOCK_CONVERSION] [NO] [YES] [YES] ]
+ [[PROVIDES_FUTURE] [DONT_PROVIDE_FUTURE] [NO] [YES] [YES] ]
+ [[PROVIDES_FUTURE_CTOR_ALLOCATORS] [DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS] [NO] [YES] [YES] ]
+ [[PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE] [DONT_PROVIDE_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE] [NO] [YES] [YES] ]
+ [[PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE] [DONT_PROVIDE_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE] [NO] [YES] [YES] ]
+ [[PROVIDES_ONCE_CXX11] [DONT_PROVIDE_ONCE_CXX11] [NO] [YES] [YES] ]
+ [[USES_MOVE] [DONT_USE_MOVE] [NO] [YES] [YES] ]
+
+ [[USES_DATETIME] [DONT_USE_DATETIME] [YES] [YES] [NO] ]
+ [[PROVIDES_THREAD_EQ] [DONT_PROVIDE_THREAD_EQ] [YES] [YES] [NO] ]
+ [[PROVIDES_CONDITION] [DONT_PROVIDE_CONDITION] [YES] [YES] [NO] ]
+ [[PROVIDES_NESTED_LOCKS] [DONT_PROVIDE_NESTED_LOCKS] [YES] [YES] [NO] ]
+ [[PROVIDES_SIGNATURE_PACKAGED_TASK] [DONT_PROVIDE_SIGNATURE_PACKAGED_TASK] [NO] [NO] [YES] ]
+ [[PROVIDES_FUTURE_INVALID_AFTER_GET] [DONT_PROVIDE_FUTURE_INVALID_AFTER_GET] [NO] [NO] [YES] ]
+ [[PROVIDES_FUTURE_CONTINUATION] [DONT_PROVIDE_FUTURE_CONTINUATION] [NO] [NO] [YES] ]
+
+ [[PROVIDES_VARIADIC_THREAD] [DONT_PROVIDE_VARIADIC_THREAD] [NO] [NO] [C++11] ]
-Boost.Thread uses by default Boost.Chrono for the time related functions. For backward compatibility and also for compilers that don't work well with Boost.Chrono the user can define `BOOST_THREAD_DONT_USE_CHRONO`.
+]
-`BOOST_THREAD_USES_CHRONO` is defined when Boost.Thread uses Boost.Chrono.
+[section:chrono Boost.Chrono]
+Boost.Thread uses by default Boost.Chrono for the time related functions and define `BOOST_THREAD_USES_CHRONO` if `BOOST_THREAD_DONT_USE_CHRONO` is not defined. The user should define `BOOST_THREAD_DONT_USE_CHRONO` for compilers that don't work well with Boost.Chrono.
[endsect]
+
[section:move Boost.Move]
Boost.Thread uses by default an internal move semantic implementation. Since version 3.0.0 you can use the move emulation emulation provided by Boost.Move.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_USES_MOVE ` if you want to use Boost.Move interface.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_USE_MOVE ` if you don't want to use Boost.Move interface.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_USE_MOVE ` if you don't want to use Boost.Move interface.
+
+[endsect]
+
+[section:date_time Boost.DateTime]
+
+The Boost.DateTime time related functions introduced in Boost 1.35.0, using the [link date_time Boost.Date_Time] library are deprecated. These include (but are not limited to):
+
+* __sleep__
+* __timed_join__
+* __cond_timed_wait__
+* __timed_lock_ref__
+
+
+When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_DONT_USE_DATETIME ` if you don't want to use Boost.DateTime related interfaces.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_USES_DATETIME ` if you want to use Boost.DateTime related interfaces.
+
+[endsect]
+
+
+[section:thread_eq `boost::thread::oprator==` deprecated]
+
+The following nested typedefs are deprecated:
+
+* `boost::thread::oprator==`
+* `boost::thread::oprator!=`
+
+When `BOOST_THREAD_PROVIDES_THREAD_EQ` is defined Boost.Thread provides these deprecated feature.
+
+Use instead
+
+* `boost::thread::id::oprator==`
+* `boost::thread::id::oprator!=`
+
+[warning This is a breaking change respect to version 1.x.]
+
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_PROVIDES_THREAD_EQ ` if you want this feature.
+When `BOOST_THREAD_VERSION<3` define `BOOST_THREAD_DONT_PROVIDE_THREAD_EQ ` if you don't want this feature.
+
+[endsect]
+
+[section:condition boost::condition deprecated]
+
+`boost::condition` is deprecated. When `BOOST_THREAD_PROVIDES_CONDITION` is defined Boost.Thread provides this deprecated feature.
+
+Use instead `boost::condition_variable_any`.
+
+[warning This is a breaking change respect to version 1.x.]
+
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_PROVIDES_CONDITION` if you want this feature.
+When `BOOST_THREAD_VERSION<3` define `BOOST_THREAD_DONT_PROVIDE_CONDITION` if you don't want this feature.
+
+[endsect]
+
+[section:nested_lock Mutex nested lock types deprecated]
+
+
+The following nested typedefs are deprecated:
+
+* `boost::mutex::scoped_lock`,
+* `boost::mutex::scoped_try_lock`,
+* `boost::timed_mutex::scoped_lock`
+* `boost::timed_mutex::scoped_try_lock`
+* `boost::timed_mutex::timed_scoped_timed_lock`
+* `boost::recursive_mutex::scoped_lock`,
+* `boost::recursive_mutex::scoped_try_lock`,
+* `boost::recursive_timed_mutex::scoped_lock`
+* `boost::recursive_timed_mutex::scoped_try_lock`
+* `boost::recursive_timed_mutex::timed_scoped_timed_lock`
+
+When `BOOST_THREAD_PROVIDES_NESTED_LOCKS` is defined Boost.Thread provides these deprecated feature.
+
+
+Use instead
+* `boost::unique_lock<boost::mutex>`,
+* `boost::unique_lock<boost::mutex>` with the `try_to_lock_t` constructor,
+* `boost::unique_lock<boost::timed_mutex>`
+* `boost::unique_lock<boost::timed_mutex>` with the `try_to_lock_t` constructor
+* `boost::unique_lock<boost::timed_mutex>`
+* `boost::unique_lock<boost::recursive_mutex>`,
+* `boost::unique_lock<boost::recursive_mutex>` with the `try_to_lock_t` constructor,
+* `boost::unique_lock<boost::recursive_timed_mutex>`
+* `boost::unique_lock<boost::recursive_timed_mutex>` with the `try_to_lock_t` constructor
+* `boost::unique_lock<boost::recursive_timed_mutex>`
+
+[warning This is a breaking change respect to version 1.x.]
+
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_PROVIDES_NESTED_LOCKS` if you want these features.
+When `BOOST_THREAD_VERSION<3` define `BOOST_THREAD_DONT_PROVIDE_NESTED_LOCKS` if you don't want thes features.
[endsect]
+[section:id thread::id]
+
+Boost.Thread uses by default a thread::id on Posix based on the pthread type (BOOST_THREAD_PROVIDES_BASIC_THREAD_ID). For backward compatibility and also for compilers that don't work well with this modification the user can define `BOOST_THREAD_DONT_PROVIDE_BASIC_THREAD_ID`.
+
+When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_BASIC_THREAD_ID ` if you want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_BASIC_THREAD_ID ` if you don't want these features.
+
+[endsect]
[section:shared_gen Shared Locking Generic]
The shared mutex implementation on Windows platform provides currently less functionality than the generic one that is used for PTheads based platforms. In order to have access to these functions, the user needs to define `BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN` to use the generic implementation, that while could be less efficient, provides all the functions.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN ` if you want these features.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_GENERIC_SHARED_MUTEX_ON_WIN ` if you don't want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_GENERIC_SHARED_MUTEX_ON_WIN ` if you don't want these features.
[endsect]
@@ -42,7 +170,7 @@
These conversions need to be used carefully to avoid deadlock or livelock. The user need to define explicitly `BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSION` to get these upwards conversions.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSION ` if you want these features.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_SHARED_MUTEX_UPWARDS_CONVERSION ` if you don't want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_SHARED_MUTEX_UPWARDS_CONVERSION ` if you don't want these features.
[endsect]
@@ -62,7 +190,7 @@
Since version 3.0.0 `boost::future` replaces `boost::unique_future` when `BOOST_THREAD_PROVIDES_FUTURE` is defined. The documentation doesn't contains anymore however `boost::unique_future`.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_FUTURE` if you want to use boost::future.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_FUTURE` if you want to use boost::unique_future.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_FUTURE` if you want to use boost::unique_future.
[endsect]
@@ -73,7 +201,7 @@
Since version 3.0.0 this difference in behavior can be configured. When `BOOST_THREAD_PROVIDES_PROMISE_LAZY` is defined the backward compatible behavior is provided.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_DONT_PROVIDE_PROMISE_LAZY ` if you want to use boost::future.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_PROVIDES_PROMISE_LAZY ` if you want to use boost::unique_future.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_PROVIDES_PROMISE_LAZY ` if you want to use boost::unique_future.
[endsect]
@@ -117,7 +245,7 @@
which introduces a dependency on Boost.Container. This feature is provided only if `BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS` is defined.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS ` if you want these features.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS ` if you don't want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS ` if you don't want these features.
[endsect]
@@ -126,10 +254,10 @@
C++11 has a different semantic for the thread destructor and the move assignment. Instead of detaching the thread, calls to terminate() if the thread was joinable. When `BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE` and `BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE` is defined Boost.Thread provides the C++ semantic.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE ` if you want these features.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE ` if you don't want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE ` if you don't want these features.
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE ` if you want these features.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE ` if you don't want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE ` if you don't want these features.
[endsect]
@@ -144,19 +272,57 @@
boost::once_flag once;
When `BOOST_THREAD_VERSION==2` define `BOOST_THREAD_PROVIDES_ONCE_CXX11` if you want these features.
-When `BOOST_THREAD_VERSION==3` define `BOOST_THREAD_DONT_PROVIDE_ONCE_CXX11` if you don't want these features.
+When `BOOST_THREAD_VERSION>=3` define `BOOST_THREAD_DONT_PROVIDE_ONCE_CXX11` if you don't want these features.
+
+[endsect]
+
+
+[section:deprecated Signature parameter for packaged_task]
+
+C++11 packaged task class has a Signature template parameter. When `BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK ` is defined Boost.Thread provides this C++ feature.
+
+[warning This is a breaking change respect to version 3.x.]
+
+When `BOOST_THREAD_VERSION<=3` define `BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK` if you want this feature.
+When `BOOST_THREAD_VERSION>4` define `BOOST_THREAD_DONT_PROVIDE_SIGNATURE_PACKAGED_TASK` if you don't want this feature.
[endsect]
-[section:deprecated Deprecated]
-Version 3.0.0 deprecates some Boost.Thread features.
+[section:thread_const-var thread constructor with variadic rvalue parameters]
-These deprecated features will be provided by default up to boost 1.52. If you don't want to include the deprecated features you could define `BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0`. Since 1.53 these features will not be included any more by default. Since this version, if you want to include the deprecated features yet you could define `BOOST_THREAD_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0`. These deprecated features will be only available until boost 1.55, that is you have 1 year and a half to move to the new features.
+C++11 thread constructor accep a variable number of rvalue argumentshas. When `BOOST_THREAD_PROVIDES_VARIADIC_THREAD ` is defined Boost.Thread provides this C++ feature if the following are not defined
+* BOOST_NO_CXX11_VARIADIC_TEMPLATES
+* BOOST_NO_CXX11_DECLTYPE
+* BOOST_NO_CXX11_RVALUE_REFERENCES
+* BOOST_NO_CXX11_HDR_TUPLE
+
+When `BOOST_THREAD_VERSION>4` define `BOOST_THREAD_DONT_PROVIDE_VARIADIC_THREAD ` if you don't want this feature.
[endsect]
+[section:get_invalid future<>::get() invalidates the future]
+
+C++11 future<>::get() invalidates the future once its value has been obtained. When `BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET ` is defined Boost.Thread provides this C++ feature.
+
+[warning This is a breaking change respect to version 3.x.]
+
+When `BOOST_THREAD_VERSION<=3` define `BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET` if you want this feature.
+When `BOOST_THREAD_VERSION>4` define `BOOST_THREAD_DONT_PROVIDE_FUTURE_INVALID_AFTER_GET` if you don't want this feature.
+
+[endsect]
+
+[section:intr Interruptions]
+
+Thread interruption, while useful, makes any interruption point less efficient than if the thread were not interruptible.
+
+When `BOOST_THREAD_PROVIDES_INTERRUPTIONS` is defined Boost.Thread provides interruptions.
+When `BOOST_THREAD_DONT_PROVIDE_INTERRUPTIONS` is defined Boost.Thread don't provide interruption.
+
+Boost.Thread defines BOOST_THREAD_PROVIDES_INTERRUPTIONS if neither BOOST_THREAD_PROVIDES_INTERRUPTIONS nor BOOST_THREAD_DONT_PROVIDE_INTERRUPTIONS are defined, so that there is no compatibility break.
+
+[endsect]
[section:version Version]
@@ -164,24 +330,33 @@
The default version is 2. In this case the following breaking or extending macros are defined if the opposite is not requested:
* `BOOST_THREAD_PROVIDES_PROMISE_LAZY`
-* `BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0`
The user can request the version 3 by defining `BOOST_THREAD_VERSION` to 3. In this case the following breaking or extending macros are defined if the opposite is not requested:
* Breaking change `BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION `
-* Breaking change `BOOST_THREAD_PROVIDES_FUTURE`
+* Conformity & Breaking change `BOOST_THREAD_PROVIDES_FUTURE`
* Uniformity `BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN`
* Extension `BOOST_THREAD_PROVIDES_SHARED_MUTEX_UPWARDS_CONVERSION`
* Conformity `BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS`
-* Breaking change BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE
-* Breaking change BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE
-* Breaking change `BOOST_THREAD_PROVIDES_ONCE_CXX11`
+* Conformity & Breaking change BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE
+* Conformity & Breaking change BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE
+* Conformity & Breaking change `BOOST_THREAD_PROVIDES_ONCE_CXX11`
* Breaking change `BOOST_THREAD_DONT_PROVIDE_PROMISE_LAZY`
-* Breaking change `BOOST_THREAD_DONT_PROVIDE_DEPRECATED_FEATURES_SINCE_V3_0_0`
The default value for `BOOST_THREAD_VERSION` will be changed to 3 since Boost 1.53.
+The user can request the version 4 by defining `BOOST_THREAD_VERSION` to 4. In this case the following breaking or extending macros are defined if the opposite is not requested:
+
+* Conformity & Breaking change `BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK `
+* Conformity & Breaking change `BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET `
+* Conformity `BOOST_THREAD_PROVIDES_VARIADIC_THREAD`
+* Breaking change `BOOST_THREAD_DONT_PROVIDE_THREAD_EQ`
+* Breaking change `BOOST_THREAD_DONT_USE_DATETIME`
+
+
+The default value for `BOOST_THREAD_VERSION` will be changed to 4 since Boost 1.56.
+
[endsect]
[endsect]
@@ -207,8 +382,19 @@
If __IBMCPP__ < 1100 the library defines
* `BOOST_THREAD_DONT_USE_CHRONO`
+* `BOOST_THREAD_USES_DATE`
And Boost.Thread doesn't links with Boost.Chrono.
+
[endsect]
+[section:ce WCE]
+
+If _WIN32_WCE && _WIN32_WCE==0x501 the library defines
+
+* `BOOST_THREAD_DONT_PROVIDE_FUTURE_CTOR_ALLOCATORS`
+
+
+[endsect]
+
[endsect]
Modified: branches/release/libs/thread/doc/future_ref.qbk
==============================================================================
--- branches/release/libs/thread/doc/future_ref.qbk (original)
+++ branches/release/libs/thread/doc/future_ref.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -12,12 +12,10 @@
namespace boost
{
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
- namespace future_state
+ namespace future_state // EXTENSION
{
enum state {uninitialized, waiting, ready, moved};
}
- #endif
enum class future_errc
{
@@ -69,12 +67,12 @@
template <typename R>
class shared_future;
- template <typename R>
+ template <typename S>
class packaged_task;
- template <class R> void swap(packaged_task<R>&, packaged_task<R>&) noexcept;
+ template <class S> void swap(packaged_task<S>&, packaged_task<S>&) noexcept;
- template <class R, class Alloc>
- struct uses_allocator<packaged_task <R>, Alloc>;
+ template <class S, class Alloc>
+ struct uses_allocator<packaged_task <S>, Alloc>;
template <class F>
future<typename result_of<typename decay<F>::type()>::type>
@@ -83,27 +81,31 @@
future<typename result_of<typename decay<F>::type()>::type>
async(launch policy, F f);
- // template <class F, class... Args>
- // future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
- // async(F&& f, Args&&... args); // NOT YET IMPLEMENTED
- // template <class F, class... Args>
- // future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
- // async(launch policy, F&& f, Args&&... args); // NOT YET IMPLEMENTED
-
-
+ template <class F, class... Args>
+ future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
+ async(F&& f, Args&&... args);
+ template <class F, class... Args>
+ future<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
+ async(launch policy, F&& f, Args&&... args);
+
template<typename Iterator>
void wait_for_all(Iterator begin,Iterator end); // EXTENSION
-
template<typename F1,typename... FS>
void wait_for_all(F1& f1,Fs&... fs); // EXTENSION
template<typename Iterator>
Iterator wait_for_any(Iterator begin,Iterator end);
-
template<typename F1,typename... Fs>
unsigned wait_for_any(F1& f1,Fs&... fs);
-
-
+
+ template <typename T>
+ future<typename decay<T>::type> make_future(T&& value); // EXTENSION
+ future<void> make_future(); // EXTENSION
+
+ template <typename T>
+ shared_future<typename decay<T>::type> make_shared_future(T&& value); // EXTENSION
+ shared_future<void> make_shared_future(); // EXTENSION
+
[section:future_state Enumeration `state`]
namespace future_state
@@ -115,18 +117,21 @@
[endsect]
-[section:future_errc Enumeration `future_errc `]
+[section:future_errc Enumeration `future_errc`]
enum class future_errc
{
- broken_promise,
- future_already_retrieved,
- promise_already_satisfied,
- no_state
+ broken_promise = implementation defined,
+ future_already_retrieved = implementation defined,
+ promise_already_satisfied = implementation defined,
+ no_state = implementation defined
}
+
+ The enum values of future_errc are distinct and not zero.
+
[endsect]
-[section:launch Enumeration `launch `]
+[section:launch Enumeration `launch`]
enum class launch
{
@@ -256,14 +261,23 @@
__unique_future__(__unique_future__ && other) noexcept;
__unique_future__& operator=(__unique_future__ && other) noexcept;
shared_future<R> share();
-
+ template<typename F>
+ __unique_future__<typename boost::result_of<F(__unique_future__&)>::type>
+ then(F&& func); // EXTENSION
+ template<typename S, typename F>
+ __unique_future__<typename boost::result_of<F(__unique_future__&)>::type>
+ then(S& scheduler, F&& func); // EXTENSION NOT_YET_IMPLEMENTED
+ template<typename F>
+ __unique_future__<typename boost::result_of<F(__unique_future__&)>::type>
+ then(launch policy, F&& func); // EXTENSION NOT_YET_IMPLEMENTED
+
void swap(__unique_future__& other) noexcept; // EXTENSION
// retrieving the value
R&& get();
// functions to check state
- bool valid() const;
+ bool valid() const noexcept;
bool is_ready() const; // EXTENSION
bool has_exception() const; // EXTENSION
bool has_value() const; // EXTENSION
@@ -275,15 +289,13 @@
template <class Clock, class Duration>
future_status wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
+ #if defined BOOST_THREAD_USES_DATE_TIME || defined BOOST_THREAD_DONT_USE_CHRONO
template<typename Duration>
- bool timed_wait(Duration const& rel_time) const;
- bool timed_wait_until(boost::system_time const& abs_time) const;
- #endif
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
- typedef future_state::state state;
- state get_state() const;
+ bool timed_wait(Duration const& rel_time) const; // DEPRECATED SINCE V3.0.0
+ bool timed_wait_until(boost::system_time const& abs_time) const; // DEPRECATED SINCE V3.0.0
#endif
+ typedef future_state::state state; // EXTENSION
+ state get_state() const; // EXTENSION
};
[section:default_constructor Default Constructor]
@@ -395,9 +407,14 @@
[[Postconditions:] [[unique_future_is_ready_link `this->is_ready()`] returns `true`. [unique_future_get_state_link
`this->get_state()`] returns __ready__.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception stored in the
-asynchronous result in place of a value.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception stored in the asynchronous result in place of a value.
+]]
[[Notes:] [`get()` is an ['interruption point].]]
@@ -407,16 +424,21 @@
[section:wait Member function `wait()`]
- void wait();
+ void wait() const;
[variablelist
[[Effects:] [If `*this` is associated with an asynchronous result, waits until the result is ready. If the result is not ready on
entry, and the result has a ['wait callback] set, that callback is invoked prior to waiting.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result
+associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [[unique_future_is_ready_link `this->is_ready()`] returns `true`. [unique_future_get_state_link
`this->get_state()`] returns __ready__.]]
@@ -427,11 +449,19 @@
[endsect]
-[section:timed_wait_duration Member function `timed_wait()`]
+[section:timed_wait_duration Member function `timed_wait()` DEPRECATED SINCE V3.0.0]
template<typename Duration>
bool timed_wait(Duration const& wait_duration);
+[warning
+DEPRECATED since 3.00.
+
+Available only up to Boost 1.56.
+
+Use instead __wait_for.
+]
+
[variablelist
[[Effects:] [If `*this` is associated with an asynchronous result, waits until the result is ready, or the time specified by
@@ -441,9 +471,13 @@
[[Returns:] [`true` if `*this` is associated with an asynchronous result, and that result is ready before the specified time has
elapsed, `false` otherwise.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [unique_future_is_ready_link `this->is_ready()`] returns `true` and
[unique_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -454,10 +488,18 @@
[endsect]
-[section:timed_wait_absolute Member function `timed_wait()`]
+[section:timed_wait_absolute Member function `timed_wait()` DEPRECATED SINCE V3.0.0]
bool timed_wait(boost::system_time const& wait_timeout);
+[warning
+DEPRECATED since 3.00.
+
+Available only up to Boost 1.56.
+
+Use instead __wait_until.
+]
+
[variablelist
[[Effects:] [If `*this` is associated with an asynchronous result, waits until the result is ready, or the time point specified by
@@ -467,9 +509,13 @@
[[Returns:] [`true` if `*this` is associated with an asynchronous result, and that result is ready before the specified time has
passed, `false` otherwise.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [unique_future_is_ready_link `this->is_ready()`] returns `true` and
[unique_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -501,9 +547,13 @@
]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [unique_future_is_ready_link `this->is_ready()`] returns `true` and
[unique_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -535,9 +585,13 @@
]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [unique_future_is_ready_link `this->is_ready()`] returns `true` and
[unique_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -551,7 +605,7 @@
[section:valid Member function `valid()`]
- bool valid() const;
+ bool valid() const noexcept;
[variablelist
@@ -625,6 +679,60 @@
[endsect]
+[section:then Member function `then()`]
+
+ template<typename F>
+ __unique_future__<typename boost::result_of<F(__unique_future__&)>::type>
+ then(F&& func); // EXTENSION
+ template<typename S, typename F>
+ __unique_future__<typename boost::result_of<F(__unique_future__&)>::type>
+ then(S& scheduler, F&& func); // EXTENSION
+ template<typename F>
+ __unique_future__<typename boost::result_of<F(__unique_future__&)>::type>
+ then(launch policy, F&& func); // EXTENSION
+
+[variablelist
+
+[[Notes:] [The three functions differ only by input parameters. The first only takes a callable object which accepts a
+future object as a parameter. The second function takes a scheduler as the first parameter and a callable object as
+the second parameter. The third function takes a launch policy as the first parameter and a callable object as the
+second parameter.]]
+
+[[Effects:] [
+
+- The continuation is called when the object's shared state is ready (has a value or exception stored).
+
+- The continuation launches according to the specified policy or scheduler.
+
+- When the scheduler or launch policy is not provided the continuation inherits the
+parent's launch policy or scheduler.
+
+- If the parent was created with std::promise or with a packaged_task (has no associated launch policy), the
+continuation behaves the same as the third overload with a policy argument of launch::async | launch::deferred and
+the same argument for func.
+
+- If the parent has a policy of launch::deferred and the continuation does not have a specified launch policy or
+scheduler, then the parent is filled by immediately calling .wait(), and the policy of the antecedent is
+launch::deferred
+
+]]
+
+[[Returns:] [An object of type future<decltype(func(*this))> that refers to the shared state created by the continuation.]]
+
+[[Postconditions:] [
+
+- The future object is moved to the parameter of the continuation function .
+
+- valid() == false on original future object immediately after it returns.
+
+]]
+
+]
+
+[endsect]
+
+
+
[endsect]
@@ -667,14 +775,12 @@
template <class Clock, class Duration>
future_status wait_until(const chrono::time_point<Clock, Duration>& abs_time) const;
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
+ #if defined BOOST_THREAD_USES_DATE_TIME || defined BOOST_THREAD_DONT_USE_CHRONO
template<typename Duration>
- bool timed_wait(Duration const& rel_time) const;
- bool timed_wait_until(boost::system_time const& abs_time) const;
- #endif
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
- state get_state() const noexcept;
+ bool timed_wait(Duration const& rel_time) const; // DEPRECATED SINCE V3.0.0
+ bool timed_wait_until(boost::system_time const& abs_time) const; // DEPRECATED SINCE V3.0.0
#endif
+ state get_state() const noexcept; // EXTENSION
};
[section:default_constructor Default Constructor]
@@ -706,8 +812,12 @@
[[Returns:] [If the result type `R` is a reference, returns the stored reference. If `R` is `void`, there is no return
value. Otherwise, returns a `const` reference to the value stored in the asynchronous result.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the
-result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+]]
[[Notes:] [`get()` is an ['interruption point].]]
@@ -717,15 +827,19 @@
[section:wait Member function `wait()`]
- void wait();
+ void wait() const;
[variablelist
[[Effects:] [If `*this` is associated with an asynchronous result, waits until the result is ready. If the result is not ready on
entry, and the result has a ['wait callback] set, that callback is invoked prior to waiting.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
+[[Throws:] [
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the
['wait callback] if such a callback is called.]]
[[Postconditions:] [[shared_future_is_ready_link `this->is_ready()`] returns `true`. [shared_future_get_state_link
@@ -751,9 +865,13 @@
[[Returns:] [`true` if `*this` is associated with an asynchronous result, and that result is ready before the specified time has
elapsed, `false` otherwise.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [shared_future_is_ready_link `this->is_ready()`] returns `true` and
[shared_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -777,9 +895,12 @@
[[Returns:] [`true` if `*this` is associated with an asynchronous result, and that result is ready before the specified time has
passed, `false` otherwise.]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [shared_future_is_ready_link `this->is_ready()`] returns `true` and
[shared_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -812,9 +933,12 @@
]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.]]
[[Postconditions:] [If this call returned `true`, then [shared_future_is_ready_link `this->is_ready()`] returns `true` and
[shared_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -846,9 +970,13 @@
]]
-[[Throws:] [__future_uninitialized__ if `*this` is not associated with an asynchronous result. __thread_interrupted__ if the result
-associated with `*this` is not ready at the point of the call, and the current thread is interrupted. Any exception thrown by the
-['wait callback] if such a callback is called.]]
+[[Throws:] [
+- __future_uninitialized__ if `*this` is not associated with an asynchronous result.
+
+- __thread_interrupted__ if the result associated with `*this` is not ready at the point of the call, and the current thread is interrupted.
+
+- Any exception thrown by the ['wait callback] if such a callback is called.
+]]
[[Postconditions:] [If this call returned `true`, then [shared_future_is_ready_link `this->is_ready()`] returns `true` and
[shared_future_get_state_link `this->get_state()`] returns __ready__.]]
@@ -861,7 +989,7 @@
[section:valid Member function `valid()`]
- bool valid() const;
+ bool valid() const noexcept;
[variablelist
@@ -962,14 +1090,12 @@
__unique_future__<R> get_future();
// Set the value
- void set_value(R& r);
- void set_value(R&& r);
+ void set_value(see below);
void set_exception(boost::exception_ptr e);
// setting the result with deferred notification
- // void set_value_at_thread_exit(const R& r); // NOT YET IMPLEMENTED
- // void set_value_at_thread_exit(see below); // NOT YET IMPLEMENTED
- // void set_exception_at_thread_exit(exception_ptr p); // NOT YET IMPLEMENTED
+ void set_value_at_thread_exit(see below);
+ void set_exception_at_thread_exit(exception_ptr p);
template<typename F>
void set_wait_callback(F f); // EXTENSION
@@ -1083,15 +1209,24 @@
[variablelist
-[[Effects:] [If `*this` was not associated with a result, allocate storage for a new asynchronous result and associate it with
-`*this`. Store the value `r` in the asynchronous result associated with `*this`. Any threads blocked waiting for the asynchronous
-result are woken.]]
+[[Effects:] [
+- If BOOST_THREAD_PROVIDES_PROMISE_LAZY is defined and if `*this` was not associated with a result, allocate storage for a new asynchronous result and associate it with `*this`.
+
+- Store the value `r` in the asynchronous result associated with `*this`. Any threads blocked waiting for the asynchronous
+result are woken.
+]]
[[Postconditions:] [All futures waiting on the asynchronous result are ['ready] and __unique_future_has_value__ or
__shared_future_has_value__ for those futures shall return `true`.]]
-[[Throws:] [__promise_already_satisfied__ if the result associated with `*this` is already ['ready]. `std::bad_alloc` if the memory
-required for storage of the result cannot be allocated. Any exception thrown by the copy or move-constructor of `R`.]]
+[[Throws:] [
+- __promise_already_satisfied__ if the result associated with `*this` is already ['ready].
+
+- __broken_promise__ if `*this` has no shared state.
+
+- `std::bad_alloc` if the memory required for storage of the result cannot be allocated.
+
+- Any exception thrown by the copy or move-constructor of `R`.]]
]
@@ -1103,21 +1238,83 @@
[variablelist
-[[Effects:] [If `*this` was not associated with a result, allocate storage for a new asynchronous result and associate it with
-`*this`. Store the exception `e` in the asynchronous result associated with `*this`. Any threads blocked waiting for the asynchronous
+[[Effects:] [
+- If BOOST_THREAD_PROVIDES_PROMISE_LAZY is defined and if `*this` was not associated with a result, allocate storage for a new asynchronous result and associate it with
+`*this`.
+
+- Store the exception `e` in the asynchronous result associated with `*this`. Any threads blocked waiting for the asynchronous
result are woken.]]
[[Postconditions:] [All futures waiting on the asynchronous result are ['ready] and __unique_future_has_exception__ or
__shared_future_has_exception__ for those futures shall return `true`.]]
-[[Throws:] [__promise_already_satisfied__ if the result associated with `*this` is already ['ready]. `std::bad_alloc` if the memory
-required for storage of the result cannot be allocated.]]
+[[Throws:] [
+- __promise_already_satisfied__ if the result associated with `*this` is already ['ready].
+
+- __broken_promise__ if `*this` has no shared state.
+
+- `std::bad_alloc` if the memory required for storage of the result cannot be allocated.
+]]
]
[endsect]
-[section:set_wait_callback Member Function `set_wait_callback()`]
+[section:set_value_at_thread_exit Member Function `set_value_at_thread_exit()`]
+
+ void set_value_at_thread_exit(R&& r);
+ void set_value_at_thread_exit(const R& r);
+ void promise<R&>::set_value_at_thread_exit(R& r);
+ void promise<void>::set_value_at_thread_exit();
+
+[variablelist
+
+[[Effects:] [
+Stores the value r in the shared state without making that state ready immediately.
+Schedules that state to be made ready when the current thread exits, after all objects of thread storage duration
+associated with the current thread have been destroyed.]]
+
+
+[[Throws:] [
+- __promise_already_satisfied__ if the result associated with `*this` is already ['ready].
+
+- __broken_promise__ if `*this` has no shared state.
+
+- `std::bad_alloc` if the memory required for storage of the result cannot be allocated.
+
+- Any exception thrown by the copy or move-constructor of `R`.
+]]
+
+]
+
+[endsect]
+
+[section:set_exception_at_thread_exit Member Function `set_exception_at_thread_exit()`]
+
+ void set_exception_at_thread_exit(boost::exception_ptr e);
+
+[variablelist
+
+[[Effects:] [
+Stores the exception pointer p in the shared state without making that state ready immediately.
+Schedules that state to be made ready when the current thread exits, after all objects of thread storage duration
+ associated with the current thread have been destroyed.]]
+
+[[Postconditions:] [All futures waiting on the asynchronous result are ['ready] and __unique_future_has_exception__ or
+__shared_future_has_exception__ for those futures shall return `true`.]]
+
+[[Throws:] [
+- __promise_already_satisfied__ if the result associated with `*this` is already ['ready].
+
+- __broken_promise__ if `*this` has no shared state.
+
+- `std::bad_alloc` if the memory required for storage of the result cannot be allocated.
+]]
+
+]
+
+[endsect]
+[section:set_wait_callback Member Function `set_wait_callback()` EXTENSION]
template<typename F>
void set_wait_callback(F f);
@@ -1141,25 +1338,27 @@
[section:packaged_task `packaged_task` class template]
+ template<typename S>
+ class packaged_task;
template<typename R
- // , class... ArgTypes // NOT YET IMPLEMENTED
+ , class... ArgTypes
>
- class packaged_task
+ class packaged_task<R(ArgTypes)>
{
public:
- typedef R result_type;
-
packaged_task(packaged_task&);// = delete;
packaged_task& operator=(packaged_task&);// = delete;
// construction and destruction
packaged_task() noexcept;
- explicit packaged_task(R(*f)());
+ explicit packaged_task(R(*f)(ArgTypes...));
template <class F>
explicit packaged_task(F&& f);
+ template <class Allocator>
+ packaged_task(allocator_arg_t, Allocator a, R(*f)(ArgTypes...));
template <class F, class Allocator>
packaged_task(allocator_arg_t, Allocator a, F&& f);
@@ -1177,9 +1376,8 @@
__unique_future__<R> get_future();
// execution
- void operator()();
- // void operator()(ArgTypes... ); // NOT YET IMPLEMENTED
- // void make_ready_at_thread_exit(ArgTypes...); // NOT YET IMPLEMENTED
+ void operator()(ArgTypes... );
+ void make_ready_at_thread_exit(ArgTypes...);
void reset();
template<typename F>
@@ -1188,22 +1386,29 @@
[section:task_constructor Task Constructor]
- packaged_task(R(*f)());
+ packaged_task(R(*f)(ArgTypes...));
template<typename F>
packaged_task(F&&f);
[variablelist
-[[Preconditions:] [`f()` is a valid expression with a return type convertible to `R`. Invoking a copy of `f` shall behave the same
+[[Preconditions:] [`f()` is a valid expression with a return type convertible to `R`. Invoking a copy of `f` must behave the same
as invoking `f`.]]
[[Effects:] [Constructs a new __packaged_task__ with `boost::forward<F>(f)` stored as the associated task.]]
-[[Throws:] [Any exceptions thrown by the copy (or move) constructor of `f`. `std::bad_alloc` if memory for the internal data
-structures could not be allocated.]]
+[[Throws:] [
+
+- Any exceptions thrown by the copy (or move) constructor of `f`.
+
+- `std::bad_alloc` if memory for the internal data structures could not be allocated.
+]]
+
+[[Notes:] [The R(*f)(ArgTypes...)) overload to allow passing a function without needing to use `&`.]]
+
+[[Remark:] [This constructor doesn't participate in overload resolution if decay<F>::type is the same type as boost::packaged_task<R>.]]
-[[Notes:] [The R(*f)()) overload to allow passing a function without needing to use `&`.]]
]
@@ -1212,7 +1417,7 @@
[section:alloc_constructor Allocator Constructor]
template <class Allocator>
- packaged_task(allocator_arg_t, Allocator a, R(*f)());
+ packaged_task(allocator_arg_t, Allocator a, R(*f)(ArgTypes...));
template <class F, class Allocator>
packaged_task(allocator_arg_t, Allocator a, F&& f);
@@ -1227,7 +1432,7 @@
structures could not be allocated.]]
[[Notes:] [Available only if BOOST_THREAD_FUTURE_USES_ALLOCATORS is defined.]]
-[[Notes:] [The R(*f)()) overload to allow passing a function without needing to use `&`.]]
+[[Notes:] [The R(*f)(ArgTypes...)) overload to allow passing a function without needing to use `&`.]]
]
@@ -1311,13 +1516,40 @@
[[Postconditions:] [All futures waiting on the asynchronous result are ['ready]]]
-[[Throws:] [__task_moved__ if ownership of the task associated with `*this` has been moved to another instance of
-__packaged_task__. __task_already_started__ if the task has already been invoked.]]
+[[Throws:] [
+
+- __task_moved__ if ownership of the task associated with `*this` has been moved to another instance of __packaged_task__.
+
+- __task_already_started__ if the task has already been invoked.]]
+
+]
+
+[endsect]
+
+[section:make_ready_at_thread_exit Member Function `make_ready_at_thread_exit()`]
+
+ void make_ready_at_thread_exit(ArgTypes...);
+
+[variablelist
+
+[[Effects:] [Invoke the task associated with `*this` and store the result in the corresponding future. If the task returns normally,
+the return value is stored as the asynchronous result, otherwise the exception thrown is stored.
+In either case, this is done without making that state ready immediately.
+Schedules the shared state to be made ready when the current thread exits, after all objects of thread storage
+duration associated with the current thread have been destroyed.]]
+
+[[Throws:] [
+
+- __task_moved__ if ownership of the task associated with `*this` has been moved to another instance of __packaged_task__.
+
+- __task_already_started__ if the task has already been invoked.
+]]
]
[endsect]
+
[section:reset Member Function `reset()`]
void reset();
@@ -1371,17 +1603,28 @@
template <class F>
__unique_future__<typename result_of<typename decay<F>::type()>::type>
- async(F f);
+ async(F&& f);
template <class F>
__unique_future__<typename result_of<typename decay<F>::type()>::type>
- async(launch policy, F f);
+ async(launch policy, F&& f);
+ template <class F, class... Args>
+ __unique_future__<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
+ async(F&& f, Args&&... args);
+ template <class F, class... Args>
+ __unique_future__<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>
+ async(launch policy, F&& f, Args&&... args);
+
The function template async provides a mechanism to launch a function potentially in a new thread and
provides the result of the function in a future object with which it shares a shared state.
[warning `async(launch::deferred, F)` is NOT YET IMPLEMENTED!]
+[warning the variadic prototype is provided only on C++11 compilers supporting rvalue references, variadic templates, decltype and a standard library providing <tuple>, and BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK is defined.]
+
+[heading Non-Variadic variant]
+
[variablelist
[[Requires:] [
@@ -1414,7 +1657,7 @@
If the implementation chooses the `launch::async` policy,
-- a call to a waiting function on an asynchronous return object that shares the shared state created by this async call shall block until the associated thread has completed, as if joined;
+- a call to a non-timed waiting function on an asynchronous return object that shares the shared state created by this async call shall block until the associated thread has completed, as if joined;
- the associated thread completion synchronizes with the return from the first function that successfully detects the ready status of the shared state or with the return from the last function that releases the shared state, whichever happens first.
]]
@@ -1433,38 +1676,69 @@
]
-[/
+[heading Variadic variant]
[variablelist
-[[Requires:] [F and each Ti in Args shall satisfy the MoveConstructible requirements. INVOKE (DECAY_- COPY (boost::forward<F>(f)), decay_copy (boost::forward<Args>(args))...) shall be a valid expression.
+[[Requires:] [
+`F` and each `Ti` in `Args` shall satisfy the `MoveConstructible` requirements.
+
+ invoke (decay_copy (boost::forward<F>(f)), decay_copy (boost::forward<Args>(args))...)
+
+shall be a valid expression.
]]
-[[Effects:] [The first function behaves the same as a call to the second function with a policy argument of launch::async | launch::deferred and the same arguments for F and Args. The second function creates a shared state that is associated with the returned future object. The further behavior of the second function depends on the policy argument as follows (if more than one of these conditions applies, the implementation may choose any of the corresponding policies):
-- if policy & launch::async is non-zero - calls INVOKE (decay_copy (boost::forward<F>(f)), decay_copy (boost::forward<Args>(args))...) (20.8.2, 30.3.1.2) as if in a new thread of exe- cution represented by a thread object with the calls to decay_copy() being evaluated in the thread that called async. Any return value is stored as the result in the shared state. Any excep- tion propagated from the execution of INVOKE(decay_copy(boost::forward<F>(f)), DECAY_- COPY (boost::forward<Args>(args))...) is stored as the exceptional result in the shared state. The thread object is stored in the shared state and affects the behavior of any asynchronous return objects that reference that state.
-- if policy & launch::deferred is non-zero - Stores decay_copy (boost::forward<F>(f)) and decay_copy (boost::forward<Args>(args))... in the shared state. These copies of f and args constitute a deferred function. Invocation of the deferred function evaluates INVOKE (boost::move(g), boost::move(xyz)) where g is the stored value of decay_copy (boost::forward<F>(f)) and xyz is the stored copy of decay_copy (boost::forward<Args>(args)).... The shared state is not made ready until the function has completed. The first call to a non-timed waiting function (30.6.4) on an asynchronous return object referring to this shared state shall invoke the deferred func- tion in the thread that called the waiting function. Once evaluation of INVOKE (boost::move(g), boost::move(xyz)) begins, the function is no longer considered deferred.
+[[Effects:] [
+
+- The first function behaves the same as a call to the second function with a policy argument of `launch::async | launch::deferred` and the same arguments for `F` and `Args`.
+
+- The second function creates a shared state that is associated with the returned future object.
+The further behavior of the second function depends on the policy argument as follows (if more than one of these conditions applies,
+the implementation may choose any of the corresponding policies):
+
+ - if `policy & launch::async` is non-zero - calls `invoke(decay_copy(forward<F>(f)), decay_copy (forward<Args>(args))...)`
+ as if in a new thread of execution represented by a thread object with the calls to `decay_copy()` being evaluated in the thread that called `async`.
+ Any return value is stored as the result in the shared state.
+ Any exception propagated from the execution of `invoke(decay_copy(boost::forward<F>(f)), decay_copy (boost::forward<Args>(args))...)`
+ is stored as the exceptional result in the shared state. The thread object is stored in the shared state and
+ affects the behavior of any asynchronous return objects that reference that state.
+
+ - if `policy & launch::deferred` is non-zero - Stores `decay_copy(forward<F>(f))` and `decay_copy(forward<Args>(args))...` in the shared state.
+ These copies of `f` and `args` constitute a deferred function. Invocation of the deferred function evaluates
+ `invoke(move(g), move(xyz))` where `g` is the stored value of `decay_copy(forward<F>(f))` and `xyz` is the stored copy of `decay_copy(forward<Args>(args))...`.
+ The shared state is not made ready until the function has completed. The first call to a non-timed waiting function on
+ an asynchronous return object referring to this shared state shall invoke the deferred function in the thread that called the waiting function.
+ Once evaluation of `invoke(move(g), move(xyz))` begins, the function is no longer considered deferred.
]]
-[[Note:] [If this policy is specified together with other policies, such as when using a policy value of launch::async | launch::deferred, implementations should defer invocation or the selection of the policy when no more concurrency can be effectively exploited.]]
-[[Returns:] [An object of type __unique_future__<typename result_of<typename decay<F>::type(typename de- cay<Args>::type...)>::type> that refers to the shared state created by this call to async.]]
+[[Note:] [If this policy is specified together with other policies, such as when using a policy value of `launch::async | launch::deferred`,
+implementations should defer invocation or the selection of the policy when no more concurrency can be effectively exploited.]]
+
+[[Returns:] [An object of type `__unique_future__<typename result_of<typename decay<F>::type(typename decay<Args>::type...)>::type>`
+that refers to the shared state created by this call to `async`.]]
[[Synchronization:] [Regardless of the provided policy argument,
-- the invocation of async synchronizes with (1.10) the invocation of f. (Note: This statement applies even when the corresponding future object is moved to another thread.); and
-- the completion of the function f is sequenced before (1.10) the shared state is made ready. (Note: f might not be called at all, so its completion might never happen.)
-If the implementation chooses the launch::async policy,
-- a call to a waiting function on an asynchronous return object that shares the shared state created by this async call shall block until the associated thread has completed, as if joined;
-- the associated thread completion synchronizes with (1.10) the return from the first function that successfully detects the ready status of the shared state or with the return from the last function that releases the shared state, whichever happens first.
+- the invocation of async synchronizes with the invocation of `f`. (Note: This statement applies even when the corresponding future object is moved to another thread.); and
+
+- the completion of the function `f` is sequenced before the shared state is made ready. (Note: f might not be called at all, so its completion might never happen.)
+If the implementation chooses the `launch::async` policy,
+
+- a call to a waiting function on an asynchronous return object that shares the shared state created by this async call
+shall block until the associated thread has completed, as if joined;
+
+- the associated thread completion synchronizes with the return from the first function that successfully detects the ready status of the shared state or
+with the return from the last function that releases the shared state, whichever happens first.
]]
-[[Throws:] [system_error if policy is launch::async and the implementation is unable to start a new thread.
+[[Throws:] [`system_error` if policy is `launch::async` and the implementation is unable to start a new thread.
]]
[[Error conditions:][
-- resource_unavailable_try_again - if policy is launch::async and the system is unable to start a new thread.
+- `resource_unavailable_try_again` - if policy is `launch::async` and the system is unable to start a new thread.
]]
[[Remarks:] [The first signature shall not participate in overload resolution if decay<F>::type is boost::launch.
@@ -1472,10 +1746,6 @@
]
-]
-
-
-
[endsect]
@@ -1555,5 +1825,72 @@
[endsect]
+[section:make_future Non-member function `make_future()`]
+
+ template <typename T>
+ future<typename decay<T>::type> make_future(T&& value); // EXTENSION
+ future<void> make_future(); // EXTENSION
+
+
+[variablelist
+
+[[Effects:] [
+The value that is passed in to the function is moved to the shared state of the returned function if it is an rvalue.
+Otherwise the value is copied to the shared state of the returned function.
+.]]
+
+[[Returns:] [
+
+- future<T>, if function is given a value of type T
+
+- future<void>, if the function is not given any inputs.
+
+]]
+
+[[Postcondition:] [
+
+- Returned future<T>, valid() == true
+
+- Returned future<T>, is_ready() = true
+
+]]
+
+]
+
+
+[endsect]
+[section:make_shared_future Non-member function `make_shared_future()`]
+
+ template <typename T>
+ shared_future<typename decay<T>::type> make_shared_future(T&& value); // EXTENSION
+ shared_future<void> make_shared_future(); // EXTENSION
+
+[variablelist
+
+[[Effects:] [
+The value that is passed in to the function is moved to the shared state of the returned function if it is an rvalue.
+Otherwise the value is copied to the shared state of the returned function.
+.]]
+
+[[Returns:] [
+
+- shared_future<T>, if function is given a value of type T
+
+- shared_future<void>, if the function is not given any inputs.
+
+]]
+
+[[Postcondition:] [
+
+- Returned shared_future<T>, valid() == true
+
+- Returned shared_future<T>, is_ready() = true
+
+]]
+
+]
+
+[endsect]
+
[endsect]
Modified: branches/release/libs/thread/doc/futures.qbk
==============================================================================
--- branches/release/libs/thread/doc/futures.qbk (original)
+++ branches/release/libs/thread/doc/futures.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -93,10 +93,13 @@
appropriate for the type.
On the other hand, many instances of __shared_future__ may reference the same result. Instances can be freely copied and assigned,
-and __shared_future_get__ returns a `const` reference so that multiple calls to __shared_future_get__ are safe. You can move an
+and __shared_future_get__ returns a non `const` reference so that multiple calls to __shared_future_get__ are safe. You can move an
instance of __unique_future__ into an instance of __shared_future__, thus transferring ownership of the associated asynchronous
result, but not vice-versa.
+`boost::async` is a simple way of running asynchronous tasks. A call to `boost::async` returns a __unique_future__ that will contain the result of the task.
+
+
You can wait for futures either individually or with one of the __wait_for_any__ and __wait_for_all__ functions.
[endsect]
@@ -184,6 +187,280 @@
[endsect]
+[section:at_thread_exit Handling Detached Threads and Thread Specific Variables]
+
+Detached threads pose a problem for objects with thread storage duration.
+If we use a mechanism other than `thread::__join` to wait for a __thread to complete its work - such as waiting for a future to be ready -
+then the destructors of thread specific variables will still be running after the waiting thread has resumed.
+This section explain how the standard mechanism can be used to make such synchronization safe by ensuring that the
+objects with thread storage duration are destroyed prior to the future being made ready. e.g.
+
+ int find_the_answer(); // uses thread specific objects
+ void thread_func(boost::promise<int>&& p)
+ {
+ p.set_value_at_thread_exit(find_the_answer());
+ }
+
+ int main()
+ {
+ boost::promise<int> p;
+ boost::thread t(thread_func,boost::move(p));
+ t.detach(); // we're going to wait on the future
+ std::cout<<p.get_future().get()<<std::endl;
+ }
+
+When the call to `get()` returns, we know that not only is the future value ready, but the thread specific variables
+on the other thread have also been destroyed.
+
+Such mechanisms are provided for `boost::condition_variable`, `boost::promise` and `boost::packaged_task`. e.g.
+
+ void task_executor(boost::packaged_task<void(int)> task,int param)
+ {
+ task.make_ready_at_thread_exit(param); // execute stored task
+ } // destroy thread specific and wake threads waiting on futures from task
+
+Other threads can wait on a future obtained from the task without having to worry about races due to the execution of
+destructors of the thread specific objects from the task's thread.
+
+ boost::condition_variable cv;
+ boost::mutex m;
+ complex_type the_data;
+ bool data_ready;
+
+ void thread_func()
+ {
+ boost::unique_lock<std::mutex> lk(m);
+ the_data=find_the_answer();
+ data_ready=true;
+ boost::notify_all_at_thread_exit(cv,boost::move(lk));
+ } // destroy thread specific objects, notify cv, unlock mutex
+
+ void waiting_thread()
+ {
+ boost::unique_lock<std::mutex> lk(m);
+ while(!data_ready)
+ {
+ cv.wait(lk);
+ }
+ process(the_data);
+ }
+
+The waiting thread is guaranteed that the thread specific objects used by `thread_func()` have been destroyed by the time
+`process(the_data)` is called. If the lock on `m` is released and re-acquired after setting `data_ready` and before calling
+`boost::notify_all_at_thread_exit()` then this does NOT hold, since the thread may return from the wait due to a
+spurious wake-up.
+
+[endsect]
+
+[section:async Executing asynchronously]
+
+`boost::async` is a simple way of running asynchronous tasks to make use of the available hardware concurrency.
+A call to `boost::async` returns a `boost::future` that will contain the result of the task. Depending on
+the launch policy, the task is either run asynchronously on its own thread or synchronously on whichever thread
+calls the `wait()` or `get()` member functions on that `future`.
+
+A launch policy of either boost::launch::async, which asks the runtime to create an asynchronous thread,
+or boost::launch::deferred, which indicates you simply want to defer the function call until a later time (lazy evaluation).
+This argument is optional - if you omit it your function will use the default policy.
+
+For example, consider computing the sum of a very large array. The first task is to not compute asynchronously when
+the overhead would be significant. The second task is to split the work into two pieces, one executed by the host
+thread and one executed asynchronously.
+
+
+ int parallel_sum(int* data, int size)
+ {
+ int sum = 0;
+ if ( size < 1000 )
+ for ( int i = 0; i < size; ++i )
+ sum += data[i];
+ else {
+ auto handle = boost::async(parallel_sum, data+size/2, size-size/2);
+ sum += parallel_sum(data, size/2);
+ sum += handle.get();
+ }
+ return sum;
+ }
+
+
+
+[endsect]
+
+[section:shared Shared Futures]
+
+`shared_future` is designed to be shared between threads,
+that is to allow multiple concurrent get operations.
+
+[heading Multiple get]
+
+The second `get()` call in the following example future
+
+ void bad_second_use( type arg ) {
+
+ auto ftr = async( [=]{ return work( arg ); } );
+ if ( cond1 )
+ {
+ use1( ftr.get() );
+ } else
+ {
+ use2( ftr.get() );
+ }
+ use3( ftr.get() ); // second use is undefined
+ }
+
+Using a `shared_mutex` solves the issue
+
+ void good_second_use( type arg ) {
+
+ shared_future<type> ftr = async( [=]{ return work( arg ); } );
+ if ( cond1 )
+ {
+ use1( ftr.get() );
+ } else
+ {
+ use2( ftr.get() );
+ }
+ use3( ftr.get() ); // second use is defined
+ }
+
+[heading share()]
+
+Namming the return type when declaring the `shared_future` is needed; auto is not available within template argument lists.
+Here `share()` could be used to simplify the code
+
+ void better_second_use( type arg ) {
+
+ auto ftr = async( [=]{ return work( arg ); } ).share();
+ if ( cond1 )
+ {
+ use1( ftr.get() );
+ } else
+ {
+ use2( ftr.get() );
+ }
+ use3( ftr.get() ); // second use is defined
+ }
+
+[heading Writting on get()]
+
+The user can either read or write the future avariable.
+
+ void write_to_get( type arg ) {
+
+ auto ftr = async( [=]{ return work( arg ); } ).share();
+ if ( cond1 )
+ {
+ use1( ftr.get() );
+ } else
+ {
+ if ( cond2 )
+ use2( ftr.get() );
+ else
+ ftr.get() = something(); // assign to non-const reference.
+ }
+ use3( ftr.get() ); // second use is defined
+ }
+
+This works because the `shared_future<>::get()` function returns a non-const reference to the appropriate storage.
+Of course the access to this storage must be ensured by the user. The library doesn't ensure the access to the internal storage is thread safe.
+
+There has been some work by the C++ standard committe on an `atomic_future` that behaves as an `atomic` variable, that is is thread_safe,
+and a `shared_future` that can be shared between several threads, but there were not enough consensus and time to get it ready for C++11.
+
+[endsect]
+
+[section:make_future Making immediate futures easier]
+
+Some functions may know the value at the point of construction. In these cases the value is immediately available,
+but needs to be returned as a future or shared_future. By using make_future (make_shared_future) a future (shared_future)
+can be created which holds a pre-computed result in its shared state.
+
+Without these features it is non-trivial to create a future directly from a value.
+First a promise must be created, then the promise is set, and lastly the future is retrieved from the promise.
+This can now be done with one operation.
+
+[heading make_future / make_shared_future]
+
+This function creates a future for a given value. If no value is given then a future<void> is returned.
+This function is primarily useful in cases where sometimes, the return value is immediately available, but sometimes
+it is not. The example below illustrates, that in an error path the value is known immediately, however in other paths
+the function must return an eventual value represented as a future.
+
+
+ boost::future<int> compute(int x)
+ {
+ if (x == 0) return boost::make_future(0);
+ if (x < 0) return boost::make_future(-1);
+ boost::future<int> f1 = boost::async([]() { return x+1; });
+ return f1;
+ }
+
+There are two variations of this function. The first takes a value of any type, and returns a future of that type.
+The input value is passed to the shared state of the returned future. The second version takes no input and returns a future<void>.
+make_shared_future has the same functionality as make_future, except has a return type of shared_future.
+
+
+[endsect]
+
+[section:then Associating future continuations]
+
+In asynchronous programming, it is very common for one asynchronous operation, on completion, to invoke a second
+operation and pass data to it. The current C++ standard does not allow one to register a continuation to a future.
+With .then, instead of waiting for the result, a continuation is "attached" to the asynchronous operation, which is
+invoked when the result is ready. Continuations registered using the .then function will help to avoid blocking waits
+or wasting threads on polling, greatly improving the responsiveness and scalability of an application.
+
+future.then provides the ability to sequentially compose two futures by declaring one to be the continuation of another.
+With .then the antecedent future is ready (has a value or exception stored in the shared state) before the continuation
+starts as instructed by the lambda function.
+
+In the example below the future<int> f2 is registered to be a continuation of future<int> f1 using the .then member
+function. This operation takes a lambda function which describes how f2 should proceed after f1 is ready.
+
+
+ #include <boost/thread/future.hpp>
+ using namespace boost;
+ int main()
+ {
+ future<int> f1 = async([]() { return 123; });
+ future<string> f2 = f1.then([](future<int> f) { return f.get().to_string(); // here .get() won't block });
+ }
+
+One key feature of this function is the ability to chain multiple asynchronous operations. In asynchronous programming,
+it's common to define a sequence of operations, in which each continuation executes only when the previous one completes.
+In some cases, the antecedent future produces a value that the continuation accepts as input. By using future.then,
+creating a chain of continuations becomes straightforward and intuitive:
+
+ myFuture.then(...).then(...).then(...).
+
+Some points to note are:
+
+* Each continuation will not begin until the preceding has completed.
+* If an exception is thrown, the following continuation can handle it in a try-catch block
+
+
+Input Parameters:
+
+* Lambda function2: One option which was considered was to follow JavaScript's approach and take two functions, one for
+success and one for error handling. However this option is not viable in C++ as there is no single base type for
+exceptions as there is in JavaScript. The lambda function takes a future as its input which carries the exception
+through. This makes propagating exceptions straightforward. This approach also simplifies the chaining of continuations.
+* Scheduler: Providing an overload to .then, to take a scheduler reference places great flexibility over the execution
+of the future in the programmer's hand. As described above, often taking a launch policy is not sufficient for powerful
+asynchronous operations. The lifetime of the scheduler must outlive the continuation.
+* Launch policy: if the additional flexibility that the scheduler provides is not required.
+
+
+Return values: The decision to return a future was based primarily on the ability to chain multiple continuations using
+.then. This benefit of composability gives the programmer incredible control and flexibility over their code. Returning
+a future object rather than a shared_future is also a much cheaper operation thereby improving performance. A
+shared_future object is not necessary to take advantage of the chaining feature. It is also easy to go from a future
+to a shared_future when needed using future::share().
+
+
+[endsect]
+
+
[include future_ref.qbk]
[endsect]
\ No newline at end of file
Modified: branches/release/libs/thread/doc/mutex_concepts.qbk
==============================================================================
--- branches/release/libs/thread/doc/mutex_concepts.qbk (original)
+++ branches/release/libs/thread/doc/mutex_concepts.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -20,8 +20,18 @@
[section:basic_lockable `BasicLockable` Concept]
+ // #include <boost/thread/lockable_concepts.hpp>
+
+ namespace boost
+ {
+
+ template<typename L>
+ class BasicLockable;
+ }
+
+
The __BasicLockable concept models exclusive ownership.
-A type `L` meets the __BasicLockable requiremets if the following expressions are well-formed and have the specified semantics (`m` denotes a value of type `L`):
+A type `L` meets the __BasicLockable requirements if the following expressions are well-formed and have the specified semantics (`m` denotes a value of type `L`):
* `m.__lock();`
* `m.__unlock();`
@@ -38,7 +48,7 @@
[[Return type:] [`void`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
[[Error Conditions:] [
@@ -59,22 +69,44 @@
[variablelist
-[[Precondition:] [The current thread owns `m`.]]
+[[Requires:] [The current thread owns `m`.]]
-[[Effects:] [Releases ownership by the current thread.]]
+[[Effects:] [Releases a lock on `m` by the current thread.]]
[[Return type:] [`void`.]]
-[[Postcondition:] [The current thread no longer owns `m`.]]
-
[[Throws:] [Nothing.]]
]
[endsect]
+[section:is_basic_lockable `is_basic_lockable` trait]
+
+ // #include <boost/thread/lockable_traits.hpp>
+
+ namespace boost
+ {
+ namespace sync
+ {
+ template<typename L>
+ class is_basic_lockable;
+ }
+ }
+
+Some of the algorithms on mutexes use this trait via SFINAE. If BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES is defined you will need to specialize this traits for the models of BasicLockable you could build.
+
+[endsect]
[endsect]
+
[section:lockable `Lockable` Concept]
+ // #include <boost/thread/lockable_concepts.hpp>
+ namespace boost
+ {
+ template<typename L>
+ class Lockable;
+ }
+
A type `L` meets the __Lockable requirements if it meets the __BasicLockable requirements and the following expressions are well-formed and have the specified semantics (`m` denotes a value of type `L`):
* `m.__try_lock()`
@@ -98,10 +130,64 @@
]
[endsect]
+[section:is_lockable `is_lockable` trait]
+
+ // #include <boost/thread/lockable_traits.hpp>
+ namespace boost
+ {
+ namespace sync
+ {
+ template<typename L>
+ class is_lockable;
+ }
+ }
+
+Some of the algorithms on mutexes use this trait via SFINAE. If BOOST_THREAD_NO_AUTO_DETECT_MUTEX_TYPES is defined you will need to specialize this traits for the models of Lockable you could build.
+
+[endsect]
+[endsect]
+
+[section:recursive Recursive Lockable Concept]
+
+The user could require that the mutex passed to an algorithm is a recursive one. Whether a lockable is recursive or not can not be checked using template meta-programming. This is the motivation for the following trait.
+
+
+[section:is_recursive_mutex_sur_parolle `is_recursive_mutex_sur_parolle` trait]
+
+ // #include <boost/thread/lockable_traits.hpp>
+
+ namespace boost
+ {
+ namespace sync
+ {
+ template<typename L>
+ class is_recursive_mutex_sur_parolle: false_type;
+ template<>
+ class is_recursive_mutex_sur_parolle<recursive_mutex>: true_type;
+ template<>
+ class is_recursive_mutex_sur_parolle<timed_recursive_mutex>: true_type;
+ }
+ }
+
+The trait `is_recursive_mutex_sur_parolle` is `false_type` by default and is specialized for the provide `recursive_mutex` and `timed_recursive_mutex`.
+
+It should be specialized by the user providing other model of recursive lockable.
+
[endsect]
+[endsect]
+
+
[section:timed_lockable `TimedLockable` Concept]
+ // #include <boost/thread/lockable_concepts.hpp>
+
+ namespace boost
+ {
+ template<typename L>
+ class TimedLockable;
+ }
+
The __timed_lockable_concept__ refines the __lockable_concept__ to add support for
timeouts when trying to acquire the lock.
@@ -144,9 +230,14 @@
]
[endsect]
-[heading Deprecated V3.0.0]
+[warning
+DEPRECATED since 3.00. The following expressions were required on version 2, but are now deprecated.
+
+Available only up to Boost 1.56.
+
+Use instead __try_lock_for, __try_lock_until.
+]
-The following expressions were required on version 2, but are now deprecated.
[*Variables:]
@@ -171,7 +262,7 @@
[[Postcondition:] [If the call returns `true`, the current thread owns `m`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -190,6 +281,15 @@
[section:shared_lockable `SharedLockable` Concept]
+ // #include <boost/thread/lockable_concepts.hpp>
+
+ namespace boost
+ {
+ template<typename L>
+ class SharedLockable;
+ }
+
+
The __shared_lockable_concept__ is a refinement of the __timed_lockable_concept__ that
allows for ['shared ownership] as well as ['exclusive ownership]. This is the
standard multiple-reader / single-write model: at most one thread can have
@@ -223,7 +323,7 @@
[[Postcondition:] [The current thread has shared ownership of `m`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -238,7 +338,7 @@
[[Postcondition:] [If the call returns `true`, the current thread has shared ownership of `m`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -255,7 +355,7 @@
[[Postcondition:] [If the call returns `true`, the current thread has shared
ownership of `m`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -272,7 +372,7 @@
[[Postcondition:] [If the call returns `true`, the current thread has shared
ownership of `m`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -292,9 +392,13 @@
]
[endsect]
-[heading Deprecated V3]
+[warning
+DEPRECATED since 3.00. The following expressions were required on version 2, but are now deprecated.
+
+Available only up to Boost 1.56.
-The following expressions were required on version 1, but are now deprecated.
+Use instead __try_lock_shared_for, __try_lock_shared_until.
+]
[*Variables:]
@@ -318,7 +422,7 @@
[[Postcondition:] [If the call returns `true`, the current thread has shared
ownership of `m`.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -329,6 +433,15 @@
[section:upgrade_lockable `UpgradeLockable` Concept]
+ // #include <boost/thread/lockable_concepts.hpp>
+
+ namespace boost
+ {
+ template<typename L>
+ class UpgradeLockable;
+ }
+
+
The __upgrade_lockable_concept__ is a refinement of the __shared_lockable_concept__ that allows for ['upgradable ownership] as well
as ['shared ownership] and ['exclusive ownership]. This is an extension to the multiple-reader / single-write model provided by the
__shared_lockable_concept__: a single thread may have ['upgradable ownership] at the same time as others have ['shared
@@ -395,7 +508,7 @@
[[Synchronization:] [Prior `__unlock_upgrade()` operations on the same object synchronize with this operation.]]
-[[Throws:] [__thread_resource_error__ if an error occurs.]]
+[[Throws:] [__lock_error__ if an error occurs.]]
]
[endsect]
@@ -789,9 +902,10 @@
[endsect]
-[section:locks Lock Types]
+[section:lock_option Lock Options]
- //#include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks_options.hpp>
namespace boost
{
@@ -801,28 +915,11 @@
constexpr defer_lock_t defer_lock;
constexpr try_to_lock_t try_to_lock;
constexpr adopt_lock_t adopt_lock;
-
- template<typename Lockable>
- class lock_guard
- template<typename Lockable>
- class unique_lock;
- template<typename Mutex>
- void swap(unique_lock <Mutex>& lhs, unique_lock <Mutex>& rhs);
- template<typename Lockable>
- class shared_lock;
- template<typename Mutex>
- void swap(shared_lock<Mutex>& lhs,shared_lock<Mutex>& rhs);
- template<typename Lockable>
- class upgrade_lock;
- template<typename Mutex>
- void swap(upgrade_lock <Mutex>& lhs, upgrade_lock <Mutex>& rhs);
- template <class Mutex>
- class upgrade_to_unique_lock;
- }
[section:lock_tags Lock option tags]
#include <boost/thread/locks.hpp>
+ #include <boost/thread/locks_options.hpp>
struct defer_lock_t {};
struct try_to_lock_t {};
@@ -839,9 +936,28 @@
[endsect]
+[endsect]
+
+[section:lock_guard Lock Guard]
+
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_guard.hpp>
+
+ namespace boost
+ {
+
+ template<typename Lockable>
+ class lock_guard
+ template <typename Lockable>
+ lock_guard<Lockable> make_lock_guard(Lockable& mtx); // EXTENSION
+ template <typename Lockable>
+ lock_guard<Lockable> make_lock_guard(Lockable& mtx, adopt_lock_t); // EXTENSION
+ }
+
[section:lock_guard Class template `lock_guard`]
- //#include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_guard.hpp>
template<typename Lockable>
class lock_guard
@@ -858,7 +974,7 @@
the constructor parameter. On destruction, the ownership is released. This
provides simple RAII-style locking of a __lockable_concept_type__ object, to facilitate exception-safe
locking and unlocking. In addition, the [link
-thread.synchronization.locks.lock_guard.constructor_adopt `lock_guard(Lockable &
+thread.synchronization.lock_guard.lock_guard.constructor_adopt `lock_guard(Lockable &
m,boost::adopt_lock_t)` constructor] allows the __lock_guard__ object to
take ownership of a lock already held by the current thread.
@@ -904,10 +1020,141 @@
[endsect]
[endsect]
+
+[section:make_lock_guard Non Member Function `make_lock_guard`]
+
+ template <typename Lockable>
+ lock_guard<Lockable> make_lock_guard(Lockable& m); // EXTENSION
+
+
+[variablelist
+
+[[Returns:] [a lock_guard as if initialized with `{m}`.]]
+
+[[Throws:] [Any exception thrown by the call to [lock_ref_link `m.lock()`].]]
+
+]
+
+
+[endsect]
+[section:make_lock_guard_adopt Non Member Function `make_lock_guard`]
+
+ template <typename Lockable>
+ lock_guard<Lockable> make_lock_guard(Lockable& m, adopt_lock_t); // EXTENSION
+
+
+[variablelist
+
+[[Returns:] [a lock_guard as if initialized with `{m, adopt_lock}`.]]
+
+[[Throws:] [Any exception thrown by the call to [lock_ref_link `m.lock()`].]]
+
+]
+
+
+[endsect]
+[endsect]
+
+[section:lock_concepts Lock Concepts]
+[section:StrictLock StrictLock]
+
+ // #include <boost/thread/lock_concepts.hpp>
+
+ namespace boost
+ {
+
+ template<typename Lock>
+ class StrictLock;
+ }
+
+
+A StrictLock is a lock that ensures that the associated mutex is locked during the lifetime if the lock.
+
+A type `L` meets the StrictLock requirements if the following expressions are well-formed and have the specified semantics
+
+* `L::mutex_type`
+* `is_strict_lock<L>`
+* `cl.owns_lock(m);`
+
+and BasicLockable<L::mutex_type>
+
+where
+
+* `cl` denotes a value of type `L const&`,
+* `m` denotes a value of type `L::mutex_type const*`,
+
+[section: mutex_type `L::mutex_type`]
+
+The type L::mutex_type denotes the mutex that is locked by this lock.
+
+[endsect] [/ mutex_type]
+
+[section:is_strict_lock_sur_parolle `is_strict_lock_sur_parolle<L>`]
+
+As the semantic "ensures that the associated mutex is locked during the lifetime if the lock. " can not be described by syntactic requirements a `is_strict_lock_sur_parolle` trait must be specialized by the user defining the lock so that the following assertion is true:
+
+ is_strict_lock_sur_parolle<L>::value == true
+
+[endsect] [/ is_strict_lock_sur_parolle]
+
+[section:mutex `cl.mutex();`]
+
+[variablelist
+
+[[Return Type:] [`L::mutex_type`]]
+[[Returns:] [A pointer to the `L::mutex_type` object that this lock `l` is locking]]
+
+[[Throws:] [Nothing.]]
+
+]
+
+
+[endsect] [/ mutex]
+
+[section Models]
+
+The following classes are models of `StrictLock`:
+
+* strict_lock: ensured by construction,
+* nested_strict_lock: ensured by construction,
+* __lock_guard__: "sur parolle" as the user could use adopt_lock_t constructor overload without having locked the mutex.
+
+[endsect] [/ Models]
+
+[endsect] [/ Strict Lock]
+
+[endsect] [/ Lock Concepts]
+
+[section:locks Lock Types]
+
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_types.hpp>
+
+ namespace boost
+ {
+
+ template<typename Lockable>
+ class unique_lock;
+ template<typename Mutex>
+ void swap(unique_lock <Mutex>& lhs, unique_lock <Mutex>& rhs);
+ template<typename Lockable>
+ class shared_lock;
+ template<typename Mutex>
+ void swap(shared_lock<Mutex>& lhs,shared_lock<Mutex>& rhs);
+ template<typename Lockable>
+ class upgrade_lock;
+ template<typename Mutex>
+ void swap(upgrade_lock <Mutex>& lhs, upgrade_lock <Mutex>& rhs);
+ template <class Mutex>
+ class upgrade_to_unique_lock;
+ }
+
+
[section:unique_lock Class template `unique_lock`]
- //#include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_types.hpp>
template<typename Lockable>
class unique_lock
@@ -961,7 +1208,7 @@
Lockable* mutex() const noexcept;
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
+ #if defined BOOST_THREAD_USE_DATE_TIME || defined BOOST_THREAD_DONT_USE_CHRONO
unique_lock(Lockable& m_,system_time const& target_time);
template<typename TimeDuration>
bool timed_lock(TimeDuration const& relative_time);
@@ -1271,7 +1518,8 @@
[section:shared_lock Class template `shared_lock`]
- //#include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_types.hpp>
template<typename Lockable>
class shared_lock
@@ -1320,7 +1568,7 @@
bool owns_lock() const;
mutex_type mutex() const;
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
+ #if defined BOOST_THREAD_USE_DATE_TIME || defined BOOST_THREAD_DONT_USE_CHRONO
shared_lock(Lockable& m_,system_time const& target_time);
bool timed_lock(boost::system_time const& target_time);
#endif
@@ -1512,7 +1760,8 @@
[section:upgrade_lock Class template `upgrade_lock`]
- //#include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_types.hpp>
template<typename Lockable>
class upgrade_lock
@@ -1593,7 +1842,8 @@
[section:upgrade_to_unique_lock Class template `upgrade_to_unique_lock`]
- #include <boost/thread/locks.hpp>
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_types.hpp>
template <class Lockable>
class upgrade_to_unique_lock
@@ -1696,6 +1946,69 @@
[section:other_locks Other Lock Types]
+[section:strict_lock Strict Lock]
+
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/strict_lock.hpp>
+
+ namespace boost
+ {
+
+ template<typename Lockable>
+ class strict_lock;
+ }
+
+[section:strict_lock Class template `strict_lock`]
+
+ // #include <boost/thread/locks.hpp>
+ // #include <boost/thread/strict_lock.hpp>
+
+ template<typename BasicLockable>
+ class strict_lock
+ {
+ public:
+ typedef BasicLockable mutex_type;
+ explicit strict_lock(mutex_type& m_);
+ ~strict_lock();
+
+ mutex_type* mutex() const;
+ };
+
+__strict_lock is a model of __StrictLock.
+
+__strict_lock is the simplest __StrictLock: on construction it acquires ownership of the implementation of the __BasicLockable concept supplied as the constructor parameter. On destruction, the ownership is released. This provides simple RAII-style locking of a __BasicLockable object, to facilitate exception-safe locking and unlocking.
+
+[heading See also __lock_guard__]
+
+[section:constructor `strict_lock(Lockable & m)`]
+
+[variablelist
+
+[[Effects:] [Stores a reference to `m`. Invokes [lock_ref_link `m.lock()`].]]
+
+[[Throws:] [Any exception thrown by the call to [lock_ref_link `m.lock()`].]]
+
+]
+
+[endsect]
+
+[section:destructor `~strict_lock()`]
+
+[variablelist
+
+[[Effects:] [Invokes [unlock_ref_link `m.unlock()`] on the __lockable_concept_type__
+object passed to the constructor.]]
+
+[[Throws:] [Nothing.]]
+
+]
+
+[endsect]
+
+[endsect]
+
+[endsect]
+
[section:shared_lock_guard Class template `shared_lock_guard`]
@@ -1816,7 +2129,7 @@
[endsect]
-[endsect]
+[endsect] [/ reverse_lock<>]
[endsect]
@@ -1826,6 +2139,7 @@
[section:lock_multiple Non-member function `lock(Lockable1,Lockable2,...)`]
// #include <boost/thread/locks.hpp>
+ // #include <boost/thread/lock_algorithms.hpp>
namespace boost
{
Modified: branches/release/libs/thread/doc/mutexes.qbk
==============================================================================
--- branches/release/libs/thread/doc/mutexes.qbk (original)
+++ branches/release/libs/thread/doc/mutexes.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -89,7 +89,7 @@
typedef unspecified-type scoped_try_lock;
typedef scoped_timed_lock scoped_lock;
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
+ #if defined BOOST_THREAD_PROVIDES_DATE_TIME || defined BOOST_THREAD_DONT_USE_CHRONO
bool timed_lock(system_time const & abs_time);
template<typename TimeDuration>
bool timed_lock(TimeDuration const & relative_time);
@@ -203,7 +203,7 @@
typedef unspecified-type scoped_try_lock;
typedef scoped_lock scoped_timed_lock;
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
+ #if defined BOOST_THREAD_PROVIDES_DATE_TIME || defined BOOST_THREAD_DONT_USE_CHRONO
bool timed_lock(system_time const & abs_time);
template<typename TimeDuration>
bool timed_lock(TimeDuration const & relative_time);
Modified: branches/release/libs/thread/doc/shared_mutex_ref.qbk
==============================================================================
--- branches/release/libs/thread/doc/shared_mutex_ref.qbk (original)
+++ branches/release/libs/thread/doc/shared_mutex_ref.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -142,3 +142,87 @@
[endsect]
+
+[section:null_mutex Class `null_mutex`]
+
+ #include <boost/thread/null_mutex.hpp>
+
+ class null_mutex
+ {
+ public:
+ null_mutex(null_mutex const&) = delete;
+ null_mutex& operator=(null_mutex const&) = delete;
+
+ null_mutex();
+ ~null_mutex();
+
+ void lock_shared();
+ bool try_lock_shared();
+ #ifdef BOOST_THREAD_USES_CHRONO
+ template <class Rep, class Period>
+ bool try_lock_shared_for(const chrono::duration<Rep, Period>& rel_time);
+ template <class Clock, class Duration>
+ bool try_lock_shared_until(const chrono::time_point<Clock, Duration>& abs_time);
+ #endif
+ void unlock_shared();
+
+ void lock();
+ bool try_lock();
+ #ifdef BOOST_THREAD_USES_CHRONO
+ template <class Rep, class Period>
+ bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
+ template <class Clock, class Duration>
+ bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time);
+ #endif
+ void unlock();
+
+ void lock_upgrade();
+ #ifdef BOOST_THREAD_USES_CHRONO
+ template <class Rep, class Period>
+ bool try_lock_upgrade_for(const chrono::duration<Rep, Period>& rel_time);
+ template <class Clock, class Duration>
+ bool try_lock_upgrade_until(const chrono::time_point<Clock, Duration>& abs_time);
+ #endif
+ void unlock_upgrade();
+
+ // Shared <-> Exclusive
+
+ bool try_unlock_shared_and_lock();
+ #ifdef BOOST_THREAD_USES_CHRONO
+ template <class Rep, class Period>
+ bool try_unlock_shared_and_lock_for(const chrono::duration<Rep, Period>& rel_time);
+ template <class Clock, class Duration>
+ bool try_unlock_shared_and_lock_until(const chrono::time_point<Clock, Duration>& abs_time);
+ #endif
+ void unlock_and_lock_shared();
+
+ // Shared <-> Upgrade
+
+ bool try_unlock_shared_and_lock_upgrade();
+ #ifdef BOOST_THREAD_USES_CHRONO
+ template <class Rep, class Period>
+ bool try_unlock_shared_and_lock_upgrade_for(const chrono::duration<Rep, Period>& rel_time);
+ template <class Clock, class Duration>
+ bool try_unlock_shared_and_lock_upgrade_until(const chrono::time_point<Clock, Duration>& abs_time);
+ #endif
+ void unlock_upgrade_and_lock_shared();
+
+ // Upgrade <-> Exclusive
+
+ void unlock_upgrade_and_lock();
+ bool try_unlock_upgrade_and_lock();
+ #ifdef BOOST_THREAD_USES_CHRONO
+ template <class Rep, class Period>
+ bool try_unlock_upgrade_and_lock_for(const chrono::duration<Rep, Period>& rel_time);
+ template <class Clock, class Duration>
+ bool try_unlock_upgrade_and_lock_until(const chrono::time_point<Clock, Duration>& abs_time);
+ #endif
+ void unlock_and_lock_upgrade();
+ };
+
+The class `boost::null_mutex` provides a no-op implementation of a multiple-reader / single-writer mutex. It is a model of the
+__UpgradeLockable concept.
+
+
+[endsect]
+
Modified: branches/release/libs/thread/doc/sync_tutorial.qbk
==============================================================================
--- branches/release/libs/thread/doc/sync_tutorial.qbk (original)
+++ branches/release/libs/thread/doc/sync_tutorial.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -11,4 +11,29 @@
[@http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2406.html Mutex, Lock, Condition Variable Rationale] adds rationale for the design decisions made for mutexes, locks and condition variables.
-[endsect]
+[section:locks Locks]
+
+In addition to the C++11 standard locks, Boost.Thread provides other locks and some utilities that help the user to make their code thread-safe.
+
+In particular, the library provides some lock factories.
+
+ template <class Lockable, class Function>
+ auto with_lock_guard(Lockable& m, Function f) -> decltype(fn())
+ {
+ auto&& _ = boost::make_lock_guard(f);
+ f();
+ }
+
+
+that can be used as
+
+ int i = with_lock_guard(mtx, {}() -> bool
+ {
+ // access the protected state
+ return true;
+ });
+
+
+[endsect] [/ Locks]
+
+[endsect] [/ Tutorial]
Modified: branches/release/libs/thread/doc/thread.qbk
==============================================================================
--- branches/release/libs/thread/doc/thread.qbk (original)
+++ branches/release/libs/thread/doc/thread.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -8,7 +8,7 @@
[library Thread
[quickbook 1.5]
- [version 3.1.0]
+ [version 4.0.0]
[authors [Williams, Anthony] [Botet Escriba, Vicente J.]]
[copyright 2007-11 Anthony Williams]
[copyright 2011-12 Vicente J. Botet Escriba]
@@ -26,9 +26,9 @@
[def __lockable_concept_type__ [lockable_concept_link `Lockable`]]
[def __BasicLockable [link thread.synchronization.mutex_concepts.basic_lockable `BasicLockable`]]
[def __Lockable [link thread.synchronization.mutex_concepts.lockable `Lockable`]]
-[def __TimedLockable [link thread.synchronization.mutex_concepts.timed_lockable `TimedLockable `]]
-[def __SharedLockable [link thread.synchronization.mutex_concepts.shared_lockable `SharedLockable `]]
-[def __UpgradeLockable [link thread.synchronization.mutex_concepts.upgrade_lockable `UpgradeLockable `]]
+[def __TimedLockable [link thread.synchronization.mutex_concepts.timed_lockable `TimedLockable`]]
+[def __SharedLockable [link thread.synchronization.mutex_concepts.shared_lockable `SharedLockable`]]
+[def __UpgradeLockable [link thread.synchronization.mutex_concepts.upgrade_lockable `UpgradeLockable`]]
[template timed_lockable_concept_link[link_text] [link thread.synchronization.mutex_concepts.timed_lockable [link_text]]]
[def __timed_lockable_concept__ [timed_lockable_concept_link `TimedLockable` concept]]
@@ -155,9 +155,12 @@
[def __recursive_timed_mutex__ [link thread.synchronization.mutex_types.recursive_timed_mutex `boost::recursive_timed_mutex`]]
[def __shared_mutex__ [link thread.synchronization.mutex_types.shared_mutex `boost::shared_mutex`]]
+
+[def __StrictLock [link thread.synchronization.lock_concepts.StrictLock `StrictLock`]]
+
[template unique_lock_link[link_text] [link thread.synchronization.locks.unique_lock [link_text]]]
-[def __lock_guard__ [link thread.synchronization.locks.lock_guard `boost::lock_guard`]]
+[def __lock_guard__ [link thread.synchronization.lock_guard.lock_guard `boost::lock_guard`]]
[def __unique_lock__ [unique_lock_link `boost::unique_lock`]]
[def __unique_lock [unique_lock_link `boost::unique_lock`]]
[def __shared_lock__ [link thread.synchronization.locks.shared_lock `boost::shared_lock`]]
@@ -167,6 +170,8 @@
[def __shared_lock_guard [link thread.synchronization.other_locks.shared_lock_guard `shared_lock_guard`]]
[def __shared_lock_guard_constructor_adopt [link thread.synchronization.other_locks.shared_lock_guard `shared_lock_guard`]]
+[def __strict_lock [link thread.synchronization.other_locks.strict_lock `strict_lock`]]
+
[def __thread__ [link thread.thread_management.thread `boost::thread`]]
[def __thread [link thread.thread_management.thread `thread`]]
@@ -177,7 +182,6 @@
[def __try_join_for [link thread.thread_management.thread.try_join_for `try_join_for`]]
[def __try_join_until [link thread.thread_management.thread.try_join_until `try_join_until`]]
-
[template timed_join_link[link_text] [link thread.thread_management.thread.timed_join [link_text]]]
[def __timed_join__ [timed_join_link `timed_join()`]]
[def __detach__ [link thread.thread_management.thread.detach `detach()`]]
@@ -223,6 +227,7 @@
[include changes.qbk]
[include thread_ref.qbk]
+[include scoped_thread.qbk]
[section:synchronization Synchronization]
[include sync_tutorial.qbk]
Modified: branches/release/libs/thread/doc/thread_ref.qbk
==============================================================================
--- branches/release/libs/thread/doc/thread_ref.qbk (original)
+++ branches/release/libs/thread/doc/thread_ref.qbk 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -21,7 +21,7 @@
{
thread::id get_id() noexcept;
template<typename TimeDuration>
- void yield() noexcept;
+ void yield() noexcept; // DEPRECATED
template <class Clock, class Duration>
void sleep_until(const chrono::time_point<Clock, Duration>& abs_time);
template <class Rep, class Period>
@@ -36,9 +36,10 @@
class disable_interruption; // EXTENSION
class restore_interruption; // EXTENSION
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
- void sleep(TimeDuration const& rel_time);
- void sleep(system_time const& abs_time);
+ #if defined BOOST_THREAD_USES_DATETIME
+ template <TimeDuration>
+ void sleep(TimeDuration const& rel_time); // DEPRECATED
+ void sleep(system_time const& abs_time); // DEPRECATED
#endif
}
class thread_group; // EXTENSION
@@ -200,18 +201,81 @@
[endsect]
-[section:join Joining and detaching]
+[section:detac Detaching thread]
+
+A thread can be detached by explicitly invoking the __detach__ member function on the __thread__
+object. In this case, the __thread__ object ceases to represent the now-detached thread, and instead represents __not_a_thread__.
+
+ int main()
+ {
+ boost::thread t(my_func);
+ t.detach();
+ }
+
+[endsect]
+
+[section:join Joining a thread]
+
+In order to wait for a thread of execution to finish, the __join__, __join_for or __join_until (__timed_join__ deprecated) member functions of the __thread__ object must be
+used. __join__ will block the calling thread until the thread represented by the __thread__ object has completed.
+
+ int main()
+ {
+ boost::thread t(my_func);
+ t.join();
+ }
+
+
+If the thread of
+execution represented by the __thread__ object has already completed, or the __thread__ object represents __not_a_thread__, then __join__
+returns immediately.
+
+ int main()
+ {
+ boost::thread t;
+ t.join(); // do nothing
+ }
+
+Timed based join are similar, except that a call to __join_for or __join_until will also return if the thread being waited for
+does not complete when the specified time has elapsed or reached respectively.
+
+ int main()
+ {
+ boost::thread t;
+ if ( t.join_for(boost::chrono::milliseconds(500)) )
+ // do something else
+ t.join(); // join anyway
+ }
+
+[endsect]
+
+[section:destructor1 Destructor V1]
When the __thread__ object that represents a thread of execution is destroyed the thread becomes ['detached]. Once a thread is
detached, it will continue executing until the invocation of the function or callable object supplied on construction has completed,
or the program is terminated. A thread can also be detached by explicitly invoking the __detach__ member function on the __thread__
object. In this case, the __thread__ object ceases to represent the now-detached thread, and instead represents __not_a_thread__.
-In order to wait for a thread of execution to finish, the __join__ or __timed_join__ member functions of the __thread__ object must be
-used. __join__ will block the calling thread until the thread represented by the __thread__ object has completed. If the thread of
-execution represented by the __thread__ object has already completed, or the __thread__ object represents __not_a_thread__, then __join__
-returns immediately. __timed_join__ is similar, except that a call to __timed_join__ will also return if the thread being waited for
-does not complete when the specified time has elapsed.
+[endsect]
+
+[section:destructor2 Destructor V2]
+
+When the __thread__ object that represents a thread of execution is destroyed the program terminates if the thread is __joinable__.
+
+ int main()
+ {
+ boost::thread t(my_func);
+ } // calls std::terminate()
+
+You can use a thread_joiner to ensure that the thread has been joined at the thread destructor.
+
+
+ int main()
+ {
+ boost::thread t(my_func);
+ boost::thread_joiner g(t);
+ // do someting else
+ } // here the thread_joiner destructor will join the thread before it is destroyed.
[endsect]
@@ -359,6 +423,8 @@
class thread
{
public:
+ class attributes; // EXTENSION
+
thread() noexcept;
thread(const thread&) = delete;
thread& operator=(const thread&) = delete;
@@ -374,15 +440,15 @@
template <class F,class A1,class A2,...>
thread(F f,A1 a1,A2 a2,...);
- // template <class F, class ...Args>
- // explicit thread(F&& f, Args&&... args); // NOT YET IMPLEMENTED
+ template <class F, class ...Args>
+ explicit thread(F&& f, Args&&... args);
template <class F>
explicit thread(attributes& attrs, F f); // EXTENSION
template <class F>
thread(attributes& attrs, F &&f); // EXTENSION
- // template <class F, class ...Args>
- // explicit thread(attributes& attrs, F&& f, Args&&... args); // NOT YET IMPLEMENTED
+ template <class F, class ...Args>
+ explicit thread(attributes& attrs, F&& f, Args&&... args);
// move support
thread(thread && x) noexcept;
@@ -391,7 +457,6 @@
void swap(thread& x) noexcept;
class id;
- class attributes; // EXTENSION
id get_id() const noexcept;
@@ -413,19 +478,19 @@
bool interruption_requested() const noexcept; // EXTENSION
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
- bool timed_join(const system_time& wait_until);
+ #if defined BOOST_THREAD_USES_DATETIME
+ bool timed_join(const system_time& wait_until); // DEPRECATED
template<typename TimeDuration>
- bool timed_join(TimeDuration const& rel_time);
+ bool timed_join(TimeDuration const& rel_time); // DEPRECATED
+ static void sleep(const system_time& xt);// DEPRECATED
#endif
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0
- bool operator==(const thread& other) const;
- bool operator!=(const thread& other) const;
+ #if defined BOOST_THREAD_PROVIDES_THREAD_EQ
+ bool operator==(const thread& other) const; // DEPRECATED
+ bool operator!=(const thread& other) const; // DEPRECATED
- static void yield();
- static void sleep(const system_time& xt);
#endif
+ static void yield() noexcept; // DEPRECATED
};
@@ -467,11 +532,25 @@
thread& operator=(thread&& other) noexcept;
+
+[warning
+DEPRECATED since 3.0.0: BOOST_THREAD_DONT_PROVIDE_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE behavior.
+
+Available only up to Boost 1.56.
+
+Join the thread before moving.
+]
+
+
[variablelist
[[Effects:] [Transfers ownership of the thread managed by `other` (if
-any) to `*this`. Version 2: If there was a thread previously associated with
-`*this` then that thread is detached, Version 3: If the thread is joinable calls to std::terminate.]]
+any) to `*this`.
+
+_ if defined BOOST_THREAD_DONT_PROVIDE_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE: If there was a thread previously associated with `*this` then that thread is detached, DEPRECATED
+
+- if defined BOOST_THREAD_PROVIDES_THREAD_MOVE_ASSIGN_CALLS_TERMINATE_IF_JOINABLE: If the thread is joinable calls to std::terminate.
+]]
[[Postconditions:] [`other->get_id()==thread::id()` and `get_id()` returns the value of `other.get_id()` prior to the assignment.]]
@@ -479,6 +558,7 @@
]
+
[endsect]
[section:callable_constructor Thread Constructor]
@@ -626,34 +706,29 @@
~thread();
-[variablelist
-
-[[Effects:] [Version 2: If `*this` has an associated thread of execution, calls __detach__, Version 3: If the thread is joinable calls to std::terminate. Destroys `*this`.]]
-
-[[Throws:] [Nothing.]]
+[warning
+DEPRECATED since 3.0.0: BOOST_THREAD_DONT_PROVIDE_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE behavior.
+
+Available only up to Boost 1.56.
+Join the thread before destroying or use a scoped thread.
]
-[endsect]
-
-[/
-[section:v2_destructor V3 Thread Destructor]
-
- ~thread();
-
[variablelist
-[[Effects:] [If `*this` has an associated thread of execution, calls terminate. Destroys `*this`.]]
-
-[[Note:] [Either implicitly detaching or joining a `joinable()` thread in its destructor could result in difficult to debug correctness (for `detach`) or performance (for `join`) bugs encountered only when an exception is raised. Thus the programmer must ensure that the destructor is never executed while the thread is still joinable.]]
+[[Effects:] [
+- if defined BOOST_THREAD_DONT_PROVIDE_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE: If `*this` has an associated thread of execution, calls __detach__, DEPRECATED
+- BOOST_THREAD_PROVIDES_THREAD_DESTRUCTOR_CALLS_TERMINATE_IF_JOINABLE: If the thread is joinable calls to std::terminate. Destroys `*this`.]]
[[Throws:] [Nothing.]]
+[[Note:] [Either implicitly detaching or joining a `joinable()` thread in its destructor could result in difficult to debug correctness (for `detach`) or performance (for `join`) bugs encountered only when an exception is raised. Thus the programmer must ensure that the destructor is never executed while the thread is still joinable.]]
+
]
[endsect]
-]
+
[section:joinable Member function `joinable()`]
@@ -686,9 +761,9 @@
[[Error Conditions:] [
-[*resource_deadlock_would_occur]: if deadlock is detected or this->get_id() == boost::this_thread::get_id().
+[*resource_deadlock_would_occur]: if deadlock is detected or `this->get_id() == boost::this_thread::get_id()` and `BOOST_THREAD_TRHOW_IF_PRECONDITION_NOT_SATISFIED` is defined..
-[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRROW_IF_PRECONDITION_NOT_SATISFIED is defined.
+[*invalid_argument]: if the thread is not joinable and `BOOST_THREAD_TRHOW_IF_PRECONDITION_NOT_SATISFIED` is defined.
[/
@@ -704,13 +779,21 @@
[endsect]
-[section:timed_join Member function `timed_join()`]
+[section:timed_join Member function `timed_join()` DEPRECATED]
bool timed_join(const system_time& wait_until);
template<typename TimeDuration>
bool timed_join(TimeDuration const& rel_time);
+[warning
+DEPRECATED since 3.00.
+
+Available only up to Boost 1.56.
+
+Use instead __try_join_for, __try_join_until.
+]
+
[variablelist
[[Preconditions:] [the thread is joinable.]]
@@ -731,7 +814,7 @@
[*resource_deadlock_would_occur]: if deadlock is detected or this->get_id() == boost::this_thread::get_id().
-[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRROW_IF_PRECONDITION_NOT_SATISFIED is defined.
+[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRHOW_IF_PRECONDITION_NOT_SATISFIED is defined.
[/
@@ -771,7 +854,7 @@
[*resource_deadlock_would_occur]: if deadlock is detected or this->get_id() == boost::this_thread::get_id().
-[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRROW_IF_PRECONDITION_NOT_SATISFIED is defined.
+[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRHOW_IF_PRECONDITION_NOT_SATISFIED is defined.
[/
@@ -811,7 +894,7 @@
[*resource_deadlock_would_occur]: if deadlock is detected or this->get_id() == boost::this_thread::get_id().
-[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRROW_IF_PRECONDITION_NOT_SATISFIED is defined.
+[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRHOW_IF_PRECONDITION_NOT_SATISFIED is defined.
[/
@@ -847,7 +930,7 @@
[*no_such_process]: if the thread is not valid.
-[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRROW_IF_PRECONDITION_NOT_SATISFIED is defined.
+[*invalid_argument]: if the thread is not joinable and BOOST_THREAD_TRHOW_IF_PRECONDITION_NOT_SATISFIED is defined.
]]
@@ -871,7 +954,7 @@
[endsect]
-[section:interrupt Member function `interrupt()`]
+[section:interrupt Member function `interrupt()` EXTENSION]
void interrupt();
@@ -919,38 +1002,61 @@
[endsect]
-[section:equals `operator==` DEPRECATED V3]
+[section:equals `operator==` DEPRECATED]
bool operator==(const thread& other) const;
+[warning
+DEPRECATED since 4.0.0.
+
+Available only up to Boost 1.58.
+
+Use `a.__get_id()==b.__get_id()` instead`.
+]
+
+
[variablelist
[[Returns:] [`get_id()==other.get_id()`]]
-[[See:] [Use `a.__get_id()==b.__get_id()` instead]]
]
[endsect]
-[section:not_equals `operator!=` DEPRECATED V3]
+[section:not_equals `operator!=` DEPRECATED]
bool operator!=(const thread& other) const;
+[warning
+DEPRECATED since 4.0.0.
+
+Available only up to Boost 1.58.
+
+Use `a.__get_id()!=b.__get_id()` instead`.
+]
+
[variablelist
[[Returns:] [`get_id()!=other.get_id()`]]
-[[See:] [Use `a.__get_id()!=b.__get_id()` instead`]]
-
]
[endsect]
-[section:sleep Static member function `sleep()`]
+[section:sleep Static member function `sleep()` DEPRECATED]
void sleep(system_time const& abs_time);
+[warning
+DEPRECATED since 3.0.0.
+
+Available only up to Boost 1.56.
+
+Use `this_thread::__sleep_for()` or `this_thread::__sleep_until()`.
+]
+
+
[variablelist
[[Effects:] [Suspends the current thread until the specified time has been reached.]]
@@ -959,22 +1065,26 @@
[[Notes:] [`sleep()` is one of the predefined __interruption_points__.]]
-[[See:] [Use `this_thread::__sleep_for()` or `this_thread::__sleep_until()`]]
-
]
[endsect]
-[section:yield Static member function `yield()`]
+[section:yield Static member function `yield()` DEPRECATED]
void yield();
+[warning
+DEPRECATED since 3.0.0.
+
+Available only up to Boost 1.56.
+
+Use `this_thread::__yield()`.
+]
+
[variablelist
[[Effects:] [See [link thread.thread_management.this_thread.yield `boost::this_thread::yield()`].]]
-[[See:] [Use `this_thread::__yield()`]]
-
]
[endsect]
@@ -1262,9 +1372,9 @@
class disable_interruption; // EXTENSION
class restore_interruption; // EXTENSION
- #if defined BOOST_THREAD_PROVIDES_DEPRECATED_FEATURES_SINCE_V3_0_0 || defined BOOST_THREAD_DONT_USE_CHRONO
- void sleep(TimeDuration const& rel_time);
- void sleep(system_time const& abs_time)
+ #if defined BOOST_THREAD_USES_DATETIME
+ void sleep(TimeDuration const& rel_time); // DEPRECATED
+ void sleep(system_time const& abs_time); // DEPRECATED
#endif
}
}
@@ -1345,7 +1455,7 @@
[endsect]
-[section:sleep Non-member function `sleep()`]
+[section:sleep Non-member function `sleep()` DEPRECATED]
#include <boost/thread/thread.hpp>
@@ -1356,6 +1466,15 @@
void sleep(system_time const& abs_time)
}
+[warning
+DEPRECATED since 3.0.0.
+
+Available only up to Boost 1.56.
+
+Use `__sleep_for()` and `__sleep_until()` instead.
+]
+
+
[variablelist
[[Effects:] [Suspends the current thread until the time period
@@ -1366,8 +1485,6 @@
[[Notes:] [`sleep()` is one of the predefined __interruption_points__.]]
-[[See:] [Use `__sleep_for()` and `__sleep_until()` instead.]]
-
]
[endsect]
@@ -1584,14 +1701,17 @@
[endsect]
-[section:threadgroup Class `thread_group`]
+[section:threadgroup Class `thread_group` EXTENSION]
#include <boost/thread/thread.hpp>
+ #include <boost/thread/thread_group.hpp>
- class thread_group:
- private noncopyable
+ class thread_group
{
public:
+ thread_group(const thread_group&) = delete;
+ thread_group& operator=(const thread_group&) = delete;
+
thread_group();
~thread_group();
@@ -1599,6 +1719,8 @@
thread* create_thread(F threadfunc);
void add_thread(thread* thrd);
void remove_thread(thread* thrd);
+ bool is_this_thread_in();
+ bool is_thread_in(thread* thrd);
void join_all();
void interrupt_all();
int size() const;
@@ -1654,7 +1776,7 @@
[variablelist
-[[Precondition:] [The expression `delete thrd` is well-formed and will not result in undefined behaviour.]]
+[[Precondition:] [The expression `delete thrd` is well-formed and will not result in undefined behaviour and `is_thread_in(thrd) == false`.]]
[[Effects:] [Take ownership of the __thread__ object pointed to by `thrd` and add it to the group.]]
@@ -1684,6 +1806,8 @@
[variablelist
+[[Requires:] [`is_this_thread_in() == false`.]]
+
[[Effects:] [Call `join()` on each __thread__ object in the group.]]
[[Postcondition:] [Every thread in the group has terminated.]]
@@ -1694,6 +1818,32 @@
[endsect]
+[section:is_this_thread_in Member function `is_this_thread_in()`]
+
+ bool is_this_thread_in();
+
+[variablelist
+
+[[Returns:] [true if there is a thread `th` in the group such that `th.get_id() == this_thread::get_id()`.]]
+
+
+]
+
+[endsect]
+
+[section:is_thread_in Member function `is_thread_in()`]
+
+ bool is_thread_in(thread* thrd);
+
+[variablelist
+
+[[Returns:] [true if there is a thread `th` in the group such that `th.get_id() == thrd->get_id()`.]]
+
+
+]
+
+[endsect]
+
[section:interrupt_all Member function `interrupt_all()`]
void interrupt_all();
Copied: branches/release/libs/thread/example/ba_externallly_locked.cpp (from r81093, /trunk/libs/thread/example/ba_externallly_locked.cpp)
==============================================================================
--- /trunk/libs/thread/example/ba_externallly_locked.cpp (original)
+++ branches/release/libs/thread/example/ba_externallly_locked.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,6 +6,7 @@
#define BOOST_THREAD_VERSION 4
#include <boost/thread/mutex.hpp>
+#include <boost/thread/lockable_adapter.hpp>
#include <boost/thread/externally_locked.hpp>
#include <boost/thread/strict_lock.hpp>
#include <boost/thread/lock_types.hpp>
@@ -32,12 +33,12 @@
};
//[AccountManager
-class AccountManager
+class AccountManager: public basic_lockable_adapter<mutex>
{
- mutex mtx_;
public:
+ typedef basic_lockable_adapter<mutex> lockable_base_type;
AccountManager() :
- checkingAcct_(mtx_), savingsAcct_(mtx_)
+ lockable_base_type(), checkingAcct_(*this), savingsAcct_(*this)
{
}
inline void Checking2Savings(int amount);
@@ -48,63 +49,63 @@
{
return true;
} /*->*/
- externally_locked<BankAccount, mutex > checkingAcct_;
- externally_locked<BankAccount, mutex > savingsAcct_;
+ externally_locked<BankAccount, AccountManager > checkingAcct_;
+ externally_locked<BankAccount, AccountManager > savingsAcct_;
};
//]
//[Checking2Savings
void AccountManager::Checking2Savings(int amount)
{
- strict_lock<mutex> guard(mtx_);
+ strict_lock<AccountManager> guard(*this);
checkingAcct_.get(guard).Withdraw(amount);
savingsAcct_.get(guard).Deposit(amount);
}
//]
-#if MUST_NOT_COMPILE
-//[AMoreComplicatedChecking2Savings_DO_NOT_COMPILE
+//#if DO_NOT_COMPILE
+////[AMoreComplicatedChecking2Savings_DO_NOT_COMPILE
+//void AccountManager::AMoreComplicatedChecking2Savings(int amount) {
+// unique_lock<AccountManager> guard(*this);
+// if (some_condition()) {
+// guard.lock();
+// }
+// checkingAcct_.get(guard).Withdraw(amount);
+// savingsAcct_.get(guard).Deposit(amount);
+// guard1.unlock();
+//}
+////]
+//#elif DO_NOT_COMPILE_2
+////[AMoreComplicatedChecking2Savings_DO_NOT_COMPILE2
+//void AccountManager::AMoreComplicatedChecking2Savings(int amount) {
+// unique_lock<AccountManager> guard1(*this);
+// if (some_condition()) {
+// guard1.lock();
+// }
+// {
+// strict_lock<AccountManager> guard(guard1);
+// checkingAcct_.get(guard).Withdraw(amount);
+// savingsAcct_.get(guard).Deposit(amount);
+// }
+// guard1.unlock();
+//}
+////]
+//#else
+////[AMoreComplicatedChecking2Savings
void AccountManager::AMoreComplicatedChecking2Savings(int amount) {
- unique_lock<mutex> guard(mtx_);
- if (some_condition()) {
- guard.lock();
- }
- checkingAcct_.get(guard).Withdraw(amount);
- savingsAcct_.get(guard).Deposit(amount);
- guard1.unlock();
-}
-//]
-#elif MUST_NOT_COMPILE_2
-//[AMoreComplicatedChecking2Savings_DO_NOT_COMPILE2
-void AccountManager::AMoreComplicatedChecking2Savings(int amount) {
- unique_lock<mutex> guard1(mtx_);
+ unique_lock<AccountManager> guard1(*this);
if (some_condition()) {
guard1.lock();
}
{
- strict_lock<mutex> guard(guard1);
+ nested_strict_lock<unique_lock<AccountManager> > guard(guard1);
checkingAcct_.get(guard).Withdraw(amount);
savingsAcct_.get(guard).Deposit(amount);
}
guard1.unlock();
}
-]
-#else
-//[AMoreComplicatedChecking2Savings
-void AccountManager::AMoreComplicatedChecking2Savings(int amount) {
- unique_lock<mutex> guard1(mtx_);
- if (some_condition()) {
- guard1.lock();
- }
- {
- nested_strict_lock<unique_lock<mutex> > guard(guard1);
- checkingAcct_.get(guard).Withdraw(amount);
- savingsAcct_.get(guard).Deposit(amount);
- }
- guard1.unlock();
-}
-//]
-#endif
+////]
+//#endif
int main()
{
Modified: branches/release/libs/thread/example/condition.cpp
==============================================================================
--- branches/release/libs/thread/example/condition.cpp (original)
+++ branches/release/libs/thread/example/condition.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -7,13 +7,14 @@
#include <iostream>
#include <vector>
#include <boost/utility.hpp>
-#include <boost/thread/condition.hpp>
+#include <boost/thread/condition_variable.hpp>
#include <boost/thread/thread.hpp>
+#include "../test/remove_error_code_unused_warning.hpp"
class bounded_buffer : private boost::noncopyable
{
public:
- typedef boost::mutex::scoped_lock lock;
+ typedef boost::unique_lock<boost::mutex> lock;
bounded_buffer(int n) : begin(0), end(0), buffered(0), circular_buf(n) { }
@@ -38,9 +39,10 @@
}
private:
- int begin, end, buffered;
+ int begin, end;
+ std::vector<int>::size_type buffered;
std::vector<int> circular_buf;
- boost::condition buffer_not_full, buffer_not_empty;
+ boost::condition_variable_any buffer_not_full, buffer_not_empty;
boost::mutex monitor;
};
@@ -54,7 +56,7 @@
buf.send(n);
if(!(n%10000))
{
- boost::mutex::scoped_lock io_lock(io_mutex);
+ boost::unique_lock<boost::mutex> io_lock(io_mutex);
std::cout << "sent: " << n << std::endl;
}
++n;
@@ -68,7 +70,7 @@
n = buf.receive();
if(!(n%10000))
{
- boost::mutex::scoped_lock io_lock(io_mutex);
+ boost::unique_lock<boost::mutex> io_lock(io_mutex);
std::cout << "received: " << n << std::endl;
}
} while (n != -1); // -1 indicates end of buffer
Copied: branches/release/libs/thread/example/future_then.cpp (from r81030, /trunk/libs/thread/example/future_then.cpp)
==============================================================================
--- /trunk/libs/thread/example/future_then.cpp (original)
+++ branches/release/libs/thread/example/future_then.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,29 +3,64 @@
// 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)
-#define BOOST_THREAD_VERSION 4
+//#define BOOST_THREAD_VERSION 4
+#define BOOST_THREAD_USES_LOG
#define BOOST_THREAD_DONT_PROVIDE_FUTURE_INVALID_AFTER_GET
+#include <boost/thread/detail/log.hpp>
#include <boost/thread/future.hpp>
-#include <iostream>
+#include <boost/assert.hpp>
#include <string>
#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
int p1()
{
+ BOOST_THREAD_LOG << "P1" << BOOST_THREAD_END_LOG;
return 123;
}
int p2(boost::future<int>& f)
{
- return 2 * f.get();
+ BOOST_THREAD_LOG << "<P2" << BOOST_THREAD_END_LOG;
+ try
+ {
+ return 2 * f.get();
+ }
+ catch (std::exception& ex)
+ {
+ BOOST_THREAD_LOG << "ERRORRRRR "<<ex.what() << "" << BOOST_THREAD_END_LOG;
+ BOOST_ASSERT(false);
+ }
+ catch (...)
+ {
+ BOOST_THREAD_LOG << " ERRORRRRR exception thrown" << BOOST_THREAD_END_LOG;
+ BOOST_ASSERT(false);
+ }
+ BOOST_THREAD_LOG << "P2>" << BOOST_THREAD_END_LOG;
}
int main()
{
- boost::future<int> f1 = boost::async(p1);
- boost::future<int> f2 = f1.then(p2);
- std::cout << f2.get() << std::endl;
+ BOOST_THREAD_LOG << "<MAIN" << BOOST_THREAD_END_LOG;
+ try
+ {
+ boost::future<int> f1 = boost::async(&p1);
+ BOOST_THREAD_LOG << BOOST_THREAD_END_LOG;
+ boost::future<int> f2 = f1.then(&p2);
+ BOOST_THREAD_LOG << BOOST_THREAD_END_LOG;
+ BOOST_THREAD_LOG << f2.get() << BOOST_THREAD_END_LOG;
+ }
+ catch (std::exception& ex)
+ {
+ BOOST_THREAD_LOG << "ERRORRRRR "<<ex.what() << "" << BOOST_THREAD_END_LOG;
+ return 1;
+ }
+ catch (...)
+ {
+ BOOST_THREAD_LOG << " ERRORRRRR exception thrown" << BOOST_THREAD_END_LOG;
+ return 2;
+ }
+ BOOST_THREAD_LOG << "MAIN>" << BOOST_THREAD_END_LOG;
return 0;
}
#else
Copied: branches/release/libs/thread/example/make_future.cpp (from r80756, /trunk/libs/thread/example/make_future.cpp)
==============================================================================
--- /trunk/libs/thread/example/make_future.cpp (original)
+++ branches/release/libs/thread/example/make_future.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -15,8 +15,8 @@
if (x == 0) return boost::make_future(0);
if (x < 0) return boost::make_future(-1);
//boost::future<int> f1 = boost::async([]() { return x+1; });
- boost::future<int> f1 = boost::async(p1);
- return f1;
+ boost::future<int> f1 = boost::async(boost::launch::async, p1);
+ return boost::move(f1);
}
boost::shared_future<int> shared_compute(int x)
{
@@ -24,7 +24,7 @@
if (x < 0) return boost::make_shared_future(-1);
//boost::future<int> f1 = boost::async([]() { return x+1; });
boost::shared_future<int> f1 = boost::async(p1).share();
- return f1;
+ return boost::move(f1);
}
Modified: branches/release/libs/thread/example/monitor.cpp
==============================================================================
--- branches/release/libs/thread/example/monitor.cpp (original)
+++ branches/release/libs/thread/example/monitor.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,7 +6,7 @@
#include <vector>
#include <iostream>
-#include <boost/thread/condition.hpp>
+#include <boost/thread/condition_variable.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/recursive_mutex.hpp>
#include <boost/thread/thread.hpp>
@@ -20,7 +20,7 @@
class buffer_t
{
public:
- typedef typename M::scoped_lock scoped_lock;
+ typedef boost::unique_lock<M> scoped_lock;
buffer_t(int n)
: p(0), c(0), full(0), buf(n)
@@ -60,7 +60,7 @@
for (int n = 0; n < ITERS; ++n)
{
{
- boost::mutex::scoped_lock lock(io_mutex);
+ boost::unique_lock<boost::mutex> lock(io_mutex);
std::cout << "sending: " << n << std::endl;
}
get_buffer().send(n);
@@ -73,7 +73,7 @@
{
int n = get_buffer().receive();
{
- boost::mutex::scoped_lock lock(io_mutex);
+ boost::unique_lock<boost::mutex> lock(io_mutex);
std::cout << "received: " << n << std::endl;
}
}
@@ -81,7 +81,7 @@
private:
M mutex;
- boost::condition cond;
+ boost::condition_variable_any cond;
unsigned int p, c, full;
std::vector<int> buf;
};
Modified: branches/release/libs/thread/example/mutex.cpp
==============================================================================
--- branches/release/libs/thread/example/mutex.cpp (original)
+++ branches/release/libs/thread/example/mutex.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -1,7 +1,7 @@
// Copyright (C) 2001-2003
// William E. Kempf
//
-// 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/mutex.hpp>
@@ -16,7 +16,7 @@
counter() : count(0) { }
int increment() {
- boost::mutex::scoped_lock scoped_lock(mutex);
+ boost::unique_lock<boost::mutex> scoped_lock(mutex);
return ++count;
}
@@ -30,7 +30,7 @@
void change_count()
{
int i = c.increment();
- boost::mutex::scoped_lock scoped_lock(io_mutex);
+ boost::unique_lock<boost::mutex> scoped_lock(io_mutex);
std::cout << "count == " << i << std::endl;
}
Modified: branches/release/libs/thread/example/recursive_mutex.cpp
==============================================================================
--- branches/release/libs/thread/example/recursive_mutex.cpp (original)
+++ branches/release/libs/thread/example/recursive_mutex.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -1,7 +1,7 @@
// Copyright (C) 2001-2003
// William E. Kempf
//
-// 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/recursive_mutex.hpp>
@@ -14,12 +14,12 @@
counter() : count(0) { }
int add(int val) {
- boost::recursive_mutex::scoped_lock scoped_lock(mutex);
+ boost::unique_lock<boost::recursive_mutex> scoped_lock(mutex);
count += val;
return count;
}
int increment() {
- boost::recursive_mutex::scoped_lock scoped_lock(mutex);
+ boost::unique_lock<boost::recursive_mutex> scoped_lock(mutex);
return add(1);
}
Copied: branches/release/libs/thread/example/scoped_thread.cpp (from r81093, /trunk/libs/thread/example/scoped_thread.cpp)
==============================================================================
--- /trunk/libs/thread/example/scoped_thread.cpp (original)
+++ branches/release/libs/thread/example/scoped_thread.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,9 +4,9 @@
// 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)
+#define BOOST_THREAD_VERSION 3
#include <iostream>
-//#include <string>
#include <boost/thread/scoped_thread.hpp>
void do_something(int& i)
@@ -36,6 +36,10 @@
{
}
+//void do_something_with_current_thread(boost::thread&& th)
+//{
+// th.join();
+//}
int main()
{
@@ -52,6 +56,14 @@
do_something_in_current_thread();
}
+// {
+// int some_local_state;
+// boost::thread t(( func(some_local_state) ));
+// boost::strict_scoped_thread<> g( (boost::move(t)) );
+//
+// do_something_in_current_thread();
+// do_something_with_current_thread(boost::thread(g));
+// }
return 0;
}
Modified: branches/release/libs/thread/example/shared_monitor.cpp
==============================================================================
--- branches/release/libs/thread/example/shared_monitor.cpp (original)
+++ branches/release/libs/thread/example/shared_monitor.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,6 +6,7 @@
#include <iostream>
#include <boost/thread/mutex.hpp>
#include <boost/thread/shared_mutex.hpp>
+#include <boost/thread/lock_algorithms.hpp>
#include <boost/thread/thread.hpp>
#if defined BOOST_THREAD_DONT_USE_CHRONO
#include <boost/chrono/chrono_io.hpp>
Modified: branches/release/libs/thread/example/shared_mutex.cpp
==============================================================================
--- branches/release/libs/thread/example/shared_mutex.cpp (original)
+++ branches/release/libs/thread/example/shared_mutex.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -10,6 +10,7 @@
#include <iostream>
#include <boost/thread/mutex.hpp>
#include <boost/thread/shared_mutex.hpp>
+#include <boost/thread/lock_algorithms.hpp>
#include <boost/thread/thread.hpp>
#include <vector>
Modified: branches/release/libs/thread/example/starvephil.cpp
==============================================================================
--- branches/release/libs/thread/example/starvephil.cpp (original)
+++ branches/release/libs/thread/example/starvephil.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,6 +4,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/mutex.hpp>
#include <boost/thread/condition.hpp>
#include <boost/thread/thread.hpp>
@@ -23,18 +25,18 @@
void get(int id)
{
- boost::mutex::scoped_lock lock(m_mutex);
+ boost::unique_lock<boost::mutex> lock(m_mutex);
while (m_chickens == 0)
{
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lk(iomx);
std::cout << "(" << clock() << ") Phil" << id <<
": wot, no chickens? I'll WAIT ..." << std::endl;
}
m_condition.wait(lock);
}
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lk(iomx);
std::cout << "(" << clock() << ") Phil" << id <<
": those chickens look good ... one please ..." << std::endl;
}
@@ -42,9 +44,9 @@
}
void put(int value)
{
- boost::mutex::scoped_lock lock(m_mutex);
+ boost::unique_lock<boost::mutex> lock(m_mutex);
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lk(iomx);
std::cout << "(" << clock()
<< ") Chef: ouch ... make room ... this dish is "
<< "very hot ..." << std::endl;
@@ -55,7 +57,7 @@
boost::thread::sleep(xt);
m_chickens += value;
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lk(iomx);
std::cout << "(" << clock() <<
") Chef: more chickens ... " << m_chickens <<
" now available ... NOTIFYING ..." << std::endl;
@@ -75,13 +77,13 @@
{
const int chickens = 4;
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lock(iomx);
std::cout << "(" << clock() << ") Chef: starting ..." << std::endl;
}
for (;;)
{
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lock(iomx);
std::cout << "(" << clock() << ") Chef: cooking ..." << std::endl;
}
boost::xtime xt;
@@ -89,7 +91,7 @@
xt.sec += 2;
boost::thread::sleep(xt);
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lock(iomx);
std::cout << "(" << clock() << ") Chef: " << chickens
<< " chickens, ready-to-go ..." << std::endl;
}
@@ -102,7 +104,7 @@
phil(int id) : m_id(id) { }
void run() {
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lock(iomx);
std::cout << "(" << clock() << ") Phil" << m_id
<< ": starting ..." << std::endl;
}
@@ -116,13 +118,13 @@
boost::thread::sleep(xt);
}
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lk(iomx);
std::cout << "(" << clock() << ") Phil" << m_id
<< ": gotta eat ..." << std::endl;
}
g_canteen.get(m_id);
{
- boost::mutex::scoped_lock lock(iomx);
+ boost::unique_lock<boost::mutex> lk(iomx);
std::cout << "(" << clock() << ") Phil" << m_id
<< ": mmm ... that's good ..." << std::endl;
}
Copied: branches/release/libs/thread/example/strict_lock.cpp (from r81093, /trunk/libs/thread/example/strict_lock.cpp)
==============================================================================
--- /trunk/libs/thread/example/strict_lock.cpp (original)
+++ branches/release/libs/thread/example/strict_lock.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,8 +5,8 @@
#define BOOST_THREAD_VERSION 4
-#include <boost/thread/lock_traits.hpp>
#include <boost/thread/mutex.hpp>
+#include <boost/thread/lock_traits.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/strict_lock.hpp>
#include <boost/thread/lock_types.hpp>
Copied: branches/release/libs/thread/example/synchronized_value.cpp (from r81093, /trunk/libs/thread/example/synchronized_value.cpp)
==============================================================================
--- /trunk/libs/thread/example/synchronized_value.cpp (original)
+++ branches/release/libs/thread/example/synchronized_value.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -29,7 +29,7 @@
std::cout<<"v="<<*v<<std::endl;
}
-void g(const boost::synchronized_value<int>::strict_synchronizer &v) {
+void g(const boost::synchronized_value<int>::const_strict_synchronizer &v) {
std::cout<<"v="<<*v<<std::endl;
}
@@ -65,7 +65,7 @@
}
{
boost::synchronized_value<std::string> s;
-#if 0
+#if 1
s->append("foo/");
#else
s.synchronize()->append("foo");
@@ -75,7 +75,7 @@
}
{
boost::synchronized_value<std::string> s;
-#if 0
+#if 1
s->append("foo");
#else
s.synchronize()->append("foo");
Modified: branches/release/libs/thread/example/tennis.cpp
==============================================================================
--- branches/release/libs/thread/example/tennis.cpp (original)
+++ branches/release/libs/thread/example/tennis.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -41,7 +41,7 @@
void player(void* param)
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
int active = (int)param;
int other = active == PLAYER_A ? PLAYER_B : PLAYER_A;
@@ -108,7 +108,7 @@
xt.sec += 1;
boost::thread::sleep(xt);
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
std::cout << "---Noise ON..." << std::endl;
}
@@ -116,7 +116,7 @@
cond.notify_all();
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
std::cout << "---Noise OFF..." << std::endl;
state = GAME_OVER;
cond.notify_all();
Modified: branches/release/libs/thread/example/thread.cpp
==============================================================================
--- branches/release/libs/thread/example/thread.cpp (original)
+++ branches/release/libs/thread/example/thread.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,6 +4,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
#include <iostream>
Modified: branches/release/libs/thread/example/thread_group.cpp
==============================================================================
--- branches/release/libs/thread/example/thread_group.cpp (original)
+++ branches/release/libs/thread/example/thread_group.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -6,20 +6,65 @@
#include <boost/thread/thread.hpp>
#include <iostream>
+#include <boost/detail/lightweight_test.hpp>
int count = 0;
boost::mutex mutex;
void increment_count()
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
+ std::cout << "count = " << ++count << std::endl;
+}
+
+boost::thread_group threads2;
+boost::thread* th2 = 0;
+
+void increment_count_2()
+{
+ boost::unique_lock<boost::mutex> lock(mutex);
+ BOOST_TEST(threads2.is_this_thread_in());
std::cout << "count = " << ++count << std::endl;
}
int main()
{
+ {
boost::thread_group threads;
- for (int i = 0; i < 10; ++i)
+ for (int i = 0; i < 3; ++i)
threads.create_thread(&increment_count);
threads.join_all();
+ }
+ {
+ boost::thread_group threads;
+ for (int i = 0; i < 3; ++i)
+ threads.create_thread(&increment_count);
+ threads.interrupt_all();
+ threads.join_all();
+ }
+ {
+ boost::thread_group threads;
+ boost::thread* th = new boost::thread(&increment_count);
+ threads.add_thread(th);
+ BOOST_TEST(! threads.is_this_thread_in());
+ threads.join_all();
+ }
+ {
+ boost::thread_group threads;
+ boost::thread* th = new boost::thread(&increment_count);
+ threads.add_thread(th);
+ BOOST_TEST(threads.is_thread_in(th));
+ threads.remove_thread(th);
+ BOOST_TEST(! threads.is_thread_in(th));
+ th->join();
+ }
+ {
+ {
+ boost::unique_lock<boost::mutex> lock(mutex);
+ boost::thread* th2 = new boost::thread(&increment_count_2);
+ threads2.add_thread(th2);
+ }
+ threads2.join_all();
+ }
+ return boost::report_errors();
}
Copied: branches/release/libs/thread/example/thread_guard.cpp (from r81093, /trunk/libs/thread/example/thread_guard.cpp)
==============================================================================
--- /trunk/libs/thread/example/thread_guard.cpp (original)
+++ branches/release/libs/thread/example/thread_guard.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -28,6 +28,10 @@
do_something(i);
}
}
+
+private:
+ func& operator=(func const&);
+
};
void do_something_in_current_thread()
Modified: branches/release/libs/thread/example/xtime.cpp
==============================================================================
--- branches/release/libs/thread/example/xtime.cpp (original)
+++ branches/release/libs/thread/example/xtime.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,6 +4,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
Modified: branches/release/libs/thread/src/pthread/thread.cpp
==============================================================================
--- branches/release/libs/thread/src/pthread/thread.cpp (original)
+++ branches/release/libs/thread/src/pthread/thread.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -1,20 +1,23 @@
// Copyright (C) 2001-2003
// William E. Kempf
// Copyright (C) 2007-8 Anthony Williams
-// (C) Copyright 2011 Vicente J. Botet Escriba
+// (C) Copyright 2011-2012 Vicente J. Botet Escriba
//
// 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)
+#define BOOST_THREAD_VERSION 2
#include <boost/thread/detail/config.hpp>
#include <boost/thread/thread.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/thread/xtime.hpp>
+#endif
#include <boost/thread/condition_variable.hpp>
#include <boost/thread/locks.hpp>
#include <boost/thread/once.hpp>
#include <boost/thread/tss.hpp>
-#include <boost/throw_exception.hpp>
+#include <boost/thread/future.hpp>
#ifdef __GLIBC__
#include <sys/sysinfo.h>
@@ -33,14 +36,17 @@
{
thread_data_base::~thread_data_base()
{
- {
for (notify_list_t::iterator i = notify.begin(), e = notify.end();
i != e; ++i)
{
i->second->unlock();
i->first->notify_all();
}
- }
+ for (async_states_t::iterator i = async_states_.begin(), e = async_states_.end();
+ i != e; ++i)
+ {
+ (*i)->make_ready();
+ }
}
struct thread_exit_callback_node
@@ -72,6 +78,7 @@
{
while(!thread_info->tss_data.empty() || thread_info->thread_exit_callbacks)
{
+
while(thread_info->thread_exit_callbacks)
{
detail::thread_exit_callback_node* const current_node=thread_info->thread_exit_callbacks;
@@ -97,7 +104,10 @@
thread_info->tss_data.erase(current);
}
}
- thread_info->self.reset();
+ if (thread_info) // fixme: should we test this?
+ {
+ thread_info->self.reset();
+ }
}
}
}
@@ -148,26 +158,33 @@
boost::detail::thread_data_ptr thread_info = static_cast<boost::detail::thread_data_base*>(param)->self;
thread_info->self.reset();
detail::set_current_thread_data(thread_info.get());
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
BOOST_TRY
{
+#endif
thread_info->run();
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
}
BOOST_CATCH (thread_interrupted const&)
{
}
- BOOST_CATCH_END
// Removed as it stops the debugger identifying the cause of the exception
// Unhandled exceptions still cause the application to terminate
// BOOST_CATCH(...)
// {
+// throw;
+//
// std::terminate();
// }
-
+ BOOST_CATCH_END
+#endif
detail::tls_destructor(thread_info.get());
detail::set_current_thread_data(0);
boost::lock_guard<boost::mutex> lock(thread_info->data_mutex);
thread_info->done=true;
thread_info->done_condition.notify_all();
+
return 0;
}
}
@@ -177,7 +194,9 @@
{
externally_launched_thread()
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
interrupt_enabled=false;
+#endif
}
void run()
@@ -215,18 +234,20 @@
thread::thread() BOOST_NOEXCEPT
{}
- void thread::start_thread()
+ bool thread::start_thread_noexcept()
{
thread_info->self=thread_info;
int const res = pthread_create(&thread_info->thread_handle, 0, &thread_proxy, thread_info.get());
if (res != 0)
{
thread_info->self.reset();
- boost::throw_exception(thread_resource_error(res, "boost thread: failed in pthread_create"));
+ return false;
+// boost::throw_exception(thread_resource_error(res, "boost thread: failed in pthread_create"));
}
+ return true;
}
- void thread::start_thread(const attributes& attr)
+ bool thread::start_thread_noexcept(const attributes& attr)
{
thread_info->self=thread_info;
const attributes::native_handle_type* h = attr.native_handle();
@@ -234,14 +255,16 @@
if (res != 0)
{
thread_info->self.reset();
- boost::throw_exception(thread_resource_error());
+ return false;
+// boost::throw_exception(thread_resource_error(res, "boost thread: failed in pthread_create"));
}
int detached_state;
res = pthread_attr_getdetachstate(h, &detached_state);
if (res != 0)
{
thread_info->self.reset();
- boost::throw_exception(thread_resource_error());
+ return false;
+// boost::throw_exception(thread_resource_error(res, "boost thread: failed in pthread_attr_getdetachstate"));
}
if (PTHREAD_CREATE_DETACHED==detached_state)
{
@@ -259,6 +282,7 @@
}
}
}
+ return true;
}
@@ -268,12 +292,8 @@
return thread_info;
}
- void thread::join()
+ bool thread::join_noexcept()
{
- if (this_thread::get_id() == get_id())
- {
- boost::throw_exception(thread_resource_error(system::errc::resource_deadlock_would_occur, "boost thread: trying joining itself"));
- }
detail::thread_data_ptr const local_thread_info=(get_thread_info)();
if(local_thread_info)
{
@@ -312,21 +332,16 @@
{
thread_info.reset();
}
+ return true;
}
else
{
-#ifdef BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED
- boost::throw_exception(thread_resource_error(system::errc::invalid_argument, "boost thread: thread not joinable"));
-#endif
+ return false;
}
}
- bool thread::do_try_join_until(struct timespec const &timeout)
+ bool thread::do_try_join_until_noexcept(struct timespec const &timeout, bool& res)
{
- if (this_thread::get_id() == get_id())
- {
- boost::throw_exception(thread_resource_error(system::errc::resource_deadlock_would_occur, "boost thread: trying joining itself"));
- }
detail::thread_data_ptr const local_thread_info=(get_thread_info)();
if(local_thread_info)
{
@@ -336,9 +351,10 @@
unique_lock<mutex> lock(local_thread_info->data_mutex);
while(!local_thread_info->done)
{
- if(!local_thread_info->done_condition.do_timed_wait(lock,timeout))
+ if(!local_thread_info->done_condition.do_wait_until(lock,timeout))
{
- return false;
+ res=false;
+ return true;
}
}
do_join=!local_thread_info->join_started;
@@ -368,13 +384,12 @@
{
thread_info.reset();
}
+ res=true;
return true;
}
else
{
-#ifdef BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED
- boost::throw_exception(thread_resource_error(system::errc::invalid_argument, "boost thread: thread not joinable"));
-#endif
+ return false;
}
}
@@ -403,61 +418,95 @@
namespace this_thread
{
-
-#ifdef __DECXXX
- /// Workaround of DECCXX issue of incorrect template substitution
- template<>
-#endif
- void sleep(const system_time& st)
+ namespace hiden
+ {
+ void BOOST_THREAD_DECL sleep_for(const timespec& ts)
{
- detail::thread_data_base* const thread_info=detail::get_current_thread_data();
+ boost::detail::thread_data_base* const thread_info=boost::detail::get_current_thread_data();
if(thread_info)
{
- unique_lock<mutex> lk(thread_info->sleep_mutex);
- while(thread_info->sleep_condition.timed_wait(lk,st)) {}
+ unique_lock<mutex> lk(thread_info->sleep_mutex);
+ while( thread_info->sleep_condition.do_wait_for(lk,ts)) {}
}
else
{
- xtime const xt=get_xtime(st);
+ if (boost::detail::timespec_ge(ts, boost::detail::timespec_zero()))
+ {
+
+ # if defined(BOOST_HAS_PTHREAD_DELAY_NP)
+ BOOST_VERIFY(!pthread_delay_np(&ts));
+ # elif defined(BOOST_HAS_NANOSLEEP)
+ // nanosleep takes a timespec that is an offset, not
+ // an absolute time.
+ nanosleep(&ts, 0);
+ # else
+ mutex mx;
+ unique_lock<mutex> lock(mx);
+ condition_variable cond;
+ cond.do_wait_for(lock, ts);
+ # endif
+ }
+ }
+ }
+
+ void BOOST_THREAD_DECL sleep_until(const timespec& ts)
+ {
+ boost::detail::thread_data_base* const thread_info=boost::detail::get_current_thread_data();
+
+ if(thread_info)
+ {
+ unique_lock<mutex> lk(thread_info->sleep_mutex);
+ while(thread_info->sleep_condition.do_wait_until(lk,ts)) {}
+ }
+ else
+ {
+ timespec now = boost::detail::timespec_now();
+ if (boost::detail::timespec_gt(ts, now))
+ {
for (int foo=0; foo < 5; ++foo)
{
-# if defined(BOOST_HAS_PTHREAD_DELAY_NP)
- timespec ts;
- to_timespec_duration(xt, ts);
- BOOST_VERIFY(!pthread_delay_np(&ts));
-# elif defined(BOOST_HAS_NANOSLEEP)
- timespec ts;
- to_timespec_duration(xt, ts);
-
- // nanosleep takes a timespec that is an offset, not
- // an absolute time.
- nanosleep(&ts, 0);
-# else
- mutex mx;
- mutex::scoped_lock lock(mx);
- condition cond;
- cond.timed_wait(lock, xt);
-# endif
- xtime cur;
- xtime_get(&cur, TIME_UTC_);
- if (xtime_cmp(xt, cur) <= 0)
- return;
+
+ # if defined(BOOST_HAS_PTHREAD_DELAY_NP)
+ timespec d = boost::detail::timespec_minus(ts, now);
+ BOOST_VERIFY(!pthread_delay_np(&d));
+ # elif defined(BOOST_HAS_NANOSLEEP)
+ // nanosleep takes a timespec that is an offset, not
+ // an absolute time.
+ timespec d = boost::detail::timespec_minus(ts, now);
+ nanosleep(&d, 0);
+ # else
+ mutex mx;
+ unique_lock<mutex> lock(mx);
+ condition_variable cond;
+ cond.do_wait_until(lock, ts);
+ # endif
+ timespec now2 = boost::detail::timespec_now();
+ if (boost::detail::timespec_ge(now2, ts))
+ {
+ return;
+ }
}
+ }
}
}
-
+ } // hiden
+ } // this_thread
+ namespace this_thread
+ {
void yield() BOOST_NOEXCEPT
{
# if defined(BOOST_HAS_SCHED_YIELD)
BOOST_VERIFY(!sched_yield());
# elif defined(BOOST_HAS_PTHREAD_YIELD)
BOOST_VERIFY(!pthread_yield());
-# else
- xtime xt;
- xtime_get(&xt, TIME_UTC_);
- sleep(xt);
+# elif defined BOOST_THREAD_USES_DATETIME
+// xtime xt;
+// xtime_get(&xt, TIME_UTC_);
+// sleep(xt);
+//# else
+ sleep_for(chrono::milliseconds(0));
# endif
}
}
@@ -479,24 +528,7 @@
#endif
}
- thread::id thread::get_id() const BOOST_NOEXCEPT
- {
- #if defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
- //return local_thread_info->thread_handle;
- return const_cast<thread*>(this)->native_handle();
- #else
- detail::thread_data_ptr const local_thread_info=(get_thread_info)();
- if(local_thread_info)
- {
- return id(local_thread_info);
- }
- else
- {
- return id();
- }
- #endif
- }
-
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void thread::interrupt()
{
detail::thread_data_ptr const local_thread_info=(get_thread_info)();
@@ -525,6 +557,7 @@
return false;
}
}
+#endif
thread::native_handle_type thread::native_handle()
{
@@ -542,18 +575,9 @@
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
namespace this_thread
{
- thread::id get_id() BOOST_NOEXCEPT
- {
- #if defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
- return pthread_self();
- #else
- boost::detail::thread_data_base* const thread_info=get_or_make_current_thread_data();
- return thread::id(thread_info?thread_info->shared_from_this():detail::thread_data_ptr());
- #endif
- }
-
void interruption_point()
{
#ifndef BOOST_NO_EXCEPTIONS
@@ -623,6 +647,7 @@
}
}
}
+#endif
namespace detail
{
Modified: branches/release/libs/thread/src/pthread/timeconv.inl
==============================================================================
--- branches/release/libs/thread/src/pthread/timeconv.inl (original)
+++ branches/release/libs/thread/src/pthread/timeconv.inl 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,6 +17,7 @@
const int MICROSECONDS_PER_SECOND = 1000000;
const int NANOSECONDS_PER_MICROSECOND = 1000;
+#if defined BOOST_THREAD_USES_DATETIME
inline void to_time(int milliseconds, boost::xtime& xt)
{
int res = 0;
@@ -33,7 +34,9 @@
xt.nsec -= NANOSECONDS_PER_SECOND;
}
}
+#endif
#if defined(BOOST_HAS_PTHREADS)
+#if defined BOOST_THREAD_USES_DATETIME
inline void to_timespec(const boost::xtime& xt, timespec& ts)
{
ts.tv_sec = static_cast<int>(xt.sec);
@@ -44,14 +47,27 @@
ts.tv_nsec %= NANOSECONDS_PER_SECOND;
}
}
-
+#endif
inline void to_time(int milliseconds, timespec& ts)
{
+#if defined BOOST_THREAD_USES_DATETIME
boost::xtime xt;
to_time(milliseconds, xt);
to_timespec(xt, ts);
+#else
+ ts.tv_sec += (milliseconds / MILLISECONDS_PER_SECOND);
+ ts.tv_nsec += ((milliseconds % MILLISECONDS_PER_SECOND) *
+ NANOSECONDS_PER_MILLISECOND);
+
+ if (ts.tv_nsec >= NANOSECONDS_PER_SECOND)
+ {
+ ++ts.tv_sec;
+ ts.tv_nsec -= NANOSECONDS_PER_SECOND;
+ }
+#endif
}
+#if defined BOOST_THREAD_USES_DATETIME
inline void to_timespec_duration(const boost::xtime& xt, timespec& ts)
{
boost::xtime cur;
@@ -82,7 +98,9 @@
}
}
#endif
+#endif
+#if defined BOOST_THREAD_USES_DATETIME
inline void to_duration(boost::xtime xt, int& milliseconds)
{
boost::xtime cur;
@@ -126,6 +144,7 @@
NANOSECONDS_PER_MICROSECOND);
}
}
+#endif
}
// Change Log:
Modified: branches/release/libs/thread/src/win32/thread.cpp
==============================================================================
--- branches/release/libs/thread/src/win32/thread.cpp (original)
+++ branches/release/libs/thread/src/win32/thread.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,7 @@
// http://www.boost.org/LICENSE_1_0.txt)
// (C) Copyright 2007 Anthony Williams
// (C) Copyright 2007 David Deakins
+// (C) Copyright 2011-2012 Vicente J. Botet Escriba
#ifndef _WIN32_WINNT
#define _WIN32_WINNT 0x400
@@ -11,17 +12,19 @@
#ifndef WINVER
#define WINVER 0x400
#endif
+#define BOOST_THREAD_VERSION 2
#include <boost/thread/thread.hpp>
#include <boost/thread/once.hpp>
#include <boost/thread/tss.hpp>
#include <boost/thread/condition_variable.hpp>
#include <boost/thread/detail/tss_hooks.hpp>
+#include <boost/thread/future.hpp>
#include <boost/assert.hpp>
-#include <boost/throw_exception.hpp>
+#if defined BOOST_THREAD_USES_DATETIME
#include <boost/date_time/posix_time/conversion.hpp>
-
+#endif
#include <memory>
#include <algorithm>
#ifndef UNDER_CE
@@ -36,16 +39,20 @@
{
thread_data_base::~thread_data_base()
{
- {
for (notify_list_t::iterator i = notify.begin(), e = notify.end();
i != e; ++i)
{
i->second->unlock();
i->first->notify_all();
}
- }
+ for (async_states_t::iterator i = async_states_.begin(), e = async_states_.end();
+ i != e; ++i)
+ {
+ (*i)->make_ready();
+ }
}
}
+
namespace
{
#ifdef BOOST_THREAD_PROVIDES_ONCE_CXX11
@@ -75,24 +82,34 @@
}
}
- detail::thread_data_base* get_current_thread_data()
- {
- if(current_thread_tls_key==TLS_OUT_OF_INDEXES)
- {
- return 0;
- }
- return (detail::thread_data_base*)TlsGetValue(current_thread_tls_key);
- }
-
void set_current_thread_data(detail::thread_data_base* new_data)
{
boost::call_once(current_thread_tls_init_flag,create_current_thread_tls_key);
- if(current_thread_tls_key!=TLS_OUT_OF_INDEXES)
+ if (current_thread_tls_key!=TLS_OUT_OF_INDEXES)
+ {
BOOST_VERIFY(TlsSetValue(current_thread_tls_key,new_data));
+ }
else
- boost::throw_exception(thread_resource_error());
+ {
+ BOOST_VERIFY(false);
+ //boost::throw_exception(thread_resource_error());
+ }
}
+ }
+ namespace detail
+ {
+ thread_data_base* get_current_thread_data()
+ {
+ if(current_thread_tls_key==TLS_OUT_OF_INDEXES)
+ {
+ return 0;
+ }
+ return (detail::thread_data_base*)TlsGetValue(current_thread_tls_key);
+ }
+ }
+ namespace
+ {
#ifndef BOOST_HAS_THREADEX
// Windows CE doesn't define _beginthreadex
@@ -151,7 +168,7 @@
{
void run_thread_exit_callbacks()
{
- detail::thread_data_ptr current_thread_data(get_current_thread_data(),false);
+ detail::thread_data_ptr current_thread_data(detail::get_current_thread_data(),false);
if(current_thread_data)
{
while(! current_thread_data->tss_data.empty() || current_thread_data->thread_exit_callbacks)
@@ -190,23 +207,24 @@
{
detail::thread_data_base* const thread_info(reinterpret_cast<detail::thread_data_base*>(param));
set_current_thread_data(thread_info);
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ BOOST_TRY
{
+#endif
thread_info->run();
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(thread_interrupted const&) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(thread_interrupted const&)
{
}
-#endif
// Removed as it stops the debugger identifying the cause of the exception
// Unhandled exceptions still cause the application to terminate
-// catch(...) // BOOST_NO_EXCEPTIONS protected
+// BOOST_CATCH(...)
// {
// std::terminate();
// }
+ BOOST_CATCH_END
+#endif
run_thread_exit_callbacks();
return 0;
}
@@ -215,29 +233,33 @@
thread::thread() BOOST_NOEXCEPT
{}
- void thread::start_thread()
+ bool thread::start_thread_noexcept()
{
uintptr_t const new_thread=_beginthreadex(0,0,&thread_start_function,thread_info.get(),CREATE_SUSPENDED,&thread_info->id);
if(!new_thread)
{
- boost::throw_exception(thread_resource_error());
+ return false;
+// boost::throw_exception(thread_resource_error());
}
intrusive_ptr_add_ref(thread_info.get());
thread_info->thread_handle=(detail::win32::handle)(new_thread);
ResumeThread(thread_info->thread_handle);
+ return true;
}
- void thread::start_thread(const attributes& attr)
+ bool thread::start_thread_noexcept(const attributes& attr)
{
//uintptr_t const new_thread=_beginthreadex(attr.get_security(),attr.get_stack_size(),&thread_start_function,thread_info.get(),CREATE_SUSPENDED,&thread_info->id);
uintptr_t const new_thread=_beginthreadex(0,static_cast<unsigned int>(attr.get_stack_size()),&thread_start_function,thread_info.get(),CREATE_SUSPENDED,&thread_info->id);
if(!new_thread)
{
- boost::throw_exception(thread_resource_error());
+ return false;
+// boost::throw_exception(thread_resource_error());
}
intrusive_ptr_add_ref(thread_info.get());
thread_info->thread_handle=(detail::win32::handle)(new_thread);
ResumeThread(thread_info->thread_handle);
+ return true;
}
thread::thread(detail::thread_data_ptr data):
@@ -252,7 +274,9 @@
externally_launched_thread()
{
++count;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
interruption_enabled=false;
+#endif
}
void run()
@@ -268,28 +292,25 @@
void make_external_thread_data()
{
externally_launched_thread* me=detail::heap_new<externally_launched_thread>();
-#ifndef BOOST_NO_EXCEPTIONS
- try // BOOST_NO_EXCEPTIONS protected
-#endif
+ BOOST_TRY
{
set_current_thread_data(me);
}
-#ifndef BOOST_NO_EXCEPTIONS
- catch(...) // BOOST_NO_EXCEPTIONS protected
+ BOOST_CATCH(...)
{
detail::heap_delete(me);
- throw; // BOOST_NO_EXCEPTIONS protected
+ BOOST_RETHROW
}
-#endif
+ BOOST_CATCH_END
}
detail::thread_data_base* get_or_make_current_thread_data()
{
- detail::thread_data_base* current_thread_data(get_current_thread_data());
+ detail::thread_data_base* current_thread_data(detail::get_current_thread_data());
if(!current_thread_data)
{
make_external_thread_data();
- current_thread_data=get_current_thread_data();
+ current_thread_data=detail::get_current_thread_data();
}
return current_thread_data;
}
@@ -311,52 +332,45 @@
{
return (get_thread_info)();
}
- void thread::join()
+ bool thread::join_noexcept()
{
- if (this_thread::get_id() == get_id())
- {
- boost::throw_exception(thread_resource_error(system::errc::resource_deadlock_would_occur, "boost thread: trying joining itself"));
- }
+
detail::thread_data_ptr local_thread_info=(get_thread_info)();
if(local_thread_info)
{
this_thread::interruptible_wait(local_thread_info->thread_handle,detail::timeout::sentinel());
release_handle();
+ return true;
}
else
{
-#ifdef BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED
- boost::throw_exception(thread_resource_error(system::errc::invalid_argument, "boost thread: thread not joinable"));
-#endif
+ return false;
}
}
+#if defined BOOST_THREAD_USES_DATETIME
bool thread::timed_join(boost::system_time const& wait_until)
{
return do_try_join_until(get_milliseconds_until(wait_until));
}
-
- bool thread::do_try_join_until(uintmax_t milli)
+#endif
+ bool thread::do_try_join_until_noexcept(uintmax_t milli, bool& res)
{
- if (this_thread::get_id() == get_id())
- {
- boost::throw_exception(thread_resource_error(system::errc::resource_deadlock_would_occur, "boost thread: trying joining itself"));
- }
detail::thread_data_ptr local_thread_info=(get_thread_info)();
if(local_thread_info)
{
if(!this_thread::interruptible_wait(local_thread_info->thread_handle,milli))
{
- return false;
+ res=false;
+ return true;
}
release_handle();
+ res=true;
return true;
}
else
{
-#ifdef BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED
- boost::throw_exception(thread_resource_error(system::errc::invalid_argument, "boost thread: thread not joinable"));
-#endif
+ return false;
}
}
@@ -370,6 +384,7 @@
thread_info=0;
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void thread::interrupt()
{
detail::thread_data_ptr local_thread_info=(get_thread_info)();
@@ -391,6 +406,7 @@
GetSystemInfo(&info);
return info.dwNumberOfProcessors;
}
+#endif
thread::native_handle_type thread::native_handle()
{
@@ -467,19 +483,22 @@
detail::win32::handle handles[3]={0};
unsigned handle_count=0;
unsigned wait_handle_index=~0U;
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
unsigned interruption_index=~0U;
+#endif
unsigned timeout_index=~0U;
if(handle_to_wait_for!=detail::win32::invalid_handle_value)
{
wait_handle_index=handle_count;
handles[handle_count++]=handle_to_wait_for;
}
- if(get_current_thread_data() && get_current_thread_data()->interruption_enabled)
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
+ if(detail::get_current_thread_data() && detail::get_current_thread_data()->interruption_enabled)
{
interruption_index=handle_count;
- handles[handle_count++]=get_current_thread_data()->interruption_handle;
+ handles[handle_count++]=detail::get_current_thread_data()->interruption_handle;
}
-
+#endif
detail::win32::handle_manager timer_handle;
#ifndef UNDER_CE
@@ -531,11 +550,13 @@
{
return true;
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
else if(notified_index==interruption_index)
{
- detail::win32::ResetEvent(get_current_thread_data()->interruption_handle);
+ detail::win32::ResetEvent(detail::get_current_thread_data()->interruption_handle);
throw thread_interrupted();
}
+#endif
else if(notified_index==timeout_index)
{
return false;
@@ -558,51 +579,53 @@
thread::id get_id() BOOST_NOEXCEPT
{
#if defined BOOST_THREAD_PROVIDES_BASIC_THREAD_ID
- //return detail::win32::GetCurrentThread();
return detail::win32::GetCurrentThreadId();
#else
return thread::id(get_or_make_current_thread_data());
#endif
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
void interruption_point()
{
if(interruption_enabled() && interruption_requested())
{
- detail::win32::ResetEvent(get_current_thread_data()->interruption_handle);
+ detail::win32::ResetEvent(detail::get_current_thread_data()->interruption_handle);
throw thread_interrupted();
}
}
bool interruption_enabled() BOOST_NOEXCEPT
{
- return get_current_thread_data() && get_current_thread_data()->interruption_enabled;
+ return detail::get_current_thread_data() && detail::get_current_thread_data()->interruption_enabled;
}
bool interruption_requested() BOOST_NOEXCEPT
{
- return get_current_thread_data() && (detail::win32::WaitForSingleObject(get_current_thread_data()->interruption_handle,0)==0);
+ return detail::get_current_thread_data() && (detail::win32::WaitForSingleObject(detail::get_current_thread_data()->interruption_handle,0)==0);
}
+#endif
void yield() BOOST_NOEXCEPT
{
detail::win32::Sleep(0);
}
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
disable_interruption::disable_interruption() BOOST_NOEXCEPT:
interruption_was_enabled(interruption_enabled())
{
if(interruption_was_enabled)
{
- get_current_thread_data()->interruption_enabled=false;
+ detail::get_current_thread_data()->interruption_enabled=false;
}
}
disable_interruption::~disable_interruption() BOOST_NOEXCEPT
{
- if(get_current_thread_data())
+ if(detail::get_current_thread_data())
{
- get_current_thread_data()->interruption_enabled=interruption_was_enabled;
+ detail::get_current_thread_data()->interruption_enabled=interruption_was_enabled;
}
}
@@ -610,18 +633,19 @@
{
if(d.interruption_was_enabled)
{
- get_current_thread_data()->interruption_enabled=true;
+ detail::get_current_thread_data()->interruption_enabled=true;
}
}
restore_interruption::~restore_interruption() BOOST_NOEXCEPT
{
- if(get_current_thread_data())
+ if(detail::get_current_thread_data())
{
- get_current_thread_data()->interruption_enabled=false;
+ detail::get_current_thread_data()->interruption_enabled=false;
}
}
}
+#endif
namespace detail
{
@@ -716,7 +740,7 @@
BOOST_THREAD_DECL void notify_all_at_thread_exit(condition_variable& cond, unique_lock<mutex> lk)
{
- detail::thread_data_base* const current_thread_data(get_current_thread_data());
+ detail::thread_data_base* const current_thread_data(detail::get_current_thread_data());
if(current_thread_data)
{
current_thread_data->notify_all_at_thread_exit(&cond, lk.release());
Modified: branches/release/libs/thread/test/Jamfile.v2
==============================================================================
--- branches/release/libs/thread/test/Jamfile.v2 (original)
+++ branches/release/libs/thread/test/Jamfile.v2 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -23,6 +23,8 @@
: requirements
<threading>multi
+ <define>BOOST_THREAD_THROW_IF_PRECONDITION_NOT_SATISFIED
+
<warnings>all
<toolset>gcc:<cxxflags>-Wextra
<toolset>gcc:<cxxflags>-pedantic
@@ -43,7 +45,7 @@
<toolset>clang:<cxxflags>-Wextra
<toolset>clang:<cxxflags>-pedantic
<toolset>clang:<cxxflags>-Wno-long-long
- <toolset>clang:<cxxflags>-ansi
+ #<toolset>clang:<cxxflags>-ansi
#<toolset>clang:<cxxflags>-fpermissive # doesn't work
<toolset>gcc-mingw-4.4.0:<cxxflags>-fdiagnostics-show-option
@@ -66,6 +68,19 @@
#<toolset>clang-3.0:<cxxflags>-Wno-unused-function
#<toolset>clang-3.0:<cxxflags>-Wno-unused-variable
+# Note: Some of the remarks from the Intel compiler are disabled
+# remark #193: zero used for undefined preprocessing identifier "XXX"
+# remark #304: access control not specified ("public" by default)
+# remark #593: variable "XXX" was set but never used
+# remark #1418: external function definition with no prior declaration
+# remark #2415: variable "XXX" of static storage duration was declared but never referenced
+
+ <toolset>intel:<cxxflags>-wd193,304,383,444
+ <toolset>intel:<cxxflags>-wd593,981
+ <toolset>intel:<cxxflags>-wd1418
+ <toolset>intel:<cxxflags>-wd2415
+
+
;
rule thread-run ( sources )
@@ -77,6 +92,7 @@
;
}
+
rule thread-test ( sources )
{
return
@@ -102,6 +118,18 @@
;
}
+rule thread-run2-h ( sources : name )
+{
+ return
+ [ run $(sources) : : :
+ <library>/boost/system//boost_system
+ <define>BOOST_THREAD_DONT_PROVIDE_INTERRUPTIONS
+ <define>BOOST_THREAD_VERSION=3
+ : $(name)_h ]
+ ;
+}
+
+
rule thread-run-lib2 ( sources : name )
{
return
@@ -187,10 +215,11 @@
[ thread-run test_5542_3.cpp ]
[ thread-run test_5891.cpp ]
[ thread-run test_6130.cpp ]
- [ thread-run test_6170.cpp ]
+ #[ thread-run test_6170.cpp ]
[ thread-run test_6174.cpp ]
- [ thread-run test_7160.cpp ]
+ #[ thread-run test_7160.cpp ]
[ thread-run test_7328.cpp ]
+ [ thread-run test_7571.cpp ]
;
@@ -228,7 +257,7 @@
[ thread-run2 ./sync/conditions/notify_all_at_thread_exit_pass.cpp : notify_all_at_thread_exit_p ]
;
- explicit ts_async ;
+ #explicit ts_async ;
test-suite ts_async
:
[ thread-run2 ./sync/futures/async/async_pass.cpp : async__async_p ]
@@ -245,7 +274,17 @@
[ thread-run2 ./sync/futures/promise/get_future_pass.cpp : promise__get_future_p ]
[ thread-run2 ./sync/futures/promise/move_ctor_pass.cpp : promise__move_ctor_p ]
[ thread-run2 ./sync/futures/promise/move_assign_pass.cpp : promise__move_asign_p ]
+ [ thread-run2 ./sync/futures/promise/set_exception_pass.cpp : promise__set_exception_p ]
+ [ thread-run2 ./sync/futures/promise/set_lvalue_pass.cpp : promise__set_lvalue_p ]
+ [ thread-run2 ./sync/futures/promise/set_rvalue_pass.cpp : promise__set_rvalue_p ]
+ [ thread-run2 ./sync/futures/promise/set_value_const_pass.cpp : promise__set_value_const_p ]
+ [ thread-run2 ./sync/futures/promise/set_value_void_pass.cpp : promise__set_value_void_p ]
[ thread-run2 ./sync/futures/promise/use_allocator_pass.cpp : promise__use_allocator_p ]
+ [ thread-run2 ./sync/futures/promise/set_exception_at_thread_exit_pass.cpp : promise__set_exception_at_thread_exit_p ]
+ [ thread-run2 ./sync/futures/promise/set_lvalue_at_thread_exit_pass.cpp : promise__set_lvalue_at_thread_exit_p ]
+ [ thread-run2 ./sync/futures/promise/set_rvalue_at_thread_exit_pass.cpp : promise__set_rvalue_at_thread_exit_p ]
+ [ thread-run2 ./sync/futures/promise/set_value_at_thread_exit_const_pass.cpp : promise__set_value_at_thread_exit_const_p ]
+ [ thread-run2 ./sync/futures/promise/set_value_at_thread_exit_void_pass.cpp : promise__set_value_at_thread_exit_void_p ]
;
#explicit ts_future ;
@@ -255,10 +294,23 @@
[ thread-compile-fail ./sync/futures/future/copy_ctor_fail.cpp : : future__copy_ctor_f ]
[ thread-run2 ./sync/futures/future/default_pass.cpp : future__default_p ]
[ thread-run2 ./sync/futures/future/dtor_pass.cpp : future__dtor_p ]
- #[ thread-run2 ./sync/futures/future/get_pass.cpp : future__get_p ]
+ [ thread-run2 ./sync/futures/future/get_pass.cpp : future__get_p ]
[ thread-run2 ./sync/futures/future/move_ctor_pass.cpp : future__move_ctor_p ]
[ thread-run2 ./sync/futures/future/move_assign_pass.cpp : future__move_asign_p ]
[ thread-run2 ./sync/futures/future/share_pass.cpp : future__share_p ]
+ [ thread-run2 ./sync/futures/future/then_pass.cpp : future__then_p ]
+ ;
+
+ #explicit ts_shared_future ;
+ test-suite ts_shared_future
+ :
+ [ thread-run2 ./sync/futures/shared_future/copy_assign_pass.cpp : shared_future__copy_assign_p ]
+ [ thread-run2 ./sync/futures/shared_future/copy_ctor_pass.cpp : shared_future__copy_ctor_p ]
+ [ thread-run2 ./sync/futures/shared_future/default_pass.cpp : shared_future__default_p ]
+ [ thread-run2 ./sync/futures/shared_future/dtor_pass.cpp : shared_future__dtor_p ]
+ [ thread-run2 ./sync/futures/shared_future/get_pass.cpp : shared_future__get_p ]
+ [ thread-run2 ./sync/futures/shared_future/move_ctor_pass.cpp : shared_future__move_ctor_p ]
+ [ thread-run2 ./sync/futures/shared_future/move_assign_pass.cpp : shared_future__move_asign_p ]
;
#explicit ts_packaged_task ;
@@ -269,16 +321,17 @@
[ thread-compile-fail ./sync/futures/packaged_task/copy_ctor_fail.cpp : : packaged_task__copy_ctor_f ]
[ thread-run2 ./sync/futures/packaged_task/default_ctor_pass.cpp : packaged_task__default_ctor_p ]
[ thread-run2 ./sync/futures/packaged_task/func_ctor_pass.cpp : packaged_task__func_ctor_p ]
- #[ thread-run2 ./sync/futures/packaged_task/dtor_pass.cpp : packaged_task__dtor_p ]
+ [ thread-run2 ./sync/futures/packaged_task/dtor_pass.cpp : packaged_task__dtor_p ]
[ thread-run2 ./sync/futures/packaged_task/get_future_pass.cpp : packaged_task__get_future_p ]
[ thread-run2 ./sync/futures/packaged_task/move_ctor_pass.cpp : packaged_task__move_ctor_p ]
[ thread-run2 ./sync/futures/packaged_task/move_assign_pass.cpp : packaged_task__move_asign_p ]
- #[ thread-run2 ./sync/futures/packaged_task/operator_pass.cpp : packaged_task__operator_p ]
+ [ thread-run2 ./sync/futures/packaged_task/operator_pass.cpp : packaged_task__operator_p ]
[ thread-run2 ./sync/futures/packaged_task/reset_pass.cpp : packaged_task__reset_p ]
[ thread-run2 ./sync/futures/packaged_task/use_allocator_pass.cpp : packaged_task__use_allocator_p ]
[ thread-run2 ./sync/futures/packaged_task/types_pass.cpp : packaged_task__types_p ]
[ thread-run2 ./sync/futures/packaged_task/member_swap_pass.cpp : packaged_task__member_swap_p ]
[ thread-run2 ./sync/futures/packaged_task/non_member_swap_pass.cpp : packaged_task__non_member_swap_p ]
+ [ thread-run2 ./sync/futures/packaged_task/make_ready_at_thread_exit_pass.cpp : packaged_task__make_ready_at_thread_exit_p ]
;
@@ -290,6 +343,8 @@
[ thread-run2 ./sync/mutual_exclusion/locks/lock_guard/adopt_lock_pass.cpp : lock_guard__cons__adopt_lock_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/lock_guard/default_pass.cpp : lock_guard__cons__default_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/lock_guard/types_pass.cpp : lock_guard__types_p ]
+ [ thread-run2 ./sync/mutual_exclusion/locks/lock_guard/make_lock_guard_pass.cpp : make_lock_guard_p ]
+ [ thread-run2 ./sync/mutual_exclusion/locks/lock_guard/make_lock_guard_adopt_lock_pass.cpp : make_lock_guard__adopt_lock_p ]
;
#explicit ts_unique_lock ;
@@ -320,9 +375,23 @@
[ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/mod/release_pass.cpp : unique_lock__release_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/obs/mutex_pass.cpp : unique_lock__mutex_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/obs/op_bool_pass.cpp : unique_lock__op_bool_p ]
- [ thread-compile-fail ./sync/mutual_exclusion/locks/unique_lock/obs/op_int_fail.cpp : : unique_lock__op_int_f ]
+ #[ thread-compile-fail ./sync/mutual_exclusion/locks/unique_lock/obs/op_int_fail.cpp : : unique_lock__op_int_f ]
[ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/obs/owns_lock_pass.cpp : unique_lock__owns_lock_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/types_pass.cpp : unique_lock__types_p ]
+
+
+ ;
+
+ #explicit ts_make_unique_lock ;
+ test-suite ts_make_unique_lock
+ :
+ [ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_mutex_pass.cpp : make_unique_lock__mutex_p ]
+ [ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_adopt_lock_pass.cpp : make_unique_lock__adopt_lock_p ]
+ [ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_defer_lock_pass.cpp : make_unique_lock__defer_lock_p ]
+ [ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/cons/make_unique_lock_try_to_lock_pass.cpp : make_unique_lock__try_to_lock_p ]
+
+ [ thread-run2 ./sync/mutual_exclusion/locks/unique_lock/cons/make_unique_locks_mutex_pass.cpp : make_unique_locks__mutex_p ]
+
;
#explicit ts_shared_lock ;
@@ -353,6 +422,10 @@
[ thread-run2 ./sync/mutual_exclusion/locks/shared_lock/obs/op_bool_pass.cpp : shared_lock__op_bool_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/shared_lock/obs/owns_lock_pass.cpp : shared_lock__owns_lock_p ]
[ thread-run2 ./sync/mutual_exclusion/locks/shared_lock/types_pass.cpp : shared_lock__types_p ]
+
+ [ thread-run2-h ./sync/mutual_exclusion/locks/shared_lock/cons/default_pass.cpp : shared_lock__cons__default_p ]
+ [ thread-run2-h ./sync/mutual_exclusion/locks/shared_lock/cons/defer_lock_pass.cpp : shared_lock__cons__defer_lock_p ]
+
;
#explicit ts_upgrade_lock ;
@@ -443,6 +516,7 @@
[ thread-run2 ./sync/mutual_exclusion/shared_mutex/try_lock_pass.cpp : shared_mutex__try_lock_p ]
[ thread-run2 ./sync/mutual_exclusion/shared_mutex/try_lock_until_pass.cpp : shared_mutex__try_lock_until_p ]
+ [ thread-run2-h ./sync/mutual_exclusion/shared_mutex/default_pass.cpp : shared_mutex__default_p ]
;
#explicit ts_this_thread ;
@@ -463,7 +537,7 @@
[ thread-run-lib2 ./threads/thread/constr/F_pass.cpp : thread__constr__F_p ]
[ thread-run-lib2 ./threads/thread/constr/FArgs_pass.cpp : thread__constr__FArgs_p ]
[ thread-run2 ./threads/thread/constr/Frvalue_pass.cpp : thread__constr__Frvalue_p ]
- #[ thread-run2 ./threads/thread/constr/FrvalueArgs_pass.cpp : thread__constr__FrvalueArgs_p ]
+ [ thread-run2 ./threads/thread/constr/FrvalueArgs_pass.cpp : thread__constr__FrvalueArgs_p ]
[ thread-run2 ./threads/thread/constr/move_pass.cpp : thread__constr__move_p ]
[ thread-run2 ./threads/thread/destr/dtor_pass.cpp : thread__destr__dtor_p ]
[ thread-run2 ./threads/thread/id/hash_pass.cpp : thread__id__hash_p ]
@@ -504,6 +578,15 @@
[ thread-run ../example/shared_mutex.cpp ]
#[ thread-run ../example/vhh_shared_monitor.cpp ]
#[ thread-run ../example/vhh_shared_mutex.cpp ]
+ [ thread-run ../example/make_future.cpp ]
+ [ thread-run ../example/future_then.cpp ]
+ [ thread-run ../example/synchronized_value.cpp ]
+ [ thread-run ../example/synchronized_person.cpp ]
+ [ thread-run ../example/thread_guard.cpp ]
+ [ thread-run ../example/scoped_thread.cpp ]
+ [ thread-run ../example/strict_lock.cpp ]
+ [ thread-run ../example/ba_externallly_locked.cpp ]
+
;
#explicit ts_shared_upwards ;
@@ -538,4 +621,12 @@
[ thread-run2 ./sync/mutual_exclusion/locks/reverse_lock/types_pass.cpp : reverse_lock__types_p ]
;
+ explicit ts_ ;
+ test-suite ts_
+ :
+ #[ thread-run test_7665.cpp ]
+ #[ thread-run test_7666.cpp ]
+ #[ thread-run ../example/unwrap.cpp ]
+ ;
+
}
Modified: branches/release/libs/thread/test/condition_test_common.hpp
==============================================================================
--- branches/release/libs/thread/test/condition_test_common.hpp (original)
+++ branches/release/libs/thread/test/condition_test_common.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -2,7 +2,7 @@
#define CONDITION_TEST_COMMON_HPP
// Copyright (C) 2007 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/condition_variable.hpp>
@@ -10,14 +10,14 @@
#include <boost/thread/thread_time.hpp>
unsigned const timeout_seconds=5;
-
+
struct wait_for_flag
{
boost::mutex mutex;
boost::condition_variable cond_var;
bool flag;
unsigned woken;
-
+
wait_for_flag():
flag(false),woken(0)
{}
@@ -25,11 +25,11 @@
struct check_flag
{
bool const& flag;
-
+
check_flag(bool const& flag_):
flag(flag_)
{}
-
+
bool operator()() const
{
return flag;
@@ -38,10 +38,10 @@
void operator=(check_flag&);
};
-
+
void wait_without_predicate()
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
while(!flag)
{
cond_var.wait(lock);
@@ -51,7 +51,7 @@
void wait_with_predicate()
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
cond_var.wait(lock,check_flag(flag));
if(flag)
{
@@ -62,8 +62,8 @@
void timed_wait_without_predicate()
{
boost::system_time const timeout=boost::get_system_time()+boost::posix_time::seconds(timeout_seconds);
-
- boost::mutex::scoped_lock lock(mutex);
+
+ boost::unique_lock<boost::mutex> lock(mutex);
while(!flag)
{
if(!cond_var.timed_wait(lock,timeout))
@@ -77,7 +77,7 @@
void timed_wait_with_predicate()
{
boost::system_time const timeout=boost::get_system_time()+boost::posix_time::seconds(timeout_seconds);
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
if(cond_var.timed_wait(lock,timeout,check_flag(flag)) && flag)
{
++woken;
@@ -85,7 +85,7 @@
}
void relative_timed_wait_with_predicate()
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
if(cond_var.timed_wait(lock,boost::posix_time::seconds(timeout_seconds),check_flag(flag)) && flag)
{
++woken;
Modified: branches/release/libs/thread/test/shared_mutex_locking_thread.hpp
==============================================================================
--- branches/release/libs/thread/test/shared_mutex_locking_thread.hpp (original)
+++ branches/release/libs/thread/test/shared_mutex_locking_thread.hpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -37,15 +37,15 @@
unblocked_count_mutex(unblocked_count_mutex_),
finish_mutex(finish_mutex_)
{}
-
+
void operator()()
{
// acquire lock
lock_type lock(rw_mutex);
-
+
// increment count to show we're unblocked
{
- boost::mutex::scoped_lock ublock(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> ublock(unblocked_count_mutex);
++unblocked_count;
unblocked_condition.notify_one();
++simultaneous_running_count;
@@ -54,11 +54,11 @@
max_simultaneous_running=simultaneous_running_count;
}
}
-
+
// wait to finish
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
{
- boost::mutex::scoped_lock ublock(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> ublock(unblocked_count_mutex);
--simultaneous_running_count;
}
}
@@ -72,9 +72,9 @@
boost::mutex& finish_mutex;
boost::mutex& unblocked_mutex;
unsigned& unblocked_count;
-
+
void operator=(simple_writing_thread&);
-
+
public:
simple_writing_thread(boost::shared_mutex& rwm_,
boost::mutex& finish_mutex_,
@@ -83,17 +83,17 @@
rwm(rwm_),finish_mutex(finish_mutex_),
unblocked_mutex(unblocked_mutex_),unblocked_count(unblocked_count_)
{}
-
+
void operator()()
{
boost::unique_lock<boost::shared_mutex> lk(rwm);
-
+
{
- boost::mutex::scoped_lock ulk(unblocked_mutex);
+ boost::unique_lock<boost::mutex> ulk(unblocked_mutex);
++unblocked_count;
}
-
- boost::mutex::scoped_lock flk(finish_mutex);
+
+ boost::unique_lock<boost::mutex> flk(finish_mutex);
}
};
@@ -103,9 +103,9 @@
boost::mutex& finish_mutex;
boost::mutex& unblocked_mutex;
unsigned& unblocked_count;
-
+
void operator=(simple_reading_thread&);
-
+
public:
simple_reading_thread(boost::shared_mutex& rwm_,
boost::mutex& finish_mutex_,
@@ -114,17 +114,17 @@
rwm(rwm_),finish_mutex(finish_mutex_),
unblocked_mutex(unblocked_mutex_),unblocked_count(unblocked_count_)
{}
-
+
void operator()()
{
boost::shared_lock<boost::shared_mutex> lk(rwm);
-
+
{
- boost::mutex::scoped_lock ulk(unblocked_mutex);
+ boost::unique_lock<boost::mutex> ulk(unblocked_mutex);
++unblocked_count;
}
-
- boost::mutex::scoped_lock flk(finish_mutex);
+
+ boost::unique_lock<boost::mutex> flk(finish_mutex);
}
};
Modified: branches/release/libs/thread/test/sync/futures/async/async_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/async/async_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/async/async_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -22,10 +22,12 @@
// future<typename result_of<F(Args...)>::type>
// async(launch policy, F&& f, Args&&... args);
-#define BOOST_THREAD_VERSION 3
+//#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
#include <boost/thread/future.hpp>
#include <boost/thread/thread.hpp>
+#include <boost/thread/detail/memory.hpp>
#include <boost/interprocess/smart_ptr/unique_ptr.hpp>
#include <memory>
#include <boost/detail/lightweight_test.hpp>
@@ -38,7 +40,7 @@
long data_;
public:
- typedef int result_type;
+ typedef long result_type;
explicit A(long i) : data_(i) {}
@@ -93,149 +95,293 @@
return boost::interprocess::unique_ptr<int, boost::default_delete<int> >(new int(i));
}
-typedef boost::interprocess::unique_ptr<int, boost::default_delete<int> > XXT;
boost::interprocess::unique_ptr<int, boost::default_delete<int> > f4(
- BOOST_THREAD_RV_REF(boost::interprocess::unique_ptr<int, boost::default_delete<int> > ) p)
+ BOOST_THREAD_RV_REF_BEG boost::interprocess::unique_ptr<int, boost::default_delete<int> > BOOST_THREAD_RV_REF_END p
+)
{
boost::this_thread::sleep_for(ms(200));
return boost::move(p);
}
-
int main()
{
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<int> f = boost::async(f0);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(f.get() == 3);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<int> f = boost::async(boost::launch::async, f0);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(f.get() == 3);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+
+
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
- boost::future<int> f = boost::async(boost::launch::async, A(3));
+ try {
+ boost::future<long> f = boost::async(boost::launch::async, A(3));
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(f.get() == 3);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<int> f = boost::async(boost::launch::async, BOOST_THREAD_MAKE_RV_REF(MoveOnly()));
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(f.get() == 3);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<int> f = boost::async(boost::launch::any, f0);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(f.get() == 3);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
-// {
-// boost::future<int> f = boost::async(boost::launch::deferred, f0);
-// boost::this_thread::sleep_for(ms(300));
-// Clock::time_point t0 = Clock::now();
-// BOOST_TEST(f.get() == 3);
-// Clock::time_point t1 = Clock::now();
-// BOOST_TEST(t1 - t0 > ms(100));
-// }
-//
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
+ boost::future<int> f = boost::async(boost::launch::deferred, f0);
+ boost::this_thread::sleep_for(ms(300));
+ Clock::time_point t0 = Clock::now();
+ BOOST_TEST(f.get() == 3);
+ Clock::time_point t1 = Clock::now();
+ BOOST_TEST(t1 - t0 > ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+ }
+#endif
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
+ {
+ try {
boost::future<int&> f = boost::async(f1);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(&f.get() == &i);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<int&> f = boost::async(boost::launch::async, f1);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(&f.get() == &i);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<int&> f = boost::async(boost::launch::any, f1);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
BOOST_TEST(&f.get() == &i);
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+ }
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
+ {
+ try {
+ boost::future<int&> f = boost::async(boost::launch::deferred, f1);
+ boost::this_thread::sleep_for(ms(300));
+ Clock::time_point t0 = Clock::now();
+ BOOST_TEST(&f.get() == &i);
+ Clock::time_point t1 = Clock::now();
+ BOOST_TEST(t1 - t0 > ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
-// {
-// boost::future<int&> f = boost::async(boost::launch::deferred, f1);
-// boost::this_thread::sleep_for(ms(300));
-// Clock::time_point t0 = Clock::now();
-// BOOST_TEST(&f.get() == &i);
-// Clock::time_point t1 = Clock::now();
-// BOOST_TEST(t1 - t0 > ms(100));
-// }
-//
+#endif
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<void> f = boost::async(f2);
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
boost::this_thread::sleep_for(ms(300));
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
Clock::time_point t0 = Clock::now();
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
f.get();
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
Clock::time_point t1 = Clock::now();
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<void> f = boost::async(boost::launch::async, f2);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
f.get();
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
{
+ try {
boost::future<void> f = boost::async(boost::launch::any, f2);
boost::this_thread::sleep_for(ms(300));
Clock::time_point t0 = Clock::now();
f.get();
Clock::time_point t1 = Clock::now();
BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+ }
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
+ {
+ try {
+ boost::future<void> f = boost::async(boost::launch::deferred, f2);
+ boost::this_thread::sleep_for(ms(300));
+ Clock::time_point t0 = Clock::now();
+ f.get();
+ Clock::time_point t1 = Clock::now();
+ BOOST_TEST(t1 - t0 > ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
}
-// {
-// boost::future<void> f = boost::async(boost::launch::deferred, f2);
-// boost::this_thread::sleep_for(ms(300));
-// Clock::time_point t0 = Clock::now();
-// f.get();
-// Clock::time_point t1 = Clock::now();
-// BOOST_TEST(t1 - t0 > ms(100));
-// }
-
-// {
-// boost::future<boost::interprocess::unique_ptr<int, boost::default_delete<int> > > f = boost::async(f3, 3);
-// boost::this_thread::sleep_for(ms(300));
-// Clock::time_point t0 = Clock::now();
-// BOOST_TEST(*f.get() == 3);
-// Clock::time_point t1 = Clock::now();
-// BOOST_TEST(t1 - t0 < ms(100));
-// }
-
-// {
-// boost::future<boost::interprocess::unique_ptr<int, boost::default_delete<int> > > f = boost::async(f4, boost::interprocess::unique_ptr<int, boost::default_delete<int> >(new int(3)));
-// boost::this_thread::sleep_for(ms(300));
-// Clock::time_point t0 = Clock::now();
-// BOOST_TEST(*f.get() == 3);
-// Clock::time_point t1 = Clock::now();
-// BOOST_TEST(t1 - t0 < ms(100));
-// }
+#endif
+
+ // todo fixme
+#if 0 && defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<std::endl;
+ {
+ try {
+ boost::future<boost::interprocess::unique_ptr<int, boost::default_delete<int> > > f = boost::async(boost::launch::async, &f3, 3);
+ boost::this_thread::sleep_for(ms(300));
+ Clock::time_point t0 = Clock::now();
+ BOOST_TEST(*f.get() == 3);
+ Clock::time_point t1 = Clock::now();
+ BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+ }
+#endif
+
+ // todo fixme
+#if 0 && defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ {
+ try {
+ boost::future<boost::interprocess::unique_ptr<int, boost::default_delete<int> > > f = boost::async(&f4, boost::interprocess::unique_ptr<int, boost::default_delete<int> >(new int(3)));
+ boost::this_thread::sleep_for(ms(300));
+ Clock::time_point t0 = Clock::now();
+ BOOST_TEST(*f.get() == 3);
+ Clock::time_point t1 = Clock::now();
+ BOOST_TEST(t1 - t0 < ms(100));
+ } catch (std::exception& ex) {
+ std::cout << __FILE__ <<"["<<__LINE__<<"]"<<ex.what() << std::endl;
+ BOOST_TEST(false && "exception thrown");
+ } catch (...) {
+ BOOST_TEST(false && "exception thrown");
+ }
+ }
+#endif
return boost::report_errors();
}
-
Modified: branches/release/libs/thread/test/sync/futures/future/dtor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/future/dtor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/future/dtor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -14,9 +14,9 @@
// <boost/thread/future.hpp>
-// class promise<R>
+// class future<R>
-// ~promise();
+// ~future();
#define BOOST_THREAD_VERSION 3
#include <boost/exception/exception.hpp>
Modified: branches/release/libs/thread/test/sync/futures/future/get_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/future/get_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/future/get_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -14,16 +14,21 @@
// <boost/thread/future.hpp>
-// class promise<R>
+// class future<R>
-// future<R> get_future();
+// const R& future::get();
+// R& future<R&>::get();
+// void future<void>::get();
-#define BOOST_THREAD_VERSION 3
+//#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
#include <boost/thread/future.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
+#if defined BOOST_THREAD_USES_CHRONO
+
namespace boost
{
template <typename T>
@@ -76,7 +81,7 @@
void func6(boost::promise<void> p)
{
boost::this_thread::sleep_for(boost::chrono::milliseconds(500));
- p.set_exception(boost::make_exception_ptr('c'));
+ p.set_exception(boost::make_exception_ptr(4));
}
@@ -87,85 +92,130 @@
{
boost::promise<T> p;
boost::future<T> f = p.get_future();
- boost::thread(func1, boost::move(p)).detach();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ boost::thread(func1, boost::move(p)).detach();
+#else
+ p.set_value(3);
+#endif
BOOST_TEST(f.valid());
BOOST_TEST(f.get() == 3);
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
BOOST_TEST(!f.valid());
+#endif
}
{
boost::promise<T> p;
boost::future<T> f = p.get_future();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
boost::thread(func2, boost::move(p)).detach();
+#else
+ p.set_exception(boost::make_exception_ptr(3));
+#endif
try
{
BOOST_TEST(f.valid());
BOOST_TEST(f.get() == 3);
BOOST_TEST(false);
}
- catch (int i)
+ catch (boost::wrap<int> const& i)
{
- BOOST_TEST(i == 3);
+ BOOST_TEST(i.value == 3);
}
+ catch (...)
+ {
+ BOOST_TEST(false);
+ }
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
BOOST_TEST(!f.valid());
+#endif
+ }
+ }
+ {
+ typedef int& T;
+ {
+ boost::promise<T> p;
+ boost::future<T> f = p.get_future();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ boost::thread(func3, boost::move(p)).detach();
+#else
+ int j=5;
+ p.set_value(j);
+#endif
+ BOOST_TEST(f.valid());
+ BOOST_TEST(f.get() == 5);
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
+ BOOST_TEST(!f.valid());
+#endif
+ }
+ {
+ boost::promise<T> p;
+ boost::future<T> f = p.get_future();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ boost::thread(func4, boost::move(p)).detach();
+#else
+ p.set_exception(boost::make_exception_ptr(3.5));
+#endif
+ try
+ {
+ BOOST_TEST(f.valid());
+ BOOST_TEST(f.get() == 3);
+ BOOST_TEST(false);
+ }
+ catch (boost::wrap<double> const& i)
+ {
+ BOOST_TEST(i.value == 3.5);
+ }
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
+ BOOST_TEST(!f.valid());
+#endif
}
}
-// {
-// typedef int& T;
-// {
-// boost::promise<T> p;
-// boost::future<T> f = p.get_future();
-// boost::thread(func3, boost::move(p)).detach();
-// BOOST_TEST(f.valid());
-// BOOST_TEST(f.get() == 5);
-// BOOST_TEST(!f.valid());
-// }
-// {
-// boost::promise<T> p;
-// boost::future<T> f = p.get_future();
-// boost::thread(func4, boost::move(p)).detach();
-// try
-// {
-// BOOST_TEST(f.valid());
-// BOOST_TEST(f.get() == 3);
-// BOOST_TEST(false);
-// }
-// catch (double i)
-// {
-// BOOST_TEST(i == 3.5);
-// }
-// BOOST_TEST(!f.valid());
-// }
-// }
-// {
-// typedef void T;
-// {
-// boost::promise<T> p;
-// boost::future<T> f = p.get_future();
-// boost::thread(func5, boost::move(p)).detach();
-// BOOST_TEST(f.valid());
-// f.get();
-// BOOST_TEST(!f.valid());
-// }
-// {
-// boost::promise<T> p;
-// boost::future<T> f = p.get_future();
-// boost::thread(func6, boost::move(p)).detach();
-// try
-// {
-// BOOST_TEST(f.valid());
-// f.get();
-// BOOST_TEST(false);
-// }
-// catch (char i)
-// {
-// BOOST_TEST(i == 'c');
-// }
-// BOOST_TEST(!f.valid());
-// }
-// }
-
+ typedef void T;
+ {
+ boost::promise<T> p;
+ boost::future<T> f = p.get_future();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ boost::thread(func5, boost::move(p)).detach();
+#else
+ p.set_value();
+#endif
+ BOOST_TEST(f.valid());
+ f.get();
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
+ BOOST_TEST(!f.valid());
+#endif
+ }
+ {
+ boost::promise<T> p;
+ boost::future<T> f = p.get_future();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ boost::thread(func6, boost::move(p)).detach();
+#else
+ p.set_exception(boost::make_exception_ptr(4));
+#endif
+ try
+ {
+ BOOST_TEST(f.valid());
+ f.get();
+ BOOST_TEST(false);
+ }
+ catch (boost::wrap<int> const& i)
+ {
+ BOOST_TEST(i.value == 4);
+ }
+ catch (...)
+ {
+ BOOST_TEST(false);
+ }
+#ifdef BOOST_THREAD_PROVIDES_FUTURE_INVALID_AFTER_GET
+ BOOST_TEST(!f.valid());
+#endif
+ }
return boost::report_errors();
}
+#else
+#error "Test not applicable: BOOST_THREAD_USES_CHRONO not defined for this platform as not supported"
+#endif
Modified: branches/release/libs/thread/test/sync/futures/future/move_assign_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/future/move_assign_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/future/move_assign_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -14,9 +14,9 @@
// <future>
-// class promise<R>
+// class future<R>
-// promise& operator=(promise&& rhs);
+// future& operator=(future&& rhs);
#define BOOST_THREAD_VERSION 3
Modified: branches/release/libs/thread/test/sync/futures/future/move_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/future/move_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/future/move_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -14,9 +14,9 @@
// <future>
-// class promise<R>
+// class future<R>
-// promise(promise&& rhs);
+// future(future&& rhs);
#define BOOST_THREAD_VERSION 3
Copied: branches/release/libs/thread/test/sync/futures/future/then_pass.cpp (from r81143, /trunk/libs/thread/test/sync/futures/future/then_pass.cpp)
==============================================================================
--- /trunk/libs/thread/test/sync/futures/future/then_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/future/then_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -1,12 +1,3 @@
-//===----------------------------------------------------------------------===//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file is dual licensed under the MIT and the University of Illinois Open
-// Source Licenses. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
// Copyright (C) 2011 Vicente J. Botet Escriba
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
@@ -20,6 +11,7 @@
// auto then(F&& func) -> BOOST_THREAD_FUTURE<decltype(func(*this))>;
#define BOOST_THREAD_VERSION 4
+#define BOOST_THREAD_DONT_PROVIDE_FUTURE_INVALID_AFTER_GET
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -44,10 +36,18 @@
BOOST_TEST(f2.get()==2);
}
{
+ boost::future<int> f2 = boost::async(p1).then(p2);
+ BOOST_TEST(f2.get()==2);
+ }
+ {
boost::future<int> f1 = boost::async(p1);
boost::future<int> f2 = f1.then(p2).then(p2);
BOOST_TEST(f2.get()==4);
}
+ {
+ boost::future<int> f2 = boost::async(p1).then(p2).then(p2);
+ BOOST_TEST(f2.get()==4);
+ }
return boost::report_errors();
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/alloc_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/alloc_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/alloc_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -20,10 +20,18 @@
// explicit packaged_task(allocator_arg_t, const Allocator& a, F&& f);
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+#include <boost/thread/detail/config.hpp>
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
+
+
#if defined BOOST_THREAD_PROVIDES_FUTURE_CTOR_ALLOCATORS
#include "../test_allocator.hpp"
@@ -81,7 +89,7 @@
int main()
{
{
- boost::packaged_task<double> p(boost::allocator_arg,
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(boost::allocator_arg,
test_allocator<A>(), BOOST_THREAD_MAKE_RV_REF(A(5)));
BOOST_TEST(test_alloc_base::count > 0);
BOOST_TEST(p.valid());
@@ -96,10 +104,10 @@
BOOST_TEST(A::n_destroy > 0);
BOOST_TEST(test_alloc_base::count == 0);
A::n_copies = 0;
- A::n_copies = 0;
+ A::n_moves = 0;
{
A a(5);
- boost::packaged_task<double> p(boost::allocator_arg,
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(boost::allocator_arg,
test_allocator<A>(), a);
BOOST_TEST(test_alloc_base::count > 0);
BOOST_TEST(p.valid());
@@ -108,14 +116,14 @@
p();
BOOST_TEST(f.get() == 5.0);
}
- BOOST_TEST(A::n_copies > 0);
- BOOST_TEST(A::n_moves > 0);
+ //BOOST_TEST(A::n_copies > 0);
+ //BOOST_TEST(A::n_moves > 0);
BOOST_TEST(test_alloc_base::count == 0);
A::n_copies = 0;
- A::n_copies = 0;
+ A::n_moves = 0;
{
const A a(5);
- boost::packaged_task<double> p(boost::allocator_arg,
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(boost::allocator_arg,
test_allocator<A>(), a);
BOOST_TEST(test_alloc_base::count > 0);
BOOST_TEST(p.valid());
@@ -124,11 +132,11 @@
p();
BOOST_TEST(f.get() == 5.0);
}
- BOOST_TEST(A::n_copies > 0);
- BOOST_TEST(A::n_moves > 0);
+ //BOOST_TEST(A::n_copies > 0);
+ //BOOST_TEST(A::n_moves > 0);
BOOST_TEST(test_alloc_base::count == 0);
{
- boost::packaged_task<double> p(boost::allocator_arg,
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(boost::allocator_arg,
test_allocator<A>(), fct);
BOOST_TEST(test_alloc_base::count > 0);
BOOST_TEST(p.valid());
@@ -138,7 +146,7 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p(boost::allocator_arg,
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(boost::allocator_arg,
test_allocator<A>(), &lfct);
BOOST_TEST(test_alloc_base::count > 0);
BOOST_TEST(p.valid());
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/copy_assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/copy_assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/copy_assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,13 @@
// packaged_task& operator=(packaged_task&) = delete;
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -37,8 +43,8 @@
int main()
{
{
- boost::packaged_task<double> p0(A(5));
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p = p0;
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/copy_ctor_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/copy_ctor_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/copy_ctor_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,13 @@
// packaged_task(packaged_task&) = delete;
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -37,8 +43,8 @@
int main()
{
{
- boost::packaged_task<double> p0(A(5));
- boost::packaged_task<double> p(p0);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(p0);
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/default_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/default_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/default_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,13 @@
// packaged_task();
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE int()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE int
+#endif
+
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -26,7 +32,7 @@
int main()
{
{
- boost::packaged_task<int> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
BOOST_TEST(!p.valid());
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/dtor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/dtor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/dtor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,14 +17,34 @@
// class packaged_task<R>
// ~packaged_task();
-;
-#define BOOST_THREAD_VERSION 3
+//#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+
#include <boost/thread/future.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double(int, char)
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5 + 3 +'a'
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double()
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5
+#endif
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5
+#endif
+
class A
{
long data_;
@@ -36,25 +56,33 @@
long operator()(long i, long j) const {return data_ + i + j;}
};
-void func(boost::packaged_task<double> p)
+void func(boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> )
{
}
-void func2(boost::packaged_task<double> p)
+void func2(boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p)
{
- //p(3, 'a');
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+#else
p();
+#endif
}
int main()
{
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(A(5));
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)
boost::thread(func, boost::move(p)).detach();
+#else
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE>* p2=new boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE>(boost::move(p));
+ delete p2;
+#endif
try
{
- double i = f.get();
+ f.get();
BOOST_TEST(false);
}
catch (const boost::future_error& e)
@@ -63,13 +91,18 @@
}
}
{
- boost::packaged_task<double> p(A(5));
+ std::cout << __LINE__ << std::endl;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p(A(5));
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)
boost::thread(func2, boost::move(p)).detach();
- BOOST_TEST(f.get() == 5.0);
+#else
+ p();
+#endif
+ std::cout << __LINE__ << std::endl;
+ BOOST_TEST(f.get() == BOOST_THREAD_DETAIL_SIGNATURE_2_RES);
+ std::cout << __LINE__ << std::endl;
}
-
-
return boost::report_errors();
}
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 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,10 +19,30 @@
// explicit packaged_task(F&& f);
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double(int, char)
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5 + 3 +'a'
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double()
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5
+#endif
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5
+#endif
+
double fct()
{
return 5.0;
@@ -69,44 +89,47 @@
int main()
{
{
- boost::packaged_task<double> p(BOOST_THREAD_MAKE_RV_REF(A(5)));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p(BOOST_THREAD_MAKE_RV_REF(A(5)));
BOOST_TEST(p.valid());
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
- //p(3, 'a');
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+#else
p();
- BOOST_TEST(f.get() == 5.0);
+#endif
+ BOOST_TEST(f.get() == BOOST_THREAD_DETAIL_SIGNATURE_2_RES);
BOOST_TEST(A::n_copies == 0);
BOOST_TEST(A::n_moves > 0);
}
A::n_copies = 0;
- A::n_copies = 0;
+ A::n_moves = 0;
{
A a(5);
- boost::packaged_task<double> p(a);
+ 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(A::n_copies > 0);
- BOOST_TEST(A::n_moves > 0);
+ //BOOST_TEST(A::n_copies > 0);
+ //BOOST_TEST(A::n_moves > 0);
}
A::n_copies = 0;
- A::n_copies = 0;
+ A::n_moves = 0;
{
const A a(5);
- boost::packaged_task<double> p(a);
+ 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(A::n_copies > 0);
- BOOST_TEST(A::n_moves > 0);
+ //BOOST_TEST(A::n_copies > 0);
+ //BOOST_TEST(A::n_moves > 0);
}
{
- boost::packaged_task<double> p(fct);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(fct);
BOOST_TEST(p.valid());
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
//p(3, 'a');
@@ -114,7 +137,7 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p(&lfct);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(&lfct);
BOOST_TEST(p.valid());
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
//p(3, 'a');
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/get_future_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/get_future_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/get_future_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,12 @@
// future<R> get_future();
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -38,14 +43,14 @@
int main()
{
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(A(5));
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
//p(3, 'a');
p();
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(A(5));
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
try
{
@@ -58,7 +63,7 @@
}
}
{
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
try
{
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,12 @@
// void swap(packaged_task& other);
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -46,8 +51,8 @@
int main()
{
{
- boost::packaged_task<double> p0(A(5));
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p.swap(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(p.valid());
@@ -57,8 +62,8 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p0;
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p.swap(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(!p.valid());
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/move_assign_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/move_assign_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/move_assign_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,12 @@
// promise& operator=(promise&& rhs);
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -39,8 +44,8 @@
{
{
- boost::packaged_task<double> p0(A(5));
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p = boost::move(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(p.valid());
@@ -50,8 +55,8 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p0;
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p = boost::move(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(!p.valid());
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/move_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/move_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/move_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,12 @@
// packaged_task(packaged_task&& other);
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -38,8 +43,8 @@
int main()
{
{
- boost::packaged_task<double> p0(A(5));
- boost::packaged_task<double> p = boost::move(p0);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p = boost::move(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(p.valid());
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
@@ -48,8 +53,8 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p0;
- boost::packaged_task<double> p = boost::move(p0);
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p = boost::move(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(!p.valid());
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/non_member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/non_member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/non_member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,12 @@
// void
// swap(packaged_task<R>& x, packaged_task<R>& y);
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -37,8 +42,8 @@
int main()
{
{
- boost::packaged_task<double> p0(A(5));
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p.swap(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(p.valid());
@@ -48,8 +53,8 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p0;
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p0;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
p.swap(p0);
BOOST_TEST(!p0.valid());
BOOST_TEST(!p.valid());
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/operator_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/operator_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/operator_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,10 +18,46 @@
// void operator()();
-#define BOOST_THREAD_VERSION 3
+//#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
+#if defined BOOST_THREAD_USES_CHRONO
+
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double(int, char)
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5 + 3 +'a'
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double()
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5
+#endif
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE_2 double
+#define BOOST_THREAD_DETAIL_SIGNATURE_2_RES 5
+#endif
+class E : public std::exception
+{
+public:
+ long data;
+ explicit E(long i) :
+ data(i)
+ {
+ }
+
+ const char* what() const throw() { return ""; }
+
+ ~E() throw() {}
+};
+
class A
{
long data_;
@@ -34,93 +70,149 @@
long operator()() const
{
+ if (data_ == 0) BOOST_THROW_EXCEPTION(E(6));
return data_;
}
long operator()(long i, long j) const
{
- if (j == 'z') throw A(6);
+ if (j == 'z') BOOST_THROW_EXCEPTION(E(6));
return data_ + i + j;
}
+ ~A() {}
};
-void func0(boost::packaged_task<double> p)
+void func0(boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p)
{
boost::this_thread::sleep_for(boost::chrono::milliseconds(500));
- //p(3, 'a');
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+#else
p();
+#endif
}
-void func1(boost::packaged_task<double(int, char)> p)
+void func1(boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p)
{
boost::this_thread::sleep_for(boost::chrono::milliseconds(500));
- //p(3, 'z');
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'z');
+#else
p();
+#endif
}
-void func2(boost::packaged_task<double(int, char)> p)
+void func2(boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p)
{
- //p(3, 'a');
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+#else
p();
+#endif
try
{
- //p(3, 'c');
- p();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'c');
+#else
+ p();
+#endif
}
catch (const boost::future_error& e)
{
- BOOST_TEST(e.code() == make_error_code(boost::future_errc::promise_already_satisfied));
+ BOOST_TEST(e.code() == boost::system::make_error_code(boost::future_errc::promise_already_satisfied));
}
}
-void func3(boost::packaged_task<double(int, char)> p)
+void func3(boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p)
{
try
{
- //p(3, 'a');
- p();
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+#else
+ p();
+#endif
}
catch (const boost::future_error& e)
{
- BOOST_TEST(e.code() == make_error_code(boost::future_errc::no_state));
+ BOOST_TEST(e.code() == boost::system::make_error_code(boost::future_errc::no_state));
}
}
int main()
{
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p(A(5));
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)
boost::thread(func0, boost::move(p)).detach();
- BOOST_TEST(f.get() == 5.0);
+#else
+ //p();
+#endif
+ //BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p(A(0));
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)
boost::thread(func1, boost::move(p)).detach();
+#endif
try
{
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+#else
+ p();
+#endif
f.get();
BOOST_TEST(false);
}
- catch (const A& e)
+ catch (const E& e)
+ {
+ BOOST_TEST(e.data == 6);
+ }
+ catch (...)
{
- //BOOST_TEST(e(3, 'a') == 106);
- BOOST_TEST(e() == 5);
+ BOOST_TEST(false);
}
}
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p(A(5));
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)
boost::thread t(func2, boost::move(p));
- BOOST_TEST(f.get() == 5.0);
+#else
+ p();
+#endif
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ BOOST_TEST(f.get() == 105);
t.join();
+#else
+ BOOST_TEST(f.get() == 5.0);
+#endif
}
{
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE_2> p;
+#if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
boost::thread t(func3, boost::move(p));
t.join();
+#else
+ try
+ {
+ #if defined BOOST_THREAD_PROVIDES_SIGNATURE_PACKAGED_TASK && defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
+ p(3, 'a');
+ #else
+ p();
+ #endif
+ }
+ catch (const boost::future_error& e)
+ {
+ BOOST_TEST(e.code() == boost::system::make_error_code(boost::future_errc::no_state));
+ }
+#endif
}
return boost::report_errors();
}
+#else
+#error "Test not applicable: BOOST_THREAD_USES_CHRONO not defined for this platform as not supported"
+#endif
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/reset_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/reset_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/reset_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,13 @@
// void operator()();
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
+
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -46,7 +52,7 @@
int main()
{
{
- boost::packaged_task<double> p(A(5));
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p(A(5));
boost::future<double> f = BOOST_THREAD_MAKE_RV_REF(p.get_future());
//p(3, 'a');
p();
@@ -58,7 +64,7 @@
BOOST_TEST(f.get() == 5.0);
}
{
- boost::packaged_task<double> p;
+ boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE> p;
try
{
p.reset();
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -29,7 +29,7 @@
int main()
{
- BOOST_STATIC_ASSERT_MSG((boost::is_same<boost::packaged_task<A>::result_type, A>::value), "");
+ //BOOST_STATIC_ASSERT_MSG((boost::is_same<boost::packaged_task<A>::result_type, A>::value), "");
return boost::report_errors();
}
Modified: branches/release/libs/thread/test/sync/futures/packaged_task/use_allocator_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/futures/packaged_task/use_allocator_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/packaged_task/use_allocator_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -21,7 +21,12 @@
// : true_type { };
-#define BOOST_THREAD_VERSION 3
+#define BOOST_THREAD_VERSION 4
+#if BOOST_THREAD_VERSION == 4
+#define BOOST_THREAD_DETAIL_SIGNATURE double()
+#else
+#define BOOST_THREAD_DETAIL_SIGNATURE double
+#endif
#include <boost/thread/future.hpp>
#include <boost/detail/lightweight_test.hpp>
@@ -33,7 +38,7 @@
int main()
{
- BOOST_STATIC_ASSERT_MSG((boost::uses_allocator<boost::packaged_task<double>, test_allocator<double> >::value), "");
+ BOOST_STATIC_ASSERT_MSG((boost::uses_allocator<boost::packaged_task<BOOST_THREAD_DETAIL_SIGNATURE>, test_allocator<double> >::value), "");
return boost::report_errors();
}
Copied: branches/release/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp (from r80756, /trunk/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp)
==============================================================================
--- /trunk/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/futures/promise/set_rvalue_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -36,7 +36,7 @@
value(i)
{
}
- A(const A&)= delete;
+ BOOST_THREAD_DELETE_COPY_CTOR(A)
A(A&& rhs)
{
if(rhs.value==0)
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/adopt_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/adopt_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/adopt_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// lock_guard(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_guard.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// lock_guard& operator=(lock_guard const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_guard.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_ctor_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_ctor_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/copy_ctor_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// lock_guard(lock_guard const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_guard.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/default_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/default_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/default_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -16,9 +16,9 @@
// template <class Mutex> class lock_guard;
-// lock_guard(lock_guard const&) = delete;
+// lock_guard(Mutex &);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_guard.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/lock_guard/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -25,8 +25,10 @@
// };
+#include <boost/thread/lock_guard.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/static_assert.hpp>
+#include <boost/type_traits/is_same.hpp>
#include <boost/detail/lightweight_test.hpp>
int main()
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -9,10 +9,10 @@
// reverse_lock& operator=(reverse_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/reverse_lock.hpp>
#include <boost/thread/mutex.hpp>
-#include <boost/detail/lightweight_test.hpp>
+#include <boost/thread/lock_types.hpp>
int main()
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_ctor_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_ctor_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/copy_ctor_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -10,10 +10,10 @@
// reverse_lock(reverse_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/reverse_lock.hpp>
#include <boost/thread/mutex.hpp>
-#include <boost/detail/lightweight_test.hpp>
+#include <boost/thread/lock_types.hpp>
boost::mutex m0;
boost::mutex m1;
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,9 +18,10 @@
#include <boost/thread/mutex.hpp>
#include <boost/thread/reverse_lock.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/static_assert.hpp>
+#include <boost/type_traits/is_same.hpp>
#include <boost/detail/lightweight_test.hpp>
int main()
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/unique_lock_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/unique_lock_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/reverse_lock/unique_lock_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -10,7 +10,7 @@
// unlock_guard(unlock_guard const&) = delete;
#include <boost/thread/reverse_lock.hpp>
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/adopt_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/adopt_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/adopt_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// shared_lock& operator=(shared_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_ctor_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_ctor_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/copy_ctor_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock(shared_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/default_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/default_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/default_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// shared_lock(shared_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/defer_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/defer_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/defer_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// shared_lock(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/duration_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/duration_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/duration_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// shared_lock(mutex_type& m, const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_assign_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_assign_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_assign_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock(shared_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock& operator=(shared_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_unique_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_unique_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_unique_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock& operator=(shared_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_upgrade_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_upgrade_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/move_ctor_upgrade_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock& operator=(shared_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/mutex_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/mutex_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/mutex_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// explicit shared_lock(Mutex& m);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/time_point_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/time_point_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/time_point_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Clock, class Duration>
// shared_lock(mutex_type& m, const chrono::time_point<Clock, Duration>& abs_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/try_to_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/try_to_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/cons/try_to_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// shared_lock(mutex_type& m, try_to_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void lock();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_for_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_for_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_for_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_until_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_until_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/try_lock_until_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Clock, class Duration>
// bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/unlock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/unlock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/locking/unlock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void swap(shared_lock& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct shared_mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/non_member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/non_member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/non_member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,7 +17,7 @@
// template <class Mutex>
// void swap(shared_lock<Mutex>& x, shared_lock<Mutex>& y);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct shared_mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/release_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/release_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/mod/release_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void Mutex* release();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct shared_mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/mutex_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/mutex_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/mutex_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// Mutex *mutex() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/op_bool_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/op_bool_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/op_bool_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// explicit operator bool() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/owns_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/owns_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/obs/owns_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// bool owns_lock() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -25,7 +25,7 @@
// };
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/static_assert.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock_guard/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock_guard/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/shared_lock_guard/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -28,6 +28,7 @@
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/shared_lock_guard.hpp>
#include <boost/static_assert.hpp>
+#include <boost/type_traits/is_same.hpp>
#include <boost/detail/lightweight_test.hpp>
int main()
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/adopt_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/adopt_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/adopt_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// unique_lock(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// unique_lock& operator=(unique_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_ctor_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_ctor_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/copy_ctor_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// unique_lock(unique_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/default_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/default_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/default_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// unique_lock(unique_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/defer_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/defer_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/defer_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// unique_lock(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/duration_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/duration_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/duration_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -21,7 +21,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_assign_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_assign_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_assign_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// unique_lock(unique_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// unique_lock(unique_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_for_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_for_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_for_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -24,7 +24,7 @@
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_try_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_try_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_try_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -22,7 +22,7 @@
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_until_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_until_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_shared_lock_until_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -24,7 +24,7 @@
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_for_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_for_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_for_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -22,7 +22,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// unique_lock(upgrade_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_try_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_try_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_try_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -20,7 +20,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_until_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_until_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/move_ctor_upgrade_lock_until_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -22,7 +22,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/mutex_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/mutex_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/mutex_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// explicit unique_lock(Mutex& m);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/time_point_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/time_point_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/time_point_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -21,7 +21,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/try_to_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/try_to_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/cons/try_to_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// unique_lock(mutex_type& m, try_to_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void lock();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_for_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_for_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_for_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_until_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_until_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/try_lock_until_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Clock, class Duration>
// bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/unlock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/unlock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/locking/unlock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// bool unlock();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void swap(unique_lock& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/non_member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/non_member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/non_member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,7 +17,7 @@
// template <class Mutex>
// void swap(unique_lock<Mutex>& x, unique_lock<Mutex>& y);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/release_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/release_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/mod/release_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void Mutex* release();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/mutex_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/mutex_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/mutex_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// Mutex *mutex() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_bool_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_bool_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_bool_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// explicit operator bool() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_int_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_int_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/op_int_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// explicit operator bool() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/owns_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/owns_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/obs/owns_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// bool owns_lock() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/unique_lock/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -25,6 +25,7 @@
// };
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/static_assert.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/adopt_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/adopt_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/adopt_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// upgrade_lock(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// upgrade_lock& operator=(upgrade_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_ctor_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_ctor_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/copy_ctor_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// upgrade_lock(upgrade_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/default_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/default_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/default_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// upgrade_lock(upgrade_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/defer_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/defer_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/defer_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// upgrade_lock(mutex_type& m, adopt_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/duration_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/duration_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/duration_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -21,7 +21,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_assign_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_assign_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_assign_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// upgrade_lock(upgrade_lock const&) = delete;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// upgrade_lock& operator=(upgrade_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_for_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_for_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_for_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -24,7 +24,7 @@
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_try_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_try_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_try_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -22,7 +22,7 @@
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_until_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_until_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_shared_lock_until_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -24,7 +24,7 @@
#define BOOST_THREAD_PROVIDES_EXPLICIT_LOCK_CONVERSION
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_unique_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_unique_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/move_ctor_unique_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// upgrade_lock& operator=(unique_lock&& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/mutex_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/mutex_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/mutex_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// explicit upgrade_lock(Mutex& m);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/time_point_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/time_point_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/time_point_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -21,7 +21,7 @@
#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/try_to_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/try_to_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/cons/try_to_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// upgrade_lock(mutex_type& m, try_to_lock_t);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void lock();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_for_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_for_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_for_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_until_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_until_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/try_lock_until_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Clock, class Duration>
// bool try_lock_until(const chrono::time_point<Clock, Duration>& abs_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/unlock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/unlock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/locking/unlock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
// template <class Rep, class Period>
// bool try_lock_for(const chrono::duration<Rep, Period>& rel_time);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
//#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void swap(upgrade_lock& u);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct shared_mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/non_member_swap_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/non_member_swap_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/non_member_swap_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,7 +17,7 @@
// template <class Mutex>
// void swap(upgrade_lock<Mutex>& x, upgrade_lock<Mutex>& y);
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct shared_mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/release_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/release_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/mod/release_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// void Mutex* release();
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/detail/lightweight_test.hpp>
struct shared_mutex
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/mutex_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/mutex_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/mutex_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// Mutex *mutex() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/op_bool_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/op_bool_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/op_bool_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// explicit operator bool() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/owns_lock_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/owns_lock_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/obs/owns_lock_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -18,7 +18,7 @@
// bool owns_lock() const;
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/types_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/types_pass.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/locks/upgrade_lock/types_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -25,7 +25,7 @@
// };
-#include <boost/thread/locks.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/static_assert.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/assign_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/assign_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/assign_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -27,5 +27,5 @@
boost::timed_mutex m1(m0);
}
-#include "impl/thread/test/remove_error_code_unused_warning.hpp"
+#include "../../../remove_error_code_unused_warning.hpp"
Modified: branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/copy_fail.cpp
==============================================================================
--- branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/copy_fail.cpp (original)
+++ branches/release/libs/thread/test/sync/mutual_exclusion/timed_mutex/copy_fail.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -27,4 +27,4 @@
boost::timed_mutex m1(m0);
}
-#include "impl/thread/test/remove_error_code_unused_warning.hpp"
+#include "../../../remove_error_code_unused_warning.hpp"
Modified: branches/release/libs/thread/test/test_2309.cpp
==============================================================================
--- branches/release/libs/thread/test/test_2309.cpp (original)
+++ branches/release/libs/thread/test/test_2309.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,9 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/test/unit_test.hpp>
#include <iostream>
@@ -21,18 +24,18 @@
}
catch (boost::thread_interrupted& interrupt)
{
- boost::mutex::scoped_lock lock(mutex_);
+ boost::unique_lock<boost::mutex> lock(mutex_);
cerr << "Thread " << boost::this_thread::get_id() << " got interrupted" << endl;
throw(interrupt);
}
catch (std::exception& e)
{
- boost::mutex::scoped_lock lock(mutex_);
+ boost::unique_lock<boost::mutex> lock(mutex_);
cerr << "Thread " << boost::this_thread::get_id() << " caught std::exception" << e.what() << endl;
}
catch (...)
{
- boost::mutex::scoped_lock lock(mutex_);
+ boost::unique_lock<boost::mutex> lock(mutex_);
cerr << "Thread " << boost::this_thread::get_id() << " caught something else" << endl;
}
}
Modified: branches/release/libs/thread/test/test_2741.cpp
==============================================================================
--- branches/release/libs/thread/test/test_2741.cpp (original)
+++ branches/release/libs/thread/test/test_2741.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/thread.hpp>
Modified: branches/release/libs/thread/test/test_3628.cpp
==============================================================================
--- branches/release/libs/thread/test/test_3628.cpp (original)
+++ branches/release/libs/thread/test/test_3628.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,12 +3,16 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/thread.hpp>
#include <boost/thread/condition.hpp>
#include <boost/thread/recursive_mutex.hpp>
#include <list>
#include <iostream>
+#if defined BOOST_THREAD_USES_CHRONO
+
using namespace std;
boost::recursive_mutex theMutex;
@@ -23,7 +27,7 @@
for (int j = 0; j < 10; j++)
{
{
- boost::recursive_mutex::scoped_lock lockMtx(theMutex);
+ boost::unique_lock<boost::recursive_mutex> lockMtx(theMutex);
theConditions.push_back(&con1);
cout << "Added " << boost::this_thread::get_id() << " " << &con1 << endl;
@@ -52,7 +56,7 @@
for (int j = 0; j < 70; j++)
{
{
- boost::recursive_mutex::scoped_lock lockMtx(theMutex);
+ boost::unique_lock<boost::recursive_mutex> lockMtx(theMutex);
cout << "<Notifier " << j << endl;
unsigned int i = 0;
@@ -87,3 +91,7 @@
return 0;
}
+
+#else
+#error "Test not applicable: BOOST_THREAD_USES_CHRONO not defined for this platform as not supported"
+#endif
Modified: branches/release/libs/thread/test/test_4521.cpp
==============================================================================
--- branches/release/libs/thread/test/test_4521.cpp (original)
+++ branches/release/libs/thread/test/test_4521.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread.hpp>
int calculate_the_answer_to_life_the_universe_and_everything()
Modified: branches/release/libs/thread/test/test_4882.cpp
==============================================================================
--- branches/release/libs/thread/test/test_4882.cpp (original)
+++ branches/release/libs/thread/test/test_4882.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,47 +3,63 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_GENERIC_SHARED_MUTEX_ON_WIN
+//#define BOOST_THREAD_USES_LOG
+
#include <boost/thread/thread.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/detail/no_exceptions_support.hpp>
-
-#include <iostream>
+//#include <boost/thread/detail/log.hpp>
boost::shared_mutex mutex;
void thread()
{
- std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ //BOOST_THREAD_LOG << "<thrd" << BOOST_THREAD_END_LOG;
BOOST_TRY
{
for (int i =0; i<10; ++i)
{
+#ifndef BOOST_THREAD_USES_CHRONO
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_THREAD_LOG << "<thrd" << " i="<<i << BOOST_THREAD_END_LOG;
boost::this_thread::sleep(boost::posix_time::milliseconds(10));
mutex.unlock();
- std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ //BOOST_THREAD_LOG << "<thrd" << " i="<<i << BOOST_THREAD_END_LOG;
+ }
+#else
+ boost::chrono::system_clock::time_point timeout = boost::chrono::system_clock::now() + boost::chrono::milliseconds(50);
+
+ //BOOST_THREAD_LOG << "<thrd" << " i="<<i << BOOST_THREAD_END_LOG;
+ if (mutex.try_lock_until(timeout))
+ {
+ //BOOST_THREAD_LOG << "<thrd" << " i="<<i << BOOST_THREAD_END_LOG;
+ boost::this_thread::sleep_for(boost::chrono::milliseconds(10));
+ mutex.unlock();
+ //BOOST_THREAD_LOG << "<thrd" << " i="<<i << BOOST_THREAD_END_LOG;
}
+#endif
}
}
BOOST_CATCH (boost::lock_error& le)
{
- std::cerr << "lock_error exception\n";
+ //BOOST_THREAD_LOG << "lock_error exception thrd>" << BOOST_THREAD_END_LOG;
}
BOOST_CATCH (...)
{
- std::cerr << " exception\n";
+ //BOOST_THREAD_LOG << "exception thrd>" << BOOST_THREAD_END_LOG;
}
BOOST_CATCH_END
- std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ //BOOST_THREAD_LOG << "thrd>" << BOOST_THREAD_END_LOG;
}
int main()
{
- std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ //BOOST_THREAD_LOG << "<main" << BOOST_THREAD_END_LOG;
const int nrThreads = 20;
boost::thread* threads[nrThreads];
@@ -53,9 +69,10 @@
for (int i = 0; i < nrThreads; ++i)
{
threads[i]->join();
- std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ //BOOST_THREAD_LOG << "main" << BOOST_THREAD_END_LOG;
delete threads[i];
+ //BOOST_THREAD_LOG << "main" << BOOST_THREAD_END_LOG;
}
- std::cout << __FILE__ << ":" << __LINE__ << std::endl;
+ //BOOST_THREAD_LOG << "main>" << BOOST_THREAD_END_LOG;
return 0;
}
Modified: branches/release/libs/thread/test/test_5351.cpp
==============================================================================
--- branches/release/libs/thread/test/test_5351.cpp (original)
+++ branches/release/libs/thread/test/test_5351.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <iostream>
#include <boost/thread.hpp>
#include <boost/date_time/posix_time/posix_time_types.hpp>
Modified: branches/release/libs/thread/test/test_5542_1.cpp
==============================================================================
--- branches/release/libs/thread/test/test_5542_1.cpp (original)
+++ branches/release/libs/thread/test/test_5542_1.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <iostream>
#include <boost/thread.hpp>
Modified: branches/release/libs/thread/test/test_5542_2.cpp
==============================================================================
--- branches/release/libs/thread/test/test_5542_2.cpp (original)
+++ branches/release/libs/thread/test/test_5542_2.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread.hpp>
void run_thread() {
Modified: branches/release/libs/thread/test/test_5542_3.cpp
==============================================================================
--- branches/release/libs/thread/test/test_5542_3.cpp (original)
+++ branches/release/libs/thread/test/test_5542_3.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <iostream>
#include <boost/thread.hpp>
#include <boost/date_time.hpp>
Modified: branches/release/libs/thread/test/test_5891.cpp
==============================================================================
--- branches/release/libs/thread/test/test_5891.cpp (original)
+++ branches/release/libs/thread/test/test_5891.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <iostream>
#include <boost/thread.hpp>
Modified: branches/release/libs/thread/test/test_6130.cpp
==============================================================================
--- branches/release/libs/thread/test/test_6130.cpp (original)
+++ branches/release/libs/thread/test/test_6130.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread.hpp>
#include <boost/date_time/posix_time/posix_time_io.hpp>
#include <assert.h>
@@ -28,7 +30,7 @@
time_t end_time;
assert(now_time < wait_time);
- boost::mutex::scoped_lock lk(mtx);
+ boost::unique_lock<boost::mutex> lk(mtx);
//const bool res =
(void)cv.timed_wait(lk, from_time_t(wait_time));
end_time = ::time(0);
Modified: branches/release/libs/thread/test/test_6174.cpp
==============================================================================
--- branches/release/libs/thread/test/test_6174.cpp (original)
+++ branches/release/libs/thread/test/test_6174.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,13 +4,14 @@
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 3
#include <boost/thread.hpp>
#include <boost/config.hpp>
-#ifndef BOOST_NO_RVALUE_REFERENCES
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
struct MovableButNonCopyable {
-#if ! defined BOOST_NO_DELETED_FUNCTIONS
+#if ! defined BOOST_NO_CXX11_DELETED_FUNCTIONS
MovableButNonCopyable(MovableButNonCopyable const&) = delete;
MovableButNonCopyable& operator=(MovableButNonCopyable const&) = delete;
#else
Modified: branches/release/libs/thread/test/test_7328.cpp
==============================================================================
--- branches/release/libs/thread/test/test_7328.cpp (original)
+++ branches/release/libs/thread/test/test_7328.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,10 +3,14 @@
// 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)
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <iostream>
#include <boost/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
+#if defined BOOST_THREAD_USES_CHRONO
+
//using namespace boost;
using namespace boost::chrono;
@@ -37,3 +41,7 @@
BOOST_TEST(interrupted);
return boost::report_errors();
}
+
+#else
+#error "Test not applicable: BOOST_THREAD_USES_CHRONO not defined for this platform as not supported"
+#endif
Copied: branches/release/libs/thread/test/test_7571.cpp (from r81143, /trunk/libs/thread/test/test_7571.cpp)
==============================================================================
--- /trunk/libs/thread/test/test_7571.cpp (original)
+++ branches/release/libs/thread/test/test_7571.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -19,7 +19,7 @@
ItemKeeper() { }
void doSomething() {
- boost::mutex::scoped_lock scoped_lock(mutex);
+ boost::unique_lock<boost::mutex> scoped_lock(mutex);
int counts = MAX_COUNTS;
while (counts--);
}
Copied: branches/release/libs/thread/test/test_7665.cpp (from r81443, /trunk/libs/thread/test/test_7665.cpp)
==============================================================================
--- /trunk/libs/thread/test/test_7665.cpp (original)
+++ branches/release/libs/thread/test/test_7665.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,27 +4,36 @@
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_USES_LOG
#include <iostream>
#include <boost/thread.hpp>
+#include <boost/thread/detail/log.hpp>
void thread()
{
- std::cout << "Sleeping for 10 seconds - change time\n";
+ BOOST_THREAD_LOG << "<thrd" << BOOST_THREAD_END_LOG;
+ try {
boost::this_thread::sleep_for(boost::chrono::seconds(30));
- std::cout << "Ended\n";
+ } catch (...)
+ {
+ BOOST_THREAD_LOG << "thrd exception" << BOOST_THREAD_END_LOG;
+ throw;
+ }
//while (1) ; // Never quit
+ BOOST_THREAD_LOG << "thrd>" << BOOST_THREAD_END_LOG;
}
boost::thread example(thread);
int main()
{
- std::cout << "Main thread START\n";
+ BOOST_THREAD_LOG << "<main" << BOOST_THREAD_END_LOG;
boost::this_thread::sleep_for(boost::chrono::seconds(30));
- std::cout << "Main thread END\n";
+ BOOST_THREAD_LOG << "main" << BOOST_THREAD_END_LOG;
//while (1) ; // Never quit
example.join();
+ BOOST_THREAD_LOG << "main>" << BOOST_THREAD_END_LOG;
return 0;
}
Modified: branches/release/libs/thread/test/test_barrier.cpp
==============================================================================
--- branches/release/libs/thread/test/test_barrier.cpp (original)
+++ branches/release/libs/thread/test/test_barrier.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,6 +4,8 @@
// 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)
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/thread.hpp>
@@ -26,7 +28,7 @@
{
if (gen_barrier.wait())
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
global_parameter++;
}
}
Modified: branches/release/libs/thread/test/test_condition.cpp
==============================================================================
--- branches/release/libs/thread/test/test_condition.cpp (original)
+++ branches/release/libs/thread/test/test_condition.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,6 +5,9 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/condition.hpp>
@@ -27,7 +30,7 @@
void condition_test_thread(condition_test_data* data)
{
- boost::mutex::scoped_lock lock(data->mutex);
+ boost::unique_lock<boost::mutex> lock(data->mutex);
BOOST_CHECK(lock ? true : false);
while (!(data->notified > 0))
data->condition.wait(lock);
@@ -50,7 +53,7 @@
void condition_test_waits(condition_test_data* data)
{
- boost::mutex::scoped_lock lock(data->mutex);
+ boost::unique_lock<boost::mutex> lock(data->mutex);
BOOST_CHECK(lock ? true : false);
// Test wait.
@@ -104,7 +107,7 @@
boost::thread thread(bind(&condition_test_waits, &data));
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
BOOST_CHECK(lock ? true : false);
boost::thread::sleep(delay(1));
Modified: branches/release/libs/thread/test/test_condition_notify_all.cpp
==============================================================================
--- branches/release/libs/thread/test/test_condition_notify_all.cpp (original)
+++ branches/release/libs/thread/test/test_condition_notify_all.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/thread.hpp>
@@ -28,7 +30,7 @@
}
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_all();
}
@@ -57,7 +59,7 @@
}
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_all();
}
@@ -86,7 +88,7 @@
}
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_all();
}
@@ -115,7 +117,7 @@
}
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_all();
}
@@ -144,7 +146,7 @@
}
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_all();
}
@@ -167,7 +169,7 @@
void wait_for_condvar_and_increase_count()
{
- boost::mutex::scoped_lock lk(multiple_wake_mutex);
+ boost::unique_lock<boost::mutex> lk(multiple_wake_mutex);
multiple_wake_cond.wait(lk);
++multiple_wake_count;
}
@@ -191,7 +193,7 @@
boost::this_thread::sleep(boost::posix_time::milliseconds(200));
{
- boost::mutex::scoped_lock lk(multiple_wake_mutex);
+ boost::unique_lock<boost::mutex> lk(multiple_wake_mutex);
BOOST_CHECK(multiple_wake_count==3);
}
Modified: branches/release/libs/thread/test/test_condition_notify_one.cpp
==============================================================================
--- branches/release/libs/thread/test/test_condition_notify_one.cpp (original)
+++ branches/release/libs/thread/test/test_condition_notify_one.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/thread.hpp>
@@ -19,7 +21,7 @@
boost::thread thread(bind(&wait_for_flag::wait_without_predicate, data));
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_one();
}
@@ -35,7 +37,7 @@
boost::thread thread(bind(&wait_for_flag::wait_with_predicate, data));
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_one();
}
@@ -51,7 +53,7 @@
boost::thread thread(bind(&wait_for_flag::timed_wait_without_predicate, data));
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_one();
}
@@ -67,7 +69,7 @@
boost::thread thread(bind(&wait_for_flag::timed_wait_with_predicate, data));
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_one();
}
@@ -83,7 +85,7 @@
boost::thread thread(bind(&wait_for_flag::relative_timed_wait_with_predicate, data));
{
- boost::mutex::scoped_lock lock(data.mutex);
+ boost::unique_lock<boost::mutex> lock(data.mutex);
data.flag=true;
data.cond_var.notify_one();
}
@@ -100,7 +102,7 @@
void wait_for_condvar_and_increase_count()
{
- boost::mutex::scoped_lock lk(multiple_wake_mutex);
+ boost::unique_lock<boost::mutex> lk(multiple_wake_mutex);
multiple_wake_cond.wait(lk);
++multiple_wake_count;
}
@@ -124,7 +126,7 @@
boost::this_thread::sleep(boost::posix_time::milliseconds(200));
{
- boost::mutex::scoped_lock lk(multiple_wake_mutex);
+ boost::unique_lock<boost::mutex> lk(multiple_wake_mutex);
BOOST_CHECK(multiple_wake_count==3);
}
Modified: branches/release/libs/thread/test/test_condition_timed_wait_times_out.cpp
==============================================================================
--- branches/release/libs/thread/test/test_condition_timed_wait_times_out.cpp (original)
+++ branches/release/libs/thread/test/test_condition_timed_wait_times_out.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/condition.hpp>
@@ -27,7 +29,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
boost::system_time const timeout=start+delay;
@@ -43,7 +45,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
boost::system_time const timeout=start+delay;
@@ -60,7 +62,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
bool const res=cond.timed_wait(lock,delay,fake_predicate);
@@ -76,7 +78,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
while(cond.timed_wait(lock,delay)) {}
@@ -91,7 +93,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
boost::system_time const timeout=start+delay;
@@ -107,7 +109,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
boost::system_time const timeout=start+delay;
@@ -124,7 +126,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
bool const res=cond.timed_wait(lock,delay,fake_predicate);
@@ -140,7 +142,7 @@
boost::mutex m;
boost::posix_time::seconds const delay(timeout_seconds);
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
boost::system_time const start=boost::get_system_time();
while(cond.timed_wait(lock,delay)) {}
Modified: branches/release/libs/thread/test/test_futures.cpp
==============================================================================
--- branches/release/libs/thread/test/test_futures.cpp (original)
+++ branches/release/libs/thread/test/test_futures.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,6 +4,8 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/thread.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/condition.hpp>
@@ -18,7 +20,7 @@
#define LOG \
if (false) {} else std::cout << std::endl << __FILE__ << "[" << __LINE__ << "]"
-#ifndef BOOST_NO_RVALUE_REFERENCES
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
template<typename T>
typename boost::remove_reference<T>::type&& cast_to_rval(T&& t)
{
Modified: branches/release/libs/thread/test/test_generic_locks.cpp
==============================================================================
--- branches/release/libs/thread/test/test_generic_locks.cpp (original)
+++ branches/release/libs/thread/test/test_generic_locks.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/test/unit_test.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
@@ -13,7 +15,7 @@
{
boost::mutex m1,m2;
- boost::mutex::scoped_lock l1(m1,boost::defer_lock),
+ boost::unique_lock<boost::mutex> l1(m1,boost::defer_lock),
l2(m2,boost::defer_lock);
BOOST_CHECK(!l1.owns_lock());
@@ -37,7 +39,7 @@
void wait()
{
- boost::mutex::scoped_lock l(m);
+ boost::unique_lock<boost::mutex> l(m);
while(!flag)
{
cond.wait(l);
@@ -49,7 +51,7 @@
{
boost::system_time const target=boost::get_system_time()+d;
- boost::mutex::scoped_lock l(m);
+ boost::unique_lock<boost::mutex> l(m);
while(!flag)
{
if(!cond.timed_wait(l,target))
@@ -62,7 +64,7 @@
void signal()
{
- boost::mutex::scoped_lock l(m);
+ boost::unique_lock<boost::mutex> l(m);
flag=true;
cond.notify_all();
}
@@ -81,7 +83,7 @@
void lock_pair(boost::mutex* m1,boost::mutex* m2)
{
boost::lock(*m1,*m2);
- boost::mutex::scoped_lock l1(*m1,boost::adopt_lock),
+ boost::unique_lock<boost::mutex> l1(*m1,boost::adopt_lock),
l2(*m2,boost::adopt_lock);
}
@@ -127,7 +129,7 @@
{
boost::mutex m1,m2,m3,m4,m5;
- boost::mutex::scoped_lock l1(m1,boost::defer_lock),
+ boost::unique_lock<boost::mutex> l1(m1,boost::defer_lock),
l2(m2,boost::defer_lock),
l3(m3,boost::defer_lock),
l4(m4,boost::defer_lock),
Modified: branches/release/libs/thread/test/test_lock_concept.cpp
==============================================================================
--- branches/release/libs/thread/test/test_lock_concept.cpp (original)
+++ branches/release/libs/thread/test/test_lock_concept.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,9 +3,12 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/test/unit_test.hpp>
#include <boost/mpl/vector.hpp>
#include <boost/thread/mutex.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/recursive_mutex.hpp>
@@ -64,7 +67,7 @@
try
{
{
- boost::mutex::scoped_lock lk(done_mutex);
+ boost::unique_lock<boost::mutex> lk(done_mutex);
BOOST_CHECK(done_cond.timed_wait(lk,boost::posix_time::seconds(2),
boost::bind(&this_type::is_done,this)));
BOOST_CHECK(!locked);
@@ -122,7 +125,7 @@
try
{
{
- boost::mutex::scoped_lock lk(done_mutex);
+ boost::unique_lock<boost::mutex> lk(done_mutex);
BOOST_CHECK(done_cond.timed_wait(lk,boost::posix_time::seconds(2),
boost::bind(&this_type::is_done,this)));
BOOST_CHECK(!locked);
@@ -180,7 +183,7 @@
try
{
{
- boost::mutex::scoped_lock lk(done_mutex);
+ boost::unique_lock<boost::mutex> lk(done_mutex);
BOOST_CHECK(done_cond.timed_wait(lk,boost::posix_time::seconds(2),
boost::bind(&this_type::is_done,this)));
BOOST_CHECK(locked);
@@ -305,7 +308,7 @@
try
{
{
- boost::mutex::scoped_lock lk(done_mutex);
+ boost::unique_lock<boost::mutex> lk(done_mutex);
BOOST_CHECK(done_cond.timed_wait(lk,boost::posix_time::seconds(2),
boost::bind(&this_type::is_done,this)));
BOOST_CHECK(!locked);
Modified: branches/release/libs/thread/test/test_ml.cpp
==============================================================================
--- branches/release/libs/thread/test/test_ml.cpp (original)
+++ branches/release/libs/thread/test/test_ml.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,7 +4,7 @@
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#include <boost/config.hpp>
-#ifndef BOOST_NO_RVALUE_REFERENCES
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
#include <boost/detail/lightweight_test.hpp>
#include <boost/thread/future.hpp>
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-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -2,6 +2,9 @@
//
// 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)
+
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/thread.hpp>
#include <boost/test/unit_test.hpp>
#include <boost/thread/mutex.hpp>
@@ -94,7 +97,7 @@
struct nc:
public boost::shared_ptr<int>
{
-#ifndef BOOST_NO_RVALUE_REFERENCES
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
nc() {}
nc(nc&&)
{
@@ -117,7 +120,7 @@
void test_move_for_user_defined_type_unaffected()
{
user_test_ns::nc src;
-#ifndef BOOST_NO_RVALUE_REFERENCES
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
user_test_ns::nc dest=boost::move(src);
#else
user_test_ns::nc dest=move(src);
Modified: branches/release/libs/thread/test/test_mutex.cpp
==============================================================================
--- branches/release/libs/thread/test/test_mutex.cpp (original)
+++ branches/release/libs/thread/test/test_mutex.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -4,9 +4,12 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/mutex.hpp>
+#include <boost/thread/lock_types.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/recursive_mutex.hpp>
#include <boost/thread/thread_time.hpp>
@@ -152,7 +155,7 @@
try
{
{
- boost::mutex::scoped_lock lk(done_mutex);
+ boost::unique_lock<boost::mutex> lk(done_mutex);
BOOST_CHECK(done_cond.timed_wait(lk,boost::posix_time::seconds(2),
boost::bind(&this_type::is_done,this)));
BOOST_CHECK(!locked);
Modified: branches/release/libs/thread/test/test_once.cpp
==============================================================================
--- branches/release/libs/thread/test/test_once.cpp (original)
+++ branches/release/libs/thread/test/test_once.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,9 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/test/unit_test.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/mutex.hpp>
@@ -18,7 +21,7 @@
void initialize_variable()
{
// ensure that if multiple threads get in here, they are serialized, so we can see the effect
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
++var_to_init;
}
@@ -36,7 +39,7 @@
break;
}
}
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
BOOST_CHECK_EQUAL(my_once_value, 1);
}
@@ -76,7 +79,7 @@
void operator()() const
{
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
++(*value);
}
};
@@ -95,7 +98,7 @@
break;
}
}
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
BOOST_CHECK_EQUAL(my_once_value, 1);
}
@@ -134,7 +137,7 @@
void operator()() const
{
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
++pass_counter;
if(pass_counter<3)
{
@@ -155,7 +158,7 @@
}
catch(throw_before_third_pass::my_exception)
{
- boost::mutex::scoped_lock lock(m);
+ boost::unique_lock<boost::mutex> lock(m);
++exception_counter;
}
}
Modified: branches/release/libs/thread/test/test_shared_mutex.cpp
==============================================================================
--- branches/release/libs/thread/test/test_shared_mutex.cpp (original)
+++ branches/release/libs/thread/test/test_shared_mutex.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,9 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/test/unit_test.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
@@ -11,7 +14,7 @@
#define CHECK_LOCKED_VALUE_EQUAL(mutex_name,value,expected_value) \
{ \
- boost::mutex::scoped_lock lock(mutex_name); \
+ boost::unique_lock<boost::mutex> lock(mutex_name); \
BOOST_CHECK_EQUAL(value,expected_value); \
}
@@ -28,7 +31,7 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_mutex;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
try
{
@@ -39,7 +42,7 @@
}
{
- boost::mutex::scoped_lock lk(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> lk(unblocked_count_mutex);
while(unblocked_count<number_of_threads)
{
unblocked_condition.wait(lk);
@@ -75,7 +78,7 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_mutex;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
try
{
@@ -115,7 +118,7 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_mutex;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
try
{
@@ -123,7 +126,7 @@
pool.create_thread(locking_thread<boost::shared_lock<boost::shared_mutex> >(rw_mutex,unblocked_count,unblocked_count_mutex,unblocked_condition,
finish_mutex,simultaneous_running_count,max_simultaneous_running));
{
- boost::mutex::scoped_lock lk(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> lk(unblocked_count_mutex);
while(unblocked_count<1)
{
unblocked_condition.wait(lk);
@@ -162,7 +165,7 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_mutex;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
unsigned const reader_count=10;
@@ -179,7 +182,7 @@
write_lock.unlock();
{
- boost::mutex::scoped_lock lk(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> lk(unblocked_count_mutex);
while(unblocked_count<reader_count)
{
unblocked_condition.wait(lk);
@@ -214,9 +217,9 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_reading_mutex;
- boost::mutex::scoped_lock finish_reading_lock(finish_reading_mutex);
+ boost::unique_lock<boost::mutex> finish_reading_lock(finish_reading_mutex);
boost::mutex finish_writing_mutex;
- boost::mutex::scoped_lock finish_writing_lock(finish_writing_mutex);
+ boost::unique_lock<boost::mutex> finish_writing_lock(finish_writing_mutex);
unsigned const reader_count=10;
unsigned const writer_count=10;
@@ -235,7 +238,7 @@
finish_writing_mutex,simultaneous_running_writers,max_simultaneous_writers));
}
{
- boost::mutex::scoped_lock lk(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> lk(unblocked_count_mutex);
while(unblocked_count<reader_count)
{
unblocked_condition.wait(lk);
@@ -247,7 +250,7 @@
finish_reading_lock.unlock();
{
- boost::mutex::scoped_lock lk(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> lk(unblocked_count_mutex);
while(unblocked_count<(reader_count+1))
{
unblocked_condition.wait(lk);
Modified: branches/release/libs/thread/test/test_shared_mutex_part_2.cpp
==============================================================================
--- branches/release/libs/thread/test/test_shared_mutex_part_2.cpp (original)
+++ branches/release/libs/thread/test/test_shared_mutex_part_2.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/test/unit_test.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
@@ -11,7 +13,7 @@
#define CHECK_LOCKED_VALUE_EQUAL(mutex_name,value,expected_value) \
{ \
- boost::mutex::scoped_lock lock(mutex_name); \
+ boost::unique_lock<boost::mutex> lock(mutex_name); \
BOOST_CHECK_EQUAL(value,expected_value); \
}
@@ -38,11 +40,11 @@
boost::upgrade_lock<boost::shared_mutex> lk(rwm);
{
- boost::mutex::scoped_lock ulk(unblocked_mutex);
+ boost::unique_lock<boost::mutex> ulk(unblocked_mutex);
++unblocked_count;
}
- boost::mutex::scoped_lock flk(finish_mutex);
+ boost::unique_lock<boost::mutex> flk(finish_mutex);
}
};
@@ -60,7 +62,7 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_mutex;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
try
{
@@ -100,7 +102,7 @@
boost::mutex unblocked_count_mutex;
boost::condition_variable unblocked_condition;
boost::mutex finish_mutex;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
unsigned const reader_count=10;
@@ -115,7 +117,7 @@
pool.create_thread(locking_thread<boost::upgrade_lock<boost::shared_mutex> >(rw_mutex,unblocked_count,unblocked_count_mutex,unblocked_condition,
finish_mutex,simultaneous_running_count,max_simultaneous_running));
{
- boost::mutex::scoped_lock lk(unblocked_count_mutex);
+ boost::unique_lock<boost::mutex> lk(unblocked_count_mutex);
while(unblocked_count<(reader_count+1))
{
unblocked_condition.wait(lk);
@@ -153,7 +155,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_writing_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep(boost::posix_time::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -176,7 +178,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_writing_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep(boost::posix_time::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -221,7 +223,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::thread::sleep(delay(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -244,7 +246,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::thread::sleep(delay(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -267,7 +269,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_upgrade_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep(boost::posix_time::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
Modified: branches/release/libs/thread/test/test_shared_mutex_timed_locks.cpp
==============================================================================
--- branches/release/libs/thread/test/test_shared_mutex_timed_locks.cpp (original)
+++ branches/release/libs/thread/test/test_shared_mutex_timed_locks.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/test/unit_test.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/xtime.hpp>
@@ -11,7 +13,7 @@
#define CHECK_LOCKED_VALUE_EQUAL(mutex_name,value,expected_value) \
{ \
- boost::mutex::scoped_lock lock(mutex_name); \
+ boost::unique_lock<boost::mutex> lock(mutex_name); \
BOOST_CHECK_EQUAL(value,expected_value); \
}
@@ -22,7 +24,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_writing_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::thread::sleep(delay(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -87,7 +89,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread reader(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::thread::sleep(delay(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -123,7 +125,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_writing_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::thread::sleep(delay(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -188,7 +190,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread reader(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::thread::sleep(delay(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -224,7 +226,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread reader(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep(boost::posix_time::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
Modified: branches/release/libs/thread/test/test_shared_mutex_timed_locks_chrono.cpp
==============================================================================
--- branches/release/libs/thread/test/test_shared_mutex_timed_locks_chrono.cpp (original)
+++ branches/release/libs/thread/test/test_shared_mutex_timed_locks_chrono.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -3,6 +3,8 @@
// accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/test/unit_test.hpp>
#include <boost/thread/thread.hpp>
#include <boost/thread/shared_mutex.hpp>
@@ -13,7 +15,7 @@
#define CHECK_LOCKED_VALUE_EQUAL(mutex_name,value,expected_value) \
{ \
- boost::mutex::scoped_lock lock(mutex_name); \
+ boost::unique_lock<boost::mutex> lock(mutex_name); \
BOOST_CHECK_EQUAL(value,expected_value); \
}
@@ -24,7 +26,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_writing_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep_for(boost::chrono::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -89,7 +91,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread reader(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep_for(boost::chrono::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -125,7 +127,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread writer(simple_writing_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep_for(boost::chrono::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -190,7 +192,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread reader(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep_for(boost::chrono::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
@@ -226,7 +228,7 @@
boost::mutex finish_mutex;
boost::mutex unblocked_mutex;
unsigned unblocked_count=0;
- boost::mutex::scoped_lock finish_lock(finish_mutex);
+ boost::unique_lock<boost::mutex> finish_lock(finish_mutex);
boost::thread reader(simple_reading_thread(rw_mutex,finish_mutex,unblocked_mutex,unblocked_count));
boost::this_thread::sleep_for(boost::chrono::seconds(1));
CHECK_LOCKED_VALUE_EQUAL(unblocked_mutex,unblocked_count,1u);
Modified: branches/release/libs/thread/test/test_thread.cpp
==============================================================================
--- branches/release/libs/thread/test/test_thread.cpp (original)
+++ branches/release/libs/thread/test/test_thread.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,6 +5,9 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/thread.hpp>
@@ -74,7 +77,7 @@
void interruption_point_thread(boost::mutex* m,bool* failed)
{
- boost::mutex::scoped_lock lk(*m);
+ boost::unique_lock<boost::mutex> lk(*m);
boost::this_thread::interruption_point();
*failed=true;
}
@@ -83,7 +86,7 @@
{
boost::mutex m;
bool failed=false;
- boost::mutex::scoped_lock lk(m);
+ boost::unique_lock<boost::mutex> lk(m);
boost::thread thrd(boost::bind(&interruption_point_thread,&m,&failed));
thrd.interrupt();
lk.unlock();
@@ -98,7 +101,7 @@
void disabled_interruption_point_thread(boost::mutex* m,bool* failed)
{
- boost::mutex::scoped_lock lk(*m);
+ boost::unique_lock<boost::mutex> lk(*m);
boost::this_thread::disable_interruption dc;
boost::this_thread::interruption_point();
*failed=false;
@@ -108,7 +111,7 @@
{
boost::mutex m;
bool failed=true;
- boost::mutex::scoped_lock lk(m);
+ boost::unique_lock<boost::mutex> lk(m);
boost::thread thrd(boost::bind(&disabled_interruption_point_thread,&m,&failed));
thrd.interrupt();
lk.unlock();
@@ -162,7 +165,7 @@
void operator()()
{
- boost::mutex::scoped_lock lk(mut);
+ boost::unique_lock<boost::mutex> lk(mut);
while(!done)
{
cond.wait(lk);
@@ -181,7 +184,7 @@
BOOST_CHECK(!joined);
BOOST_CHECK(thrd.joinable());
{
- boost::mutex::scoped_lock lk(f.mut);
+ boost::unique_lock<boost::mutex> lk(f.mut);
f.done=true;
f.cond.notify_one();
}
Modified: branches/release/libs/thread/test/test_thread_launching.cpp
==============================================================================
--- branches/release/libs/thread/test/test_thread_launching.cpp (original)
+++ branches/release/libs/thread/test/test_thread_launching.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -2,6 +2,9 @@
//
// 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)
+
+#define BOOST_THREAD_VERSION 3
+
#include <boost/thread/thread.hpp>
#include <boost/test/unit_test.hpp>
#include <boost/ref.hpp>
Modified: branches/release/libs/thread/test/test_thread_mf.cpp
==============================================================================
--- branches/release/libs/thread/test/test_thread_mf.cpp (original)
+++ branches/release/libs/thread/test/test_thread_mf.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,6 +5,7 @@
// See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt
//
+#define BOOST_THREAD_VERSION 3
#include <boost/thread/thread.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/release/libs/thread/test/test_tss.cpp
==============================================================================
--- branches/release/libs/thread/test/test_tss.cpp (original)
+++ branches/release/libs/thread/test/test_tss.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,6 +5,9 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+#define BOOST_THREAD_PROVIDES_INTERRUPTIONS
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/tss.hpp>
@@ -31,14 +34,14 @@
{
tss_value_t()
{
- boost::mutex::scoped_lock lock(tss_mutex);
+ boost::unique_lock<boost::mutex> lock(tss_mutex);
++tss_instances;
++tss_total;
value = 0;
}
~tss_value_t()
{
- boost::mutex::scoped_lock lock(tss_mutex);
+ boost::unique_lock<boost::mutex> lock(tss_mutex);
--tss_instances;
}
int value;
@@ -56,7 +59,7 @@
// be thread safe. Must evaluate further.
if (n != i)
{
- boost::mutex::scoped_lock lock(check_mutex);
+ boost::unique_lock<boost::mutex> lock(check_mutex);
BOOST_CHECK_EQUAL(n, i);
}
++n;
Modified: branches/release/libs/thread/test/test_xtime.cpp
==============================================================================
--- branches/release/libs/thread/test/test_xtime.cpp (original)
+++ branches/release/libs/thread/test/test_xtime.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -5,6 +5,8 @@
// 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)
+#define BOOST_THREAD_VERSION 2
+
#include <boost/thread/detail/config.hpp>
#include <boost/thread/xtime.hpp>
@@ -86,7 +88,7 @@
boost::condition_variable_any cond_any;
boost::mutex m;
- boost::mutex::scoped_lock lk(m);
+ boost::unique_lock<boost::mutex> lk(m);
cond.timed_wait(lk,boost::get_xtime(boost::get_system_time()+boost::posix_time::milliseconds(10)));
cond.timed_wait(lk,boost::get_xtime(boost::get_system_time()+boost::posix_time::milliseconds(10)),predicate);
cond_any.timed_wait(lk,boost::get_xtime(boost::get_system_time()+boost::posix_time::milliseconds(10)));
Modified: branches/release/libs/thread/test/threads/container/thread_ptr_list_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/threads/container/thread_ptr_list_pass.cpp (original)
+++ branches/release/libs/thread/test/threads/container/thread_ptr_list_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -33,7 +33,7 @@
void increment_count()
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
std::cout << "count = " << ++count << std::endl;
}
Modified: branches/release/libs/thread/test/threads/container/thread_vector_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/threads/container/thread_vector_pass.cpp (original)
+++ branches/release/libs/thread/test/threads/container/thread_vector_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -10,6 +10,7 @@
#include <boost/container/vector.hpp>
#include <iostream>
#include <boost/detail/lightweight_test.hpp>
+#include <boost/static_assert.hpp>
int count = 0;
boost::mutex mutex;
@@ -28,19 +29,25 @@
template <typename TC>
void interrupt_all(TC & tc)
{
+#if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS
for (typename TC::iterator it = tc.begin(); it != tc.end(); ++it)
{
it->interrupt();
}
+#endif
}
}
void increment_count()
{
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
std::cout << "count = " << ++count << std::endl;
}
+#if defined BOOST_NO_CXX11_RVALUE_REFERENCES && defined BOOST_THREAD_USES_MOVE
+BOOST_STATIC_ASSERT(::boost::is_function<boost::rv<boost::rv<boost::thread> >&>::value==false);
+#endif
+
int main()
{
typedef boost::container::vector<boost::thread> thread_vector;
@@ -83,6 +90,7 @@
threads.emplace_back(&increment_count);
}
interrupt_all(threads);
+ join_all(threads);
}
return boost::report_errors();
}
Modified: branches/release/libs/thread/test/threads/thread/assign/move_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/threads/thread/assign/move_pass.cpp (original)
+++ branches/release/libs/thread/test/threads/thread/assign/move_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -92,7 +92,6 @@
BOOST_TEST(G::n_alive == 0);
{
boost::thread t0(G(), 5, 5.5);
- boost::thread::id id = t0.get_id();
boost::thread t1;
t0 = boost::move(t1);
BOOST_TEST(false);
Modified: branches/release/libs/thread/test/threads/thread/constr/FrvalueArgs_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/threads/thread/constr/FrvalueArgs_pass.cpp (original)
+++ branches/release/libs/thread/test/threads/thread/constr/FrvalueArgs_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -17,6 +17,8 @@
// template <class F, class ...Args> thread(F&& f, Args&&... args);
+#define BOOST_THREAD_VERSION 4
+
#include <boost/thread/thread.hpp>
#include <new>
#include <cstdlib>
@@ -25,6 +27,7 @@
class MoveOnly
{
+public:
BOOST_THREAD_MOVABLE_ONLY(MoveOnly)
MoveOnly()
{
@@ -39,9 +42,11 @@
int main()
{
+#if defined(BOOST_THREAD_PROVIDES_VARIADIC_THREAD)
{
- boost::thread t = boost::thread( BOOST_THREAD_MAKE_RV_REF(MoveOnly()), BOOST_THREAD_MAKE_RV_REF(MoveOnly()) );
+ boost::thread t = boost::thread( MoveOnly(), MoveOnly() );
t.join();
}
+#endif
return boost::report_errors();
}
Modified: branches/release/libs/thread/test/threads/thread/constr/Frvalue_pass.cpp
==============================================================================
--- branches/release/libs/thread/test/threads/thread/constr/Frvalue_pass.cpp (original)
+++ branches/release/libs/thread/test/threads/thread/constr/Frvalue_pass.cpp 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -24,6 +24,7 @@
#include <cstdlib>
#include <cassert>
#include <boost/detail/lightweight_test.hpp>
+#include <boost/static_assert.hpp>
class MoveOnly
{
@@ -44,6 +45,10 @@
return BOOST_THREAD_MAKE_RV_REF(MoveOnly());
}
+#if defined BOOST_NO_CXX11_RVALUE_REFERENCES && defined BOOST_THREAD_USES_MOVE
+BOOST_STATIC_ASSERT(::boost::is_function<boost::rv<boost::rv<MoveOnly> >&>::value==false);
+#endif
+
int main()
{
{
Modified: branches/release/libs/thread/test/util.inl
==============================================================================
--- branches/release/libs/thread/test/util.inl (original)
+++ branches/release/libs/thread/test/util.inl 2012-12-02 04:22:33 EST (Sun, 02 Dec 2012)
@@ -74,7 +74,7 @@
void start()
{
if (type != use_sleep_only) {
- boost::mutex::scoped_lock lock(mutex); done = false;
+ boost::unique_lock<boost::mutex> lock(mutex); done = false;
} else {
done = false;
}
@@ -82,7 +82,7 @@
void finish()
{
if (type != use_sleep_only) {
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
done = true;
if (type == use_condition)
cond.notify_one();
@@ -96,7 +96,7 @@
if (type != use_condition)
boost::thread::sleep(xt);
if (type != use_sleep_only) {
- boost::mutex::scoped_lock lock(mutex);
+ boost::unique_lock<boost::mutex> lock(mutex);
while (type == use_condition && !done) {
if (!cond.timed_wait(lock, xt))
break;
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