|
Boost-Commit : |
From: nicola.musatti_at_[hidden]
Date: 2007-09-26 17:55:58
Author: nmusatti
Date: 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
New Revision: 39560
URL: http://svn.boost.org/trac/boost/changeset/39560
Log:
Merge from trunk
Added:
branches/bcbboost/boost/interprocess/mem_algo/detail/mem_algo_common.hpp
- copied unchanged from r39559, /trunk/boost/interprocess/mem_algo/detail/mem_algo_common.hpp
branches/bcbboost/boost/interprocess/sync/emulation/named_creation_functor.hpp
- copied unchanged from r39559, /trunk/boost/interprocess/sync/emulation/named_creation_functor.hpp
branches/bcbboost/boost/intrusive/detail/generic_hook.hpp
- copied unchanged from r39559, /trunk/boost/intrusive/detail/generic_hook.hpp
branches/bcbboost/boost/intrusive/detail/no_exceptions_support.hpp
- copied unchanged from r39559, /trunk/boost/intrusive/detail/no_exceptions_support.hpp
branches/bcbboost/boost/intrusive/detail/transform_iterator.hpp
- copied unchanged from r39559, /trunk/boost/intrusive/detail/transform_iterator.hpp
branches/bcbboost/boost/intrusive/link_mode.hpp
- copied unchanged from r39559, /trunk/boost/intrusive/link_mode.hpp
branches/bcbboost/boost/intrusive/options.hpp
- copied unchanged from r39559, /trunk/boost/intrusive/options.hpp
branches/bcbboost/libs/interprocess/example/doc_shared_ptr.cpp
- copied unchanged from r39559, /trunk/libs/interprocess/example/doc_shared_ptr.cpp
branches/bcbboost/libs/interprocess/example/doc_shared_ptr_explicit.cpp
- copied unchanged from r39559, /trunk/libs/interprocess/example/doc_shared_ptr_explicit.cpp
branches/bcbboost/libs/interprocess/example/doc_unique_ptr.cpp
- copied unchanged from r39559, /trunk/libs/interprocess/example/doc_unique_ptr.cpp
branches/bcbboost/libs/interprocess/proj/to-do.txt
- copied unchanged from r39559, /trunk/libs/interprocess/proj/to-do.txt
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_ptr.vcproj
- copied unchanged from r39559, /trunk/libs/interprocess/proj/vc7ide/doc_shared_ptr.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_ptr_explicit.vcproj
- copied unchanged from r39559, /trunk/libs/interprocess/proj/vc7ide/doc_shared_ptr_explicit.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_unique_ptr.vcproj
- copied unchanged from r39559, /trunk/libs/interprocess/proj/vc7ide/doc_unique_ptr.vcproj
branches/bcbboost/libs/intrusive/example/doc_bucket_traits.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/example/doc_bucket_traits.cpp
branches/bcbboost/libs/intrusive/example/doc_external_value_traits.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/example/doc_external_value_traits.cpp
branches/bcbboost/libs/intrusive/example/doc_stateful_value_traits.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/example/doc_stateful_value_traits.cpp
branches/bcbboost/libs/intrusive/proj/vc7ide/custom_bucket_traits/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/custom_bucket_traits/
branches/bcbboost/libs/intrusive/proj/vc7ide/custom_bucket_traits/custom_bucket_traits.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/custom_bucket_traits/custom_bucket_traits.vcproj
branches/bcbboost/libs/intrusive/proj/vc7ide/default_hook/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/default_hook/
branches/bcbboost/libs/intrusive/proj/vc7ide/default_hook/default_hook.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/default_hook/default_hook.vcproj
branches/bcbboost/libs/intrusive/proj/vc7ide/external_value_traits/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/external_value_traits/
branches/bcbboost/libs/intrusive/proj/vc7ide/external_value_traits/external_value_traits.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/external_value_traits/external_value_traits.vcproj
branches/bcbboost/libs/intrusive/proj/vc7ide/make_functions/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/make_functions/
branches/bcbboost/libs/intrusive/proj/vc7ide/make_functions/make_functions.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/make_functions/make_functions.vcproj
branches/bcbboost/libs/intrusive/proj/vc7ide/perf_test/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/perf_test/
branches/bcbboost/libs/intrusive/proj/vc7ide/perf_test/perf_test.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/perf_test/perf_test.vcproj
branches/bcbboost/libs/intrusive/proj/vc7ide/stateful_value_traits/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/stateful_value_traits/
branches/bcbboost/libs/intrusive/proj/vc7ide/stateful_value_traits/stateful_value_traits.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/stateful_value_traits/stateful_value_traits.vcproj
branches/bcbboost/libs/intrusive/proj/vc7ide/to-do.txt
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/to-do.txt
branches/bcbboost/libs/intrusive/proj/vc7ide/virtual_base/
- copied from r39559, /trunk/libs/intrusive/proj/vc7ide/virtual_base/
branches/bcbboost/libs/intrusive/proj/vc7ide/virtual_base/virtual_base.vcproj
- copied unchanged from r39559, /trunk/libs/intrusive/proj/vc7ide/virtual_base/virtual_base.vcproj
branches/bcbboost/libs/intrusive/test/custom_bucket_traits_test.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/test/custom_bucket_traits_test.cpp
branches/bcbboost/libs/intrusive/test/default_hook_test.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/test/default_hook_test.cpp
branches/bcbboost/libs/intrusive/test/external_value_traits_test.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/test/external_value_traits_test.cpp
branches/bcbboost/libs/intrusive/test/make_functions_test.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/test/make_functions_test.cpp
branches/bcbboost/libs/intrusive/test/stateful_value_traits_test.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/test/stateful_value_traits_test.cpp
branches/bcbboost/libs/intrusive/test/virtual_base_test.cpp
- copied unchanged from r39559, /trunk/libs/intrusive/test/virtual_base_test.cpp
Removed:
branches/bcbboost/boost/interprocess/detail/basic_segment_manager.hpp
branches/bcbboost/boost/interprocess/detail/gcd_lcm.hpp
branches/bcbboost/boost/interprocess/detail/generic_cast.hpp
branches/bcbboost/boost/interprocess/detail/null_create_func.hpp
branches/bcbboost/boost/intrusive/linking_policy.hpp
branches/bcbboost/boost/intrusive/tag.hpp
branches/bcbboost/libs/interprocess/example/alloc_example.cpp
branches/bcbboost/libs/interprocess/example/doc_named_conditionA.cpp
branches/bcbboost/libs/interprocess/example/doc_named_conditionB.cpp
branches/bcbboost/libs/interprocess/example/named_alloc_example.cpp
branches/bcbboost/libs/interprocess/example/print_container.hpp
branches/bcbboost/libs/interprocess/example/printcontainer.hpp
branches/bcbboost/libs/interprocess/example/process_a_example.cpp
branches/bcbboost/libs/interprocess/example/process_a_fixed_example.cpp
branches/bcbboost/libs/interprocess/example/process_b_example.cpp
branches/bcbboost/libs/interprocess/example/process_b_fixed_example.cpp
branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessA.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessAFixed.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessB.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessBFixed.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/allocate_ex.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/file_lock_test.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/hash_table_ex.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/intersegment_ptr_test.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/named_allocate_ex.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/read_write_mutex_test.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/sharable_mutex.vcproj
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mapping_test.vcproj
branches/bcbboost/libs/interprocess/test/allocation_test_template.hpp
branches/bcbboost/libs/interprocess/test/get_compiler_name.hpp
branches/bcbboost/libs/interprocess/test/printcontainer.hpp
branches/bcbboost/libs/intrusive/test/test_intrusive_associative_container.hpp
branches/bcbboost/libs/intrusive/test/test_intrusive_sequence_container.hpp
branches/bcbboost/libs/intrusive/test/test_intrusive_unordered_container.hpp
Properties modified:
branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_node_pool_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_pool_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/allocexcept_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/barrier_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/bufferstream_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/cached_adaptive_pool_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/cached_node_allocator_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/condition_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/data_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/deque_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_adaptive_pool.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_allocator.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_bufferstream.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_adaptive_pool.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_node_allocator.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cont.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping2.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_intrusive.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_aligned_allocation.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_allocation_command.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_construction_info.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_heap_memory.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_mapped_file.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_multiple_allocation.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_raw_allocation.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_map.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_move_containers.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionA.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionB.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_mutex.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_node_allocator.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_offset_ptr.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_adaptive_pool.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_node_allocator.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_scoped_ptr.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory2.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_vectorstream.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_where_allocate.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory2.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/file_mapping_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/flat_map_index_allocation_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/flat_tree_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/interprocesslib.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/intrusive_ptr_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/iset_index_allocation_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/iunordered_set_index_allocation_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/list_ex.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/managed_mapped_file_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/managed_windows_shared_memory.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/map_index_allocation_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/mapped_file_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/memory_algorithm_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/message_queue.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/mutex_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/named_condition_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/named_mutex_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/named_recursive_mutex_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/named_semaphore_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/named_upgradable_mutex.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/node_allocator_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/node_pool_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/null_index_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/private_adaptive_pool_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/private_node_allocator_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/recursive_mutex_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/semaphore_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mappable_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_ptr_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/slist_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/string_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/tree_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/unique_ptr_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/upgradable_mutex.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/user_buffer_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/vector_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/vectorstream_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_mapping_test.vcproj (contents, props changed)
branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_test.vcproj (contents, props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/Intrusive.vcproj (props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/_intrusivelib/_intrusivelib.vcproj (contents, props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/list/list.vcproj (contents, props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/multiset/multiset.vcproj (contents, props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/set/set.vcproj (props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/slist/slist.vcproj (props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/unordered_multiset/unordered_multiset.vcproj (props changed)
branches/bcbboost/libs/intrusive/proj/vc7ide/unordered_set/unordered_set.vcproj (props changed)
Text files modified:
branches/bcbboost/boost/config/compiler/gcc.hpp | 4
branches/bcbboost/boost/filesystem/convenience.hpp | 3
branches/bcbboost/boost/interprocess/allocators/allocation_type.hpp | 4
branches/bcbboost/boost/interprocess/allocators/allocator.hpp | 12
branches/bcbboost/boost/interprocess/allocators/cached_node_allocator.hpp | 118 +-
branches/bcbboost/boost/interprocess/allocators/detail/adaptive_node_pool.hpp | 19
branches/bcbboost/boost/interprocess/allocators/detail/node_pool.hpp | 19
branches/bcbboost/boost/interprocess/allocators/detail/node_tools.hpp | 8
branches/bcbboost/boost/interprocess/allocators/private_adaptive_pool.hpp | 3
branches/bcbboost/boost/interprocess/allocators/private_node_allocator.hpp | 3
branches/bcbboost/boost/interprocess/containers/deque.hpp | 601 +++++------
branches/bcbboost/boost/interprocess/containers/detail/flat_tree.hpp | 5
branches/bcbboost/boost/interprocess/containers/detail/node_alloc_holder.hpp | 154 +-
branches/bcbboost/boost/interprocess/containers/detail/tree.hpp | 165 +-
branches/bcbboost/boost/interprocess/containers/flat_set.hpp | 12
branches/bcbboost/boost/interprocess/containers/list.hpp | 115 +-
branches/bcbboost/boost/interprocess/containers/map.hpp | 11
branches/bcbboost/boost/interprocess/containers/set.hpp | 6
branches/bcbboost/boost/interprocess/containers/slist.hpp | 139 +-
branches/bcbboost/boost/interprocess/containers/string.hpp | 116 +-
branches/bcbboost/boost/interprocess/containers/vector.hpp | 1015 ++++++++++---------
branches/bcbboost/boost/interprocess/creation_tags.hpp | 2
branches/bcbboost/boost/interprocess/detail/algorithms.hpp | 166 --
branches/bcbboost/boost/interprocess/detail/config_begin.hpp | 39
branches/bcbboost/boost/interprocess/detail/file_wrapper.hpp | 60
branches/bcbboost/boost/interprocess/detail/in_place_interface.hpp | 5
branches/bcbboost/boost/interprocess/detail/managed_memory_impl.hpp | 45
branches/bcbboost/boost/interprocess/detail/managed_open_or_create_impl.hpp | 6
branches/bcbboost/boost/interprocess/detail/move.hpp | 24
branches/bcbboost/boost/interprocess/detail/named_proxy.hpp | 30
branches/bcbboost/boost/interprocess/detail/os_file_functions.hpp | 2
branches/bcbboost/boost/interprocess/detail/segment_manager_helper.hpp | 26
branches/bcbboost/boost/interprocess/detail/type_traits.hpp | 25
branches/bcbboost/boost/interprocess/detail/utilities.hpp | 85 +
branches/bcbboost/boost/interprocess/detail/win32_api.hpp | 24
branches/bcbboost/boost/interprocess/detail/workaround.hpp | 4
branches/bcbboost/boost/interprocess/errors.hpp | 5
branches/bcbboost/boost/interprocess/exceptions.hpp | 29
branches/bcbboost/boost/interprocess/file_mapping.hpp | 50
branches/bcbboost/boost/interprocess/indexes/flat_map_index.hpp | 7
branches/bcbboost/boost/interprocess/indexes/iset_index.hpp | 55
branches/bcbboost/boost/interprocess/indexes/iunordered_set_index.hpp | 76
branches/bcbboost/boost/interprocess/indexes/map_index.hpp | 44
branches/bcbboost/boost/interprocess/indexes/null_index.hpp | 28
branches/bcbboost/boost/interprocess/indexes/unordered_map_index.hpp | 32
branches/bcbboost/boost/interprocess/interprocess_fwd.hpp | 45
branches/bcbboost/boost/interprocess/ipc/message_queue.hpp | 231 ++--
branches/bcbboost/boost/interprocess/managed_external_buffer.hpp | 7
branches/bcbboost/boost/interprocess/managed_heap_memory.hpp | 8
branches/bcbboost/boost/interprocess/managed_mapped_file.hpp | 68
branches/bcbboost/boost/interprocess/managed_shared_memory.hpp | 27
branches/bcbboost/boost/interprocess/managed_windows_shared_memory.hpp | 42
branches/bcbboost/boost/interprocess/mapped_region.hpp | 60
branches/bcbboost/boost/interprocess/mem_algo/detail/simple_seq_fit_impl.hpp | 484 ++-------
branches/bcbboost/boost/interprocess/mem_algo/rbtree_best_fit.hpp | 629 ++---------
branches/bcbboost/boost/interprocess/mem_algo/simple_seq_fit.hpp | 15
branches/bcbboost/boost/interprocess/offset_ptr.hpp | 136 +-
branches/bcbboost/boost/interprocess/segment_manager.hpp | 43
branches/bcbboost/boost/interprocess/shared_memory_object.hpp | 23
branches/bcbboost/boost/interprocess/smart_ptr/detail/shared_count.hpp | 95
branches/bcbboost/boost/interprocess/smart_ptr/enable_shared_from_this.hpp | 3
branches/bcbboost/boost/interprocess/smart_ptr/intrusive_ptr.hpp | 124 +-
branches/bcbboost/boost/interprocess/smart_ptr/scoped_ptr.hpp | 3
branches/bcbboost/boost/interprocess/smart_ptr/shared_ptr.hpp | 248 +++-
branches/bcbboost/boost/interprocess/smart_ptr/unique_ptr.hpp | 314 ++++-
branches/bcbboost/boost/interprocess/smart_ptr/weak_ptr.hpp | 111 ++
branches/bcbboost/boost/interprocess/sync/file_lock.hpp | 89
branches/bcbboost/boost/interprocess/sync/interprocess_barrier.hpp | 36
branches/bcbboost/boost/interprocess/sync/interprocess_condition.hpp | 43
branches/bcbboost/boost/interprocess/sync/interprocess_mutex.hpp | 56
branches/bcbboost/boost/interprocess/sync/interprocess_recursive_mutex.hpp | 54
branches/bcbboost/boost/interprocess/sync/interprocess_semaphore.hpp | 46
branches/bcbboost/boost/interprocess/sync/interprocess_upgradable_mutex.hpp | 208 ++--
branches/bcbboost/boost/interprocess/sync/lock_options.hpp | 11
branches/bcbboost/boost/interprocess/sync/mutex_family.hpp | 13
branches/bcbboost/boost/interprocess/sync/named_condition.hpp | 233 ++-
branches/bcbboost/boost/interprocess/sync/named_mutex.hpp | 156 +-
branches/bcbboost/boost/interprocess/sync/named_recursive_mutex.hpp | 104 -
branches/bcbboost/boost/interprocess/sync/named_semaphore.hpp | 171 +-
branches/bcbboost/boost/interprocess/sync/named_upgradable_mutex.hpp | 263 ++--
branches/bcbboost/boost/interprocess/sync/null_mutex.hpp | 90
branches/bcbboost/boost/interprocess/sync/posix/pthread_helpers.hpp | 34
branches/bcbboost/boost/interprocess/sync/posix/semaphore_wrapper.hpp | 273 ++++-
branches/bcbboost/boost/interprocess/sync/scoped_lock.hpp | 302 ++--
branches/bcbboost/boost/interprocess/sync/sharable_lock.hpp | 232 ++--
branches/bcbboost/boost/interprocess/sync/upgradable_lock.hpp | 234 ++--
branches/bcbboost/boost/interprocess/windows_shared_memory.hpp | 8
branches/bcbboost/boost/intrusive/circular_list_algorithms.hpp | 1
branches/bcbboost/boost/intrusive/circular_slist_algorithms.hpp | 1
branches/bcbboost/boost/intrusive/derivation_value_traits.hpp | 7
branches/bcbboost/boost/intrusive/detail/config_begin.hpp | 6
branches/bcbboost/boost/intrusive/detail/ebo_functor_holder.hpp | 2
branches/bcbboost/boost/intrusive/detail/hashtable_node.hpp | 296 +----
branches/bcbboost/boost/intrusive/detail/list_node.hpp | 220 +--
branches/bcbboost/boost/intrusive/detail/mpl.hpp | 128 ++
branches/bcbboost/boost/intrusive/detail/parent_from_member.hpp | 13
branches/bcbboost/boost/intrusive/detail/rbtree_node.hpp | 209 +--
branches/bcbboost/boost/intrusive/detail/slist_node.hpp | 206 +--
branches/bcbboost/boost/intrusive/detail/utilities.hpp | 435 +++++--
branches/bcbboost/boost/intrusive/hashtable.hpp | 1172 +++++++++++++++------
branches/bcbboost/boost/intrusive/intrusive_fwd.hpp | 203 ++-
branches/bcbboost/boost/intrusive/list.hpp | 574 ++++++++---
branches/bcbboost/boost/intrusive/list_hook.hpp | 393 ++-----
branches/bcbboost/boost/intrusive/member_value_traits.hpp | 7
branches/bcbboost/boost/intrusive/pointer_plus_bit.hpp | 4
branches/bcbboost/boost/intrusive/rbtree.hpp | 704 +++++++++---
branches/bcbboost/boost/intrusive/rbtree_algorithms.hpp | 547 +++++++++-
branches/bcbboost/boost/intrusive/set.hpp | 691 +++++++++---
branches/bcbboost/boost/intrusive/set_hook.hpp | 392 ++----
branches/bcbboost/boost/intrusive/slist.hpp | 570 +++++++---
branches/bcbboost/boost/intrusive/slist_hook.hpp | 386 ++-----
branches/bcbboost/boost/intrusive/trivial_value_traits.hpp | 12
branches/bcbboost/boost/intrusive/unordered_set.hpp | 616 +++++++----
branches/bcbboost/boost/intrusive/unordered_set_hook.hpp | 348 +++---
branches/bcbboost/boost/system/error_code.hpp | 47
branches/bcbboost/libs/filesystem/src/operations.cpp | 3
branches/bcbboost/libs/filesystem/src/path.cpp | 2
branches/bcbboost/libs/interprocess/doc/Jamfile.v2 | 6
branches/bcbboost/libs/interprocess/doc/interprocess.qbk | 2058 +++++++++++++++++++++------------------
branches/bcbboost/libs/interprocess/example/doc_managed_multiple_allocation.cpp | 27
branches/bcbboost/libs/interprocess/example/doc_offset_ptr.cpp | 2
branches/bcbboost/libs/interprocess/example/doc_vectorstream.cpp | 2
branches/bcbboost/libs/interprocess/proj/conceptgcc/MakeAll | 70
branches/bcbboost/libs/interprocess/proj/cygwin/MakeAll | 78
branches/bcbboost/libs/interprocess/proj/linux/MakeAll | 64
branches/bcbboost/libs/interprocess/proj/mingw/MakeAll | 70
branches/bcbboost/libs/interprocess/proj/qnx/MakeAll | 66
branches/bcbboost/libs/interprocess/proj/vc7ide/Interprocess.sln | 1622 +++++++++++++++---------------
branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_node_pool_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_pool_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/allocexcept_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/barrier_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/bufferstream_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/cached_adaptive_pool_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/cached_node_allocator_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/condition_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/data_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/deque_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_adaptive_pool.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_allocator.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_bufferstream.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_adaptive_pool.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_node_allocator.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cont.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping2.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_intrusive.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_aligned_allocation.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_allocation_command.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_construction_info.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_heap_memory.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_mapped_file.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_multiple_allocation.vcproj | 1
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_raw_allocation.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_map.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_move_containers.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionA.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionB.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_mutex.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_node_allocator.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_offset_ptr.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_adaptive_pool.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_node_allocator.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_scoped_ptr.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory2.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_vectorstream.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_where_allocate.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory2.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/file_mapping_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/flat_map_index_allocation_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/flat_tree_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/interprocesslib.vcproj | 593 ++++++++++
branches/bcbboost/libs/interprocess/proj/vc7ide/intrusive_ptr_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/iset_index_allocation_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/iunordered_set_index_allocation_test.vcproj | 264 ++--
branches/bcbboost/libs/interprocess/proj/vc7ide/list_ex.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/managed_mapped_file_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/managed_windows_shared_memory.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/map_index_allocation_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/mapped_file_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/memory_algorithm_test.vcproj | 3
branches/bcbboost/libs/interprocess/proj/vc7ide/message_queue.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/mutex_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/named_condition_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/named_mutex_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/named_recursive_mutex_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/named_semaphore_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/named_upgradable_mutex.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/node_allocator_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/node_pool_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/null_index_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/private_adaptive_pool_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/private_node_allocator_test.vcproj | 1
branches/bcbboost/libs/interprocess/proj/vc7ide/recursive_mutex_test.vcproj | 1
branches/bcbboost/libs/interprocess/proj/vc7ide/semaphore_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mappable_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/shared_ptr_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/slist_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/string_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/tree_test.vcproj | 264 ++--
branches/bcbboost/libs/interprocess/proj/vc7ide/unique_ptr_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/upgradable_mutex.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/user_buffer_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/vector_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/vectorstream_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_mapping_test.vcproj | 2
branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_test.vcproj | 2
branches/bcbboost/libs/interprocess/test/check_equal_containers.hpp | 2
branches/bcbboost/libs/interprocess/test/memory_algorithm_test_template.hpp | 501 ++++-----
branches/bcbboost/libs/interprocess/test/node_pool_test.cpp | 11
branches/bcbboost/libs/interprocess/test/shared_ptr_test.cpp | 1
branches/bcbboost/libs/interprocess/test/unique_ptr_test.cpp | 13
branches/bcbboost/libs/intrusive/doc/Jamfile.v2 | 16
branches/bcbboost/libs/intrusive/doc/intrusive.qbk | 773 +++++++++-----
branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits.cpp | 12
branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits2.cpp | 6
branches/bcbboost/libs/intrusive/example/doc_assoc_optimized_code.cpp | 76
branches/bcbboost/libs/intrusive/example/doc_auto_unlink.cpp | 33
branches/bcbboost/libs/intrusive/example/doc_clone_from.cpp | 24
branches/bcbboost/libs/intrusive/example/doc_entity.cpp | 27
branches/bcbboost/libs/intrusive/example/doc_erasing_and_disposing.cpp | 17
branches/bcbboost/libs/intrusive/example/doc_how_to_use.cpp | 47
branches/bcbboost/libs/intrusive/example/doc_iterator_from_value.cpp | 59
branches/bcbboost/libs/intrusive/example/doc_list.cpp | 50
branches/bcbboost/libs/intrusive/example/doc_offset_ptr.cpp | 103 +
branches/bcbboost/libs/intrusive/example/doc_set.cpp | 61
branches/bcbboost/libs/intrusive/example/doc_slist.cpp | 49
branches/bcbboost/libs/intrusive/example/doc_unordered_set.cpp | 75
branches/bcbboost/libs/intrusive/example/doc_value_traits.cpp | 15
branches/bcbboost/libs/intrusive/example/doc_window.cpp | 12
branches/bcbboost/libs/intrusive/perf/perf_list.cpp | 103 +
branches/bcbboost/libs/intrusive/proj/vc7ide/Intrusive.sln | 198 ++-
branches/bcbboost/libs/intrusive/proj/vc7ide/_intrusivelib/_intrusivelib.vcproj | 41
branches/bcbboost/libs/intrusive/proj/vc7ide/list/list.vcproj | 5
branches/bcbboost/libs/intrusive/proj/vc7ide/multiset/multiset.vcproj | 2
branches/bcbboost/libs/intrusive/test/common_functors.hpp | 14
branches/bcbboost/libs/intrusive/test/itestvalue.hpp | 323 ++---
branches/bcbboost/libs/intrusive/test/list_test.cpp | 221 ++-
branches/bcbboost/libs/intrusive/test/multiset_test.cpp | 226 ++-
branches/bcbboost/libs/intrusive/test/set_test.cpp | 215 ++-
branches/bcbboost/libs/intrusive/test/slist_test.cpp | 208 ++-
branches/bcbboost/libs/intrusive/test/smart_ptr.hpp | 93
branches/bcbboost/libs/intrusive/test/test_container.hpp | 17
branches/bcbboost/libs/intrusive/test/unordered_multiset_test.cpp | 284 ++--
branches/bcbboost/libs/intrusive/test/unordered_set_test.cpp | 277 ++--
branches/bcbboost/libs/system/test/error_code_user_test.cpp | 33
branches/bcbboost/more/formal_review_schedule.html | 15
branches/bcbboost/tools/jam/src/execunix.c | 12
267 files changed, 14849 insertions(+), 11763 deletions(-)
Modified: branches/bcbboost/boost/config/compiler/gcc.hpp
==============================================================================
--- branches/bcbboost/boost/config/compiler/gcc.hpp (original)
+++ branches/bcbboost/boost/config/compiler/gcc.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -43,6 +43,10 @@
# define BOOST_FUNCTION_SCOPE_USING_DECLARATION_BREAKS_ADL
# define BOOST_NO_IS_ABSTRACT
#elif __GNUC__ == 3
+# if defined (__PATHSCALE__)
+# define BOOST_NO_TWO_PHASE_NAME_LOOKUP
+# define BOOST_NO_IS_ABSTRACT
+# endif
//
// gcc-3.x problems:
//
Modified: branches/bcbboost/boost/filesystem/convenience.hpp
==============================================================================
--- branches/bcbboost/boost/filesystem/convenience.hpp (original)
+++ branches/bcbboost/boost/filesystem/convenience.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -45,8 +45,7 @@
if ( !ph.empty() && !is_directory(ph) )
boost::throw_exception( basic_filesystem_error<Path>(
"boost::filesystem::create_directories", ph,
- boost::system::make_error_code(
- boost::system::posix::file_exists ) ) );
+ make_error_code( boost::system::posix::file_exists ) ) );
return false;
}
Modified: branches/bcbboost/boost/interprocess/allocators/allocation_type.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/allocation_type.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/allocation_type.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -32,7 +32,8 @@
// expand_or_new = allocate_new | expand_both,
shrink_in_place_v = 0x08,
nothrow_allocation_v = 0x10,
- zero_memory_v = 0x20
+ zero_memory_v = 0x20,
+ try_shrink_in_place_v = 0x40
};
typedef int allocation_type;
@@ -41,6 +42,7 @@
static const allocation_type expand_fwd = (allocation_type)expand_fwd_v;
static const allocation_type expand_bwd = (allocation_type)expand_bwd_v;
static const allocation_type shrink_in_place = (allocation_type)shrink_in_place_v;
+static const allocation_type try_shrink_in_place= (allocation_type)try_shrink_in_place_v;
static const allocation_type nothrow_allocation = (allocation_type)nothrow_allocation_v;
static const allocation_type zero_memory = (allocation_type)zero_memory_v;
Modified: branches/bcbboost/boost/interprocess/allocators/allocator.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/allocator.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/allocator.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -201,11 +201,8 @@
//!preferred_elements. The number of actually allocated elements is
//!will be assigned to received_size. Memory allocated with this function
//!must be deallocated only with deallocate_one().
- multiallocation_iterator allocate_individual(std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements)
- {
- return this->allocate_many
- (1, min_elements, preferred_elements, received_elements);
- }
+ multiallocation_iterator allocate_individual(std::size_t num_elements)
+ { return this->allocate_many(1, num_elements); }
/// @endcond
@@ -223,11 +220,10 @@
//!preferred_elements. The number of actually allocated elements is
//!will be assigned to received_size. The elements must be deallocated
//!with deallocate(...)
- multiallocation_iterator allocate_many(size_type elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements)
+ multiallocation_iterator allocate_many(size_type elem_size, std::size_t num_elements)
{
return multiallocation_iterator
- (mp_mngr->allocate_many
- (sizeof(T)*elem_size, min_elements, preferred_elements, received_elements));
+ (mp_mngr->allocate_many(sizeof(T)*elem_size, num_elements));
}
//!Allocates n_elements elements, each one of size elem_sizes[i]in a
Modified: branches/bcbboost/boost/interprocess/allocators/cached_node_allocator.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/cached_node_allocator.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/cached_node_allocator.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -30,22 +30,20 @@
#include <stdio.h>
#include <cstddef>
-/*!\file
- Describes cached_cached_node_allocator pooled shared memory STL compatible allocator
-*/
+//!\file
+//!Describes cached_cached_node_allocator pooled shared memory STL compatible allocator
namespace boost {
-
namespace interprocess {
-/*!An STL node allocator that uses a segment manager as memory
- source. The internal pointer type will of the same type (raw, smart) as
- "typename SegmentManager::void_pointer" type. This allows
- placing the allocator in shared memory, memory mapped-files, etc...
- This node allocator shares a segregated storage between all instances of
- cached_node_allocator with equal sizeof(T) placed in the same fixed size
- memory segment. But also caches some nodes privately to
- avoid some synchronization overhead.*/
+//!An STL node allocator that uses a segment manager as memory
+//!source. The internal pointer type will of the same type (raw, smart) as
+//!"typename SegmentManager::void_pointer" type. This allows
+//!placing the allocator in shared memory, memory mapped-files, etc...
+//!This node allocator shares a segregated storage between all instances of
+//!cached_node_allocator with equal sizeof(T) placed in the same fixed size
+//!memory segment. But also caches some nodes privately to
+//!avoid some synchronization overhead.
template<class T, class SegmentManager, std::size_t NodesPerChunk>
class cached_node_allocator
{
@@ -97,30 +95,30 @@
cached_node_allocator& operator=
(const cached_node_allocator<T2, SegmentManager2, N2>&);
- /*!Not assignable from other cached_node_allocator*/
+ //!Not assignable from other cached_node_allocator
cached_node_allocator& operator=(const cached_node_allocator&);
/// @endcond
public:
- /*!Constructor from a segment manager. If not present, constructs
- a node pool. Increments the reference count of the node pool.
- Can throw boost::interprocess::bad_alloc*/
+ //!Constructor from a segment manager. If not present, constructs
+ //!a node pool. Increments the reference count of the node pool.
+ //!Can throw boost::interprocess::bad_alloc
cached_node_allocator(segment_manager *segment_mngr,
std::size_t max_cached_nodes = DEFAULT_MAX_CACHED_NODES)
: mp_node_pool(priv_get_or_create(segment_mngr)),
m_max_cached_nodes(max_cached_nodes)
{}
- /*!Copy constructor from other cached_node_allocator. Increments the
- reference count of the associated node pool. Never throws*/
+ //!Copy constructor from other cached_node_allocator. Increments the
+ //!reference count of the associated node pool. Never throws
cached_node_allocator(const cached_node_allocator &other)
: mp_node_pool(other.get_node_pool()),
m_max_cached_nodes(other.get_max_cached_nodes())
{ mp_node_pool->inc_ref_count(); }
- /*!Copy constructor from related cached_node_allocator. If not present, constructs
- a node pool. Increments the reference count of the associated node pool.
- Can throw boost::interprocess::bad_alloc*/
+ //!Copy constructor from related cached_node_allocator. If not present, constructs
+ //!a node pool. Increments the reference count of the associated node pool.
+ //!Can throw boost::interprocess::bad_alloc
template<class T2>
cached_node_allocator
(const cached_node_allocator<T2, SegmentManager, NodesPerChunk> &other)
@@ -128,31 +126,34 @@
m_max_cached_nodes(other.get_max_cached_nodes())
{ }
- /*!Destructor, removes node_pool_t from memory
- if its reference count reaches to zero. Never throws*/
+ //!Destructor, removes node_pool_t from memory
+ //!if its reference count reaches to zero. Never throws
~cached_node_allocator()
{
priv_deallocate_all_cached_nodes();
priv_destroy_if_last_link();
}
- /*!Returns a pointer to the node pool. Never throws*/
+ //!Returns a pointer to the node pool.
+ //!Never throws
node_pool_t* get_node_pool() const
{ return detail::get_pointer(mp_node_pool); }
- /*!Returns the segment manager. Never throws*/
+ //!Returns the segment manager.
+ //!Never throws
segment_manager* get_segment_manager()const
{ return mp_node_pool->get_segment_manager(); }
- /*!Sets the new max cached nodes value. This can provoke deallocations
- if "newmax" is less than current cached nodes. Never throws*/
+ //!Sets the new max cached nodes value. This can provoke deallocations
+ //!if "newmax" is less than current cached nodes. Never throws
void set_max_cached_nodes(std::size_t newmax)
{
m_max_cached_nodes = newmax;
priv_deallocate_remaining_nodes();
}
- /*!Returns the max cached nodes parameter. Never throws*/
+ //!Returns the max cached nodes parameter.
+ //!Never throws
std::size_t get_max_cached_nodes() const
{ return m_max_cached_nodes; }
@@ -160,8 +161,8 @@
size_type max_size() const
{ return this->get_segment_manager()->get_size()/sizeof(value_type); }
- /*!Allocate memory for an array of count elements.
- Throws boost::interprocess::bad_alloc if there is no enough memory*/
+ //!Allocate memory for an array of count elements.
+ //!Throws boost::interprocess::bad_alloc if there is no enough memory
pointer allocate(size_type count, cvoid_pointer hint = 0)
{
(void)hint;
@@ -186,7 +187,8 @@
return pointer(static_cast<T*>(ret));
}
- /*!Deallocate allocated memory. Never throws*/
+ //!Deallocate allocated memory.
+ //!Never throws
void deallocate(const pointer &ptr, size_type count)
{
typedef detail::shared_node_pool
@@ -208,8 +210,8 @@
}
}
- /*!Swaps allocators. Does not throw. If each allocator is placed in a
- different shared memory segments, the result is undefined.*/
+ //!Swaps allocators. Does not throw. If each allocator is placed in a
+ //!different shared memory segments, the result is undefined.
friend void swap(self_t &alloc1, self_t &alloc2)
{
detail::do_swap(alloc1.mp_node_pool, alloc2.mp_node_pool);
@@ -233,7 +235,8 @@
pointer address(reference value) const
{ return pointer(boost::addressof(value)); }
- /*!Returns address of non mutable object. Never throws*/
+ //!Returns address of non mutable object.
+ //!Never throws
const_pointer address(const_reference value) const
{ return const_pointer(boost::addressof(value)); }
@@ -250,15 +253,15 @@
/// @cond
private:
- /*!Object function that creates the node allocator if it is not created and
- increments reference count if it is already created*/
+ //!Object function that creates the node allocator if it is not created and
+ //!increments reference count if it is already created
struct get_or_create_func
{
typedef detail::shared_node_pool
<SegmentManager, mutex_type, sizeof(T), NodesPerChunk> node_pool_t;
- /*!This connects or constructs the unique instance of node_pool_t
- Can throw boost::interprocess::bad_alloc*/
+ //!This connects or constructs the unique instance of node_pool_t
+ //!Can throw boost::interprocess::bad_alloc
void operator()()
{
//Find or create the node_pool_t
@@ -269,18 +272,21 @@
mp_node_pool->inc_ref_count();
}
- /*!Constructor. Initializes function object parameters*/
+ //!Constructor. Initializes function
+ //!object parameters
get_or_create_func(segment_manager *hdr) : mp_named_alloc(hdr){}
node_pool_t *mp_node_pool;
segment_manager *mp_named_alloc;
};
- /*!Frees all cached nodes. Never throws*/
+ //!Frees all cached nodes.
+ //!Never throws
void priv_deallocate_all_cached_nodes()
{ mp_node_pool->deallocate_nodes(m_cached_nodes); }
- /*!Frees all cached nodes at once. Never throws*/
+ //!Frees all cached nodes at once.
+ //!Never throws
void priv_deallocate_remaining_nodes()
{
if(m_cached_nodes.size() > m_max_cached_nodes){
@@ -288,12 +294,13 @@
}
}
- /*!Frees n cached nodes at once. Never throws*/
+ //!Frees n cached nodes at once.
+ //!Never throws
void priv_deallocate_n_nodes(std::size_t n)
{ mp_node_pool->deallocate_nodes(m_cached_nodes, n); }
- /*!Initialization function, creates an executes atomically the
- initialization object functions. Can throw boost::interprocess::bad_alloc*/
+ //!Initialization function, creates an executes atomically the
+ //!initialization object functions. Can throw boost::interprocess::bad_alloc
node_pool_t *priv_get_or_create(segment_manager *named_alloc)
{
get_or_create_func func(named_alloc);
@@ -301,16 +308,16 @@
return func.mp_node_pool;
}
- /*!Object function that decrements the reference count. If the count
- reaches to zero destroys the node allocator from memory.
- Never throws*/
+ //!Object function that decrements the reference count. If the count
+ //!reaches to zero destroys the node allocator from memory.
+ //!Never throws
struct destroy_if_last_link_func
{
typedef detail::shared_node_pool
<SegmentManager, mutex_type,sizeof(T), NodesPerChunk> node_pool_t;
- /*!Decrements reference count and destroys the object if there is no
- more attached allocators. Never throws*/
+ //!Decrements reference count and destroys the object if there is no
+ //!more attached allocators. Never throws
void operator()()
{
//If not the last link return
@@ -320,7 +327,8 @@
mp_named_alloc->template destroy<node_pool_t>(unique_instance);
}
- /*!Constructor. Initializes function object parameters*/
+ //!Constructor. Initializes function object
+ //!parameters
destroy_if_last_link_func(segment_manager *nhdr,
node_pool_t *phdr)
: mp_named_alloc(nhdr), mp_node_pool(phdr){}
@@ -329,8 +337,8 @@
node_pool_t *mp_node_pool;
};
- /*!Destruction function, initializes and executes destruction function
- object. Never throws*/
+ //!Destruction function, initializes and executes destruction function
+ //!object. Never throws
void priv_destroy_if_last_link()
{
typedef detail::shared_node_pool
@@ -349,13 +357,15 @@
/// @endcond
};
-/*!Equality test for same type of cached_node_allocator*/
+//!Equality test for same type of
+//!cached_node_allocator
template<class T, class S, std::size_t NodesPerChunk> inline
bool operator==(const cached_node_allocator<T, S, NodesPerChunk> &alloc1,
const cached_node_allocator<T, S, NodesPerChunk> &alloc2)
{ return alloc1.get_node_pool() == alloc2.get_node_pool(); }
-/*!Inequality test for same type of cached_node_allocator*/
+//!Inequality test for same type of
+//!cached_node_allocator
template<class T, class S, std::size_t NodesPerChunk> inline
bool operator!=(const cached_node_allocator<T, S, NodesPerChunk> &alloc1,
const cached_node_allocator<T, S, NodesPerChunk> &alloc2)
Modified: branches/bcbboost/boost/interprocess/allocators/detail/adaptive_node_pool.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/detail/adaptive_node_pool.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/detail/adaptive_node_pool.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,8 +13,6 @@
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
-# pragma warning (disable : 4503)
-
#endif
#include <boost/interprocess/detail/config_begin.hpp>
@@ -34,9 +32,8 @@
#include <cassert>
#include <assert.h>
-/*!\file
- Describes the real adaptive pool shared by many Interprocess pool allocators
-*/
+//!\file
+//!Describes the real adaptive pool shared by many Interprocess pool allocators
namespace boost {
namespace interprocess {
@@ -62,8 +59,8 @@
private:
//This hook will be used to chain the memory chunks
- typedef boost::intrusive::list_base_hook
- < boost::intrusive::tag, boost::intrusive::normal_link, void_pointer> list_hook_t;
+ typedef typename bi::make_list_base_hook
+ <bi::void_pointer<void_pointer>, bi::link_mode<bi::normal_link> >::type list_hook_t;
struct chunk_info_t
: public list_hook_t
@@ -71,9 +68,7 @@
//An intrusive list of free node from this chunk
free_nodes_t free_nodes;
};
-
- typedef boost::intrusive::list
- <typename list_hook_t::template value_traits<chunk_info_t> > chunk_list_t;
+ typedef typename bi::make_list<chunk_info_t, bi::base_hook<list_hook_t> >::type chunk_list_t;
public:
//!Segment manager typedef
@@ -324,7 +319,7 @@
//We put the node at the beginning of the free node list
node_t * to_deallocate = static_cast<node_t*>(pElem);
chunk_info->free_nodes.push_front(*to_deallocate);
- chunk_iterator this_chunk(chunk_list_t::iterator_to(*chunk_info));
+ chunk_iterator this_chunk(chunk_list_t::s_iterator_to(*chunk_info));
chunk_iterator next_chunk(this_chunk);
++next_chunk;
@@ -343,7 +338,7 @@
}
//Update m_first_free_chunk if the moved chunk crosses the empty boundary
else if(this_chunk->free_nodes.size() == 1){
- m_first_free_chunk = chunk_list_t::iterator_to(*chunk_info);
+ m_first_free_chunk = chunk_list_t::s_iterator_to(*chunk_info);
}
//Now move the chunk to the new position
m_chunklist.erase(this_chunk);
Modified: branches/bcbboost/boost/interprocess/allocators/detail/node_pool.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/detail/node_pool.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/detail/node_pool.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,7 +13,6 @@
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
-# pragma warning (disable : 4503)
#endif
#include <boost/interprocess/detail/config_begin.hpp>
@@ -31,9 +30,8 @@
#include <algorithm>
#include <assert.h>
-/*!\file
- Describes the real adaptive pool shared by many Interprocess adaptive pool allocators
-*/
+//!\file
+//!Describes the real adaptive pool shared by many Interprocess adaptive pool allocators
namespace boost {
namespace interprocess {
@@ -49,15 +47,14 @@
//A node object will hold node_t when it's not allocated
public:
- typedef typename SegmentManagerBase::void_pointer void_pointer;
- typedef typename node_slist<void_pointer>::slist_hook_t slist_hook_t;
- typedef typename node_slist<void_pointer>::node_t node_t;
- typedef typename node_slist<void_pointer>::node_slist_t free_nodes_t;
+ typedef typename SegmentManagerBase::void_pointer void_pointer;
+ typedef typename node_slist<void_pointer>::slist_hook_t slist_hook_t;
+ typedef typename node_slist<void_pointer>::node_t node_t;
+ typedef typename node_slist<void_pointer>::node_slist_t free_nodes_t;
private:
- typedef boost::intrusive::slist
- <typename slist_hook_t::template value_traits<node_t>, false > chunkslist_t;
-
+ typedef typename bi::make_slist < node_t, bi::base_hook<slist_hook_t>
+ , bi::constant_time_size<false> >::type chunkslist_t;
public:
//!Segment manager typedef
Modified: branches/bcbboost/boost/interprocess/allocators/detail/node_tools.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/detail/node_tools.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/detail/node_tools.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,7 +13,6 @@
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
-# pragma warning (disable : 4503)
#endif
#include <boost/interprocess/detail/config_begin.hpp>
@@ -30,16 +29,15 @@
struct node_slist
{
//This hook will be used to chain the individual nodes
- typedef boost::intrusive::slist_base_hook
- <boost::intrusive::tag, boost::intrusive::normal_link, VoidPointer> slist_hook_t;
+ typedef typename bi::make_slist_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type slist_hook_t;
//A node object will hold node_t when it's not allocated
struct node_t
: public slist_hook_t
{};
- typedef boost::intrusive::slist
- <typename slist_hook_t::template value_traits<node_t> > node_slist_t;
+ typedef typename bi::make_slist<node_t, bi::base_hook<slist_hook_t> >::type node_slist_t;
};
} //namespace detail {
Modified: branches/bcbboost/boost/interprocess/allocators/private_adaptive_pool.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/private_adaptive_pool.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/private_adaptive_pool.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -158,7 +158,8 @@
pointer address(reference value) const
{ return pointer(boost::addressof(value)); }
- /*!Returns address of non mutable object. Never throws*/
+ //!Returns address of non mutable object.
+ //!Never throws
const_pointer address(const_reference value) const
{ return const_pointer(boost::addressof(value)); }
Modified: branches/bcbboost/boost/interprocess/allocators/private_node_allocator.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/allocators/private_node_allocator.hpp (original)
+++ branches/bcbboost/boost/interprocess/allocators/private_node_allocator.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -156,7 +156,8 @@
pointer address(reference value) const
{ return pointer(boost::addressof(value)); }
- /*!Returns address of non mutable object. Never throws*/
+ //!Returns address of non mutable object.
+ //!Never throws
const_pointer address(const_reference value) const
{ return const_pointer(boost::addressof(value)); }
Modified: branches/bcbboost/boost/interprocess/containers/deque.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/deque.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/deque.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -85,35 +85,24 @@
// exception safety easier.
template <class T, class Alloc>
class deque_base
- : public Alloc::template rebind<T>::other,
- public Alloc::template rebind<typename Alloc::pointer>::other
{
- public:
- typedef typename Alloc::value_type val_alloc_val;
- typedef typename Alloc::pointer val_alloc_ptr;
- typedef typename Alloc::const_pointer val_alloc_cptr;
- typedef typename Alloc::reference val_alloc_ref;
- typedef typename Alloc::const_reference val_alloc_cref;
- typedef typename Alloc::value_type val_alloc_diff;
+ public:
+ typedef typename Alloc::value_type val_alloc_val;
+ typedef typename Alloc::pointer val_alloc_ptr;
+ typedef typename Alloc::const_pointer val_alloc_cptr;
+ typedef typename Alloc::reference val_alloc_ref;
+ typedef typename Alloc::const_reference val_alloc_cref;
+ typedef typename Alloc::value_type val_alloc_diff;
typedef typename Alloc::template rebind
- <typename Alloc::pointer>::other ptr_alloc;
- typedef typename ptr_alloc::value_type ptr_alloc_val;
- typedef typename ptr_alloc::pointer ptr_alloc_ptr;
- typedef typename ptr_alloc::const_pointer ptr_alloc_cptr;
- typedef typename ptr_alloc::reference ptr_alloc_ref;
- typedef typename ptr_alloc::const_reference ptr_alloc_cref;
+ <typename Alloc::pointer>::other ptr_alloc_t;
+ typedef typename ptr_alloc_t::value_type ptr_alloc_val;
+ typedef typename ptr_alloc_t::pointer ptr_alloc_ptr;
+ typedef typename ptr_alloc_t::const_pointer ptr_alloc_cptr;
+ typedef typename ptr_alloc_t::reference ptr_alloc_ref;
+ typedef typename ptr_alloc_t::const_reference ptr_alloc_cref;
typedef typename Alloc::template
- rebind<T>::other allocator_type;
- typedef allocator_type stored_allocator_type;
-
- allocator_type get_allocator() const
- { return *this; }
-
- const stored_allocator_type &get_stored_allocator() const
- { return *this; }
-
- stored_allocator_type &get_stored_allocator()
- { return *this; }
+ rebind<T>::other allocator_type;
+ typedef allocator_type stored_allocator_type;
protected:
enum { trivial_dctr_after_move = boost::has_trivial_destructor<val_alloc_val>::value };
@@ -122,16 +111,16 @@
rebind<typename Alloc::pointer>::other map_allocator_type;
val_alloc_ptr priv_allocate_node()
- { return this->allocator_type::allocate(deque_buf_size(sizeof(T))); }
+ { return this->alloc().allocate(deque_buf_size(sizeof(T))); }
void priv_deallocate_node(val_alloc_ptr p)
- { this->allocator_type::deallocate(p, deque_buf_size(sizeof(T))); }
+ { this->alloc().deallocate(p, deque_buf_size(sizeof(T))); }
ptr_alloc_ptr priv_allocate_map(std::size_t n)
- { return this->map_allocator_type::allocate(n); }
+ { return this->ptr_alloc().allocate(n); }
void priv_deallocate_map(ptr_alloc_ptr p, std::size_t n)
- { this->map_allocator_type::deallocate(p, n); }
+ { this->ptr_alloc().deallocate(p, n); }
public:
// Class invariants:
@@ -302,7 +291,7 @@
{ return x + n; }
};
- //Vector iterator
+ //Deque iterator
class iterator : public const_iterator
{
public:
@@ -368,75 +357,48 @@
};
deque_base(const allocator_type& a, std::size_t num_elements)
- : allocator_type(a), map_allocator_type(a),
- m_map(0), m_map_size(0),
- m_start(), m_finish()
- { this->priv_initialize_map(num_elements); }
+ : members_(a)
+ { this->priv_initialize_map(num_elements); }
deque_base(const allocator_type& a)
- : allocator_type(a), map_allocator_type(a),
- m_map(0), m_map_size(0), m_start(), m_finish() {}
-
- #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
- deque_base(const detail::moved_object<deque_base> &md)
- : allocator_type(md.get()), map_allocator_type(md.get()),
- m_map(md.get().m_map), m_map_size(md.get().m_map_size),
- m_start(md.get().m_start), m_finish(md.get().m_finish)
- {
- m_map = 0;
- m_map_size = 0;
- m_start = iterator();
- m_finish = iterator();
- }
- #else
- deque_base(deque_base &&md)
- : allocator_type(md), map_allocator_type(md),
- m_map(md.m_map), m_map_size(md.m_map_size),
- m_start(md.m_start), m_finish(md.m_finish)
- {
- m_map = 0;
- m_map_size = 0;
- m_start = iterator();
- m_finish = iterator();
- }
- #endif
+ : members_(a)
+ {}
~deque_base()
{
- if (this->m_map) {
- this->priv_destroy_nodes(this->m_start.m_node, this->m_finish.m_node + 1);
- this->priv_deallocate_map(this->m_map, this->m_map_size);
+ if (this->members_.m_map) {
+ this->priv_destroy_nodes(this->members_.m_start.m_node, this->members_.m_finish.m_node + 1);
+ this->priv_deallocate_map(this->members_.m_map, this->members_.m_map_size);
}
}
- protected:
+ protected:
void priv_initialize_map(std::size_t num_elements)
{
std::size_t num_nodes = num_elements / deque_buf_size(sizeof(T)) + 1;
- this->m_map_size = max_value((std::size_t) InitialMapSize, num_nodes + 2);
- this->m_map = this->priv_allocate_map(this->m_map_size);
+ this->members_.m_map_size = max_value((std::size_t) InitialMapSize, num_nodes + 2);
+ this->members_.m_map = this->priv_allocate_map(this->members_.m_map_size);
- ptr_alloc_ptr nstart = this->m_map + (this->m_map_size - num_nodes) / 2;
+ ptr_alloc_ptr nstart = this->members_.m_map + (this->members_.m_map_size - num_nodes) / 2;
ptr_alloc_ptr nfinish = nstart + num_nodes;
BOOST_TRY {
this->priv_create_nodes(nstart, nfinish);
}
BOOST_CATCH(...){
- this->priv_deallocate_map(this->m_map, this->m_map_size);
- this->m_map = 0;
- this->m_map_size = 0;
+ this->priv_deallocate_map(this->members_.m_map, this->members_.m_map_size);
+ this->members_.m_map = 0;
+ this->members_.m_map_size = 0;
BOOST_RETHROW
}
BOOST_CATCH_END
- this->m_start.priv_set_node(nstart);
- this->m_finish.priv_set_node(nfinish - 1);
- this->m_start.m_cur = this->m_start.m_first;
- this->m_finish.m_cur = this->m_finish.m_first +
+ this->members_.m_start.priv_set_node(nstart);
+ this->members_.m_finish.priv_set_node(nfinish - 1);
+ this->members_.m_start.m_cur = this->members_.m_start.m_first;
+ this->members_.m_finish.m_cur = this->members_.m_finish.m_first +
num_elements % deque_buf_size(sizeof(T));
-
}
void priv_create_nodes(ptr_alloc_ptr nstart, ptr_alloc_ptr nfinish)
@@ -461,11 +423,34 @@
enum { InitialMapSize = 8 };
- protected:
- ptr_alloc_ptr m_map;
- std::size_t m_map_size;
- iterator m_start;
- iterator m_finish;
+ protected:
+ struct members_holder
+ : public ptr_alloc_t
+ , public allocator_type
+ {
+ members_holder(const allocator_type &a)
+ : map_allocator_type(a), allocator_type(a)
+ , m_map(0), m_map_size(0)
+ , m_start(), m_finish()
+ {}
+
+ ptr_alloc_ptr m_map;
+ std::size_t m_map_size;
+ iterator m_start;
+ iterator m_finish;
+ } members_;
+
+ ptr_alloc_t &ptr_alloc()
+ { return members_; }
+
+ const ptr_alloc_t &ptr_alloc() const
+ { return members_; }
+
+ allocator_type &alloc()
+ { return members_; }
+
+ const allocator_type &alloc() const
+ { return members_; }
};
/// @endcond
@@ -483,12 +468,12 @@
typedef typename Alloc::reference val_alloc_ref;
typedef typename Alloc::const_reference val_alloc_cref;
typedef typename Alloc::template
- rebind<val_alloc_ptr>::other ptr_alloc;
- typedef typename ptr_alloc::value_type ptr_alloc_val;
- typedef typename ptr_alloc::pointer ptr_alloc_ptr;
- typedef typename ptr_alloc::const_pointer ptr_alloc_cptr;
- typedef typename ptr_alloc::reference ptr_alloc_ref;
- typedef typename ptr_alloc::const_reference ptr_alloc_cref;
+ rebind<val_alloc_ptr>::other ptr_alloc_t;
+ typedef typename ptr_alloc_t::value_type ptr_alloc_val;
+ typedef typename ptr_alloc_t::pointer ptr_alloc_ptr;
+ typedef typename ptr_alloc_t::const_pointer ptr_alloc_cptr;
+ typedef typename ptr_alloc_t::reference ptr_alloc_ref;
+ typedef typename ptr_alloc_t::const_reference ptr_alloc_cref;
typedef T value_type;
typedef val_alloc_ptr pointer;
@@ -499,7 +484,7 @@
typedef std::ptrdiff_t difference_type;
typedef typename Base::allocator_type allocator_type;
- allocator_type get_allocator() const { return Base::get_allocator(); }
+ allocator_type get_allocator() const { return Base::alloc(); }
public: // Iterators
typedef typename Base::iterator iterator;
@@ -513,52 +498,38 @@
typedef ptr_alloc_ptr index_pointer;
static std::size_t s_buffer_size()
{ return deque_buf_size(sizeof(T)); }
-
- protected:
- using Base::priv_initialize_map;
- using Base::priv_create_nodes;
- using Base::priv_destroy_nodes;
- using Base::priv_allocate_node;
- using Base::priv_deallocate_node;
- using Base::priv_allocate_map;
- using Base::priv_deallocate_map;
-
- using Base::m_map;
- using Base::m_map_size;
- using Base::m_start;
- using Base::m_finish;
/// @endcond
public: // Basic accessors
iterator begin()
- { return this->m_start; }
+ { return this->members_.m_start; }
iterator end()
- { return this->m_finish; }
+ { return this->members_.m_finish; }
const_iterator begin() const
- { return this->m_start; }
+ { return this->members_.m_start; }
const_iterator end() const
- { return this->m_finish; }
+ { return this->members_.m_finish; }
reverse_iterator rbegin()
- { return reverse_iterator(this->m_finish); }
+ { return reverse_iterator(this->members_.m_finish); }
reverse_iterator rend()
- { return reverse_iterator(this->m_start); }
+ { return reverse_iterator(this->members_.m_start); }
const_reverse_iterator rbegin() const
- { return const_reverse_iterator(this->m_finish); }
+ { return const_reverse_iterator(this->members_.m_finish); }
const_reverse_iterator rend() const
- { return const_reverse_iterator(this->m_start); }
+ { return const_reverse_iterator(this->members_.m_start); }
reference operator[](size_type n)
- { return this->m_start[difference_type(n)]; }
+ { return this->members_.m_start[difference_type(n)]; }
const_reference operator[](size_type n) const
- { return this->m_start[difference_type(n)]; }
+ { return this->members_.m_start[difference_type(n)]; }
void priv_range_check(size_type n) const
{ if (n >= this->size()) BOOST_RETHROW std::out_of_range("deque"); }
@@ -569,44 +540,45 @@
const_reference at(size_type n) const
{ this->priv_range_check(n); return (*this)[n]; }
- reference front() { return *this->m_start; }
+ reference front() { return *this->members_.m_start; }
reference back()
{
- iterator tmp = this->m_finish;
+ iterator tmp = this->members_.m_finish;
--tmp;
return *tmp;
}
const_reference front() const
- { return *this->m_start; }
+ { return *this->members_.m_start; }
const_reference back() const
- { const_iterator tmp = this->m_finish; --tmp; return *tmp; }
+ { const_iterator tmp = this->members_.m_finish; --tmp; return *tmp; }
size_type size() const
- { return this->m_finish - this->m_start; }
+ { return this->members_.m_finish - this->members_.m_start; }
size_type max_size() const
- { return allocator_type::max_size(); }
+ { return this->alloc().max_size(); }
bool empty() const
- { return this->m_finish == this->m_start; }
+ { return this->members_.m_finish == this->members_.m_start; }
explicit deque(const allocator_type& a = allocator_type())
: Base(a, 0) {}
- deque(const deque& x) : Base(x.get_allocator(), x.size())
- { std::uninitialized_copy(x.begin(), x.end(), this->m_start); }
+ deque(const deque& x)
+ : Base(x.alloc(), x.size())
+ { std::uninitialized_copy(x.begin(), x.end(), this->members_.m_start); }
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
deque(const detail::moved_object<deque> &mx)
- : Base(move((Base&)mx.get()))
- {}
+ : Base(mx.get())
+ { this->swap(mx.get()); }
#else
- deque(deque &&mx)
- : Base(move((Base&)mx))
- {}
+ deque(deque &&x)
+ : Base(x))
+ { this->swap(x); }
#endif
deque(size_type n, const value_type& value,
@@ -628,18 +600,18 @@
}
~deque()
- { priv_destroy_range(this->m_start, this->m_finish); }
+ { priv_destroy_range(this->members_.m_start, this->members_.m_finish); }
deque& operator= (const deque& x)
{
const size_type len = size();
if (&x != this) {
if (len >= x.size())
- this->erase(std::copy(x.begin(), x.end(), this->m_start), this->m_finish);
+ this->erase(std::copy(x.begin(), x.end(), this->members_.m_start), this->members_.m_finish);
else {
const_iterator mid = x.begin() + difference_type(len);
- std::copy(x.begin(), mid, this->m_start);
- this->insert(this->m_finish, mid, x.end());
+ std::copy(x.begin(), mid, this->members_.m_start);
+ this->insert(this->members_.m_finish, mid, x.end());
}
}
return *this;
@@ -655,10 +627,10 @@
void swap(deque& x)
{
- std::swap(this->m_start, x.m_start);
- std::swap(this->m_finish, x.m_finish);
- std::swap(this->m_map, x.m_map);
- std::swap(this->m_map_size, x.m_map_size);
+ std::swap(this->members_.m_start, x.members_.m_start);
+ std::swap(this->members_.m_finish, x.members_.m_finish);
+ std::swap(this->members_.m_map, x.members_.m_map);
+ std::swap(this->members_.m_map_size, x.members_.m_map_size);
}
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
@@ -669,9 +641,8 @@
{ this->swap(mx); }
#endif
- void assign(size_type n, const T& val) {
- this->priv_fill_assign(n, val);
- }
+ void assign(size_type n, const T& val)
+ { this->priv_fill_assign(n, val); }
template <class InpIt>
void assign(InpIt first, InpIt last) {
@@ -683,9 +654,9 @@
void push_back(const value_type& t)
{
- if (this->m_finish.m_cur != this->m_finish.m_last - 1) {
- new(detail::get_pointer(this->m_finish.m_cur))value_type(t);
- ++this->m_finish.m_cur;
+ if (this->members_.m_finish.m_cur != this->members_.m_finish.m_last - 1) {
+ new(detail::get_pointer(this->members_.m_finish.m_cur))value_type(t);
+ ++this->members_.m_finish.m_cur;
}
else
this->priv_push_back_aux(t);
@@ -694,9 +665,9 @@
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void push_back(const detail::moved_object<value_type> &mt)
{
- if (this->m_finish.m_cur != this->m_finish.m_last - 1) {
- new(detail::get_pointer(this->m_finish.m_cur))value_type(mt);
- ++this->m_finish.m_cur;
+ if (this->members_.m_finish.m_cur != this->members_.m_finish.m_last - 1) {
+ new(detail::get_pointer(this->members_.m_finish.m_cur))value_type(mt);
+ ++this->members_.m_finish.m_cur;
}
else
this->priv_push_back_aux(mt);
@@ -704,9 +675,9 @@
#else
void push_back(value_type &&mt)
{
- if (this->m_finish.m_cur != this->m_finish.m_last - 1) {
- new(detail::get_pointer(this->m_finish.m_cur))value_type(move(mt));
- ++this->m_finish.m_cur;
+ if (this->members_.m_finish.m_cur != this->members_.m_finish.m_last - 1) {
+ new(detail::get_pointer(this->members_.m_finish.m_cur))value_type(move(mt));
+ ++this->members_.m_finish.m_cur;
}
else
this->priv_push_back_aux(move(mt));
@@ -715,9 +686,9 @@
void push_front(const value_type& t)
{
- if (this->m_start.m_cur != this->m_start.m_first) {
- new(detail::get_pointer(this->m_start.m_cur)- 1)value_type(t);
- --this->m_start.m_cur;
+ if (this->members_.m_start.m_cur != this->members_.m_start.m_first) {
+ new(detail::get_pointer(this->members_.m_start.m_cur)- 1)value_type(t);
+ --this->members_.m_start.m_cur;
}
else
this->priv_push_front_aux(t);
@@ -726,9 +697,9 @@
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void push_front(const detail::moved_object<value_type> &mt)
{
- if (this->m_start.m_cur != this->m_start.m_first) {
- new(detail::get_pointer(this->m_start.m_cur)- 1)value_type(mt);
- --this->m_start.m_cur;
+ if (this->members_.m_start.m_cur != this->members_.m_start.m_first) {
+ new(detail::get_pointer(this->members_.m_start.m_cur)- 1)value_type(mt);
+ --this->members_.m_start.m_cur;
}
else
this->priv_push_front_aux(mt);
@@ -736,9 +707,9 @@
#else
void push_front(value_type &&mt)
{
- if (this->m_start.m_cur != this->m_start.m_first) {
- new(detail::get_pointer(this->m_start.m_cur)- 1)value_type(move(mt));
- --this->m_start.m_cur;
+ if (this->members_.m_start.m_cur != this->members_.m_start.m_first) {
+ new(detail::get_pointer(this->members_.m_start.m_cur)- 1)value_type(move(mt));
+ --this->members_.m_start.m_cur;
}
else
this->priv_push_front_aux(move(mt));
@@ -747,9 +718,9 @@
void pop_back()
{
- if (this->m_finish.m_cur != this->m_finish.m_first) {
- --this->m_finish.m_cur;
- detail::get_pointer(this->m_finish.m_cur)->~value_type();
+ if (this->members_.m_finish.m_cur != this->members_.m_finish.m_first) {
+ --this->members_.m_finish.m_cur;
+ detail::get_pointer(this->members_.m_finish.m_cur)->~value_type();
}
else
this->priv_pop_back_aux();
@@ -757,9 +728,9 @@
void pop_front()
{
- if (this->m_start.m_cur != this->m_start.m_last - 1) {
- detail::get_pointer(this->m_start.m_cur)->~value_type();
- ++this->m_start.m_cur;
+ if (this->members_.m_start.m_cur != this->members_.m_start.m_last - 1) {
+ detail::get_pointer(this->members_.m_start.m_cur)->~value_type();
+ ++this->members_.m_start.m_cur;
}
else
this->priv_pop_front_aux();
@@ -767,13 +738,13 @@
iterator insert(iterator position, const value_type& x)
{
- if (position.m_cur == this->m_start.m_cur) {
+ if (position.m_cur == this->members_.m_start.m_cur) {
this->push_front(x);
- return this->m_start;
+ return this->members_.m_start;
}
- else if (position.m_cur == this->m_finish.m_cur) {
+ else if (position.m_cur == this->members_.m_finish.m_cur) {
this->push_back(x);
- iterator tmp = this->m_finish;
+ iterator tmp = this->members_.m_finish;
--tmp;
return tmp;
}
@@ -785,13 +756,13 @@
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
iterator insert(iterator position, const detail::moved_object<value_type> &mx)
{
- if (position.m_cur == this->m_start.m_cur) {
+ if (position.m_cur == this->members_.m_start.m_cur) {
this->push_front(mx);
- return this->m_start;
+ return this->members_.m_start;
}
- else if (position.m_cur == this->m_finish.m_cur) {
+ else if (position.m_cur == this->members_.m_finish.m_cur) {
this->push_back(mx);
- iterator tmp = this->m_finish;
+ iterator tmp = this->members_.m_finish;
--tmp;
return tmp;
}
@@ -802,13 +773,13 @@
#else
iterator insert(iterator position, value_type &&mx)
{
- if (position.m_cur == this->m_start.m_cur) {
+ if (position.m_cur == this->members_.m_start.m_cur) {
this->push_front(move(mx));
- return this->m_start;
+ return this->members_.m_start;
}
- else if (position.m_cur == this->m_finish.m_cur) {
+ else if (position.m_cur == this->members_.m_finish.m_cur) {
this->push_back(move(mx));
- iterator tmp = this->m_finish;
+ iterator tmp = this->members_.m_finish;
--tmp;
return tmp;
}
@@ -835,16 +806,16 @@
{
const size_type len = size();
if (new_size < len)
- this->erase(this->m_start + new_size, this->m_finish);
+ this->erase(this->members_.m_start + new_size, this->members_.m_finish);
else
- this->insert(this->m_finish, new_size - len, x);
+ this->insert(this->members_.m_finish, new_size - len, x);
}
void resize(size_type new_size)
{
const size_type len = size();
if (new_size < len)
- this->erase(this->m_start + new_size, this->m_finish);
+ this->erase(this->members_.m_start + new_size, this->members_.m_finish);
else{
size_type n = new_size - this->size();
this->priv_reserve_elements_at_back(new_size);
@@ -865,73 +836,73 @@
{
iterator next = pos;
++next;
- difference_type index = pos - this->m_start;
+ difference_type index = pos - this->members_.m_start;
if (size_type(index) < (this->size() >> 1)) {
- std::copy_backward( detail::make_move_iterator(this->m_start)
+ std::copy_backward( detail::make_move_iterator(this->members_.m_start)
, detail::make_move_iterator(pos)
, next);
pop_front();
}
else {
std::copy( detail::make_move_iterator(next)
- , detail::make_move_iterator(this->m_finish)
+ , detail::make_move_iterator(this->members_.m_finish)
, pos);
pop_back();
}
- return this->m_start + index;
+ return this->members_.m_start + index;
}
iterator erase(iterator first, iterator last)
{
- if (first == this->m_start && last == this->m_finish) {
+ if (first == this->members_.m_start && last == this->members_.m_finish) {
this->clear();
- return this->m_finish;
+ return this->members_.m_finish;
}
else {
difference_type n = last - first;
- difference_type elems_before = first - this->m_start;
+ difference_type elems_before = first - this->members_.m_start;
if (elems_before < static_cast<difference_type>(this->size() - n) - elems_before) {
- std::copy_backward( detail::make_move_iterator(this->m_start)
+ std::copy_backward( detail::make_move_iterator(this->members_.m_start)
, detail::make_move_iterator(first)
, last);
- iterator new_start = this->m_start + n;
+ iterator new_start = this->members_.m_start + n;
if(!Base::trivial_dctr_after_move)
- this->priv_destroy_range(this->m_start, new_start);
- this->priv_destroy_nodes(new_start.m_node, this->m_start.m_node);
- this->m_start = new_start;
+ this->priv_destroy_range(this->members_.m_start, new_start);
+ this->priv_destroy_nodes(new_start.m_node, this->members_.m_start.m_node);
+ this->members_.m_start = new_start;
}
else {
std::copy( detail::make_move_iterator(last)
- , detail::make_move_iterator(this->m_finish)
+ , detail::make_move_iterator(this->members_.m_finish)
, first);
- iterator new_finish = this->m_finish - n;
+ iterator new_finish = this->members_.m_finish - n;
if(!Base::trivial_dctr_after_move)
- this->priv_destroy_range(new_finish, this->m_finish);
- this->priv_destroy_nodes(new_finish.m_node + 1, this->m_finish.m_node + 1);
- this->m_finish = new_finish;
+ this->priv_destroy_range(new_finish, this->members_.m_finish);
+ this->priv_destroy_nodes(new_finish.m_node + 1, this->members_.m_finish.m_node + 1);
+ this->members_.m_finish = new_finish;
}
- return this->m_start + elems_before;
+ return this->members_.m_start + elems_before;
}
}
void clear()
{
- for (index_pointer node = this->m_start.m_node + 1;
- node < this->m_finish.m_node;
+ for (index_pointer node = this->members_.m_start.m_node + 1;
+ node < this->members_.m_finish.m_node;
++node) {
this->priv_destroy_range(*node, *node + this->s_buffer_size());
this->priv_deallocate_node(*node);
}
- if (this->m_start.m_node != this->m_finish.m_node) {
- this->priv_destroy_range(this->m_start.m_cur, this->m_start.m_last);
- this->priv_destroy_range(this->m_finish.m_first, this->m_finish.m_cur);
- this->priv_deallocate_node(this->m_finish.m_first);
+ if (this->members_.m_start.m_node != this->members_.m_finish.m_node) {
+ this->priv_destroy_range(this->members_.m_start.m_cur, this->members_.m_start.m_last);
+ this->priv_destroy_range(this->members_.m_finish.m_first, this->members_.m_finish.m_cur);
+ this->priv_deallocate_node(this->members_.m_finish.m_first);
}
else
- this->priv_destroy_range(this->m_start.m_cur, this->m_finish.m_cur);
+ this->priv_destroy_range(this->members_.m_start.m_cur, this->members_.m_finish.m_cur);
- this->m_finish = this->m_start;
+ this->members_.m_finish = this->members_.m_start;
}
/// @cond
@@ -948,26 +919,26 @@
size_type n = 0;
n = std::distance(first, last);
- if (pos.m_cur == this->m_start.m_cur) {
+ if (pos.m_cur == this->members_.m_start.m_cur) {
iterator new_start = this->priv_reserve_elements_at_front(n);
BOOST_TRY{
- boost::interprocess::uninitialized_copy(first, last, new_start);
- this->m_start = new_start;
+ std::uninitialized_copy(first, last, new_start);
+ this->members_.m_start = new_start;
}
BOOST_CATCH(...){
- this->priv_destroy_nodes(new_start.m_node, this->m_start.m_node);
+ this->priv_destroy_nodes(new_start.m_node, this->members_.m_start.m_node);
BOOST_RETHROW
}
BOOST_CATCH_END
}
- else if (pos.m_cur == this->m_finish.m_cur) {
+ else if (pos.m_cur == this->members_.m_finish.m_cur) {
iterator new_finish = this->priv_reserve_elements_at_back(n);
BOOST_TRY{
- boost::interprocess::uninitialized_copy(first, last, this->m_finish);
- this->m_finish = new_finish;
+ std::uninitialized_copy(first, last, this->members_.m_finish);
+ this->members_.m_finish = new_finish;
}
BOOST_CATCH(...){
- this->priv_destroy_nodes(this->m_finish.m_node + 1, new_finish.m_node + 1);
+ this->priv_destroy_nodes(this->members_.m_finish.m_node + 1, new_finish.m_node + 1);
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1113,17 +1084,17 @@
template <class FwdIt>
void priv_insert_aux(iterator pos, FwdIt first, FwdIt last, size_type n)
{
- const difference_type elemsbefore = pos - this->m_start;
+ const difference_type elemsbefore = pos - this->members_.m_start;
size_type length = size();
if (elemsbefore < static_cast<difference_type>(length / 2)) {
iterator new_start = this->priv_reserve_elements_at_front(n);
- iterator old_start = this->m_start;
- pos = this->m_start + elemsbefore;
+ iterator old_start = this->members_.m_start;
+ pos = this->members_.m_start + elemsbefore;
BOOST_TRY {
if (elemsbefore >= difference_type(n)) {
- iterator start_n = this->m_start + difference_type(n);
- boost::interprocess::uninitialized_copy(detail::make_move_iterator(this->m_start), detail::make_move_iterator(start_n), new_start);
- this->m_start = new_start;
+ iterator start_n = this->members_.m_start + difference_type(n);
+ std::uninitialized_copy(detail::make_move_iterator(this->members_.m_start), detail::make_move_iterator(start_n), new_start);
+ this->members_.m_start = new_start;
std::copy(detail::make_move_iterator(start_n), detail::make_move_iterator(pos), old_start);
std::copy(first, last, pos - difference_type(n));
}
@@ -1131,41 +1102,41 @@
FwdIt mid = first;
std::advance(mid, difference_type(n) - elemsbefore);
this->priv_uninitialized_copy_copy
- (detail::make_move_iterator(this->m_start), detail::make_move_iterator(pos), first, mid, new_start);
- this->m_start = new_start;
+ (detail::make_move_iterator(this->members_.m_start), detail::make_move_iterator(pos), first, mid, new_start);
+ this->members_.m_start = new_start;
std::copy(mid, last, old_start);
}
}
BOOST_CATCH(...){
- this->priv_destroy_nodes(new_start.m_node, this->m_start.m_node);
+ this->priv_destroy_nodes(new_start.m_node, this->members_.m_start.m_node);
BOOST_RETHROW
}
BOOST_CATCH_END
}
else {
iterator new_finish = this->priv_reserve_elements_at_back(n);
- iterator old_finish = this->m_finish;
+ iterator old_finish = this->members_.m_finish;
const difference_type elemsafter =
difference_type(length) - elemsbefore;
- pos = this->m_finish - elemsafter;
+ pos = this->members_.m_finish - elemsafter;
BOOST_TRY {
if (elemsafter > difference_type(n)) {
- iterator finish_n = this->m_finish - difference_type(n);
- boost::interprocess::uninitialized_copy(detail::make_move_iterator(finish_n), detail::make_move_iterator(this->m_finish), this->m_finish);
- this->m_finish = new_finish;
+ iterator finish_n = this->members_.m_finish - difference_type(n);
+ std::uninitialized_copy(detail::make_move_iterator(finish_n), detail::make_move_iterator(this->members_.m_finish), this->members_.m_finish);
+ this->members_.m_finish = new_finish;
std::copy_backward(detail::make_move_iterator(pos), detail::make_move_iterator(finish_n), old_finish);
std::copy(first, last, pos);
}
else {
FwdIt mid = first;
std::advance(mid, elemsafter);
- this->priv_uninitialized_copy_copy(mid, last, detail::make_move_iterator(pos), detail::make_move_iterator(this->m_finish), this->m_finish);
- this->m_finish = new_finish;
+ this->priv_uninitialized_copy_copy(mid, last, detail::make_move_iterator(pos), detail::make_move_iterator(this->members_.m_finish), this->members_.m_finish);
+ this->members_.m_finish = new_finish;
std::copy(first, mid, pos);
}
}
BOOST_CATCH(...){
- this->priv_destroy_nodes(this->m_finish.m_node + 1, new_finish.m_node + 1);
+ this->priv_destroy_nodes(this->members_.m_finish.m_node + 1, new_finish.m_node + 1);
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1178,19 +1149,19 @@
this->insert(pos, c_it(x, n), c_it());
}
- // Precondition: this->m_start and this->m_finish have already been initialized,
+ // Precondition: this->members_.m_start and this->members_.m_finish have already been initialized,
// but none of the deque's elements have yet been constructed.
void priv_fill_initialize(const value_type& value)
{
index_pointer cur;
BOOST_TRY {
- for (cur = this->m_start.m_node; cur < this->m_finish.m_node; ++cur){
- boost::interprocess::uninitialized_fill(*cur, *cur + this->s_buffer_size(), value);
+ for (cur = this->members_.m_start.m_node; cur < this->members_.m_finish.m_node; ++cur){
+ std::uninitialized_fill(*cur, *cur + this->s_buffer_size(), value);
}
- boost::interprocess::uninitialized_fill(this->m_finish.m_first, this->m_finish.m_cur, value);
+ std::uninitialized_fill(this->members_.m_finish.m_first, this->members_.m_finish.m_cur, value);
}
BOOST_CATCH(...){
- this->priv_destroy_range(this->m_start, iterator(*cur, cur));
+ this->priv_destroy_range(this->members_.m_start, iterator(*cur, cur));
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1220,53 +1191,53 @@
index_pointer cur_node;
BOOST_TRY {
- for (cur_node = this->m_start.m_node;
- cur_node < this->m_finish.m_node;
+ for (cur_node = this->members_.m_start.m_node;
+ cur_node < this->members_.m_finish.m_node;
++cur_node) {
FwdIt mid = first;
std::advance(mid, this->s_buffer_size());
- boost::interprocess::uninitialized_copy(first, mid, *cur_node);
+ std::uninitialized_copy(first, mid, *cur_node);
first = mid;
}
- boost::interprocess::uninitialized_copy(first, last, this->m_finish.m_first);
+ std::uninitialized_copy(first, last, this->members_.m_finish.m_first);
}
BOOST_CATCH(...){
- this->priv_destroy_range(this->m_start, iterator(*cur_node, cur_node));
+ this->priv_destroy_range(this->members_.m_start, iterator(*cur_node, cur_node));
BOOST_RETHROW
}
BOOST_CATCH_END
}
- // Called only if this->m_finish.m_cur == this->m_finish.m_last - 1.
+ // Called only if this->members_.m_finish.m_cur == this->members_.m_finish.m_last - 1.
void priv_push_back_aux(const value_type& t = value_type())
{
this->priv_reserve_map_at_back();
- *(this->m_finish.m_node + 1) = this->priv_allocate_node();
+ *(this->members_.m_finish.m_node + 1) = this->priv_allocate_node();
BOOST_TRY {
- new(detail::get_pointer(this->m_finish.m_cur))value_type(t);
- this->m_finish.priv_set_node(this->m_finish.m_node + 1);
- this->m_finish.m_cur = this->m_finish.m_first;
+ new(detail::get_pointer(this->members_.m_finish.m_cur))value_type(t);
+ this->members_.m_finish.priv_set_node(this->members_.m_finish.m_node + 1);
+ this->members_.m_finish.m_cur = this->members_.m_finish.m_first;
}
BOOST_CATCH(...){
- this->priv_deallocate_node(*(this->m_finish.m_node + 1));
+ this->priv_deallocate_node(*(this->members_.m_finish.m_node + 1));
BOOST_RETHROW
}
BOOST_CATCH_END
}
- // Called only if this->m_finish.m_cur == this->m_finish.m_last - 1.
+ // Called only if this->members_.m_finish.m_cur == this->members_.m_finish.m_last - 1.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void priv_push_back_aux(const detail::moved_object<value_type> &mt)
{
this->priv_reserve_map_at_back();
- *(this->m_finish.m_node + 1) = this->priv_allocate_node();
+ *(this->members_.m_finish.m_node + 1) = this->priv_allocate_node();
BOOST_TRY {
- new(detail::get_pointer(this->m_finish.m_cur))value_type(mt);
- this->m_finish.priv_set_node(this->m_finish.m_node + 1);
- this->m_finish.m_cur = this->m_finish.m_first;
+ new(detail::get_pointer(this->members_.m_finish.m_cur))value_type(mt);
+ this->members_.m_finish.priv_set_node(this->members_.m_finish.m_node + 1);
+ this->members_.m_finish.m_cur = this->members_.m_finish.m_first;
}
BOOST_CATCH(...){
- this->priv_deallocate_node(*(this->m_finish.m_node + 1));
+ this->priv_deallocate_node(*(this->members_.m_finish.m_node + 1));
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1275,33 +1246,33 @@
void priv_push_back_aux(value_type &&mt)
{
this->priv_reserve_map_at_back();
- *(this->m_finish.m_node + 1) = this->priv_allocate_node();
+ *(this->members_.m_finish.m_node + 1) = this->priv_allocate_node();
BOOST_TRY {
- new(detail::get_pointer(this->m_finish.m_cur))value_type(move(mt));
- this->m_finish.priv_set_node(this->m_finish.m_node + 1);
- this->m_finish.m_cur = this->m_finish.m_first;
+ new(detail::get_pointer(this->members_.m_finish.m_cur))value_type(move(mt));
+ this->members_.m_finish.priv_set_node(this->members_.m_finish.m_node + 1);
+ this->members_.m_finish.m_cur = this->members_.m_finish.m_first;
}
BOOST_CATCH(...){
- this->priv_deallocate_node(*(this->m_finish.m_node + 1));
+ this->priv_deallocate_node(*(this->members_.m_finish.m_node + 1));
BOOST_RETHROW
}
BOOST_CATCH_END
}
#endif
- // Called only if this->m_start.m_cur == this->m_start.m_first.
+ // Called only if this->members_.m_start.m_cur == this->members_.m_start.m_first.
void priv_push_front_aux(const value_type& t)
{
this->priv_reserve_map_at_front();
- *(this->m_start.m_node - 1) = this->priv_allocate_node();
+ *(this->members_.m_start.m_node - 1) = this->priv_allocate_node();
BOOST_TRY {
- this->m_start.priv_set_node(this->m_start.m_node - 1);
- this->m_start.m_cur = this->m_start.m_last - 1;
- new(detail::get_pointer(this->m_start.m_cur))value_type(t);
+ this->members_.m_start.priv_set_node(this->members_.m_start.m_node - 1);
+ this->members_.m_start.m_cur = this->members_.m_start.m_last - 1;
+ new(detail::get_pointer(this->members_.m_start.m_cur))value_type(t);
}
BOOST_CATCH(...){
- ++this->m_start;
- this->priv_deallocate_node(*(this->m_start.m_node - 1));
+ ++this->members_.m_start;
+ this->priv_deallocate_node(*(this->members_.m_start.m_node - 1));
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1311,15 +1282,15 @@
void priv_push_front_aux(const detail::moved_object<value_type> &mt)
{
this->priv_reserve_map_at_front();
- *(this->m_start.m_node - 1) = this->priv_allocate_node();
+ *(this->members_.m_start.m_node - 1) = this->priv_allocate_node();
BOOST_TRY {
- this->m_start.priv_set_node(this->m_start.m_node - 1);
- this->m_start.m_cur = this->m_start.m_last - 1;
- new(detail::get_pointer(this->m_start.m_cur))value_type(mt);
+ this->members_.m_start.priv_set_node(this->members_.m_start.m_node - 1);
+ this->members_.m_start.m_cur = this->members_.m_start.m_last - 1;
+ new(detail::get_pointer(this->members_.m_start.m_cur))value_type(mt);
}
BOOST_CATCH(...){
- ++this->m_start;
- this->priv_deallocate_node(*(this->m_start.m_node - 1));
+ ++this->members_.m_start;
+ this->priv_deallocate_node(*(this->members_.m_start.m_node - 1));
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1328,56 +1299,56 @@
void priv_push_front_aux(value_type &&mt)
{
this->priv_reserve_map_at_front();
- *(this->m_start.m_node - 1) = this->priv_allocate_node();
+ *(this->members_.m_start.m_node - 1) = this->priv_allocate_node();
BOOST_TRY {
- this->m_start.priv_set_node(this->m_start.m_node - 1);
- this->m_start.m_cur = this->m_start.m_last - 1;
- new(detail::get_pointer(this->m_start.m_cur))value_type(move(mt));
+ this->members_.m_start.priv_set_node(this->members_.m_start.m_node - 1);
+ this->members_.m_start.m_cur = this->members_.m_start.m_last - 1;
+ new(detail::get_pointer(this->members_.m_start.m_cur))value_type(move(mt));
}
BOOST_CATCH(...){
- ++this->m_start;
- this->priv_deallocate_node(*(this->m_start.m_node - 1));
+ ++this->members_.m_start;
+ this->priv_deallocate_node(*(this->members_.m_start.m_node - 1));
BOOST_RETHROW
}
BOOST_CATCH_END
}
#endif
- // Called only if this->m_finish.m_cur == this->m_finish.m_first.
+ // Called only if this->members_.m_finish.m_cur == this->members_.m_finish.m_first.
void priv_pop_back_aux()
{
- this->priv_deallocate_node(this->m_finish.m_first);
- this->m_finish.priv_set_node(this->m_finish.m_node - 1);
- this->m_finish.m_cur = this->m_finish.m_last - 1;
- detail::get_pointer(this->m_finish.m_cur)->~value_type();
+ this->priv_deallocate_node(this->members_.m_finish.m_first);
+ this->members_.m_finish.priv_set_node(this->members_.m_finish.m_node - 1);
+ this->members_.m_finish.m_cur = this->members_.m_finish.m_last - 1;
+ detail::get_pointer(this->members_.m_finish.m_cur)->~value_type();
}
- // Called only if this->m_start.m_cur == this->m_start.m_last - 1. Note that
+ // Called only if this->members_.m_start.m_cur == this->members_.m_start.m_last - 1. Note that
// if the deque has at least one element (a precondition for this member
- // function), and if this->m_start.m_cur == this->m_start.m_last, then the deque
+ // function), and if this->members_.m_start.m_cur == this->members_.m_start.m_last, then the deque
// must have at least two nodes.
void priv_pop_front_aux()
{
- detail::get_pointer(this->m_start.m_cur)->~value_type();
- this->priv_deallocate_node(this->m_start.m_first);
- this->m_start.priv_set_node(this->m_start.m_node + 1);
- this->m_start.m_cur = this->m_start.m_first;
+ detail::get_pointer(this->members_.m_start.m_cur)->~value_type();
+ this->priv_deallocate_node(this->members_.m_start.m_first);
+ this->members_.m_start.priv_set_node(this->members_.m_start.m_node + 1);
+ this->members_.m_start.m_cur = this->members_.m_start.m_first;
}
iterator priv_reserve_elements_at_front(size_type n)
{
- size_type vacancies = this->m_start.m_cur - this->m_start.m_first;
+ size_type vacancies = this->members_.m_start.m_cur - this->members_.m_start.m_first;
if (n > vacancies)
this->priv_new_elements_at_front(n - vacancies);
- return this->m_start - difference_type(n);
+ return this->members_.m_start - difference_type(n);
}
iterator priv_reserve_elements_at_back(size_type n)
{
- size_type vacancies = (this->m_finish.m_last - this->m_finish.m_cur) - 1;
+ size_type vacancies = (this->members_.m_finish.m_last - this->members_.m_finish.m_cur) - 1;
if (n > vacancies)
this->priv_new_elements_at_back(n - vacancies);
- return this->m_finish + difference_type(n);
+ return this->members_.m_finish + difference_type(n);
}
void priv_new_elements_at_front(size_type new_elems)
@@ -1388,11 +1359,11 @@
size_type i;
BOOST_TRY {
for (i = 1; i <= new_nodes; ++i)
- *(this->m_start.m_node - i) = this->priv_allocate_node();
+ *(this->members_.m_start.m_node - i) = this->priv_allocate_node();
}
BOOST_CATCH(...) {
for (size_type j = 1; j < i; ++j)
- this->priv_deallocate_node(*(this->m_start.m_node - j));
+ this->priv_deallocate_node(*(this->members_.m_start.m_node - j));
BOOST_RETHROW
}
BOOST_CATCH_END
@@ -1406,62 +1377,62 @@
size_type i;
BOOST_TRY {
for (i = 1; i <= new_nodes; ++i)
- *(this->m_finish.m_node + i) = this->priv_allocate_node();
+ *(this->members_.m_finish.m_node + i) = this->priv_allocate_node();
}
BOOST_CATCH(...) {
for (size_type j = 1; j < i; ++j)
- this->priv_deallocate_node(*(this->m_finish.m_node + j));
+ this->priv_deallocate_node(*(this->members_.m_finish.m_node + j));
BOOST_RETHROW
}
BOOST_CATCH_END
}
- // Makes sure the this->m_map has space for new nodes. Does not actually
- // add the nodes. Can invalidate this->m_map pointers. (And consequently,
+ // Makes sure the this->members_.m_map has space for new nodes. Does not actually
+ // add the nodes. Can invalidate this->members_.m_map pointers. (And consequently,
// deque iterators.)
void priv_reserve_map_at_back (size_type nodes_to_add = 1)
{
- if (nodes_to_add + 1 > this->m_map_size - (this->m_finish.m_node - this->m_map))
+ if (nodes_to_add + 1 > this->members_.m_map_size - (this->members_.m_finish.m_node - this->members_.m_map))
this->priv_reallocate_map(nodes_to_add, false);
}
void priv_reserve_map_at_front (size_type nodes_to_add = 1)
{
- if (nodes_to_add > size_type(this->m_start.m_node - this->m_map))
+ if (nodes_to_add > size_type(this->members_.m_start.m_node - this->members_.m_map))
this->priv_reallocate_map(nodes_to_add, true);
}
void priv_reallocate_map(size_type nodes_to_add, bool add_at_front)
{
- size_type old_num_nodes = this->m_finish.m_node - this->m_start.m_node + 1;
+ size_type old_num_nodes = this->members_.m_finish.m_node - this->members_.m_start.m_node + 1;
size_type new_num_nodes = old_num_nodes + nodes_to_add;
index_pointer new_nstart;
- if (this->m_map_size > 2 * new_num_nodes) {
- new_nstart = this->m_map + (this->m_map_size - new_num_nodes) / 2
+ if (this->members_.m_map_size > 2 * new_num_nodes) {
+ new_nstart = this->members_.m_map + (this->members_.m_map_size - new_num_nodes) / 2
+ (add_at_front ? nodes_to_add : 0);
- if (new_nstart < this->m_start.m_node)
- std::copy(this->m_start.m_node, this->m_finish.m_node + 1, new_nstart);
+ if (new_nstart < this->members_.m_start.m_node)
+ std::copy(this->members_.m_start.m_node, this->members_.m_finish.m_node + 1, new_nstart);
else
- std::copy_backward(this->m_start.m_node, this->m_finish.m_node + 1,
+ std::copy_backward(this->members_.m_start.m_node, this->members_.m_finish.m_node + 1,
new_nstart + old_num_nodes);
}
else {
size_type new_map_size =
- this->m_map_size + max_value(this->m_map_size, nodes_to_add) + 2;
+ this->members_.m_map_size + max_value(this->members_.m_map_size, nodes_to_add) + 2;
index_pointer new_map = this->priv_allocate_map(new_map_size);
new_nstart = new_map + (new_map_size - new_num_nodes) / 2
+ (add_at_front ? nodes_to_add : 0);
- std::copy(this->m_start.m_node, this->m_finish.m_node + 1, new_nstart);
- this->priv_deallocate_map(this->m_map, this->m_map_size);
+ std::copy(this->members_.m_start.m_node, this->members_.m_finish.m_node + 1, new_nstart);
+ this->priv_deallocate_map(this->members_.m_map, this->members_.m_map_size);
- this->m_map = new_map;
- this->m_map_size = new_map_size;
+ this->members_.m_map = new_map;
+ this->members_.m_map_size = new_map_size;
}
- this->m_start.priv_set_node(new_nstart);
- this->m_finish.priv_set_node(new_nstart + old_num_nodes - 1);
+ this->members_.m_start.priv_set_node(new_nstart);
+ this->members_.m_finish.priv_set_node(new_nstart + old_num_nodes - 1);
}
// this->priv_uninitialized_copy_fill
@@ -1471,9 +1442,9 @@
iterator first2, iterator last2,
const T& x)
{
- iterator mid2 = boost::interprocess::uninitialized_copy(first1, last1, first2);
+ iterator mid2 = std::uninitialized_copy(first1, last1, first2);
BOOST_TRY {
- boost::interprocess::uninitialized_fill(mid2, last2, x);
+ std::uninitialized_fill(mid2, last2, x);
}
BOOST_CATCH(...){
for(;first2 != mid2; ++first2){
@@ -1490,9 +1461,9 @@
const T& x,
iterator first, iterator last)
{
- boost::interprocess::uninitialized_fill(result, mid, x);
+ std::uninitialized_fill(result, mid, x);
BOOST_TRY {
- return boost::interprocess::uninitialized_copy(first, last, mid);
+ return std::uninitialized_copy(first, last, mid);
}
BOOST_CATCH(...){
for(;result != mid; ++result){
@@ -1512,9 +1483,9 @@
InpIt2 first2, InpIt2 last2,
FwdIt result)
{
- FwdIt mid = boost::interprocess::uninitialized_copy(first1, last1, result);
+ FwdIt mid = std::uninitialized_copy(first1, last1, result);
BOOST_TRY {
- return boost::interprocess::uninitialized_copy(first2, last2, mid);
+ return std::uninitialized_copy(first2, last2, mid);
}
BOOST_CATCH(...){
for(;result != mid; ++result){
Modified: branches/bcbboost/boost/interprocess/containers/detail/flat_tree.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/detail/flat_tree.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/detail/flat_tree.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -348,8 +348,6 @@
typedef typename
std::iterator_traits<InIt>::iterator_category ItCat;
priv_insert_equal(first, last, ItCat());
-// for ( ; first != last; ++first)
-// this->insert_equal(*first);
}
iterator erase(const_iterator position)
@@ -360,9 +358,8 @@
std::pair<iterator,iterator > itp = this->equal_range(k);
size_type ret = static_cast<size_type>(itp.second-itp.first);
if (ret){
- this->erase(itp.first, itp.second);
+ this->m_data.m_vect.erase(itp.first, itp.second);
}
-
return ret;
}
Modified: branches/bcbboost/boost/interprocess/containers/detail/node_alloc_holder.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/detail/node_alloc_holder.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/detail/node_alloc_holder.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -21,10 +21,11 @@
#include <boost/interprocess/interprocess_fwd.hpp>
#include <boost/interprocess/detail/version_type.hpp>
#include <boost/interprocess/detail/move.hpp>
+#include <boost/interprocess/detail/algorithms.hpp>
#include <boost/interprocess/detail/type_traits.hpp>
#include <boost/interprocess/detail/utilities.hpp>
-#include <boost/interprocess/detail/algorithms.hpp>
#include <boost/interprocess/detail/mpl.hpp>
+#include <boost/intrusive/options.hpp>
#include <utility>
#include <functional>
@@ -58,7 +59,6 @@
template<class A, class ICont>
struct node_alloc_holder
- : public A::template rebind<typename ICont::value_type>::other
{
typedef node_alloc_holder<A, ICont> self_t;
typedef typename A::value_type value_type;
@@ -76,91 +76,68 @@
version<NodeAlloc>::value> alloc_version;
node_alloc_holder(const ValAlloc &a)
- : NodeAlloc(a)
- {}
-
- #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
- node_alloc_holder(const detail::moved_object<ValAlloc> &a)
- : NodeAlloc(a.get())
- {}
- #else
- node_alloc_holder(ValAlloc &&a)
- : NodeAlloc(a)
+ : members_(a)
{}
- #endif
node_alloc_holder(const node_alloc_holder &other)
- : NodeAlloc(other)
+ : members_(other.node_alloc())
{}
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
node_alloc_holder(const detail::moved_object<node_alloc_holder> &other)
- : NodeAlloc(move((NodeAlloc&)other.get()))
+ : members_(move(other.get().node_alloc()))
{ this->swap(other.get()); }
#else
node_alloc_holder(node_alloc_holder &&other)
- : NodeAlloc(move((NodeAlloc&)other))
+ : members_(move(other.node_alloc()))
{ this->swap(other); }
#endif
template<class Pred>
node_alloc_holder(const ValAlloc &a, const Pred &c)
- : NodeAlloc(a), m_icont(typename ICont::value_compare(c))
+ : members_(a, typename ICont::value_compare(c))
{}
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
template<class Pred>
node_alloc_holder(const detail::moved_object<ValAlloc> &a, const Pred &c)
- : NodeAlloc(a.get()), m_icont(typename ICont::value_compare(c))
+ : members_(a.get(), typename ICont::value_compare(c))
{}
#else
template<class Pred>
node_alloc_holder(ValAlloc &&a, const Pred &c)
- : NodeAlloc(a), m_icont(typename ICont::value_compare(c))
+ : members_(a, typename ICont::value_compare(c))
{}
#endif
template<class Pred>
node_alloc_holder(const node_alloc_holder &other, const Pred &c)
- : NodeAlloc(other), m_icont(typename ICont::value_compare(c))
+ : members_(other.node_alloc(), typename ICont::value_compare(c))
{}
- #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
- template<class Pred>
- node_alloc_holder
- (const detail::moved_object<node_alloc_holder> &other, const Pred &c)
- : NodeAlloc(move((NodeAlloc&)other.get())), m_icont(typename ICont::value_compare(c))
- { this->swap(other.get()); }
- #else
- template<class Pred>
- node_alloc_holder(node_alloc_holder &&other, const Pred &c)
- : NodeAlloc(move((NodeAlloc&)other)), m_icont(typename ICont::value_compare(c))
- { this->swap(other); }
- #endif
-
~node_alloc_holder()
{}
size_type max_size() const
- { return NodeAlloc::max_size(); }
+ { return this->node_alloc().max_size(); }
NodePtr allocate_one()
{ return this->allocate_one(alloc_version()); }
NodePtr allocate_one(allocator_v1)
- { return NodeAlloc::allocate(1); }
+ { return this->node_alloc().allocate(1); }
NodePtr allocate_one(allocator_v2)
- { return NodeAlloc::allocate_one(); }
+ { return this->node_alloc().allocate_one(); }
void deallocate_one(NodePtr p)
{ return this->deallocate_one(p, alloc_version()); }
void deallocate_one(NodePtr p, allocator_v1)
- { NodeAlloc::deallocate(p, 1); }
+ { this->node_alloc().deallocate(p, 1); }
void deallocate_one(NodePtr p, allocator_v2)
- { NodeAlloc::deallocate_one(p); }
+ { this->node_alloc().deallocate_one(p); }
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
template<class Convertible>
@@ -187,7 +164,7 @@
//Hook constructor does not throw
new(static_cast<hook_type*>(nodeptr))hook_type();
- //Now construct pair members
+ //Now construct pair members_holder
value_type *valueptr = &nodeptr->m_data;
new((void*)&valueptr->first) first_type(move(value.get().first));
BOOST_TRY{
@@ -212,7 +189,7 @@
//Hook constructor does not throw
new(static_cast<hook_type*>(nodeptr))hook_type();
- //Now construct pair members
+ //Now construct pair members_holder
value_type *valueptr = &nodeptr->m_data;
new((void*)&valueptr->first) first_type(move(value.first));
BOOST_TRY{
@@ -235,7 +212,7 @@
NodePtr create_node(const Convertible& x)
{
NodePtr p = this->allocate_one();
- Deallocator node_deallocator(p, *this);
+ Deallocator node_deallocator(p, this->node_alloc());
self_t::construct(p, x);
node_deallocator.release();
return (p);
@@ -245,7 +222,7 @@
NodePtr create_node(Convertible &&x)
{
NodePtr p = this->allocate_one();
- Deallocator node_deallocator(p, *this);
+ Deallocator node_deallocator(p, this->node_alloc());
self_t::construct(p, forward<Convertible>(x));
node_deallocator.release();
return (p);
@@ -256,8 +233,8 @@
NodePtr create_node_from_it(It it)
{
NodePtr p = this->allocate_one();
- Deallocator node_deallocator(p, *this);
- construct_in_place(detail::get_pointer(p), it);
+ Deallocator node_deallocator(p, this->node_alloc());
+ ::boost::interprocess::construct_in_place(detail::get_pointer(p), it);
node_deallocator.release();
return (p);
}
@@ -265,7 +242,7 @@
NodePtr create_node()
{
NodePtr p = this->allocate_one();
- Deallocator node_deallocator(p, *this);
+ Deallocator node_deallocator(p, this->node_alloc());
self_t::construct(p);
node_deallocator.release();
return (p);
@@ -279,36 +256,52 @@
void swap(node_alloc_holder &x)
{
- NodeAlloc& this_alloc = static_cast<NodeAlloc&>(*this);
- NodeAlloc& other_alloc = static_cast<NodeAlloc&>(x);
+ NodeAlloc& this_alloc = this->node_alloc();
+ NodeAlloc& other_alloc = x.node_alloc();
if (this_alloc != other_alloc){
detail::do_swap(this_alloc, other_alloc);
}
- this->m_icont.swap(x.m_icont);
+ this->icont().swap(x.icont());
}
- template<class FwdIterator, class MultiAllocator>
+ template<class FwdIterator, class Inserter>
FwdIterator allocate_many_and_construct
- (FwdIterator beg, difference_type n, MultiAllocator &multi_beg, size_type &constructed)
+ (FwdIterator beg, difference_type n, Inserter inserter)
{
typedef typename NodeAlloc::multiallocation_iterator multiallocation_iterator;
//Try to allocate memory in a single chunk
- MultiAllocator itbeg = NodeAlloc::allocate_individual(1, n, constructed), itend, it;
-
- //Prepare exception-safety machinery
- detail::multiallocation_deallocator<NodeAlloc> multi_deallocator(itbeg, *this);
-
- //Initialize all the data (this can throw)
- FwdIterator next =
- boost::interprocess::n_uninitialized_copy_n(beg, constructed, itbeg);
-
- //Exception-unsafe zone passed. Disable auto-deallocation
- multi_deallocator.release();
- multi_beg = itbeg;
- return next;
+ multiallocation_iterator itbeg =
+ this->node_alloc().allocate_individual(n), itend, itold;
+ int constructed = 0;
+ Node *p;
+ BOOST_TRY{
+ for(difference_type i = 0; i < n; ++i, ++beg, --constructed){
+ p = &*itbeg;
+ ++itbeg;
+ //This can throw
+ boost::interprocess::construct_in_place(p, beg);
+ ++constructed;
+ //This can throw in some containers (predicate might throw)
+ inserter(*p);
+ }
+ }
+ BOOST_CATCH(...){
+ if(constructed){
+ this->destroy(p);
+ }
+ this->deallocate_one(p);
+ multiallocation_iterator itend;
+ while(itbeg != itend){
+ Node *n = &*itbeg;
+ ++itbeg;
+ this->deallocate_one(n);
+ }
+ }
+ BOOST_CATCH_END
+ return beg;
}
protected:
@@ -336,11 +329,40 @@
node_alloc_holder &m_holder;
};
- //The intrusive container
- ICont m_icont;
+ struct members_holder
+ : public NodeAlloc
+ {
+ private:
+ members_holder(const members_holder&);
+
+ public:
+ template<class ConvertibleToAlloc>
+ members_holder(const ConvertibleToAlloc &c2alloc)
+ : NodeAlloc(c2alloc)
+ {}
+
+ template<class ConvertibleToAlloc, class Pred>
+ members_holder(const ConvertibleToAlloc &c2alloc, const Pred &c)
+ : NodeAlloc(c2alloc), m_icont(c)
+ {}
+ //The intrusive container
+ ICont m_icont;
+ } members_;
ICont &non_const_icont() const
- { return const_cast<ICont&>(this->m_icont); }
+ { return const_cast<ICont&>(this->members_.m_icont); }
+
+ ICont &icont()
+ { return this->members_.m_icont; }
+
+ const ICont &icont() const
+ { return this->members_.m_icont; }
+
+ NodeAlloc &node_alloc()
+ { return this->members_; }
+
+ const NodeAlloc &node_alloc() const
+ { return this->members_; }
};
} //namespace detail {
Modified: branches/bcbboost/boost/interprocess/containers/detail/tree.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/detail/tree.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/detail/tree.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -86,15 +86,11 @@
template <class T, class VoidPointer>
struct rbtree_node
- : public boost::intrusive::set_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , VoidPointer>
-{
- typedef boost::intrusive::set_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , VoidPointer> hook_type;
+ : public bi::make_set_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type
+{
+ typedef typename bi::make_set_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type hook_type;
typedef T value_type;
@@ -129,16 +125,11 @@
public:
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
+
template<class Convertible>
static void construct(node_type *ptr, const Convertible &value)
{ new(ptr) node_type(value); }
- #else
- template<class Convertible>
- static void construct(node_type *ptr, Convertible &&value)
- { new(ptr) node_type(forward<Convertible>(value)); }
- #endif
- #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
template<class Convertible1, class Convertible2>
static void construct(node_type *ptr,
const detail::moved_object<std::pair<Convertible1, Convertible2> > &value)
@@ -151,7 +142,13 @@
new((void*)ptr) hack_node_t(value);
}
+
#else
+
+ template<class Convertible>
+ static void construct(node_type *ptr, Convertible &&value)
+ { new(ptr) node_type(forward<Convertible>(value)); }
+
template<class Convertible1, class Convertible2>
static void construct(node_type *ptr,
std::pair<Convertible1, Convertible2> &&value)
@@ -164,6 +161,7 @@
new((void*)ptr) hack_node_t(value);
}
+
#endif
};
@@ -187,14 +185,13 @@
typedef typename detail::rbtree_node
<value_type, void_pointer> node_type;
typedef node_compare<ValueCompare, node_type> node_compare_type;
-
- typedef typename boost::intrusive::rbtree
- <typename node_type::hook_type::
- template value_traits<node_type>
- ,node_compare_type
- ,boost::intrusive::safe_link
- ,typename A::size_type> container_type;
-
+ typedef typename bi::make_rbtree
+ <node_type
+ ,bi::compare<node_compare_type>
+ ,bi::base_hook<typename node_type::hook_type>
+ ,bi::constant_time_size<true>
+ ,bi::size_type<typename A::size_type>
+ >::type container_type;
typedef container_type type ;
};
@@ -241,9 +238,10 @@
NodePtr operator()(const Node &other) const
{
- if(!m_icont.empty()){
+// if(!m_icont.empty()){
+ if(NodePtr p = m_icont.unlink_leftmost_without_rebalance()){
//First recycle a node (this can't throw)
- NodePtr p = m_icont.unlink_leftmost_without_rebalance();
+ //NodePtr p = m_icont.unlink_leftmost_without_rebalance();
try{
//This can throw
*p = other;
@@ -421,8 +419,8 @@
rbtree(const rbtree& x)
: AllocHolder(x, x.key_comp())
{
- this->m_icont.clone_from
- (x.m_icont, typename AllocHolder::cloner(*this), Destroyer(*this));
+ this->icont().clone_from
+ (x.icont(), typename AllocHolder::cloner(*this), Destroyer(this->node_alloc()));
}
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
@@ -444,12 +442,15 @@
//Transfer all the nodes to a temporary tree
//If anything goes wrong, all the nodes will be destroyed
//automatically
- Icont other_tree(this->m_icont.value_comp());
- other_tree.swap(this->m_icont);
+ Icont other_tree(this->icont().value_comp());
+ other_tree.swap(this->icont());
//Now recreate the source tree reusing nodes stored by other_tree
- this->m_icont.clone_from
- (x.m_icont, RecyclingCloner(*this, other_tree), Destroyer(*this));
+ this->icont().clone_from
+ (x.icont()
+ , RecyclingCloner(*this, other_tree)
+ //, AllocHolder::cloner(*this)
+ , Destroyer(this->node_alloc()));
//If there are remaining nodes, destroy them
NodePtr p;
@@ -471,28 +472,28 @@
public:
// accessors:
value_compare value_comp() const
- { return this->m_icont.value_comp().value_comp(); }
+ { return this->icont().value_comp().value_comp(); }
key_compare key_comp() const
- { return this->m_icont.value_comp().value_comp().key_comp(); }
+ { return this->icont().value_comp().value_comp().key_comp(); }
allocator_type get_allocator() const
- { return allocator_type(*this); }
+ { return allocator_type(this->node_alloc()); }
const stored_allocator_type &get_stored_allocator() const
- { return static_cast<const stored_allocator_type &>(*this); }
+ { return this->node_alloc(); }
stored_allocator_type &get_stored_allocator()
- { return static_cast<stored_allocator_type&>(*this); }
+ { return this->node_alloc(); }
iterator begin()
- { return iterator(this->m_icont.begin()); }
+ { return iterator(this->icont().begin()); }
const_iterator begin() const
{ return const_iterator(this->non_const_icont().begin()); }
iterator end()
- { return iterator(this->m_icont.end()); }
+ { return iterator(this->icont().end()); }
const_iterator end() const
{ return const_iterator(this->non_const_icont().end()); }
@@ -513,7 +514,7 @@
{ return !this->size(); }
size_type size() const
- { return this->m_icont.size(); }
+ { return this->icont().size(); }
size_type max_size() const
{ return AllocHolder::max_size(); }
@@ -538,7 +539,7 @@
(const key_type& key, insert_commit_data &data)
{
std::pair<iiterator, bool> ret =
- this->m_icont.insert_unique_check(key, KeyNodeCompare(value_comp()), data);
+ this->icont().insert_unique_check(key, KeyNodeCompare(value_comp()), data);
return std::pair<iterator, bool>(iterator(ret.first), ret.second);
}
@@ -546,14 +547,14 @@
(const_iterator hint, const key_type& key, insert_commit_data &data)
{
std::pair<iiterator, bool> ret =
- this->m_icont.insert_unique_check(hint.get(), key, KeyNodeCompare(value_comp()), data);
+ this->icont().insert_unique_check(hint.get(), key, KeyNodeCompare(value_comp()), data);
return std::pair<iterator, bool>(iterator(ret.first), ret.second);
}
iterator insert_unique_commit(const value_type& v, insert_commit_data &data)
{
NodePtr tmp = AllocHolder::create_node(v);
- iiterator it(this->m_icont.insert_unique_commit(*tmp, data));
+ iiterator it(this->icont().insert_unique_commit(*tmp, data));
return iterator(it);
}
@@ -563,7 +564,7 @@
(const detail::moved_object<MovableConvertible>& mv, insert_commit_data &data)
{
NodePtr tmp = AllocHolder::create_node(mv);
- iiterator it(this->m_icont.insert_unique_commit(*tmp, data));
+ iiterator it(this->icont().insert_unique_commit(*tmp, data));
return iterator(it);
}
#else
@@ -572,7 +573,7 @@
(MovableConvertible && mv, insert_commit_data &data)
{
NodePtr tmp = AllocHolder::create_node(forward<MovableConvertible>(mv));
- iiterator it(this->m_icont.insert_unique_commit(*tmp, data));
+ iiterator it(this->icont().insert_unique_commit(*tmp, data));
return iterator(it);
}
#endif
@@ -670,7 +671,7 @@
iterator insert_equal(const value_type& v)
{
NodePtr p(AllocHolder::create_node(v));
- return iterator(this->m_icont.insert_equal_upper_bound(*p));
+ return iterator(this->icont().insert_equal_upper_bound(*p));
}
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
@@ -678,21 +679,21 @@
iterator insert_equal(const detail::moved_object<MovableConvertible> &mv)
{
NodePtr p(AllocHolder::create_node(mv));
- return iterator(this->m_icont.insert_equal_upper_bound(*p));
+ return iterator(this->icont().insert_equal_upper_bound(*p));
}
#else
template<class MovableConvertible>
iterator insert_equal(MovableConvertible &&mv)
{
NodePtr p(AllocHolder::create_node(forward<MovableConvertible>(mv)));
- return iterator(this->m_icont.insert_equal_upper_bound(*p));
+ return iterator(this->icont().insert_equal_upper_bound(*p));
}
#endif
iterator insert_equal(const_iterator hint, const value_type& v)
{
NodePtr p(AllocHolder::create_node(v));
- return iterator(this->m_icont.insert_equal(hint.get(), *p));
+ return iterator(this->icont().insert_equal(hint.get(), *p));
}
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
@@ -700,14 +701,14 @@
iterator insert_equal(const_iterator hint, const detail::moved_object<MovableConvertible> &mv)
{
NodePtr p(AllocHolder::create_node(mv));
- return iterator(this->m_icont.insert_equal(hint.get(), *p));
+ return iterator(this->icont().insert_equal(hint.get(), *p));
}
#else
template<class MovableConvertible>
iterator insert_equal(const_iterator hint, MovableConvertible &&mv)
{
NodePtr p(AllocHolder::create_node(move(mv)));
- return iterator(this->m_icont.insert_equal(hint.get(), *p));
+ return iterator(this->icont().insert_equal(hint.get(), *p));
}
#endif
@@ -728,35 +729,35 @@
}
iterator erase(const_iterator position)
- { return iterator(this->m_icont.erase_and_dispose(position.get(), Destroyer(*this))); }
+ { return iterator(this->icont().erase_and_dispose(position.get(), Destroyer(this->node_alloc()))); }
size_type erase(const key_type& k)
- { return this->m_icont.erase_and_dispose(k, KeyNodeCompare(value_comp()), Destroyer(*this)); }
+ { return this->icont().erase_and_dispose(k, KeyNodeCompare(value_comp()), Destroyer(this->node_alloc())); }
iterator erase(const_iterator first, const_iterator last)
- { return iterator(this->m_icont.erase_and_dispose(first.get(), last.get(), Destroyer(*this))); }
+ { return iterator(this->icont().erase_and_dispose(first.get(), last.get(), Destroyer(this->node_alloc()))); }
void clear()
- { this->m_icont.clear_and_dispose(Destroyer(*this)); }
+ { this->icont().clear_and_dispose(Destroyer(this->node_alloc())); }
// set operations:
iterator find(const key_type& k)
- { return iterator(this->m_icont.find(k, KeyNodeCompare(value_comp()))); }
+ { return iterator(this->icont().find(k, KeyNodeCompare(value_comp()))); }
const_iterator find(const key_type& k) const
{ return const_iterator(this->non_const_icont().find(k, KeyNodeCompare(value_comp()))); }
size_type count(const key_type& k) const
- { return size_type(this->m_icont.count(k, KeyNodeCompare(value_comp()))); }
+ { return size_type(this->icont().count(k, KeyNodeCompare(value_comp()))); }
iterator lower_bound(const key_type& k)
- { return iterator(this->m_icont.lower_bound(k, KeyNodeCompare(value_comp()))); }
+ { return iterator(this->icont().lower_bound(k, KeyNodeCompare(value_comp()))); }
const_iterator lower_bound(const key_type& k) const
{ return const_iterator(this->non_const_icont().lower_bound(k, KeyNodeCompare(value_comp()))); }
iterator upper_bound(const key_type& k)
- { return iterator(this->m_icont.upper_bound(k, KeyNodeCompare(value_comp()))); }
+ { return iterator(this->icont().upper_bound(k, KeyNodeCompare(value_comp()))); }
const_iterator upper_bound(const key_type& k) const
{ return const_iterator(this->non_const_icont().upper_bound(k, KeyNodeCompare(value_comp()))); }
@@ -764,7 +765,7 @@
std::pair<iterator,iterator> equal_range(const key_type& k)
{
std::pair<iiterator, iiterator> ret =
- this->m_icont.equal_range(k, KeyNodeCompare(value_comp()));
+ this->icont().equal_range(k, KeyNodeCompare(value_comp()));
return std::pair<iterator,iterator>(iterator(ret.first), iterator(ret.second));
}
@@ -809,6 +810,24 @@
priv_create_and_insert_nodes(beg, end, unique, allocator_v1(), std::input_iterator_tag());
}
+ class insertion_functor;
+ friend class insertion_functor;
+
+ class insertion_functor
+ {
+ Icont &icont_;
+ typename Icont::iterator pos_;
+
+ public:
+ insertion_functor(Icont &icont)
+ : icont_(icont)
+ {}
+
+ void operator()(Node &n)
+ { this->icont_.insert_equal_upper_bound(n); }
+ };
+
+
template<class FwdIterator>
void priv_create_and_insert_nodes
(FwdIterator beg, FwdIterator end, bool unique, allocator_v2, std::forward_iterator_tag)
@@ -817,31 +836,9 @@
priv_create_and_insert_nodes(beg, end, unique, allocator_v2(), std::input_iterator_tag());
}
else{
- //Optimize memory allocation obtaining the distance between iterators
- size_type n = std::distance(beg, end);
-
- //Allocate and construct as many nodes as possible with
- //the one-shot allocation
- typedef typename NodeAlloc::multiallocation_iterator multiallocation_iterator;
- multiallocation_iterator many_beg, itend, it;
- size_type received_array;
- FwdIterator next = this->allocate_many_and_construct
- (beg, n, many_beg, received_array);
-
- detail::multiallocation_destroy_dealloc<NodeAlloc>
- multi_destroy_dealloc(many_beg, *this);
-
- //Insert constructed nodes (this does not throw)
- for (it = many_beg; it != itend; ++it){
- this->m_icont.insert_equal_upper_bound(*it);
- multi_destroy_dealloc.next();
- }
-
- //Insert remaining nodes using individual allocation
- //(this can throw, but there is no leak)
- for (size_type i = received_array; i < n; ++i, ++next){
- this->insert_equal(*next);
- }
+ //Optimized allocation and construction
+ this->allocate_many_and_construct
+ (beg, std::distance(beg, end), insertion_functor(this->icont()));
}
}
};
Modified: branches/bcbboost/boost/interprocess/containers/flat_set.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/flat_set.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/flat_set.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -8,8 +8,8 @@
//
//////////////////////////////////////////////////////////////////////////////
-#ifndef BOOST_INTERPROCESS_SHMEM_FLAT_SET_HPP
-#define BOOST_INTERPROCESS_SHMEM_FLAT_SET_HPP
+#ifndef BOOST_INTERPROCESS_FLAT_SET_HPP
+#define BOOST_INTERPROCESS_FLAT_SET_HPP
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
@@ -556,7 +556,8 @@
#endif
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class T, class P, class A>
struct is_movable<flat_set<T, P, A> >
{
@@ -1055,7 +1056,8 @@
#endif
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class T, class P, class A>
struct is_movable<flat_multiset<T, P, A> >
{
@@ -1077,4 +1079,4 @@
#include <boost/interprocess/detail/config_end.hpp>
-#endif /* BOOST_INTERPROCESS_SHMEM_FLAT_SET_HPP */
+#endif /* BOOST_INTERPROCESS_FLAT_SET_HPP */
Modified: branches/bcbboost/boost/interprocess/containers/list.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/list.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/list.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -75,15 +75,11 @@
template <class T, class VoidPointer>
struct list_node
- : public boost::intrusive::list_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , VoidPointer>
+ : public bi::make_list_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type
{
- typedef boost::intrusive::list_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , VoidPointer> hook_type;
+ typedef typename bi::make_list_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type hook_type;
list_node()
: m_data()
@@ -112,12 +108,12 @@
<typename A::pointer, void>::type void_pointer;
typedef typename detail::list_node
<value_type, void_pointer> node_type;
-
- typedef typename boost::intrusive::list
- <typename node_type::hook_type::
- template value_traits<node_type>
- ,true
- ,typename A::size_type> container_type;
+ typedef typename bi::make_list
+ < node_type
+ , bi::base_hook<typename node_type::hook_type>
+ , bi::constant_time_size<true>
+ , bi::size_type<typename A::size_type>
+ >::type container_type;
typedef container_type type ;
};
@@ -390,13 +386,13 @@
//!
//! <b>Complexity</b>: Constant.
allocator_type get_allocator() const
- { return allocator_type(*this); }
+ { return allocator_type(this->node_alloc()); }
const stored_allocator_type &get_stored_allocator() const
- { return *this; }
+ { return this->node_alloc(); }
stored_allocator_type &get_stored_allocator()
- { return *this; }
+ { return this->node_alloc(); }
//! <b>Effects</b>: Erases all the elements of the list.
//!
@@ -404,7 +400,7 @@
//!
//! <b>Complexity</b>: Linear to the number of elements in the list.
void clear()
- { this->m_icont.clear_and_dispose(Destroyer(*this)); }
+ { this->icont().clear_and_dispose(Destroyer(this->node_alloc())); }
//! <b>Effects</b>: Returns an iterator to the first element contained in the list.
//!
@@ -412,7 +408,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator begin()
- { return iterator(this->m_icont.begin()); }
+ { return iterator(this->icont().begin()); }
//! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
//!
@@ -428,7 +424,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator end()
- { return iterator(this->m_icont.end()); }
+ { return iterator(this->icont().end()); }
//! <b>Effects</b>: Returns a const_iterator to the end of the list.
//!
@@ -488,7 +484,7 @@
//!
//! <b>Complexity</b>: Constant.
size_type size() const
- { return this->m_icont.size(); }
+ { return this->icont().size(); }
//! <b>Effects</b>: Returns the largest possible size of the list.
//!
@@ -744,7 +740,7 @@
iterator insert(iterator p, const T& x)
{
NodePtr tmp = AllocHolder::create_node(x);
- return iterator(this->m_icont.insert(p.get(), *tmp));
+ return iterator(this->icont().insert(p.get(), *tmp));
}
//! <b>Requires</b>: p must be a valid iterator of *this.
@@ -758,13 +754,13 @@
iterator insert(iterator p, const detail::moved_object<T>& x)
{
NodePtr tmp = AllocHolder::create_node(x);
- return iterator(this->m_icont.insert(p.get(), *tmp));
+ return iterator(this->icont().insert(p.get(), *tmp));
}
#else
iterator insert(iterator p, T &&x)
{
NodePtr tmp = AllocHolder::create_node(move(x));
- return iterator(this->m_icont.insert(p.get(), *tmp));
+ return iterator(this->icont().insert(p.get(), *tmp));
}
#endif
@@ -776,7 +772,7 @@
//!
//! <b>Complexity</b>: Amortized constant time.
iterator erase(iterator p)
- { return iterator(this->m_icont.erase_and_dispose(p.get(), Destroyer(*this))); }
+ { return iterator(this->icont().erase_and_dispose(p.get(), Destroyer(this->node_alloc()))); }
//! <b>Requires</b>: first and last must be valid iterator to elements in *this.
//!
@@ -786,7 +782,7 @@
//!
//! <b>Complexity</b>: Linear to the distance between first and last.
iterator erase(iterator first, iterator last)
- { return iterator(this->m_icont.erase_and_dispose(first.get(), last.get(), Destroyer(*this))); }
+ { return iterator(this->icont().erase_and_dispose(first.get(), last.get(), Destroyer(this->node_alloc()))); }
//! <b>Effects</b>: Assigns the n copies of val to *this.
//!
@@ -826,7 +822,7 @@
void splice(iterator p, ThisType& x)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice(p.get(), x.m_icont);
+ this->icont().splice(p.get(), x.icont());
}
else{
throw std::runtime_error("list::splice called with unequal allocators");
@@ -853,7 +849,7 @@
void splice(iterator p, ThisType &x, iterator i)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice(p.get(), x.m_icont, i.get());
+ this->icont().splice(p.get(), x.icont(), i.get());
}
else{
throw std::runtime_error("list::splice called with unequal allocators");
@@ -879,7 +875,7 @@
void splice(iterator p, ThisType &x, iterator first, iterator last)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice(p.get(), x.m_icont, first.get(), last.get());
+ this->icont().splice(p.get(), x.icont(), first.get(), last.get());
}
else{
throw std::runtime_error("list::splice called with unequal allocators");
@@ -906,7 +902,7 @@
void splice(iterator p, ThisType &x, iterator first, iterator last, size_type n)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice(p.get(), x.m_icont, first.get(), last.get(), n);
+ this->icont().splice(p.get(), x.icont(), first.get(), last.get(), n);
}
else{
throw std::runtime_error("list::splice called with unequal allocators");
@@ -924,7 +920,7 @@
//!
//! <b>Note</b>: Iterators and references are not invalidated
void reverse()
- { this->m_icont.reverse(); }
+ { this->icont().reverse(); }
//! <b>Effects</b>: Removes all the elements that compare equal to value.
//!
@@ -950,7 +946,7 @@
void remove_if(Pred pred)
{
typedef ValueCompareToNodeCompare<Pred> Predicate;
- this->m_icont.remove_and_dispose_if(Predicate(pred), Destroyer(*this));
+ this->icont().remove_and_dispose_if(Predicate(pred), Destroyer(this->node_alloc()));
}
//! <b>Effects</b>: Removes adjacent duplicate elements or adjacent
@@ -978,7 +974,7 @@
void unique(BinaryPredicate binary_pred)
{
typedef ValueCompareToNodeCompare<BinaryPredicate> Predicate;
- this->m_icont.unique_and_dispose(Predicate(binary_pred), Destroyer(*this));
+ this->icont().unique_and_dispose(Predicate(binary_pred), Destroyer(this->node_alloc()));
}
//! <b>Requires</b>: The lists x and *this must be distinct.
@@ -1027,7 +1023,7 @@
void merge(list<T, A>& x, StrictWeakOrdering comp)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.merge(x.m_icont,
+ this->icont().merge(x.icont(),
ValueCompareToNodeCompare<StrictWeakOrdering>(comp));
}
else{
@@ -1080,7 +1076,7 @@
// nothing if the list has length 0 or 1.
if (this->size() < 2)
return;
- this->m_icont.sort(ValueCompareToNodeCompare<StrictWeakOrdering>(comp));
+ this->icont().sort(ValueCompareToNodeCompare<StrictWeakOrdering>(comp));
}
/// @cond
@@ -1099,7 +1095,7 @@
(const_iterator pos, InpIterator beg, InpIterator end, allocator_v1, std::input_iterator_tag)
{
for (; beg != end; ++beg){
- this->m_icont.insert(pos.get(), *this->create_node_from_it(beg));
+ this->icont().insert(pos.get(), *this->create_node_from_it(beg));
}
}
@@ -1110,36 +1106,31 @@
priv_create_and_insert_nodes(pos, beg, end, allocator_v1(), std::input_iterator_tag());
}
- template<class FwdIterator>
- void priv_create_and_insert_nodes
- (const_iterator pos, FwdIterator beg, FwdIterator end, allocator_v2, std::forward_iterator_tag)
+ class insertion_functor;
+ friend class insertion_functor;
+
+ class insertion_functor
{
- //Optimize memory allocation obtaining the distance between iterators
- size_type n = std::distance(beg, end);
+ Icont &icont_;
+ typename Icont::iterator pos_;
- //Allocate and construct as many nodes as possible with
- //the one-shot allocation
- typedef typename NodeAlloc::multiallocation_iterator multiallocation_iterator;
- multiallocation_iterator many_beg, itend, it;
- size_type received_array;
- FwdIterator next = this->allocate_many_and_construct
- (beg, n, many_beg, received_array);
-
- //Insert constructed nodes (this does not throw)
- for (it = many_beg; it != itend; ++it){
- this->m_icont.insert(pos.get(), *it);
- }
+ public:
+ insertion_functor(Icont &icont, typename Icont::iterator pos)
+ : icont_(icont), pos_(pos)
+ {}
- //Insert remaining nodes using individual allocation
- //(this can throw, but there is no leak)
- for (size_type i = received_array; i < n; ++i, ++next){
- this->m_icont.insert(pos.get(), *this->create_node_from_it(next));
- }
+ void operator()(Node &n)
+ { this->icont_.insert(pos_, n); }
+ };
- //good old version
- //for (; beg != end; ++beg){
- // this->m_icont.insert(pos.get(), *this->create_node(*beg));
- //}
+
+ template<class FwdIterator>
+ void priv_create_and_insert_nodes
+ (const_iterator pos, FwdIterator beg, FwdIterator end, allocator_v2, std::forward_iterator_tag)
+ {
+ //Optimized allocation and construction
+ this->allocate_many_and_construct
+ (beg, std::distance(beg, end), insertion_functor(this->icont(), pos.get()));
}
//Default constructed version
Modified: branches/bcbboost/boost/interprocess/containers/map.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/map.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/map.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -40,8 +40,8 @@
*
*/
-#ifndef BOOST_INTERPROCESS_SHMEM_MAP_HPP
-#define BOOST_INTERPROCESS_SHMEM_MAP_HPP
+#ifndef BOOST_INTERPROCESS_MAP_HPP
+#define BOOST_INTERPROCESS_MAP_HPP
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
@@ -687,10 +687,9 @@
#endif
-
-
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class T, class P, class A>
struct is_movable<map<T, P, A> >
{
@@ -1238,5 +1237,5 @@
#include <boost/interprocess/detail/config_end.hpp>
-#endif /* BOOST_INTERPROCESS_SHMEM_MAP_HPP */
+#endif /* BOOST_INTERPROCESS_MAP_HPP */
Modified: branches/bcbboost/boost/interprocess/containers/set.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/set.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/set.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -532,7 +532,8 @@
#endif
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class T, class P, class A>
struct is_movable<set<T, P, A> >
{
@@ -1015,7 +1016,8 @@
#endif
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class T, class P, class A>
struct is_movable<multiset<T, P, A> >
{
Modified: branches/bcbboost/boost/interprocess/containers/slist.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/slist.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/slist.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -71,15 +71,11 @@
/// @cond
template <class T, class VoidPointer>
struct slist_node
- : public boost::intrusive::slist_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , VoidPointer>
+ : public bi::make_slist_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type
{
- typedef boost::intrusive::slist_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , VoidPointer> hook_type;
+ typedef typename bi::make_slist_base_hook
+ <bi::void_pointer<VoidPointer>, bi::link_mode<bi::normal_link> >::type hook_type;
slist_node()
: m_data()
@@ -106,11 +102,12 @@
typedef typename detail::slist_node
<value_type, void_pointer> node_type;
- typedef typename boost::intrusive::slist
- <typename node_type::hook_type::
- template value_traits<node_type>
- ,true
- ,typename A::size_type> container_type;
+ typedef typename bi::make_slist
+ <node_type
+ ,bi::base_hook<typename node_type::hook_type>
+ ,bi::constant_time_size<true>
+ ,bi::size_type<typename A::size_type>
+ >::type container_type;
typedef container_type type ;
};
@@ -355,7 +352,7 @@
//!
//! <b>Complexity</b>: Linear to the elements x contains.
slist(const slist& x)
- : AllocHolder(static_cast<const NodeAlloc&>(x))
+ : AllocHolder(x)
{ this->insert_after(this->before_begin(), x.begin(), x.end()); }
//! <b>Effects</b>: Move constructor. Moves mx's resources to *this.
@@ -432,13 +429,13 @@
//!
//! <b>Complexity</b>: Constant.
allocator_type get_allocator() const
- { return allocator_type(*this); }
+ { return allocator_type(this->node_alloc()); }
const stored_allocator_type &get_stored_allocator() const
- { return *this; }
+ { return this->node_alloc(); }
stored_allocator_type &get_stored_allocator()
- { return *this; }
+ { return this->node_alloc(); }
public:
@@ -470,7 +467,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator begin()
- { return iterator(this->m_icont.begin()); }
+ { return iterator(this->icont().begin()); }
//! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
//!
@@ -486,7 +483,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator end()
- { return iterator(this->m_icont.end()); }
+ { return iterator(this->icont().end()); }
//! <b>Effects</b>: Returns a const_iterator to the end of the list.
//!
@@ -522,7 +519,7 @@
//!
//! <b>Complexity</b>: Constant.
size_type size() const
- { return this->m_icont.size(); }
+ { return this->icont().size(); }
//! <b>Effects</b>: Returns the largest possible size of the list.
//!
@@ -579,7 +576,7 @@
//!
//! <b>Complexity</b>: Amortized constant time.
void push_front(const value_type& x)
- { this->m_icont.push_front(*this->create_node(x)); }
+ { this->icont().push_front(*this->create_node(x)); }
//! <b>Effects</b>: Constructs a new element in the beginning of the list
//! and moves the resources of t to this new element.
@@ -589,10 +586,10 @@
//! <b>Complexity</b>: Amortized constant time.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void push_front(const detail::moved_object<T>& x)
- { this->m_icont.push_front(*this->create_node(x)); }
+ { this->icont().push_front(*this->create_node(x)); }
#else
void push_front(T && x)
- { this->m_icont.push_front(*this->create_node(move(x))); }
+ { this->icont().push_front(*this->create_node(move(x))); }
#endif
//! <b>Effects</b>: Removes the first element from the list.
@@ -601,7 +598,7 @@
//!
//! <b>Complexity</b>: Amortized constant time.
void pop_front()
- { this->m_icont.pop_front_and_dispose(Destroyer(*this)); }
+ { this->icont().pop_front_and_dispose(Destroyer(this->node_alloc())); }
//! <b>Returns</b>: The iterator to the element before i in the sequence.
//! Returns the end-iterator, if either i is the begin-iterator or the
@@ -611,7 +608,7 @@
//!
//! <b>Complexity</b>: Linear to the number of elements before i.
iterator previous(iterator p)
- { return iterator(this->m_icont.previous(p.get())); }
+ { return iterator(this->icont().previous(p.get())); }
//! <b>Returns</b>: The const_iterator to the element before i in the sequence.
//! Returns the end-const_iterator, if either i is the begin-const_iterator or
@@ -621,7 +618,7 @@
//!
//! <b>Complexity</b>: Linear to the number of elements before i.
const_iterator previous(const_iterator p)
- { return const_iterator(this->m_icont.previous(p.get())); }
+ { return const_iterator(this->icont().previous(p.get())); }
//! <b>Requires</b>: p must be a valid iterator of *this.
//!
@@ -637,7 +634,7 @@
//! <b>Note</b>: Does not affect the validity of iterators and references of
//! previous values.
iterator insert_after(iterator prev_pos, const value_type& x)
- { return iterator(this->m_icont.insert_after(prev_pos.get(), *this->create_node(x))); }
+ { return iterator(this->icont().insert_after(prev_pos.get(), *this->create_node(x))); }
//! <b>Requires</b>: prev_pos must be a valid iterator of *this.
//!
@@ -654,10 +651,10 @@
//! previous values.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
iterator insert_after(iterator prev_pos, const detail::moved_object<value_type>& x)
- { return iterator(this->m_icont.insert_after(prev_pos.get(), *this->create_node(x))); }
+ { return iterator(this->icont().insert_after(prev_pos.get(), *this->create_node(x))); }
#else
iterator insert_after(iterator prev_pos, value_type && x)
- { return iterator(this->m_icont.insert_after(prev_pos.get(), *this->create_node(move(x)))); }
+ { return iterator(this->icont().insert_after(prev_pos.get(), *this->create_node(move(x)))); }
#endif
//! <b>Requires</b>: prev_pos must be a valid iterator of *this.
@@ -754,7 +751,7 @@
//! <b>Note</b>: Does not invalidate iterators or references to non erased elements.
iterator erase_after(iterator prev_pos)
{
- return iterator(this->m_icont.erase_after_and_dispose(prev_pos.get(), Destroyer(*this)));
+ return iterator(this->icont().erase_after_and_dispose(prev_pos.get(), Destroyer(this->node_alloc())));
}
//! <b>Effects</b>: Erases the range (before_first, last) from
@@ -770,7 +767,7 @@
//! <b>Note</b>: Does not invalidate iterators or references to non erased elements.
iterator erase_after(iterator before_first, iterator last)
{
- return iterator(this->m_icont.erase_after_and_dispose(before_first.get(), last.get(), Destroyer(*this)));
+ return iterator(this->icont().erase_after_and_dispose(before_first.get(), last.get(), Destroyer(this->node_alloc())));
}
//! <b>Requires</b>: p must be a valid iterator of *this.
@@ -802,7 +799,7 @@
//! <b>Complexity</b>: Linear to the difference between size() and new_size.
void resize(size_type new_size, const T& x)
{
- typename Icont::iterator end_n(this->m_icont.end()), cur(end_n), cur_next;
+ typename Icont::iterator end_n(this->icont().end()), cur(end_n), cur_next;
while (++(cur_next = cur) != end_n && new_size > 0){
--new_size;
cur = cur_next;
@@ -821,7 +818,7 @@
//! <b>Complexity</b>: Linear to the difference between size() and new_size.
void resize(size_type new_size)
{
- typename Icont::iterator end_n(this->m_icont.end()), cur(end_n), cur_next;
+ typename Icont::iterator end_n(this->icont().end()), cur(end_n), cur_next;
size_type len = this->size();
size_type left = new_size;
@@ -843,7 +840,7 @@
//!
//! <b>Complexity</b>: Linear to the number of elements in the list.
void clear()
- { this->m_icont.clear_and_dispose(Destroyer(*this)); }
+ { this->icont().clear_and_dispose(Destroyer(this->node_alloc())); }
//! <b>Requires</b>: p must point to an element contained
//! by the list. x != *this
@@ -861,7 +858,7 @@
void splice_after(iterator prev_pos, slist& x)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice_after(prev_pos.get(), x.m_icont);
+ this->icont().splice_after(prev_pos.get(), x.icont());
}
else{
throw std::runtime_error("slist::splice called with unequal allocators");
@@ -891,7 +888,7 @@
void splice_after(iterator prev_pos, slist& x, iterator prev)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice_after(prev_pos.get(), x.m_icont, prev.get());
+ this->icont().splice_after(prev_pos.get(), x.icont(), prev.get());
}
else{
throw std::runtime_error("slist::splice called with unequal allocators");
@@ -923,8 +920,8 @@
iterator before_first, iterator before_last)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice_after
- (prev_pos.get(), x.m_icont, before_first.get(), before_last.get());
+ this->icont().splice_after
+ (prev_pos.get(), x.icont(), before_first.get(), before_last.get());
}
else{
throw std::runtime_error("slist::splice called with unequal allocators");
@@ -955,8 +952,8 @@
size_type n)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.splice_after
- (prev_pos.get(), x.m_icont, before_first.get(), before_last.get(), n);
+ this->icont().splice_after
+ (prev_pos.get(), x.icont(), before_first.get(), before_last.get(), n);
}
else{
throw std::runtime_error("slist::splice called with unequal allocators");
@@ -1034,7 +1031,7 @@
//!
//! <b>Note</b>: Iterators and references are not invalidated
void reverse()
- { this->m_icont.reverse(); }
+ { this->icont().reverse(); }
//! <b>Effects</b>: Removes all the elements that compare equal to value.
//!
@@ -1060,7 +1057,7 @@
void remove_if(Pred pred)
{
typedef ValueCompareToNodeCompare<Pred> Predicate;
- this->m_icont.remove_and_dispose_if(Predicate(pred), Destroyer(*this));
+ this->icont().remove_and_dispose_if(Predicate(pred), Destroyer(this->node_alloc()));
}
//! <b>Effects</b>: Removes adjacent duplicate elements or adjacent
@@ -1088,7 +1085,7 @@
void unique(Pred pred)
{
typedef ValueCompareToNodeCompare<Pred> Predicate;
- this->m_icont.unique_and_dispose(Predicate(pred), Destroyer(*this));
+ this->icont().unique_and_dispose(Predicate(pred), Destroyer(this->node_alloc()));
}
//! <b>Requires</b>: The lists x and *this must be distinct.
@@ -1126,7 +1123,7 @@
void merge(slist& x, StrictWeakOrdering comp)
{
if((NodeAlloc&)*this == (NodeAlloc&)x){
- this->m_icont.merge(x.m_icont,
+ this->icont().merge(x.icont(),
ValueCompareToNodeCompare<StrictWeakOrdering>(comp));
}
else{
@@ -1165,11 +1162,12 @@
// nothing if the slist has length 0 or 1.
if (this->size() < 2)
return;
- this->m_icont.sort(ValueCompareToNodeCompare<StrictWeakOrdering>(comp));
+ this->icont().sort(ValueCompareToNodeCompare<StrictWeakOrdering>(comp));
}
/// @cond
private:
+
//Iterator range version
template<class InpIterator>
void priv_create_and_insert_nodes
@@ -1184,7 +1182,7 @@
(const_iterator prev, InpIterator beg, InpIterator end, allocator_v1, std::input_iterator_tag)
{
for (; beg != end; ++beg){
- this->m_icont.insert_after(prev.get(), *this->create_node_from_it(beg));
+ this->icont().insert_after(prev.get(), *this->create_node_from_it(beg));
++prev;
}
}
@@ -1196,39 +1194,30 @@
priv_create_and_insert_nodes(prev, beg, end, allocator_v1(), std::input_iterator_tag());
}
- template<class FwdIterator>
- void priv_create_and_insert_nodes
- (const_iterator prev, FwdIterator beg, FwdIterator end, allocator_v2, std::forward_iterator_tag)
+ class insertion_functor;
+ friend class insertion_functor;
+
+ class insertion_functor
{
- //Optimize memory allocation obtaining the distance between iterators
- size_type n = std::distance(beg, end);
+ Icont &icont_;
+ typename Icont::iterator prev_;
- //Allocate and construct as many nodes as possible with
- //the one-shot allocation
- typedef typename NodeAlloc::multiallocation_iterator multiallocation_iterator;
- multiallocation_iterator many_beg, itend, it;
- size_type received_array;
- FwdIterator next = this->allocate_many_and_construct
- (beg, n, many_beg, received_array);
-
- //Insert constructed nodes (this does not throw)
- for (it = many_beg; it != itend; ++it){
- this->m_icont.insert_after(prev.get(), *it);
- ++prev;
- }
+ public:
+ insertion_functor(Icont &icont, typename Icont::iterator prev)
+ : icont_(icont), prev_(prev)
+ {}
- //Insert remaining nodes using individual allocation
- //(this can throw, but there is no leak)
- for (size_type i = received_array; i < n; ++i, ++next){
- this->m_icont.insert_after(prev.get(), *this->create_node_from_it(next));
- ++prev;
- }
+ void operator()(Node &n)
+ { prev_ = this->icont_.insert_after(prev_, n); }
+ };
- //good old version
- //for (; beg != end; ++beg){
- // this->m_icont.insert_after(prev.get(), *this->create_node(*beg));
- // ++prev;
- //}
+ template<class FwdIterator>
+ void priv_create_and_insert_nodes
+ (const_iterator prev, FwdIterator beg, FwdIterator end, allocator_v2, std::forward_iterator_tag)
+ {
+ //Optimized allocation and construction
+ this->allocate_many_and_construct
+ (beg, std::distance(beg, end), insertion_functor(this->icont(), prev.get()));
}
//Default constructed version
Modified: branches/bcbboost/boost/interprocess/containers/string.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/string.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/string.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -75,7 +75,6 @@
// allocator and whose size is this->m_storage.
template <class A>
class basic_string_base
- : private A
{
basic_string_base();
public:
@@ -86,20 +85,12 @@
typedef typename A::value_type value_type;
typedef typename A::size_type size_type;
- allocator_type get_allocator() const { return *this; }
-
- const stored_allocator_type &get_stored_allocator() const
- { return *this; }
-
- stored_allocator_type &get_stored_allocator()
- { return *this; }
-
basic_string_base(const allocator_type& a)
- : allocator_type(a)
+ : members_(a)
{ init(); }
basic_string_base(const allocator_type& a, std::size_t n)
- : allocator_type(a)
+ : members_(a)
{
this->init();
this->allocate_initial_block(n);
@@ -107,14 +98,14 @@
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_string_base(const detail::moved_object<basic_string_base<A> >& b)
- : allocator_type(static_cast<allocator_type&>(b.get()))
+ : members_(b.get().members_)
{
init();
this->swap(b.get());
}
#else
basic_string_base(basic_string_base<A> && b)
- : allocator_type(static_cast<allocator_type&>(b))
+ : members_(b.members_)
{
init();
this->swap(b);
@@ -125,7 +116,7 @@
{
this->deallocate_block();
if(!this->is_short()){
- static_cast<long_t*>(static_cast<void*>(&m_repr.r))->~long_t();
+ static_cast<long_t*>(static_cast<void*>(&this->members_.m_repr.r))->~long_t();
}
}
@@ -212,7 +203,23 @@
long_t &long_repr() const
{ return *static_cast<long_t*>(const_cast<void*>(static_cast<const void*>(&r))); }
- } m_repr;
+ };
+
+ struct members_holder
+ : public A
+ {
+ members_holder(const A &a)
+ : A(a)
+ {}
+
+ repr_t m_repr;
+ } members_;
+
+ const A &alloc() const
+ { return members_; }
+
+ A &alloc()
+ { return members_; }
static const size_type InternalBufferChars = (sizeof(repr_t) - ShortDataOffset)/sizeof(value_type);
@@ -222,24 +229,24 @@
protected:
bool is_short() const
- { return static_cast<bool>(m_repr.s.h.is_short != 0); }
+ { return static_cast<bool>(this->members_.m_repr.s.h.is_short != 0); }
void is_short(bool yes)
{
if(yes && !this->is_short()){
- static_cast<long_t*>(static_cast<void*>(&m_repr.r))->~long_t();
+ static_cast<long_t*>(static_cast<void*>(&this->members_.m_repr.r))->~long_t();
}
else{
- new(static_cast<void*>(&m_repr.r))long_t();
+ new(static_cast<void*>(&this->members_.m_repr.r))long_t();
}
- m_repr.s.h.is_short = yes;
+ this->members_.m_repr.s.h.is_short = yes;
}
private:
void init()
{
- m_repr.s.h.is_short = 1;
- m_repr.s.h.length = 0;
+ this->members_.m_repr.s.h.is_short = 1;
+ this->members_.m_repr.s.h.length = 0;
}
protected:
@@ -276,7 +283,7 @@
if(!(command & allocate_new))
return std::pair<pointer, bool>(0, 0);
received_size = preferred_size;
- return std::make_pair(A::allocate(received_size), false);
+ return std::make_pair(this->alloc().allocate(received_size), false);
}
std::pair<pointer, bool>
@@ -287,17 +294,17 @@
pointer reuse,
allocator_v2)
{
- return A::allocation_command(command, limit_size, preferred_size,
- received_size, reuse);
+ return this->alloc().allocation_command(command, limit_size, preferred_size,
+ received_size, reuse);
}
size_type next_capacity(size_type additional_objects) const
- { return get_next_capacity(A::max_size(), this->priv_storage(), additional_objects); }
+ { return get_next_capacity(this->alloc().max_size(), this->priv_storage(), additional_objects); }
void deallocate(pointer p, std::size_t n)
{
if (p && (n > InternalBufferChars))
- allocator_type::deallocate(p, n);
+ this->alloc().deallocate(p, n);
}
void construct(pointer p, const value_type &value = value_type())
@@ -332,7 +339,7 @@
{ this->deallocate(this->priv_addr(), this->priv_storage()); }
std::size_t max_size() const
- { return A::max_size() - 1; }
+ { return this->alloc().max_size() - 1; }
// Helper functions for exception handling.
void throw_length_error() const
@@ -341,66 +348,60 @@
void throw_out_of_range() const
{ throw(std::out_of_range("basic_string")); }
- A & get_alloc()
- { return *this; }
-
- const A & get_alloc() const
- { return *this; }
-
protected:
size_type priv_capacity() const
{ return this->priv_storage() - 1; }
pointer priv_addr() const
- { return this->is_short() ? pointer(&m_repr.short_repr().data[0]) : m_repr.long_repr().start; }
+ { return this->is_short() ? pointer(&this->members_.m_repr.short_repr().data[0]) : this->members_.m_repr.long_repr().start; }
void priv_addr(pointer addr)
- { m_repr.long_repr().start = addr; }
+ { this->members_.m_repr.long_repr().start = addr; }
size_type priv_storage() const
- { return this->is_short() ? InternalBufferChars : m_repr.long_repr().storage; }
+ { return this->is_short() ? InternalBufferChars : this->members_.m_repr.long_repr().storage; }
void priv_storage(size_type storage)
{
if(!this->is_short())
- m_repr.long_repr().storage = storage;
+ this->members_.m_repr.long_repr().storage = storage;
}
size_type priv_size() const
- { return this->is_short() ? m_repr.short_repr().h.length : m_repr.long_repr().length; }
+ { return this->is_short() ? this->members_.m_repr.short_repr().h.length : this->members_.m_repr.long_repr().length; }
void priv_size(size_type sz)
{
if(this->is_short())
- m_repr.s.h.length = (unsigned char)sz;
+ this->members_.m_repr.s.h.length = (unsigned char)sz;
else
- m_repr.long_repr().length = static_cast<typename A::size_type>(sz);
+ this->members_.m_repr.long_repr().length = static_cast<typename A::size_type>(sz);
}
void swap(basic_string_base& other)
{
if(this->is_short()){
if(other.is_short()){
- std::swap(m_repr, other.m_repr);
+ std::swap(this->members_.m_repr, other.members_.m_repr);
}
else{
- repr_t copy(m_repr);
- m_repr.long_repr() = other.m_repr.long_repr();
- other.m_repr = copy;
+ repr_t copied(this->members_.m_repr);
+ this->members_.m_repr.long_repr() = other.members_.m_repr.long_repr();
+ other.members_.m_repr = copied;
}
}
else{
if(other.is_short()){
- repr_t copy(other.m_repr);
- other.m_repr.long_repr() = m_repr.long_repr();
- m_repr = copy;
+ repr_t copied(other.members_.m_repr);
+ other.members_.m_repr.long_repr() = this->members_.m_repr.long_repr();
+ this->members_.m_repr = copied;
}
else{
- std::swap(m_repr.long_repr(), other.m_repr.long_repr());
+ std::swap(this->members_.m_repr.long_repr(), other.members_.m_repr.long_repr());
}
}
- allocator_type & this_al = this->get_alloc(), &other_al = other.get_alloc();
+ allocator_type & this_al = this->alloc(), &other_al = other.alloc();
if(this_al != other_al){
detail::do_swap(this_al, other_al);
}
@@ -540,7 +541,7 @@
//!
//! <b>Throws</b>: If allocator_type's default constructor or copy constructor throws.
basic_string(const basic_string& s)
- : base_t(s.get_allocator())
+ : base_t(s.alloc())
{ this->priv_range_initialize(s.begin(), s.end()); }
//! <b>Effects</b>: Move constructor. Moves mx's resources to *this.
@@ -735,7 +736,7 @@
//!
//! <b>Complexity</b>: Constant.
allocator_type get_allocator() const
- { return base_t::get_allocator(); }
+ { return this->alloc(); }
//! <b>Effects</b>: Returns the number of the elements contained in the vector.
//!
@@ -1531,7 +1532,7 @@
if (pos > size())
this->throw_out_of_range();
return basic_string(this->priv_addr() + pos,
- this->priv_addr() + pos + min_value(n, size() - pos), this->get_alloc());
+ this->priv_addr() + pos + min_value(n, size() - pos), this->alloc());
}
//! <b>Effects</b>: Three-way lexicographical comparison of s and *this.
@@ -1917,7 +1918,7 @@
typedef basic_string<CharT,Traits,A> str_t;
typedef typename str_t::reserve_t reserve_t;
reserve_t reserve;
- str_t result(reserve, x.size() + y.size(), x.get_allocator());
+ str_t result(reserve, x.size() + y.size(), x.alloc());
result.append(x);
result.append(y);
return result;
@@ -2038,7 +2039,7 @@
typedef typename str_t::reserve_t reserve_t;
reserve_t reserve;
const std::size_t n = Traits::length(s);
- str_t result(reserve, x.size() + n, x.get_allocator());
+ str_t result(reserve, x.size() + n, x.alloc());
result.append(x);
result.append(s, s + n);
return result;
@@ -2071,7 +2072,7 @@
typedef basic_string<CharT,Traits,A> str_t;
typedef typename str_t::reserve_t reserve_t;
reserve_t reserve;
- str_t result(reserve, x.size() + 1, x.get_allocator());
+ str_t result(reserve, x.size() + 1, x.alloc());
result.append(x);
result.push_back(c);
return result;
@@ -2457,14 +2458,15 @@
}
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class C, class T, class A>
struct is_movable<basic_string<C, T, A> >
{
enum { value = true };
};
-/*!This class is movable*/
+//!This class is movable
template <class A>
struct is_movable<detail::basic_string_base<A> >
{
Modified: branches/bcbboost/boost/interprocess/containers/vector.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/containers/vector.hpp (original)
+++ branches/bcbboost/boost/interprocess/containers/vector.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -52,10 +52,14 @@
#include <stdexcept>
#include <iterator>
#include <utility>
+#include <string.h> //for memcopy, memmove
#include <boost/detail/no_exceptions_support.hpp>
#include <boost/type_traits/has_trivial_destructor.hpp>
-
+#include <boost/type_traits/has_trivial_copy.hpp>
+#include <boost/type_traits/has_trivial_assign.hpp>
+#include <boost/type_traits/has_nothrow_copy.hpp>
+#include <boost/type_traits/has_nothrow_assign.hpp>
#include <boost/interprocess/detail/version_type.hpp>
#include <boost/interprocess/allocators/allocation_type.hpp>
#include <boost/interprocess/detail/utilities.hpp>
@@ -71,40 +75,191 @@
namespace interprocess {
/// @cond
+
namespace detail {
+
+//! Const vector_iterator used to iterate through a vector.
+template <class Pointer>
+class vector_const_iterator
+ : public std::iterator<std::random_access_iterator_tag
+ ,const typename std::iterator_traits<Pointer>::value_type
+ ,typename std::iterator_traits<Pointer>::difference_type
+ ,typename pointer_to_other
+ <Pointer
+ ,const typename std::iterator_traits<Pointer>::value_type
+ >::type
+ ,const typename std::iterator_traits<Pointer>::value_type &>
+{
+ public:
+ typedef const typename std::iterator_traits<Pointer>::value_type value_type;
+ typedef typename std::iterator_traits<Pointer>::difference_type difference_type;
+ typedef typename pointer_to_other<Pointer, value_type>::type pointer;
+ typedef value_type& reference;
+
+ /// @cond
+ protected:
+ Pointer m_ptr;
+
+ public:
+ Pointer get_ptr() const { return m_ptr; }
+ explicit vector_const_iterator(Pointer ptr) : m_ptr(ptr){}
+ /// @endcond
+
+ public:
+
+ //Constructors
+ vector_const_iterator() : m_ptr(0){}
+
+ //Pointer like operators
+ reference operator*() const
+ { return *m_ptr; }
+
+ const value_type * operator->() const
+ { return detail::get_pointer(m_ptr); }
+
+ reference operator[](difference_type off) const
+ { return m_ptr[off]; }
+
+ //Increment / Decrement
+ vector_const_iterator& operator++()
+ { ++m_ptr; return *this; }
+
+ vector_const_iterator operator++(int)
+ { Pointer tmp = m_ptr; ++*this; return vector_const_iterator(tmp); }
+
+ vector_const_iterator& operator--()
+ { --m_ptr; return *this; }
+
+ vector_const_iterator operator--(int)
+ { Pointer tmp = m_ptr; --*this; return vector_const_iterator(tmp); }
+
+ //Arithmetic
+ vector_const_iterator& operator+=(difference_type off)
+ { m_ptr += off; return *this; }
+
+ vector_const_iterator operator+(difference_type off) const
+ { return vector_const_iterator(m_ptr+off); }
+
+ friend vector_const_iterator operator+(difference_type off, const vector_const_iterator& right)
+ { return vector_const_iterator(off + right.m_ptr); }
+
+ vector_const_iterator& operator-=(difference_type off)
+ { m_ptr -= off; return *this; }
+
+ vector_const_iterator operator-(difference_type off) const
+ { return vector_const_iterator(m_ptr-off); }
+
+ difference_type operator-(const vector_const_iterator& right) const
+ { return m_ptr - right.m_ptr; }
+
+ //Comparison operators
+ bool operator== (const vector_const_iterator& r) const
+ { return m_ptr == r.m_ptr; }
+
+ bool operator!= (const vector_const_iterator& r) const
+ { return m_ptr != r.m_ptr; }
+
+ bool operator< (const vector_const_iterator& r) const
+ { return m_ptr < r.m_ptr; }
+
+ bool operator<= (const vector_const_iterator& r) const
+ { return m_ptr <= r.m_ptr; }
+
+ bool operator> (const vector_const_iterator& r) const
+ { return m_ptr > r.m_ptr; }
+
+ bool operator>= (const vector_const_iterator& r) const
+ { return m_ptr >= r.m_ptr; }
+};
+
+//! Iterator used to iterate through a vector
+template <class Pointer>
+class vector_iterator
+ : public vector_const_iterator<Pointer>
+{
+ public:
+ explicit vector_iterator(Pointer ptr)
+ : vector_const_iterator<Pointer>(ptr)
+ {}
+
+ public:
+ typedef typename std::iterator_traits<Pointer>::value_type value_type;
+ typedef typename vector_const_iterator<Pointer>::difference_type difference_type;
+ typedef Pointer pointer;
+ typedef value_type& reference;
+
+ //Constructors
+ vector_iterator()
+ {}
+
+ //Pointer like operators
+ reference operator*() const
+ { return *this->m_ptr; }
+
+ value_type* operator->() const
+ { return detail::get_pointer(this->m_ptr); }
+
+ reference operator[](difference_type off) const
+ { return this->m_ptr[off]; }
+
+ //Increment / Decrement
+ vector_iterator& operator++()
+ { ++this->m_ptr; return *this; }
+
+ vector_iterator operator++(int)
+ { pointer tmp = this->m_ptr; ++*this; return vector_iterator(tmp); }
+
+ vector_iterator& operator--()
+ { --this->m_ptr; return *this; }
+
+ vector_iterator operator--(int)
+ { vector_iterator tmp = *this; --*this; return vector_iterator(tmp); }
+
+ // Arithmetic
+ vector_iterator& operator+=(difference_type off)
+ { this->m_ptr += off; return *this; }
+
+ vector_iterator operator+(difference_type off) const
+ { return vector_iterator(this->m_ptr+off); }
+
+ friend vector_iterator operator+(difference_type off, const vector_iterator& right)
+ { return vector_iterator(off + right.m_ptr); }
+
+ vector_iterator& operator-=(difference_type off)
+ { this->m_ptr -= off; return *this; }
+
+ vector_iterator operator-(difference_type off) const
+ { return vector_iterator(this->m_ptr-off); }
+
+ difference_type operator-(const vector_const_iterator<Pointer>& right) const
+ { return static_cast<const vector_const_iterator<Pointer>&>(*this) - right; }
+};
+
//!This struct deallocates and allocated memory
template <class A>
struct vector_alloc_holder
- : public A
{
typedef typename A::pointer pointer;
typedef typename A::size_type size_type;
typedef typename A::value_type value_type;
- enum { trivial_dctr_after_move =
- has_trivial_destructor_after_move<value_type>::value ||
- boost::has_trivial_destructor<value_type>::value };
+ static const bool trivial_dctr = boost::has_trivial_destructor<value_type>::value;
+ static const bool trivial_dctr_after_move =
+ has_trivial_destructor_after_move<value_type>::value || trivial_dctr;
+ static const bool trivial_copy = has_trivial_copy<value_type>::value;
+ static const bool nothrow_copy = has_nothrow_copy<value_type>::value;
+ static const bool trivial_assign = has_trivial_assign<value_type>::value;
+ static const bool nothrow_assign = has_nothrow_assign<value_type>::value;
//Constructor, does not throw
vector_alloc_holder(const A &a)
- : A(a), m_start(0), m_size(0), m_capacity(0)
+ : members_(a)
{}
//Constructor, does not throw
vector_alloc_holder(const vector_alloc_holder<A> &h)
- : A((A&)h), m_start(0), m_size(0), m_capacity(0)
- {}
-
- //Constructor, does not throw
- #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
- vector_alloc_holder(const detail::moved_object<vector_alloc_holder<A> > &h)
- : A(move((A&)h.get())), m_start(0), m_size(0), m_capacity(0)
+ : members_(h.alloc())
{}
- #else
- vector_alloc_holder(vector_alloc_holder<A> &&h)
- : A(move((A&)h)), m_start(0), m_size(0), m_capacity(0)
- {}
- #endif
//Destructor
~vector_alloc_holder()
@@ -137,7 +292,7 @@
if(!(command & allocate_new))
return std::pair<pointer, bool>(0, 0);
received_size = preferred_size;
- return std::make_pair(A::allocate(received_size), false);
+ return std::make_pair(this->alloc().allocate(received_size), false);
}
std::pair<pointer, bool>
@@ -148,38 +303,56 @@
const pointer &reuse,
allocator_v2)
{
- return A::allocation_command(command, limit_size, preferred_size,
- received_size, reuse);
+ return this->alloc().allocation_command(command, limit_size, preferred_size,
+ received_size, reuse);
}
size_type next_capacity(size_type additional_objects) const
- { return get_next_capacity(A::max_size(), this->m_capacity, additional_objects); }
+ { return get_next_capacity(this->alloc().max_size(), this->members_.m_capacity, additional_objects); }
- pointer m_start;
- size_type m_size;
- size_type m_capacity;
+ struct members_holder
+ : public A
+ {
+ private:
+ members_holder(const members_holder&);
+
+ public:
+ members_holder(const A &alloc)
+ : A(alloc), m_start(0), m_size(0), m_capacity(0)
+ {}
+
+ pointer m_start;
+ size_type m_size;
+ size_type m_capacity;
+ } members_;
protected:
void prot_deallocate()
{
- if(!m_start) return;
- this->deallocate(m_start, m_capacity);
- m_start = 0;
- m_size = 0;
- m_capacity = 0;
+ if(!this->members_.m_start) return;
+ this->alloc().deallocate(this->members_.m_start, this->members_.m_capacity);
+ this->members_.m_start = 0;
+ this->members_.m_size = 0;
+ this->members_.m_capacity = 0;
}
- void destroy(pointer p)
+ void destroy(value_type* p)
{
- if(!has_trivial_destructor<value_type>::value)
+ if(!trivial_dctr)
detail::get_pointer(p)->~value_type();
}
- void destroy_n(pointer p, size_type n)
+ void destroy_n(value_type* p, size_type n)
{
- if(!has_trivial_destructor<value_type>::value)
- for(; n--; ++p) detail::get_pointer(p)->~value_type();
+ if(!trivial_dctr)
+ for(; n--; ++p) p->~value_type();
}
+
+ A &alloc()
+ { return members_; }
+
+ const A &alloc() const
+ { return members_; }
};
} //namespace detail {
@@ -197,192 +370,28 @@
/// @cond
typedef vector<T, A> self_t;
typedef detail::vector_alloc_holder<A> base_t;
- typedef detail::scoped_array_deallocator<A> dealloc_t;
/// @endcond
public:
//! The type of object, T, stored in the vector
- typedef T value_type;
+ typedef T value_type;
//! Pointer to T
- typedef typename A::pointer pointer;
+ typedef typename A::pointer pointer;
//! Const pointer to T
- typedef typename A::const_pointer const_pointer;
+ typedef typename A::const_pointer const_pointer;
//! Reference to T
- typedef typename A::reference reference;
+ typedef typename A::reference reference;
//! Const reference to T
- typedef typename A::const_reference const_reference;
+ typedef typename A::const_reference const_reference;
//! An unsigned integral type
- typedef typename A::size_type size_type;
+ typedef typename A::size_type size_type;
//! A signed integral type
- typedef typename A::difference_type difference_type;
+ typedef typename A::difference_type difference_type;
//! The allocator type
- typedef A allocator_type;
- //! The stored allocator type
- typedef allocator_type stored_allocator_type;
-
- /// @cond
- private:
- //This shouldn't be needed but VC6.0 needs this
- typedef typename A::pointer vec_ptr;
- typedef typename A::const_pointer vec_cptr;
- typedef typename A::reference vec_ref;
- typedef typename A::const_reference vec_cref;
- typedef typename A::difference_type vec_diff;
-
-
- typedef typename base_t::allocator_v1 allocator_v1;
- typedef typename base_t::allocator_v2 allocator_v2;
- typedef typename base_t::alloc_version alloc_version;
-
- typedef constant_iterator<T, difference_type> cvalue_iterator;
- /// @endcond
- public:
-
- /// @cond
-
- //! Const iterator used to iterate through a vector.
- class const_iterator
- : public std::iterator<std::random_access_iterator_tag
- ,value_type
- ,vec_diff
- ,vec_cptr
- ,vec_cref>
- {
- /// @cond
- private:
- vec_ptr get_ptr() const { return m_ptr; }
-
- protected:
- vec_ptr m_ptr;
- explicit const_iterator(vec_ptr ptr) : m_ptr(ptr){}
- /// @endcond
- public:
- friend class vector<T, A>;
- typedef vec_diff difference_type;
-
- //Constructors
- const_iterator() : m_ptr(0){}
-
- //Pointer like operators
- const_reference operator*() const
- { return *m_ptr; }
-
- const_pointer operator->() const
- { return m_ptr; }
-
- const_reference operator[](difference_type off) const
- { return m_ptr[off]; }
-
- //Increment / Decrement
- const_iterator& operator++()
- { ++m_ptr; return *this; }
-
- const_iterator operator++(int)
- { vec_ptr tmp = m_ptr; ++*this; return const_iterator(tmp); }
-
- const_iterator& operator--()
- { --m_ptr; return *this; }
-
- const_iterator operator--(int)
- { vec_ptr tmp = m_ptr; --*this; return const_iterator(tmp); }
-
- //Arithmetic
- const_iterator& operator+=(difference_type off)
- { m_ptr += off; return *this; }
-
- const_iterator operator+(difference_type off) const
- { return const_iterator(m_ptr+off); }
-
- friend const_iterator operator+(difference_type off, const const_iterator& right)
- { return const_iterator(off + right.m_ptr); }
-
- const_iterator& operator-=(difference_type off)
- { m_ptr -= off; return *this; }
-
- const_iterator operator-(difference_type off) const
- { return const_iterator(m_ptr-off); }
-
- difference_type operator-(const const_iterator& right) const
- { return m_ptr - right.m_ptr; }
-
- //Comparison operators
- bool operator== (const const_iterator& r) const
- { return m_ptr == r.m_ptr; }
-
- bool operator!= (const const_iterator& r) const
- { return m_ptr != r.m_ptr; }
-
- bool operator< (const const_iterator& r) const
- { return m_ptr < r.m_ptr; }
-
- bool operator<= (const const_iterator& r) const
- { return m_ptr <= r.m_ptr; }
-
- bool operator> (const const_iterator& r) const
- { return m_ptr > r.m_ptr; }
-
- bool operator>= (const const_iterator& r) const
- { return m_ptr >= r.m_ptr; }
- };
-
- //! Iterator used to iterate through a vector
- class iterator
- : public const_iterator
- {
- protected:
- explicit iterator(vec_ptr ptr) : const_iterator(ptr){}
-
- public:
- friend class vector<T, A>;
- typedef vec_ptr pointer;
- typedef vec_ref reference;
-
- //Constructors
- iterator(){}
-
- //Pointer like operators
- reference operator*() const
- { return *this->m_ptr; }
-
- pointer operator->() const
- { return this->m_ptr; }
-
- reference operator[](difference_type off) const
- { return this->m_ptr[off]; }
-
- //Increment / Decrement
- iterator& operator++()
- { ++this->m_ptr; return *this; }
-
- iterator operator++(int)
- { pointer tmp = this->m_ptr; ++*this; return iterator(tmp); }
-
- iterator& operator--()
- { --this->m_ptr; return *this; }
-
- iterator operator--(int)
- { iterator tmp = *this; --*this; return iterator(tmp); }
-
- // Arithmetic
- iterator& operator+=(difference_type off)
- { this->m_ptr += off; return *this; }
-
- iterator operator+(difference_type off) const
- { return iterator(this->m_ptr+off); }
-
- friend iterator operator+(difference_type off, const iterator& right)
- { return iterator(off + right.m_ptr); }
-
- iterator& operator-=(difference_type off)
- { this->m_ptr -= off; return *this; }
-
- iterator operator-(difference_type off) const
- { return iterator(this->m_ptr-off); }
-
- difference_type operator-(const const_iterator& right) const
- { return *((const_iterator*)this) - right; }
- };
-
- /// @endcond
+ typedef A allocator_type;
+ //! The random access iterator
+ typedef detail::vector_iterator<pointer> iterator;
+ //! The random access const_iterator
+ typedef detail::vector_const_iterator<pointer> const_iterator;
//! Iterator used to iterate backwards through a vector.
typedef std::reverse_iterator<iterator>
@@ -390,6 +399,56 @@
//! Const iterator used to iterate backwards through a vector.
typedef std::reverse_iterator<const_iterator>
const_reverse_iterator;
+ //! The stored allocator type
+ typedef allocator_type stored_allocator_type;
+
+ /// @cond
+ private:
+
+ typedef typename base_t::allocator_v1 allocator_v1;
+ typedef typename base_t::allocator_v2 allocator_v2;
+ typedef typename base_t::alloc_version alloc_version;
+
+ typedef constant_iterator<T, difference_type> cvalue_iterator;
+ typedef repeat_iterator<T, difference_type> repeat_iterator;
+ typedef detail::move_iterator<repeat_iterator> repeat_move_it;
+ //This is the anti-exception array destructor
+ //to deallocate values already constructed
+ typedef typename detail::if_c
+ <base_t::trivial_dctr
+ ,detail::null_scoped_destructor_n<allocator_type>
+ ,detail::scoped_destructor_n<allocator_type>
+ >::type OldArrayDestructor;
+ //This is the anti-exception array destructor
+ //to destroy objects created with copy construction
+ typedef typename detail::if_c
+ <base_t::nothrow_copy
+ ,detail::null_scoped_destructor_n<allocator_type>
+ ,detail::scoped_destructor_n<allocator_type>
+ >::type UCopiedArrayDestructor;
+ //This is the anti-exception array deallocator
+ typedef typename detail::if_c
+ <base_t::nothrow_copy
+ ,detail::null_scoped_array_deallocator<allocator_type>
+ ,detail::scoped_array_deallocator<allocator_type>
+ >::type UCopiedArrayDeallocator;
+
+ //This is the optimized move iterator for copy constructors
+ //so that std::copy and similar can use memcpy
+ typedef typename detail::if_c
+ <base_t::trivial_copy
+ ,T*
+ ,detail::move_iterator<T*>
+ >::type copy_move_it;
+
+ //This is the optimized move iterator for assignments
+ //so that std::uninitialized_copy and similar can use memcpy
+ typedef typename detail::if_c
+ <base_t::trivial_assign
+ ,T*
+ ,detail::move_iterator<T*>
+ >::type assign_move_it;
+ /// @endcond
public:
@@ -430,28 +489,12 @@
//! <b>Complexity</b>: Constant.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
vector(const detail::moved_object<vector<T, A> >& mx)
- : base_t(move((base_t&)mx.get()))
- {
- vector<T, A> &x = mx.get();
- this->m_start = x.m_start;
- this->m_size = x.m_size;
- this->m_capacity = x.m_capacity;
- x.m_start = 0;
- x.m_size = 0;
- x.m_capacity = 0;
- }
+ : base_t(mx.get())
+ { this->swap(mx.get()); }
#else
vector(vector<T, A> && mx)
- : base_t(move((base_t&)mx))
- {
- vector<T, A> &x = mx;
- this->m_start = x.m_start;
- this->m_size = x.m_size;
- this->m_capacity = x.m_capacity;
- x.m_start = 0;
- x.m_size = 0;
- x.m_capacity = 0;
- }
+ : base_t(mx)
+ { this->swap(mx); }
#endif
//! <b>Effects</b>: Constructs a vector that will use a copy of allocator a
@@ -481,7 +524,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator begin()
- { return iterator(this->m_start); }
+ { return iterator(this->members_.m_start); }
//! <b>Effects</b>: Returns a const_iterator to the first element contained in the vector.
//!
@@ -489,7 +532,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator begin() const
- { return const_iterator(this->m_start); }
+ { return const_iterator(this->members_.m_start); }
//! <b>Effects</b>: Returns an iterator to the end of the vector.
//!
@@ -497,7 +540,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator end()
- { return iterator(this->m_start + this->m_size); }
+ { return iterator(this->members_.m_start + this->members_.m_size); }
//! <b>Effects</b>: Returns a const_iterator to the end of the vector.
//!
@@ -505,7 +548,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator end() const
- { return const_iterator(this->m_start + this->m_size); }
+ { return const_iterator(this->members_.m_start + this->members_.m_size); }
//! <b>Effects</b>: Returns a reverse_iterator pointing to the beginning
//! of the reversed vector.
@@ -552,7 +595,7 @@
//!
//! <b>Complexity</b>: Constant.
reference front()
- { return *this->m_start; }
+ { return *this->members_.m_start; }
//! <b>Requires</b>: !empty()
//!
@@ -563,7 +606,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference front() const
- { return *this->m_start; }
+ { return *this->members_.m_start; }
//! <b>Requires</b>: !empty()
//!
@@ -574,7 +617,7 @@
//!
//! <b>Complexity</b>: Constant.
reference back()
- { return this->m_start[this->m_size - 1]; }
+ { return this->members_.m_start[this->members_.m_size - 1]; }
//! <b>Requires</b>: !empty()
//!
@@ -585,7 +628,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference back() const
- { return this->m_start[this->m_size - 1]; }
+ { return this->members_.m_start[this->members_.m_size - 1]; }
//! <b>Effects</b>: Returns the number of the elements contained in the vector.
//!
@@ -593,7 +636,7 @@
//!
//! <b>Complexity</b>: Constant.
size_type size() const
- { return this->m_size; }
+ { return this->members_.m_size; }
//! <b>Effects</b>: Returns the largest possible size of the vector.
//!
@@ -601,7 +644,7 @@
//!
//! <b>Complexity</b>: Constant.
size_type max_size() const
- { return allocator_type::max_size(); }
+ { return this->alloc().max_size(); }
//! <b>Effects</b>: Number of elements for which memory has been allocated.
//! capacity() is always greater than or equal to size().
@@ -610,7 +653,7 @@
//!
//! <b>Complexity</b>: Constant.
size_type capacity() const
- { return this->m_capacity; }
+ { return this->members_.m_capacity; }
//! <b>Effects</b>: Returns true if the vector contains no elements.
//!
@@ -618,7 +661,7 @@
//!
//! <b>Complexity</b>: Constant.
bool empty() const
- { return !this->m_size; }
+ { return !this->members_.m_size; }
//! <b>Requires</b>: size() < n.
//!
@@ -629,7 +672,7 @@
//!
//! <b>Complexity</b>: Constant.
reference operator[](size_type n)
- { return this->m_start[n]; }
+ { return this->members_.m_start[n]; }
//! <b>Requires</b>: size() < n.
//!
@@ -640,7 +683,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference operator[](size_type n) const
- { return this->m_start[n]; }
+ { return this->members_.m_start[n]; }
//! <b>Requires</b>: size() < n.
//!
@@ -651,7 +694,7 @@
//!
//! <b>Complexity</b>: Constant.
reference at(size_type n)
- { this->priv_check_range(n); return this->m_start[n]; }
+ { this->priv_check_range(n); return this->members_.m_start[n]; }
//! <b>Requires</b>: size() < n.
//!
@@ -662,7 +705,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference at(size_type n) const
- { this->priv_check_range(n); return this->m_start[n]; }
+ { this->priv_check_range(n); return this->members_.m_start[n]; }
//! <b>Effects</b>: Returns a copy of the internal allocator.
//!
@@ -670,13 +713,13 @@
//!
//! <b>Complexity</b>: Constant.
allocator_type get_allocator() const
- { return *this; }
+ { return this->alloc(); }
const stored_allocator_type &get_stored_allocator() const
- { return *this; }
+ { return this->alloc(); }
stored_allocator_type &get_stored_allocator()
- { return *this; }
+ { return this->alloc(); }
//! <b>Effects</b>: If n is less than or equal to capacity(), this call has no
//! effect. Otherwise, it is a request for allocation of additional memory.
@@ -694,27 +737,35 @@
std::pair<pointer, bool> ret =
this->allocation_command
(allocate_new | expand_fwd | expand_bwd,
- new_cap, new_cap, real_cap, this->m_start);
+ new_cap, new_cap, real_cap, this->members_.m_start);
//Check for forward expansion
- same_buffer_start = ret.second && this->m_start == ret.first;
+ same_buffer_start = ret.second && this->members_.m_start == ret.first;
if(same_buffer_start){
- this->m_capacity = real_cap;
+ this->members_.m_capacity = real_cap;
}
-
//If there is no forward expansion, move objects
- if (!same_buffer_start){
+ else{
//We will reuse insert code, so create a dummy input iterator
- detail::move_iterator<pointer> dummy_it(this->m_start);
+ copy_move_it dummy_it(detail::get_pointer(this->members_.m_start));
//Backwards (and possibly forward) expansion
if(ret.second){
this->priv_range_insert_expand_backwards
- (ret.first, real_cap, this->m_start, dummy_it, dummy_it, 0);
+ ( detail::get_pointer(ret.first)
+ , real_cap
+ , detail::get_pointer(this->members_.m_start)
+ , dummy_it
+ , dummy_it
+ , 0);
}
//New buffer
else{
this->priv_range_insert_new_allocation
- (ret.first, real_cap, this->m_start, dummy_it, dummy_it);
+ ( detail::get_pointer(ret.first)
+ , real_cap
+ , detail::get_pointer(this->members_.m_start)
+ , dummy_it
+ , dummy_it);
}
}
}
@@ -731,7 +782,7 @@
vector<T, A>& operator=(const vector<T, A>& x)
{
if (&x != this){
- this->assign(x.m_start, x.m_start + x.m_size);
+ this->assign(x.members_.m_start, x.members_.m_start + x.members_.m_size);
}
return *this;
}
@@ -801,10 +852,10 @@
//! <b>Complexity</b>: Amortized constant time.
void push_back(const T& x)
{
- if (this->m_size < this->m_capacity){
+ if (this->members_.m_size < this->members_.m_capacity){
//There is more memory, just construct a new object at the end
- new(detail::get_pointer(this->m_start) + this->m_size)value_type(x);
- ++this->m_size;
+ new(detail::get_pointer(this->members_.m_start) + this->members_.m_size)value_type(x);
+ ++this->members_.m_size;
}
else{
this->insert(this->end(), x);
@@ -820,10 +871,10 @@
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void push_back(const detail::moved_object<T> & mx)
{
- if (this->m_size < this->m_capacity){
+ if (this->members_.m_size < this->members_.m_capacity){
//There is more memory, just construct a new object at the end
- new(detail::get_pointer(this->m_start + this->m_size))value_type(mx);
- ++this->m_size;
+ new(detail::get_pointer(this->members_.m_start + this->members_.m_size))value_type(mx);
+ ++this->members_.m_size;
}
else{
this->insert(this->end(), mx);
@@ -832,10 +883,10 @@
#else
void push_back(T && mx)
{
- if (this->m_size < this->m_capacity){
+ if (this->members_.m_size < this->members_.m_capacity){
//There is more memory, just construct a new object at the end
- new(detail::get_pointer(this->m_start + this->m_size))value_type(move(mx));
- ++this->m_size;
+ new(detail::get_pointer(this->members_.m_start + this->members_.m_size))value_type(move(mx));
+ ++this->members_.m_size;
}
else{
this->insert(this->end(), move(mx));
@@ -852,11 +903,11 @@
//! <b>Complexity</b>: Constant.
void swap(vector<T, A>& x)
{
- allocator_type &this_al = *this, &other_al = x;
+ allocator_type &this_al = this->alloc(), &other_al = x.alloc();
//Just swap internals
- detail::do_swap(this->m_start, x.m_start);
- detail::do_swap(this->m_size, x.m_size);
- detail::do_swap(this->m_capacity, x.m_capacity);
+ detail::do_swap(this->members_.m_start, x.members_.m_start);
+ detail::do_swap(this->members_.m_size, x.members_.m_size);
+ detail::do_swap(this->members_.m_capacity, x.members_.m_capacity);
if (this_al != other_al){
detail::do_swap(this_al, other_al);
@@ -897,7 +948,7 @@
//Just call more general insert(pos, size, value) and return iterator
size_type n = position - begin();
this->insert(position, (size_type)1, x);
- return iterator(this->m_start + n);
+ return iterator(this->members_.m_start + n);
}
//! <b>Requires</b>: position must be a valid iterator of *this.
@@ -911,26 +962,22 @@
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
iterator insert(iterator position, const detail::moved_object<T> &mx)
{
- typedef repeat_iterator<T, difference_type> r_iterator;
- typedef detail::move_iterator<r_iterator> move_it;
//Just call more general insert(pos, size, value) and return iterator
size_type n = position - begin();
this->insert(position
- ,move_it(r_iterator(mx.get(), 1))
- ,move_it(r_iterator()));
- return iterator(this->m_start + n);
+ ,repeat_move_it(repeat_iterator(mx.get(), 1))
+ ,repeat_move_it(repeat_iterator()));
+ return iterator(this->members_.m_start + n);
}
#else
iterator insert(iterator position, T &&mx)
{
- typedef repeat_iterator<T, difference_type> r_iterator;
- typedef detail::move_iterator<r_iterator> move_it;
//Just call more general insert(pos, size, value) and return iterator
size_type n = position - begin();
this->insert(position
- ,move_it(r_iterator(mx, 1))
- ,move_it(r_iterator()));
- return iterator(this->m_start + n);
+ ,repeat_move_it(repeat_iterator(mx, 1))
+ ,repeat_move_it(repeat_iterator()));
+ return iterator(this->members_.m_start + n);
}
#endif
@@ -969,8 +1016,8 @@
void pop_back()
{
//Destroy last element
- --this->m_size;
- this->destroy(this->m_start + this->m_size);
+ --this->members_.m_size;
+ this->destroy(detail::get_pointer(this->members_.m_start) + this->members_.m_size);
}
//! <b>Effects</b>: Erases the element at position pos.
@@ -981,16 +1028,13 @@
//! last element. Constant if pos is the first or the last element.
iterator erase(const_iterator position)
{
- size_type p_off = position.get_ptr() - this->m_start;
- if (p_off + 1 != this->m_size){
- //If not the last element, copy left [position, end()) elements
- copy_n(detail::make_move_iterator(this->m_start + (p_off + 1))
- ,this->m_size - (p_off + 1)
- ,this->m_start + p_off);
- }
- --this->m_size;
+ T *pos = detail::get_pointer(position.get_ptr());
+ T *beg = detail::get_pointer(this->members_.m_start);
+
+ std::copy(assign_move_it(pos + 1), assign_move_it(beg + this->members_.m_size), pos);
+ --this->members_.m_size;
//Destroy last element
- base_t::destroy(this->m_start + this->m_size);
+ base_t::destroy(detail::get_pointer(this->members_.m_start) + this->members_.m_size);
return iterator(position.get_ptr());
}
@@ -1001,19 +1045,17 @@
//! <b>Complexity</b>: Linear to the distance between first and last.
iterator erase(const_iterator first, const_iterator last)
{
- //Overwrite [last, end()) elements to first
- size_type f_off = first.get_ptr() - this->m_start;
- size_type l_off = last.get_ptr() - this->m_start;
- size_type n = l_off - f_off;
- size_type rem = this->m_size - l_off;
- size_type to_destroy = this->m_size - (f_off + rem);
- size_type destroy_off = f_off + rem;
-
- //Overwrite [last, end()) elements to first
- copy_n(detail::make_move_iterator(last.get_ptr()), rem, first.get_ptr());
- //Destroy remaining objects
- this->destroy_n(this->m_start + destroy_off, to_destroy);
- this->m_size -= n;
+ if (first != last){ // worth doing, copy down over hole
+ T* end_pos = detail::get_pointer(this->members_.m_start) + this->members_.m_size;
+ T* ptr = detail::get_pointer(std::copy
+ (assign_move_it(detail::get_pointer(last.get_ptr()))
+ ,assign_move_it(end_pos)
+ ,detail::get_pointer(first.get_ptr())
+ ));
+ size_type destroyed = (end_pos - ptr);
+ this->destroy_n(ptr, destroyed);
+ this->members_.m_size -= destroyed;
+ }
return iterator(first.get_ptr());
}
@@ -1025,10 +1067,10 @@
//! <b>Complexity</b>: Linear to the difference between size() and new_size.
void resize(size_type new_size, const T& x)
{
- pointer finish = this->m_start + this->m_size;
+ pointer finish = this->members_.m_start + this->members_.m_size;
if (new_size < size()){
//Destroy last elements
- this->erase(iterator(this->m_start + new_size), this->end());
+ this->erase(iterator(this->members_.m_start + new_size), this->end());
}
else{
//Insert new elements at the end
@@ -1046,16 +1088,16 @@
{
if (new_size < this->size()){
//Destroy last elements
- this->erase(iterator(this->m_start + new_size), this->end());
+ this->erase(iterator(this->members_.m_start + new_size), this->end());
}
else{
size_type n = new_size - this->size();
this->reserve(new_size);
- T *ptr = detail::get_pointer(this->m_start + this->m_size);
+ T *ptr = detail::get_pointer(this->members_.m_start + this->members_.m_size);
while(n--){
//Default construct
new(ptr++)T();
- ++this->m_size;
+ ++this->members_.m_size;
}
}
}
@@ -1068,8 +1110,10 @@
void clear()
{ this->priv_destroy_all(); }
+ /// @cond
+
//! <b>Effects</b>: Tries to deallocate the excess of memory created
- // with previous allocations. The size of the vector is unchanged
+ //! with previous allocations. The size of the vector is unchanged
//!
//! <b>Throws</b>: If memory allocation throws, or T's copy constructor throws.
//!
@@ -1077,11 +1121,10 @@
void shrink_to_fit()
{ priv_shrink_to_fit(alloc_version()); }
- /// @cond
private:
void priv_shrink_to_fit(allocator_v1)
{
- if(this->m_start){
+ if(this->members_.m_start){
if(!size()){
this->prot_deallocate();
}
@@ -1094,22 +1137,22 @@
void priv_shrink_to_fit(allocator_v2)
{
- if(this->m_start){
+ if(this->members_.m_start){
if(!size()){
this->prot_deallocate();
}
else{
size_type received_size;
- A::allocation_command(shrink_in_place, this->size(), this->capacity()
- ,received_size, this->m_start);
+ this->alloc().allocation_command(shrink_in_place, this->size(), this->capacity()
+ ,received_size, this->members_.m_start);
}
}
}
void priv_destroy_all()
{
- destroy_n(this->m_start, this->m_size);
- this->m_size = 0;
+ destroy_n(detail::get_pointer(this->members_.m_start), this->members_.m_size);
+ this->members_.m_size = 0;
}
template <class FwdIt>
@@ -1119,10 +1162,10 @@
if (first != last){
size_type n = std::distance(first, last);
//Check if we have enough memory or try to expand current memory
- size_type remaining = this->m_capacity - this->m_size;
+ size_type remaining = this->members_.m_capacity - this->members_.m_size;
bool same_buffer_start;
std::pair<pointer, bool> ret;
- size_type real_cap = this->m_capacity;
+ size_type real_cap = this->members_.m_capacity;
//Check if we already have room
if (n <= remaining){
@@ -1134,132 +1177,143 @@
size_type new_cap = this->next_capacity(n);
ret = this->allocation_command
(allocate_new | expand_fwd | expand_bwd,
- this->m_size + n, new_cap, real_cap, this->m_start);
+ this->members_.m_size + n, new_cap, real_cap, this->members_.m_start);
//Check for forward expansion
- same_buffer_start = ret.second && this->m_start == ret.first;
+ same_buffer_start = ret.second && this->members_.m_start == ret.first;
if(same_buffer_start){
- this->m_capacity = real_cap;
+ this->members_.m_capacity = real_cap;
}
}
//If we had room or we have expanded forward
if (same_buffer_start){
this->priv_range_insert_expand_forward
- (pos, first, last, n);
+ (detail::get_pointer(pos), first, last, n);
}
//Backwards (and possibly forward) expansion
else if(ret.second){
this->priv_range_insert_expand_backwards
- (ret.first, real_cap, pos, first, last, n);
+ ( detail::get_pointer(ret.first)
+ , real_cap
+ , detail::get_pointer(pos)
+ , first
+ , last
+ , n);
}
//New buffer
else{
this->priv_range_insert_new_allocation
- (ret.first, real_cap, pos, first, last);
+ ( detail::get_pointer(ret.first)
+ , real_cap
+ , detail::get_pointer(pos)
+ , first
+ , last);
}
}
}
template <class FwdIt>
void priv_range_insert_expand_forward
- (pointer pos, FwdIt first, FwdIt last, size_type n)
+ (T* pos, FwdIt first, FwdIt last, size_type n)
{
- typedef detail::move_iterator<pointer> move_it;
//There is enough memory
- pointer old_finish = this->m_start + this->m_size;
+ T* old_finish = detail::get_pointer(this->members_.m_start) + this->members_.m_size;
const size_type elems_after = old_finish - pos;
if (elems_after > n){
//New elements can be just copied.
//Move to uninitialized memory last objects
- boost::interprocess::n_uninitialized_copy
- (move_it(old_finish - n), move_it(old_finish), old_finish);
- this->m_size += n;
+ std::uninitialized_copy(copy_move_it(old_finish - n), copy_move_it(old_finish), old_finish);
+ this->members_.m_size += n;
//Copy previous to last objects to the initialized end
- std::copy_backward(move_it(pos), move_it(old_finish - n), old_finish);
+ std::copy_backward(assign_move_it(detail::get_pointer(pos)), assign_move_it(old_finish - n), old_finish);
//Insert new objects in the pos
- copy_n(first, n, pos);
+ std::copy(first, last, detail::get_pointer(pos));
}
else {
//The new elements don't fit in the [pos, end()) range. Copy
//to the beginning of the unallocated zone the last new elements.
FwdIt mid = first;
std::advance(mid, elems_after);
- boost::interprocess::n_uninitialized_copy(mid, last, old_finish);
- this->m_size += n - elems_after;
+ std::uninitialized_copy(mid, last, old_finish);
+ this->members_.m_size += n - elems_after;
//Copy old [pos, end()) elements to the uninitialized memory
- boost::interprocess::n_uninitialized_copy
- (move_it(pos), move_it(old_finish), this->m_start + this->m_size);
- this->m_size += elems_after;
+ std::uninitialized_copy
+ ( copy_move_it(detail::get_pointer(pos))
+ , copy_move_it(old_finish)
+ , detail::get_pointer(this->members_.m_start) + this->members_.m_size);
+ this->members_.m_size += elems_after;
//Copy first new elements in pos
- std::copy(first, mid, pos);
+ std::copy(first, mid, detail::get_pointer(pos));
}
}
template <class FwdIt>
void priv_range_insert_new_allocation
- (pointer new_start, size_type new_cap, pointer pos, FwdIt first, FwdIt last)
+ (T* new_start, size_type new_cap, T* pos, FwdIt first, FwdIt last)
{
- typedef detail::move_iterator<pointer> move_it;
- //Anti-exception rollback
- dealloc_t scoped_alloc(new_start, *this, new_cap);
- pointer new_finish = new_start;
- BOOST_TRY{
- //Initialize with [begin(), pos) old buffer
- //the start of the new buffer
- new_finish += boost::interprocess::n_uninitialized_copy
- (move_it(this->m_start), move_it(pos), new_start);
- //Initialize new objects, starting from previous point
- new_finish += boost::interprocess::n_uninitialized_copy
- (first, last, new_finish);
- //Initialize from the rest of the old buffer,
- //starting from previous point
- new_finish += boost::interprocess::n_uninitialized_copy
- (move_it(pos), move_it(this->m_start + this->m_size), new_finish);
- }
- BOOST_CATCH(...){
- this->destroy_n(new_start, new_finish - new_start);
- BOOST_RETHROW
- }
- BOOST_CATCH_END
+ T* new_finish = new_start;
+ T *old_finish;
+ //Anti-exception rollbacks
+ UCopiedArrayDeallocator scoped_alloc(new_start, this->alloc(), new_cap);
+ UCopiedArrayDestructor construted_values_destroyer(new_start, 0u);
+
+ //Initialize with [begin(), pos) old buffer
+ //the start of the new buffer
+ new_finish = std::uninitialized_copy
+ ( copy_move_it(detail::get_pointer(this->members_.m_start))
+ , copy_move_it(detail::get_pointer(pos))
+ , old_finish = new_finish);
+ construted_values_destroyer.increment_size(new_finish - old_finish);
+ //Initialize new objects, starting from previous point
+ new_finish = std::uninitialized_copy
+ (first, last, old_finish = new_finish);
+ construted_values_destroyer.increment_size(new_finish - old_finish);
+ //Initialize from the rest of the old buffer,
+ //starting from previous point
+ new_finish = std::uninitialized_copy
+ ( copy_move_it(detail::get_pointer(pos))
+ , copy_move_it(detail::get_pointer(this->members_.m_start) + this->members_.m_size)
+ , detail::get_pointer(new_finish));
+
+ //All construction successful, disable rollbacks
+ construted_values_destroyer.release();
scoped_alloc.release();
//Destroy and deallocate old elements
//If there is allocated memory, destroy and deallocate
- if(this->m_start != 0){
+ if(this->members_.m_start != 0){
if(!base_t::trivial_dctr_after_move)
- this->destroy_n(this->m_start, this->m_size);
- this->deallocate(this->m_start, this->m_capacity);
+ this->destroy_n(detail::get_pointer(this->members_.m_start), this->members_.m_size);
+ this->alloc().deallocate(this->members_.m_start, this->members_.m_capacity);
}
- this->m_start = new_start;
- this->m_size = new_finish - new_start;
- this->m_capacity = new_cap;
+ this->members_.m_start = new_start;
+ this->members_.m_size = new_finish - new_start;
+ this->members_.m_capacity = new_cap;
}
template <class FwdIt>
void priv_range_insert_expand_backwards
- (pointer new_start, size_type new_capacity,
- pointer pos, FwdIt first, FwdIt last, size_type n)
+ (T* new_start, size_type new_capacity,
+ T* pos, FwdIt first, FwdIt last, size_type n)
{
- typedef detail::scoped_destructor_n<allocator_type> ValueArrayDestructor;
- typedef detail::move_iterator<pointer> move_it;
//Backup old data
- pointer old_start = this->m_start;
- pointer old_finish = this->m_start + this->m_size;
- size_type old_size = this->m_size;
+ T* old_start = detail::get_pointer(this->members_.m_start);
+ T* old_finish = old_start + this->members_.m_size;
+ size_type old_size = this->members_.m_size;
//We can have 8 possibilities:
- const size_type elemsbefore = (size_type)(pos - this->m_start);
+ const size_type elemsbefore = (size_type)(pos - old_start);
const size_type s_before = (size_type)(old_start - new_start);
//Update the vector buffer information to a safe state
- this->m_start = new_start;
- this->m_capacity = new_capacity;
- this->m_size = 0;
+ this->members_.m_start = new_start;
+ this->members_.m_capacity = new_capacity;
+ this->members_.m_size = 0;
//If anything goes wrong, this object will destroy
//all the old objects to fulfill previous vector state
- ValueArrayDestructor old_values_destroyer(old_start, old_size);
+ OldArrayDestructor old_values_destroyer(old_start, old_size);
//Check if s_before is so big that even copying the old data + new data
//there is a gap between the new data and the old data
@@ -1277,14 +1331,16 @@
//Copy first old values before pos, after that the
//new objects
boost::interprocess::uninitialized_copy_copy
- (move_it(old_start), move_it(pos), first, last, new_start);
- ValueArrayDestructor new_values_destroyer(new_start, elemsbefore);
+ (copy_move_it(old_start), copy_move_it(detail::get_pointer(pos)), first, last, detail::get_pointer(new_start));
+ UCopiedArrayDestructor new_values_destroyer(new_start, elemsbefore);
//Now initialize the rest of memory with the last old values
- boost::interprocess::uninitialized_copy(move_it(pos), move_it(old_finish)
- ,new_start + elemsbefore + n);
+ std::uninitialized_copy
+ ( copy_move_it(detail::get_pointer(pos))
+ , copy_move_it(old_finish)
+ , detail::get_pointer(new_start) + elemsbefore + n);
//All new elements correctly constructed, avoid new element destruction
new_values_destroyer.release();
- this->m_size = old_size + n;
+ this->members_.m_size = old_size + n;
//Old values destroyed automatically with "old_values_destroyer"
//when "old_values_destroyer" goes out of scope unless the have trivial
//destructor after move.
@@ -1306,28 +1362,31 @@
//Copy first old values before pos, after that the
//new objects
boost::interprocess::uninitialized_copy_copy
- (move_it(old_start), move_it(pos), first, last, new_start);
- ValueArrayDestructor new_values_destroyer(new_start, elemsbefore);
+ ( copy_move_it(old_start)
+ , copy_move_it(detail::get_pointer(pos))
+ , first, last, detail::get_pointer(new_start));
+ UCopiedArrayDestructor new_values_destroyer(new_start, elemsbefore);
size_type raw_gap = s_before - (elemsbefore + n);
//Now initialize the rest of s_before memory with the
//first of elements after new values
- boost::interprocess::uninitialized_copy
- (move_it(pos), move_it(pos + raw_gap), new_start + elemsbefore + n);
+ std::uninitialized_copy
+ ( copy_move_it(detail::get_pointer(pos))
+ , copy_move_it(detail::get_pointer(pos) + raw_gap)
+ , detail::get_pointer(new_start) + elemsbefore + n);
//All new elements correctly constructed, avoid new element destruction
new_values_destroyer.release();
//All new elements correctly constructed, avoid old element destruction
old_values_destroyer.release();
//Update size since we have a contiguous buffer
- this->m_size = old_size + s_before;
+ this->members_.m_size = old_size + s_before;
//Now copy remaining last objects in the old buffer begin
- pointer to_destroy =
- std::copy(move_it(pos + raw_gap), move_it(old_finish), old_start);
+ T *to_destroy = std::copy(assign_move_it(detail::get_pointer(pos) + raw_gap), assign_move_it(old_finish), old_start);
//Now destroy redundant elements except if they were moved and
//they have trivial destructor after move
size_type n_destroy = old_finish - to_destroy;
if(!base_t::trivial_dctr_after_move)
this->destroy_n(to_destroy, n_destroy);
- this->m_size -= n_destroy;
+ this->members_.m_size -= n_destroy;
}
else{
//Check if we have to do the insertion in two phases
@@ -1385,30 +1444,32 @@
//|___________|_____|_________|_____________________|
//
//Copy the first part of old_begin to raw_mem
- pointer start_n = old_start + difference_type(s_before);
- boost::interprocess::uninitialized_copy
- (move_it(old_start), move_it(start_n), new_start);
+ T *start_n = old_start + difference_type(s_before);
+ std::uninitialized_copy
+ ( copy_move_it(old_start)
+ , copy_move_it(start_n)
+ , detail::get_pointer(new_start));
//The buffer is all constructed until old_end,
//release destroyer and update size
old_values_destroyer.release();
- this->m_size = old_size + s_before;
+ this->members_.m_size = old_size + s_before;
//Now copy the second part of old_begin overwriting himself
- pointer next = std::copy(move_it(start_n), move_it(pos), old_start);
+ T* next = std::copy(assign_move_it(start_n), assign_move_it(detail::get_pointer(pos)), old_start);
if(do_after){
//Now copy the new_beg elements
- std::copy(first, before_end, next);
+ std::copy(first, before_end, detail::get_pointer(next));
}
else{
//Now copy the all the new elements
- pointer move_start = std::copy(first, last, next);
+ T* move_start = std::copy(first, last, detail::get_pointer(next));
//Now displace old_end elements
- pointer move_end = std::copy(move_it(pos), move_it(old_finish), move_start);
+ T* move_end = std::copy(assign_move_it(detail::get_pointer(pos)), assign_move_it(old_finish), detail::get_pointer(move_start));
//Destroy remaining moved elements from old_end except if
//they have trivial destructor after being moved
difference_type n_destroy = s_before - n;
if(!base_t::trivial_dctr_after_move)
this->destroy_n(move_end, n_destroy);
- this->m_size -= n_destroy;
+ this->members_.m_size -= n_destroy;
}
}
else {
@@ -1438,11 +1499,13 @@
size_type n_new_init = difference_type(s_before) - elemsbefore;
std::advance(mid, n_new_init);
boost::interprocess::uninitialized_copy_copy
- (move_it(old_start), move_it(pos), first, mid, new_start);
+ ( copy_move_it(old_start)
+ , copy_move_it(detail::get_pointer(pos))
+ , first, mid, detail::get_pointer(new_start));
//The buffer is all constructed until old_end,
//release destroyer and update size
old_values_destroyer.release();
- this->m_size = old_size + s_before;
+ this->members_.m_size = old_size + s_before;
if(do_after){
//Copy new_beg part
@@ -1450,15 +1513,15 @@
}
else{
//Copy all new elements
- pointer move_start = std::copy(mid, last, old_start);
+ T* move_start = std::copy(mid, last, old_start);
//Displace old_end
- pointer move_end = std::copy(move_it(pos), move_it(old_finish), move_start);
+ T* move_end = std::copy(copy_move_it(detail::get_pointer(pos)), copy_move_it(old_finish), detail::get_pointer(move_start));
//Destroy remaining moved elements from old_end except if they
//have trivial destructor after being moved
difference_type n_destroy = s_before - n;
if(!base_t::trivial_dctr_after_move)
this->destroy_n(move_end, n_destroy);
- this->m_size -= n_destroy;
+ this->members_.m_size -= n_destroy;
}
}
@@ -1505,14 +1568,16 @@
//|__________________________|_________|________|_________|
//
//First copy the part of old_end raw_mem
- pointer finish_n = old_finish - difference_type(n_after);
- boost::interprocess::uninitialized_copy
- (move_it(finish_n), move_it(old_finish), old_finish);
- this->m_size += n_after;
+ T* finish_n = old_finish - difference_type(n_after);
+ std::uninitialized_copy
+ ( copy_move_it(detail::get_pointer(finish_n))
+ , copy_move_it(old_finish)
+ , old_finish);
+ this->members_.m_size += n_after;
//Displace the rest of old_end to the new position
- std::copy_backward(move_it(pos), move_it(finish_n), old_finish);
+ std::copy_backward(assign_move_it(detail::get_pointer(pos)), assign_move_it(detail::get_pointer(finish_n)), old_finish);
//Now overwrite with new_end
- std::copy(first, last, pos);
+ std::copy(first, last, detail::get_pointer(pos));
}
else {
//The raw_mem from end will divide new_end part
@@ -1531,10 +1596,13 @@
std::advance(mid, elemsafter);
//First initialize data in raw memory
boost::interprocess::uninitialized_copy_copy
- (mid, last, move_it(pos), move_it(old_finish), old_finish);
- this->m_size += n_after;
+ ( mid, last
+ , copy_move_it(detail::get_pointer(pos))
+ , copy_move_it(old_finish)
+ , old_finish);
+ this->members_.m_size += n_after;
//Now copy the part of new_end over constructed elements
- std::copy(first, mid, pos);
+ std::copy(first, mid, detail::get_pointer(pos));
}
}
}
@@ -1575,10 +1643,10 @@
{
size_type n = std::distance(first, last);
//Check if we have enough memory or try to expand current memory
- size_type remaining = this->m_capacity - this->m_size;
+ size_type remaining = this->members_.m_capacity - this->members_.m_size;
bool same_buffer_start;
std::pair<pointer, bool> ret;
- size_type real_cap = this->m_capacity;
+ size_type real_cap = this->members_.m_capacity;
if (n <= remaining){
same_buffer_start = true;
@@ -1588,76 +1656,76 @@
size_type new_cap = this->next_capacity(n);
ret = this->allocation_command
(allocate_new | expand_fwd | expand_bwd,
- this->size() + n, new_cap, real_cap, this->m_start);
- same_buffer_start = ret.second && this->m_start == ret.first;
+ this->size() + n, new_cap, real_cap, this->members_.m_start);
+ same_buffer_start = ret.second && this->members_.m_start == ret.first;
if(same_buffer_start){
- this->m_capacity = real_cap;
+ this->members_.m_capacity = real_cap;
}
}
if(same_buffer_start){
+ T *start = detail::get_pointer(this->members_.m_start);
if (this->size() >= n){
//There is memory, but there are more old elements than new ones
//Overwrite old elements with new ones
- copy_n(first, n, this->m_start);
+ std::copy(first, last, start);
//Destroy remaining old elements
- this->destroy_n(this->m_start + n, this->m_size - n);
- this->m_size = n;
+ this->destroy_n(start + n, this->members_.m_size - n);
+ this->members_.m_size = n;
}
else{
//There is memory, but there are less old elements than new ones
- //Overwrite old elements with new ones
+ //First overwrite some old elements with new ones
FwdIt mid = first;
std::advance(mid, this->size());
- std::copy(first, mid, this->m_start);
+ T *end = std::copy(first, mid, start);
//Initialize the remaining new elements in the uninitialized memory
- boost::interprocess::n_uninitialized_copy
- (mid, last, this->m_start + this->m_size);
- this->m_size = n;
+ std::uninitialized_copy(mid, last, end);
+ this->members_.m_size = n;
}
}
else if(!ret.second){
- dealloc_t scoped_alloc(ret.first, *this, real_cap);
- boost::interprocess::n_uninitialized_copy(first, last, ret.first);
+ UCopiedArrayDeallocator scoped_alloc(ret.first, this->alloc(), real_cap);
+ std::uninitialized_copy(first, last, detail::get_pointer(ret.first));
scoped_alloc.release();
//Destroy and deallocate old buffer
- if(this->m_start != 0){
- this->destroy_n(this->m_start, this->m_size);
- this->deallocate(this->m_start, this->m_capacity);
- }
- this->m_start = ret.first;
- this->m_size = n;
- this->m_capacity = real_cap;
+ if(this->members_.m_start != 0){
+ this->destroy_n(detail::get_pointer(this->members_.m_start), this->members_.m_size);
+ this->alloc().deallocate(this->members_.m_start, this->members_.m_capacity);
+ }
+ this->members_.m_start = ret.first;
+ this->members_.m_size = n;
+ this->members_.m_capacity = real_cap;
}
else{
//Backwards expansion
//If anything goes wrong, this object will destroy
//all old objects
- typedef detail::scoped_destructor_n<allocator_type> ValueArrayDestructor;
- pointer old_start = this->m_start;
- size_type old_size = this->m_size;
- ValueArrayDestructor old_values_destroyer(old_start, old_size);
+ T *old_start = detail::get_pointer(this->members_.m_start);
+ size_type old_size = this->members_.m_size;
+ OldArrayDestructor old_values_destroyer(old_start, old_size);
//If something goes wrong size will be 0
//but holding the whole buffer
- this->m_size = 0;
- this->m_start = ret.first;
- this->m_capacity = real_cap;
+ this->members_.m_size = 0;
+ this->members_.m_start = ret.first;
+ this->members_.m_capacity = real_cap;
//Backup old buffer data
- size_type old_offset = old_start - ret.first;
+ size_type old_offset = old_start - detail::get_pointer(ret.first);
size_type first_count = min_value(n, old_offset);
- FwdIt mid = boost::interprocess::n_uninitialized_copy_n(first, first_count, ret.first);
+ FwdIt mid = boost::interprocess::n_uninitialized_copy_n
+ (first, first_count, detail::get_pointer(ret.first));
if(old_offset > n){
//All old elements will be destroyed by "old_values_destroyer"
- this->m_size = n;
+ this->members_.m_size = n;
}
else{
//We have constructed objects from the new begin until
//the old end so release the rollback destruction
old_values_destroyer.release();
- this->m_start = ret.first;
- this->m_size = first_count + old_size;
+ this->members_.m_start = ret.first;
+ this->members_.m_size = first_count + old_size;
//Now overwrite the old values
size_type second_count = min_value(old_size, n - first_count);
mid = copy_n(mid, second_count, old_start);
@@ -1666,15 +1734,17 @@
//uninitialized end
if(second_count == old_size){
boost::interprocess::n_uninitialized_copy_n
- (mid, n - first_count - second_count, old_start + old_size);
+ ( mid
+ , n - first_count - second_count
+ , old_start + old_size);
}
else{
//We have to destroy some old values
this->destroy_n
(old_start + second_count, old_size - second_count);
- this->m_size = n;
+ this->members_.m_size = n;
}
- this->m_size = n;
+ this->members_.m_size = n;
}
}
}
@@ -1706,36 +1776,6 @@
this->priv_range_insert(pos.get_ptr(), first, last, ItCat());
}
- template <class Integer>
- void priv_initialize_aux(Integer n, Integer value, detail::true_)
- {
- this->priv_range_initialize(cvalue_iterator(value, n),
- cvalue_iterator(),
- cvalue_iterator::iterator_category());
- }
-
- template <class InIt>
- void priv_initialize_aux(InIt first, InIt last,
- detail::false_)
- {
- //Dispatch depending on integer/iterator
- typedef typename
- std::iterator_traits<InIt>::iterator_category ItCat;
- this->priv_range_initialize(first, last, ItCat());
- }
-
- template <class FwdIt>
- pointer priv_reserve_and_copy(size_type n, size_type &cap
- ,FwdIt first, FwdIt last)
- {
- //Allocate n element buffer and initialize from range
- pointer result = this->allocation_command(allocate_new, n, n, cap).first;
- dealloc_t scoped_alloc(result, *this, cap);
- boost::interprocess::n_uninitialized_copy(first, last, result);
- scoped_alloc.release();
- return result;
- }
-
void priv_check_range(size_type n) const
{
//If n is out of range, throw an out_of_range exception
@@ -1790,7 +1830,8 @@
#endif
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class T, class A>
struct is_movable<vector<T, A> >
{
Modified: branches/bcbboost/boost/interprocess/creation_tags.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/creation_tags.hpp (original)
+++ branches/bcbboost/boost/interprocess/creation_tags.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -44,7 +44,7 @@
namespace detail {
enum create_enum_t
-{ DoCreate, DoOpen, DoCreateOrOpen };
+{ DoCreate, DoOpen, DoOpenOrCreate };
} //namespace detail {
Modified: branches/bcbboost/boost/interprocess/detail/algorithms.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/algorithms.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/algorithms.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,13 +20,11 @@
#include <boost/interprocess/detail/config_begin.hpp>
#include <boost/interprocess/detail/workaround.hpp>
#include <boost/interprocess/detail/iterators.hpp>
-#include <boost/interprocess/detail/mpl.hpp>
-#include <boost/interprocess/detail/utilities.hpp>
#include <boost/get_pointer.hpp>
#include <boost/detail/no_exceptions_support.hpp>
namespace boost {
-namespace interprocess {
+namespace interprocess {
template<class T>
struct has_own_construct_from_it
@@ -34,96 +32,16 @@
static const bool value = false;
};
-template<class FwdIt, class T>
-void uninitialized_fill(FwdIt first, FwdIt last, const T& val)
-{
- typedef typename std::iterator_traits<FwdIt>::value_type value_type;
- //Save initial position
- FwdIt init = first;
-
- BOOST_TRY{
- //Construct objects
- for (; first != last; ++first){
- new(detail::get_pointer(&*first))value_type(val);
- }
- }
- BOOST_CATCH(...){
- //Call destructors
- for (; init != first; ++init){
- detail::get_pointer(&*init)->~value_type();
- }
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
-}
-
-template<class FwdIt, class Count, class T>
-void uninitialized_fill_n(FwdIt first, Count count,
- const T& val)
-{
- typedef typename std::iterator_traits<FwdIt>::value_type value_type;
- //Save initial position
- FwdIt init = first;
-
- BOOST_TRY{
- //Construct objects
- for (; count--; ++first){
- new(detail::get_pointer(&*first))value_type(val);
- }
- }
- BOOST_CATCH(...){
- //Call destructors
- for (; init != first; ++init){
- detail::get_pointer(&*init)->~value_type();
- }
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
-}
-
-template<class InIt, class OutIt>
-InIt copy_n(InIt first, typename std::iterator_traits<InIt>::difference_type length, OutIt dest)
-{
- for (; length--; ++dest, ++first)
- *dest = *first;
- return first;
-}
-
-template<class InIt, class FwdIt>
-typename std::iterator_traits<InIt>::difference_type
- n_uninitialized_copy(InIt first, InIt last, FwdIt dest)
-{
- typedef typename std::iterator_traits<FwdIt>::value_type value_type;
- //Save initial destination position
- FwdIt dest_init = dest;
- typename std::iterator_traits<InIt>::difference_type constructed = 0;
- BOOST_TRY{
- //Try to build objects
- for (; first != last; ++dest, ++first, ++constructed){
- new(detail::get_pointer(&*dest))value_type(*first);
- }
- }
- BOOST_CATCH(...){
- //Call destructors
- for (; dest_init != dest; ++dest_init){
- detail::get_pointer(&*dest_init)->~value_type();
- }
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
- return (constructed);
-}
-
namespace detail {
template<class T, class InpIt>
-inline void construct_in_place(T* dest, const InpIt &source, detail::true_)
+inline void construct_in_place_impl(T* dest, const InpIt &source, detail::true_)
{
T::construct(dest, *source);
}
template<class T, class InpIt>
-inline void construct_in_place(T* dest, const InpIt &source, detail::false_)
+inline void construct_in_place_impl(T* dest, const InpIt &source, detail::false_)
{
new(dest)T(*source);
}
@@ -134,7 +52,7 @@
inline void construct_in_place(T* dest, InpIt source)
{
typedef detail::bool_<has_own_construct_from_it<T>::value> boolean_t;
- detail::construct_in_place(dest, source, boolean_t());
+ detail::construct_in_place_impl(dest, source, boolean_t());
}
template<class T, class U, class D>
@@ -143,28 +61,12 @@
new(dest)T();
}
-template<class InIt, class FwdIt> inline
-FwdIt uninitialized_copy(InIt first, InIt last, FwdIt dest)
+template<class InIt, class OutIt>
+InIt copy_n(InIt first, typename std::iterator_traits<InIt>::difference_type length, OutIt dest)
{
- typedef typename std::iterator_traits<FwdIt>::value_type value_type;
- //Save initial destination position
- FwdIt dest_init = dest;
- typename std::iterator_traits<InIt>::difference_type constructed = 0;
- BOOST_TRY{
- //Try to build objects
- for (; first != last; ++dest, ++first, ++constructed){
- new(detail::get_pointer(&*dest))value_type(*first);
- }
- }
- BOOST_CATCH(...){
- //Call destructors
- for (; dest_init != dest; ++dest_init){
- detail::get_pointer(&*dest_init)->~value_type();
- }
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
- return (dest);
+ for (; length--; ++dest, ++first)
+ *dest = *first;
+ return first;
}
template<class InIt, class FwdIt> inline
@@ -201,63 +103,23 @@
// copies [first2, last2) into
// [result + (last1 - first1), result + (last1 - first1) + (last2 - first2)).
template <class InpIt1, class InpIt2, class FwdIt>
-FwdIt uninitialized_copy_copy(InpIt1 first1, InpIt1 last1,
- InpIt2 first2, InpIt2 last2,
- FwdIt result)
+FwdIt uninitialized_copy_copy
+ (InpIt1 first1, InpIt1 last1, InpIt2 first2, InpIt2 last2, FwdIt result)
{
typedef typename std::iterator_traits<FwdIt>::value_type value_type;
- FwdIt mid = boost::interprocess::uninitialized_copy(first1, last1, result);
+ FwdIt mid = std::uninitialized_copy(first1, last1, result);
BOOST_TRY {
- return boost::interprocess::uninitialized_copy(first2, last2, mid);
+ return std::uninitialized_copy(first2, last2, mid);
}
BOOST_CATCH(...){
for(;result != mid; ++result){
- detail::get_pointer(&*result)->~value_type();
+ result->~value_type();
}
BOOST_RETHROW
}
BOOST_CATCH_END
}
-// uninitialized_copy_n_copy_n
-// Copies [first1, first1 + n1) into [result, result + n1), and
-// copies [first2, first2 + n2) into
-// [result + n1, result + n1 + n2).
-template <class InpIt1, class InpIt2, class FwdIt>
-InpIt2 uninitialized_copy_n_copy_n
- (InpIt1 first1,
- typename std::iterator_traits<InpIt1>::difference_type n1,
- InpIt2 first2,
- typename std::iterator_traits<InpIt2>::difference_type n2,
- FwdIt result)
-{
- typedef typename std::iterator_traits<FwdIt>::value_type value_type;
- typename std::iterator_traits<InpIt1>::difference_type c1 = n1+1;
- typename std::iterator_traits<InpIt2>::difference_type c2 = n2+1;
- FwdIt dest_init = result;
-
- BOOST_TRY{
- //Try to build objects
- for (; --c1; ++result, ++first1){
- new(detail::get_pointer(&*result))value_type(*first1);
- }
- for (; --c2; ++result, ++first2){
- new(detail::get_pointer(&*result))value_type(*first2);
- }
- }
- BOOST_CATCH(...){
- //Call destructors
- typename std::iterator_traits<FwdIt>::
- difference_type c = (n1 - c1) + (n2 - c2);
- for (; c--; ++dest_init){
- detail::get_pointer(&*dest_init)->~value_type();
- }
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
- return first2;
-}
-
} //namespace interprocess {
} //namespace boost {
Deleted: branches/bcbboost/boost/interprocess/detail/basic_segment_manager.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/basic_segment_manager.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,389 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2005-2007. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTERPROCESS_BASIC_SEGMENT_MANAGER_HPP
-#define BOOST_INTERPROCESS_BASIC_SEGMENT_MANAGER_HPP
-
-#if (defined _MSC_VER) && (_MSC_VER >= 1200)
-# pragma once
-#endif
-
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/detail/no_exceptions_support.hpp>
-#include <boost/interprocess/detail/type_traits.hpp>
-#include <boost/interprocess/detail/utilities.hpp>
-#include <boost/interprocess/detail/in_place_interface.hpp>
-#include <boost/interprocess/exceptions.hpp>
-#include <cstddef> //std::size_t
-#include <string> //char_traits
-#include <new> //std::nothrow
-#include <utility> //std::pair
-#ifndef BOOST_NO_EXCEPTIONS
-#include <exception>
-#endif
-
-/*!\file
- Describes the object placed in a memory segment that provides
- named object allocation capabilities for single-segment and
- multi-segment allocations.
-*/
-
-namespace boost{
-namespace interprocess{
-namespace detail{
-
-template<class MemoryAlgorithm>
-class mem_algo_deallocator
-{
- void * m_ptr;
- MemoryAlgorithm & m_algo;
-
- public:
- mem_algo_deallocator(void *ptr, MemoryAlgorithm &algo)
- : m_ptr(ptr), m_algo(algo)
- {}
-
- void release()
- { m_ptr = 0; }
-
- ~mem_algo_deallocator()
- { if(m_ptr) m_algo.deallocate(m_ptr); }
-};
-
-//!An integer that describes the type of the
-//!instance constructed in memory
-enum instance_type { anonymous_type, named_type, unique_type, max_allocation_type };
-
-/// @cond
-struct block_header
-{
- std::size_t m_value_bytes;
- unsigned short m_num_char;
- unsigned char m_value_alignment;
- unsigned char m_alloc_type_sizeof_char;
-
- block_header(std::size_t value_bytes
- ,std::size_t value_alignment
- ,std::size_t allocation_type
- ,std::size_t sizeof_char
- ,std::size_t num_char
- )
- : m_value_bytes(value_bytes)
- , m_num_char(num_char)
- , m_value_alignment(value_alignment)
- , m_alloc_type_sizeof_char
- ( ((unsigned char)allocation_type << 5u) |
- ((unsigned char)sizeof_char & 0x1F) )
- {};
-
-
- template<class T>
- block_header &operator= (const T& )
- { return *this; }
-
- std::size_t total_size() const
- {
- if(allocation_type() != detail::anonymous_type){
- return name_offset() + (m_num_char+1)*sizeof_char();
- }
- else{
- return value_offset() + m_value_bytes;
- }
- }
-
- template<class Header>
- std::size_t total_size_with_header() const
- {
- return get_rounded_size
- ( sizeof(Header)
- , detail::alignment_of<block_header>::value)
- + total_size();
- }
-
- std::size_t allocation_type() const
- { return (m_alloc_type_sizeof_char >> 5u)&(unsigned char)0x7; }
-
- std::size_t sizeof_char() const
- { return m_alloc_type_sizeof_char & (unsigned char)0x1F; }
-
- template<class CharType>
- CharType *name() const
- {
- return reinterpret_cast<CharType*>
- (detail::char_ptr_cast(this) + name_offset());
- }
-
- std::size_t name_length() const
- { return m_num_char; }
-
- std::size_t name_offset() const
- {
- return value_offset() + get_rounded_size(m_value_bytes, sizeof_char());
- }
-
- void *value() const
- {
- return detail::char_ptr_cast(this) + value_offset();
- }
-
- std::size_t value_offset() const
- {
- return get_rounded_size(sizeof(block_header), m_value_alignment);
- }
-
- template<class CharType>
- bool less(const block_header &b) const
- {
- return m_num_char < b.m_num_char ||
- (m_num_char < b.m_num_char &&
- std::char_traits<CharType>::compare
- (name<CharType>(), b.name<CharType>(), m_num_char) < 0);
- }
-
- template<class CharType>
- bool equal(const block_header &b) const
- {
- return m_num_char == b.m_num_char &&
- std::char_traits<CharType>::compare
- (name<CharType>(), b.name<CharType>(), m_num_char) == 0;
- }
-
- template<class T>
- static block_header *block_header_from_value(T *value)
- { return block_header_from_value(value, sizeof(T), detail::alignment_of<T>::value); }
-
- static block_header *block_header_from_value(const void *value, std::size_t sz, std::size_t algn)
- {
- block_header * hdr =
- reinterpret_cast<block_header*>(detail::char_ptr_cast(value) -
- get_rounded_size(sizeof(block_header), algn));
- (void)sz;
- //Some sanity checks
- assert(hdr->m_value_alignment == algn);
- assert(hdr->m_value_bytes % sz == 0);
- return hdr;
- }
-
- template<class Header>
- static block_header *from_first_header(Header *header)
- {
- block_header * hdr =
- reinterpret_cast<block_header*>(detail::char_ptr_cast(header) +
- get_rounded_size(sizeof(Header), detail::alignment_of<block_header>::value));
- //Some sanity checks
- return hdr;
- }
-
- template<class Header>
- static Header *to_first_header(block_header *bheader)
- {
- Header * hdr =
- reinterpret_cast<Header*>(detail::char_ptr_cast(bheader) -
- get_rounded_size(sizeof(Header), detail::alignment_of<block_header>::value));
- //Some sanity checks
- return hdr;
- }
-};
-
-inline void array_construct(void *mem, std::size_t num, detail::in_place_interface &table)
-{
- //Try constructors
- std::size_t constructed = 0;
- BOOST_TRY{
- table.construct_n(mem, num, constructed);
- }
- //If there is an exception call destructors and erase index node
- BOOST_CATCH(...){
- std::size_t destroyed = 0;
- table.destroy_n(mem, constructed, destroyed);
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
-}
-
-template<class MemoryAlgorithm>
-class basic_segment_manager
- : private MemoryAlgorithm
-{
- public:
- typedef typename MemoryAlgorithm::void_pointer void_pointer;
- typedef typename MemoryAlgorithm::mutex_family mutex_family;
-
- MemoryAlgorithm &memory_algorithm()
- { return *this; }
-
- const MemoryAlgorithm &memory_algorithm() const
- { return *this; }
-
- enum { PayloadPerAllocation = MemoryAlgorithm::PayloadPerAllocation };
-
- basic_segment_manager(std::size_t size, std::size_t reserved_bytes)
- : MemoryAlgorithm(size, reserved_bytes)
- {
- assert((sizeof(basic_segment_manager<MemoryAlgorithm>) == sizeof(MemoryAlgorithm)));
- }
-
- //!Returns the size of the memory segment
- std::size_t get_size() const
- { return MemoryAlgorithm::get_size(); }
-
- //!Returns the number of unallocated bytes of the memory segment
- std::size_t get_free_memory() const
- { return MemoryAlgorithm::get_free_memory(); }
-
- //!Obtains the minimum size needed by the segment manager
- static std::size_t get_min_size (std::size_t size)
- { return MemoryAlgorithm::get_min_size(size); }
-
- //!Allocates nbytes bytes. This function is only used in
- //!single-segment management. Never throws
- void * allocate (std::size_t nbytes, std::nothrow_t)
- { return MemoryAlgorithm::allocate(nbytes); }
-
- //!Allocates nbytes bytes. This function is only used in
- //!single-segment management. Throws bad_alloc when fails
- void * allocate(std::size_t nbytes)
- {
- void * ret = MemoryAlgorithm::allocate(nbytes);
- if(!ret)
- throw bad_alloc();
- return ret;
- }
-
- //!Allocates nbytes bytes. This function is only used in
- //!single-segment management. Never throws
- void * allocate_aligned (std::size_t nbytes, std::size_t alignment, std::nothrow_t)
- { return MemoryAlgorithm::allocate_aligned(nbytes, alignment); }
-
- //!Allocates nbytes bytes. This function is only used in
- //!single-segment management. Throws bad_alloc when fails
- void * allocate_aligned(std::size_t nbytes, std::size_t alignment)
- {
- void * ret = MemoryAlgorithm::allocate_aligned(nbytes, alignment);
- if(!ret)
- throw bad_alloc();
- return ret;
- }
-
- std::pair<void *, bool>
- allocation_command (allocation_type command, std::size_t limit_size,
- std::size_t preferred_size,std::size_t &received_size,
- void *reuse_ptr = 0, std::size_t backwards_multiple = 1)
- {
- std::pair<void *, bool> ret = MemoryAlgorithm::allocation_command
- ( command | nothrow_allocation, limit_size, preferred_size, received_size
- , reuse_ptr, backwards_multiple);
- if(!(command & nothrow_allocation) && !ret.first)
- throw bad_alloc();
- return ret;
- }
-
- //!Deallocates the bytes allocated with allocate/allocate_at_least()
- //!pointed by addr
- void deallocate (void *addr)
- { MemoryAlgorithm::deallocate(addr); }
-
- //!Increases managed memory in extra_size bytes more. This only works
- //!with single-segment management*
- void grow(std::size_t extra_size)
- { MemoryAlgorithm::grow(extra_size); }
-
- //!Returns the result of "all_memory_deallocated()" function
- //!of the used memory algorithm
- bool all_memory_deallocated()
- { return MemoryAlgorithm::all_memory_deallocated(); }
-
- //!Returns the result of "check_sanity()" function
- //!of the used memory algorithm
- bool check_sanity()
- { return MemoryAlgorithm::check_sanity(); }
-
- //!Writes to zero free memory (memory not yet allocated) of the memory algorithm
- void zero_free_memory()
- { MemoryAlgorithm::zero_free_memory(); }
-
- /// @cond
- protected:
- void * prot_anonymous_construct
- (std::size_t num, bool dothrow, detail::in_place_interface &table)
- {
- typedef detail::block_header block_header_t;
- block_header_t block_info ( table.size*num
- , table.alignment
- , detail::anonymous_type
- , 1
- , 0);
-
- //Allocate memory
- void *ptr_struct = this->allocate(block_info.total_size(), std::nothrow_t());
-
- //Check if there is enough memory
- if(!ptr_struct){
- if(dothrow){
- throw bad_alloc();
- }
- else{
- return 0;
- }
- }
-
- //Build scoped ptr to avoid leaks with constructor exception
- detail::mem_algo_deallocator<MemoryAlgorithm> mem(ptr_struct, *this);
-
- //Now construct the header
- block_header_t * hdr = new(ptr_struct) block_header_t(block_info);
- void *ptr = hdr->value();
-
- //Now call constructors
- detail::array_construct(ptr, num, table);
-
- //All constructors successful, we don't want erase memory
- mem.release();
- return ptr;
- }
-
- //!Calls the destructor and makes an anonymous deallocate
- bool prot_anonymous_destroy(const void *object, detail::in_place_interface &table)
- {
- if(!object)
- return false;
-
- //Get control data from associated with this object
- typedef detail::block_header block_header_t;
- block_header_t *ctrl_data = block_header_t::block_header_from_value(object, table.size, table.alignment);
-
- //-------------------------------
- //boost::interprocess::scoped_lock<rmutex> guard(m_header);
- //-------------------------------
-
- if(ctrl_data->allocation_type() != detail::anonymous_type){
- //This is not an anonymous object, the pointer is wrong!
- assert(0);
- return false;
- }
-
- //Call destructors and free memory
- //Build scoped ptr to avoid leaks with destructor exception
- std::size_t destroyed = 0;
- table.destroy_n((void*)object, ctrl_data->m_value_bytes/table.size, destroyed);
- this->deallocate(ctrl_data);
- return true;
- }
-};
-
-} //namespace detail {
-}} //namespace boost { namespace interprocess
-
-#include <boost/interprocess/detail/config_end.hpp>
-
-#endif //#ifndef BOOST_INTERPROCESS_BASIC_SEGMENT_MANAGER_HPP
-
Modified: branches/bcbboost/boost/interprocess/detail/config_begin.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/config_begin.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/config_begin.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -9,29 +9,22 @@
#define _CRT_SECURE_NO_DEPRECATE
#endif
#pragma warning (push)
- //
- //'function' : resolved overload was found by argument-dependent lookup
- //A function found by argument-dependent lookup (Koenig lookup) was eventually
- //chosen by overload resolution.
- //
- //In Visual C++ .NET and earlier compilers, a different function would have
- //been called. To pick the original function, use an explicitly qualified name.
- //
-
- //warning C4275: non dll-interface class 'x' used as base for
- //dll-interface class 'Y'
- #pragma warning (disable : 4275)
- //warning C4251: 'x' : class 'y' needs to have dll-interface to
- //be used by clients of class 'z'
- #pragma warning (disable : 4251)
- #pragma warning (disable : 4675)
- #pragma warning (disable : 4996)
- #pragma warning (disable : 4503)
+ #pragma warning (disable : 4146) // unary minus operator applied to unsigned type, result still unsigned
#pragma warning (disable : 4284) // odd return type for operator->
#pragma warning (disable : 4244) // possible loss of data
- #pragma warning (disable : 4521) ////Disable "multiple copy constructors specified"
- #pragma warning (disable : 4522)
- #pragma warning (disable : 4146)
- #pragma warning (disable : 4503) //Decorated name length exceeded
- #pragma warning (disable : 4267) //conversion from 'X' to 'Y', possible loss of data
+ #pragma warning (disable : 4251) // 'identifier' : class 'type' needs to have dll-interface to be used by clients of class 'type2'
+ #pragma warning (disable : 4267) // conversion from 'X' to 'Y', possible loss of data
+ #pragma warning (disable : 4275) // non DLL-interface classkey 'identifier' used as base for DLL-interface classkey 'identifier'
+ #pragma warning (disable : 4355) // 'this' : used in base member initializer list
+ #pragma warning (disable : 4503) // 'identifier' : decorated name length exceeded, name was truncated
+ #pragma warning (disable : 4511) // copy constructor could not be generated
+ #pragma warning (disable : 4512) // assignment operator could not be generated
+ #pragma warning (disable : 4514) // unreferenced inline removed
+ #pragma warning (disable : 4521) // Disable "multiple copy constructors specified"
+ #pragma warning (disable : 4522) // 'class' : multiple assignment operators specified
+ #pragma warning (disable : 4675) // 'method' should be declared 'static' and have exactly one parameter
+ #pragma warning (disable : 4710) // function not inlined
+ #pragma warning (disable : 4711) // function selected for automatic inline expansion
+ #pragma warning (disable : 4786) // identifier truncated in debug info
+ #pragma warning (disable : 4996) // 'function': was declared deprecated
#endif
Modified: branches/bcbboost/boost/interprocess/detail/file_wrapper.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/file_wrapper.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/file_wrapper.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -26,28 +26,29 @@
{
public:
- /*!Default constructor. Represents an empty file_wrapper.*/
+ //!Default constructor.
+ //!Represents an empty file_wrapper.
file_wrapper();
- /*!Creates a shared memory object with name "name" and mode "mode", with the access mode "mode"
- If the file previously exists, throws an error.*/
+ //!Creates a file object with name "name" and mode "mode", with the access mode "mode"
+ //!If the file previously exists, throws an error.
file_wrapper(create_only_t, const char *name, mode_t mode)
{ this->priv_open_or_create(detail::DoCreate, name, mode); }
- /*!Tries to create a file with name "name" and mode "mode", with the
- access mode "mode". If the file previously exists, it tries to open it with mode "mode".
- Otherwise throws an error.*/
+ //!Tries to create a file with name "name" and mode "mode", with the
+ //!access mode "mode". If the file previously exists, it tries to open it with mode "mode".
+ //!Otherwise throws an error.
file_wrapper(open_or_create_t, const char *name, mode_t mode)
- { this->priv_open_or_create(detail::DoCreateOrOpen, name, mode); }
+ { this->priv_open_or_create(detail::DoOpenOrCreate, name, mode); }
- /*!Tries to open a shared memory object with name "name", with the access mode "mode".
- If the file does not previously exist, it throws an error.*/
+ //!Tries to open a file with name "name", with the access mode "mode".
+ //!If the file does not previously exist, it throws an error.
file_wrapper(open_only_t, const char *name, mode_t mode)
{ this->priv_open_or_create(detail::DoOpen, name, mode); }
- /*!Moves the ownership of "moved"'s shared memory object to *this.
- After the call, "moved" does not represent any shared memory object.
- Does not throw*/
+ //!Moves the ownership of "moved"'s file to *this.
+ //!After the call, "moved" does not represent any file.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
file_wrapper
(detail::moved_object<file_wrapper> &moved)
@@ -57,9 +58,9 @@
{ this->swap(moved); }
#endif
- /*!Moves the ownership of "moved"'s shared memory to *this.
- After the call, "moved" does not represent any shared memory.
- Does not throw*/
+ //!Moves the ownership of "moved"'s file to *this.
+ //!After the call, "moved" does not represent any file.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
file_wrapper &operator=
(detail::moved_object<file_wrapper> &moved)
@@ -77,33 +78,37 @@
}
#endif
- /*!Swaps to shared_memory_objects. Does not throw*/
+ //!Swaps to file_wrappers.
+ //!Does not throw
void swap(file_wrapper &other);
- /*!Erases a shared memory object from the system.*/
+ //!Erases a file from the system.
+ //!Returns false on error. Never throws
static bool remove(const char *name);
- /*!Sets the size of the shared memory mapping*/
+ //!Sets the size of the fil
void truncate(offset_t length);
- /*!Closes the shared memory mapping. All mapped regions are still
- valid after destruction. The shared memory object still exists and
- can be newly opened.*/
+ //!Closes the
+ //!file
~file_wrapper();
- /*!Returns the name of the file.*/
+ //!Returns the name of the file
+ //!used in the constructor
const char *get_name() const;
- /*!Returns access mode*/
+ //!Returns access mode
+ //!used in the constructor
mode_t get_mode() const;
- /*!Get mapping handle*/
+ //!Get mapping handle
+ //!to use with mapped_region
mapping_handle_t get_mapping_handle() const;
private:
- /*!Closes a previously opened file mapping. Never throws.*/
+ //!Closes a previously opened file mapping. Never throws.
void priv_close();
- /*!Closes a previously opened file mapping. Never throws.*/
+ //!Closes a previously opened file mapping. Never throws.
bool priv_open_or_create(detail::create_enum_t type, const char *filename, mode_t mode);
file_handle_t m_handle;
@@ -118,7 +123,6 @@
inline file_wrapper::~file_wrapper()
{ this->priv_close(); }
-/*!Returns the name of the file.*/
inline const char *file_wrapper::get_name() const
{ return m_filename.c_str(); }
@@ -155,7 +159,7 @@
case detail::DoCreate:
m_handle = create_new_file(filename, mode);
break;
- case detail::DoCreateOrOpen:
+ case detail::DoOpenOrCreate:
m_handle = create_or_open_file(filename, mode);
break;
default:
Deleted: branches/bcbboost/boost/interprocess/detail/gcd_lcm.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/gcd_lcm.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,63 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Stephen Cleary 2000.
-// (C) Copyright Ion Gaztanaga 2007.
-//
-// 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-// This file is a slightly modified file from Boost.Pool
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTERPROCESS_DETAIL_GCD_LCM_HPP
-#define BOOST_INTERPROCESS_DETAIL_GCD_LCM_HPP
-
-namespace boost {
-namespace interprocess {
-namespace detail {
-
-// Greatest common divisor and least common multiple
-
-//
-// gcd is an algorithm that calculates the greatest common divisor of two
-// integers, using Euclid's algorithm.
-//
-// Pre: A > 0 && B > 0
-// Recommended: A > B
-template <typename Integer>
-Integer gcd(Integer A, Integer B)
-{
- do
- {
- const Integer tmp(B);
- B = A % B;
- A = tmp;
- } while (B != 0);
-
- return A;
-}
-
-//
-// lcm is an algorithm that calculates the least common multiple of two
-// integers.
-//
-// Pre: A > 0 && B > 0
-// Recommended: A > B
-template <typename Integer>
-Integer lcm(const Integer & A, const Integer & B)
-{
- Integer ret = A;
- ret /= gcd(A, B);
- ret *= B;
- return ret;
-}
-
-} // namespace detail
-} // namespace interprocess
-} // namespace boost
-
-#endif
Deleted: branches/bcbboost/boost/interprocess/detail/generic_cast.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/generic_cast.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,57 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2005-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTERPROCESS_GENERIC_CAST_HPP
-#define BOOST_INTERPROCESS_GENERIC_CAST_HPP
-
-#if (defined _MSC_VER) && (_MSC_VER >= 1200)
-# pragma once
-#endif
-
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/type_traits/is_pointer.hpp>
-
-
-namespace boost{
-namespace interprocess{
-
-template<class T>
-class cast_to;
-
-template<class T>
-class cast_to<T*>
-{
- public:
- template<class S>
- static T* using_static_cast(S *s)
- { return static_cast<T*>(s); }
-
- template<class S>
- static T* using_dynamic_cast(S *s)
- { return dynamic_cast<T*>(s); }
-
- template<class S>
- static T* using_const_cast(S *s)
- { return const_cast<T*>(s); }
-
- template<class S>
- static T* using_reinterpret_cast(S *s)
- { return reinterpret_cast<T*>(s); }
-};
-
-} //namespace interprocess{
-} //namespace boost{
-
-#include <boost/interprocess/detail/config_end.hpp>
-
-#endif //#ifndef BOOST_INTERPROCESS_GENERIC_CAST_HPP
-
Modified: branches/bcbboost/boost/interprocess/detail/in_place_interface.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/in_place_interface.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/in_place_interface.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,9 +20,8 @@
#include <boost/interprocess/detail/type_traits.hpp>
#include <typeinfo> //typeid
-/*!\file
- Describes an abstract interface for placement construction and destruction.
-*/
+//!\file
+//!Describes an abstract interface for placement construction and destruction.
namespace boost {
namespace interprocess {
Modified: branches/bcbboost/boost/interprocess/detail/managed_memory_impl.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/managed_memory_impl.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/managed_memory_impl.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -86,8 +86,11 @@
typedef typename MemoryAlgorithm::mutex_family mutex_family;
typedef CharType char_t;
typedef std::ptrdiff_t handle_t;
- typedef typename segment_manager::const_named_iterator const_named_iterator;
- typedef typename segment_manager::const_unique_iterator const_unique_iterator;
+ typedef typename segment_manager::
+ const_named_iterator const_named_iterator;
+ typedef typename segment_manager::
+ const_unique_iterator const_unique_iterator;
+
/// @cond
//Experimental. Don't use.
@@ -294,16 +297,16 @@
//Experimental. Don't use.
//!Allocates n_elements of elem_size bytes.
- multiallocation_iterator allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements)
- { return mp_header->allocate_many(elem_size, min_elements, preferred_elements, received_elements); }
+ multiallocation_iterator allocate_many(std::size_t elem_bytes, std::size_t num_elements)
+ { return mp_header->allocate_many(elem_bytes, num_elements); }
//!Allocates n_elements, each one of elem_sizes[i] bytes.
multiallocation_iterator allocate_many(const std::size_t *elem_sizes, std::size_t n_elements)
{ return mp_header->allocate_many(elem_sizes, n_elements); }
//!Allocates n_elements of elem_size bytes.
- multiallocation_iterator allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements, std::nothrow_t nothrow)
- { return mp_header->allocate_many(elem_size, min_elements, preferred_elements, received_elements, nothrow); }
+ multiallocation_iterator allocate_many(std::size_t elem_bytes, std::size_t num_elements, std::nothrow_t nothrow)
+ { return mp_header->allocate_many(elem_bytes, num_elements, nothrow); }
//!Allocates n_elements, each one of elem_sizes[i] bytes.
multiallocation_iterator allocate_many(const std::size_t *elem_sizes, std::size_t n_elements, std::nothrow_t nothrow)
@@ -662,6 +665,36 @@
const_unique_iterator unique_end() const
{ return mp_header->unique_end(); }
+ //!This is the default allocator to allocate types T
+ //!from this managed segment
+ template<class T>
+ struct allocator
+ {
+ typedef typename segment_manager::template allocator<T>::type type;
+ };
+
+ //!Returns an instance of the default allocator for type T
+ //!initialized that allocates memory from this segment manager.
+ template<class T>
+ typename allocator<T>::type
+ get_allocator()
+ { return mp_header->get_allocator<T>(); }
+
+ //!This is the default deleter to delete types T
+ //!from this managed segment.
+ template<class T>
+ struct deleter
+ {
+ typedef typename segment_manager::template deleter<T>::type type;
+ };
+
+ //!Returns an instance of the default allocator for type T
+ //!initialized that allocates memory from this segment manager.
+ template<class T>
+ typename deleter<T>::type
+ get_deleter()
+ { return mp_header->get_deleter<T>(); }
+
protected:
//!Sets the base address of the memory in this process.
//!This is very low level, so use it only if you know what are
Modified: branches/bcbboost/boost/interprocess/detail/managed_open_or_create_impl.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/managed_open_or_create_impl.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/managed_open_or_create_impl.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -90,7 +90,7 @@
{
m_name = name;
priv_open_or_create
- ( detail::DoCreateOrOpen
+ ( detail::DoOpenOrCreate
, size
, mode
, addr
@@ -140,7 +140,7 @@
{
m_name = name;
priv_open_or_create
- ( detail::DoCreateOrOpen
+ ( detail::DoOpenOrCreate
, size
, mode
, addr
@@ -281,7 +281,7 @@
create_device<FileBased>(dev, m_name.c_str(), size, file_like_t());
created = true;
}
- else if(type == detail::DoCreateOrOpen){
+ else if(type == detail::DoOpenOrCreate){
//This loop is very ugly, but brute force is sometimes better
//than diplomacy. If someone knows how to open or create a
//file and know if we have really created it or just open it
Modified: branches/bcbboost/boost/interprocess/detail/move.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/move.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/move.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -18,13 +18,14 @@
#include <boost/interprocess/detail/config_begin.hpp>
#include <boost/interprocess/detail/workaround.hpp>
-/*!\file
- Describes a function and a type to emulate move semantics.
-*/
+//!\file
+//!Describes a function and a type to emulate move semantics.
+
namespace boost {
namespace interprocess {
-/*!Trait class to detect if a type is movable*/
+//!Trait class to detect if a type is
+//!movable
template <class T>
struct is_movable
{
@@ -43,7 +44,8 @@
namespace interprocess {
namespace detail {
-/*!An object that represents a moved object.*/
+//!An object that represents a
+//!moved object.
template<class T>
struct moved_object
{
@@ -69,8 +71,10 @@
template <typename T>
class move_return
{
+ typedef moved_object<T> moved_type;
private:
- T m_moved;
+ mutable T m_moved;
+
public:
typedef T type;
@@ -83,8 +87,8 @@
: m_moved(const_cast<move_return&>(operand))
{}
- operator moved_object<T>()
- { return moved_object<T>(m_moved); }
+ operator moved_type() const
+ { return moved_type(m_moved); }
};
template <typename T>
@@ -102,8 +106,8 @@
namespace boost {
namespace interprocess {
-/*!A function that converts an object to a moved object so that
- it can match a function taking a detail::moved_object object.*/
+//!A function that converts an object to a moved object so that
+//!it can match a function taking a detail::moved_object object.
template<class Object>
typename detail::move_type<Object>::type move
(const Object &object)
Modified: branches/bcbboost/boost/interprocess/detail/named_proxy.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/named_proxy.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/named_proxy.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -28,15 +28,15 @@
#include <boost/interprocess/detail/mpl.hpp>
#include <iterator>
-/*!\file
- Describes a proxy class that implements named allocation syntax.
-*/
+//!\file
+//!Describes a proxy class that implements named allocation syntax.
namespace boost {
namespace interprocess {
namespace detail {
-/*!Function object that makes placement new without arguments*/
+//!Function object that makes placement new
+//!without arguments
template<class T>
struct Ctor0Arg : public placement_destroy<T>
{
@@ -120,20 +120,19 @@
//bind rvalues with non-const references, we have to be ugly
#define BOOST_INTERPROCESS_AUX_PARAM_LIST(z, n, data) \
const BOOST_PP_CAT(P, n) & BOOST_PP_CAT(p, n) \
-/**/
+//!
#define BOOST_INTERPROCESS_AUX_PARAM_INIT(z, n, data) \
BOOST_PP_CAT(m_p, n) (const_cast<BOOST_PP_CAT(P, n) &>(BOOST_PP_CAT(p, n))) \
-/**/
+//!
#define BOOST_INTERPROCESS_AUX_PARAM_INC(z, n, data) \
BOOST_PP_CAT(++m_p, n) \
-/**/
+//!
#define BOOST_INTERPROCESS_AUX_PARAM_DEFINE(z, n, data) \
BOOST_PP_CAT(P, n) & BOOST_PP_CAT(m_p, n); \
-
-/**/
+//!
#define BOOST_PP_LOCAL_MACRO(n) \
template<class T, bool is_iterator, BOOST_PP_ENUM_PARAMS(n, class P) > \
@@ -180,7 +179,7 @@
\
BOOST_PP_REPEAT(n, BOOST_INTERPROCESS_AUX_PARAM_DEFINE, _) \
}; \
-/**/
+//!
#define BOOST_PP_LOCAL_LIMITS (1, BOOST_INTERPROCESS_MAX_CONSTRUCTOR_PARAMETERS)
@@ -213,23 +212,24 @@
, m_find(find), m_dothrow(dothrow)
{}
- /*!makes a named allocation and calls the default constructor*/
+ //!makes a named allocation and calls the
+ //!default constructor
T *operator()() const
{
Ctor0Arg<T> ctor_obj;
return mp_mngr->template
generic_construct<T>(mp_name, m_num, m_find, m_dothrow, ctor_obj);
}
- /**/
+ //!
// Boost preprocessor used to create operator() overloads
#define BOOST_INTERPROCESS_AUX_TYPE_LIST(z, n, data) \
BOOST_PP_CAT(P, n) \
- /**/
+ //!
#define BOOST_INTERPROCESS_AUX_PARAM_LIST(z, n, data) \
const BOOST_PP_CAT(P, n) BOOST_PP_CAT(&p, n) \
- /**/
+ //!
#define BOOST_PP_LOCAL_MACRO(n) \
template<BOOST_PP_ENUM_PARAMS(n, class P)> \
@@ -242,7 +242,7 @@
return mp_mngr->template generic_construct<T> \
(mp_name, m_num, m_find, m_dothrow, ctor_obj); \
} \
- /**/
+ //!
#define BOOST_PP_LOCAL_LIMITS ( 1, BOOST_INTERPROCESS_MAX_CONSTRUCTOR_PARAMETERS )
#include BOOST_PP_LOCAL_ITERATE()
Deleted: branches/bcbboost/boost/interprocess/detail/null_create_func.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/null_create_func.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,34 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2005-2007. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTERPROCESS_DETAIL_NULL_CREATION_FUNCTOR_HPP
-#define BOOST_INTERPROCESS_DETAIL_NULL_CREATION_FUNCTOR_HPP
-
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-namespace boost {
-namespace interprocess {
-namespace detail{
-
-/*!No-op functor*/
-struct null_func_t
-{
- bool operator()(const segment_info_t *, bool) const
- { return true; }
-};
-
-} //namespace detail{
-} //namespace interprocess {
-} //namespace boost {
-
-#include <boost/interprocess/detail/config_end.hpp>
-
-#endif //BOOST_INTERPROCESS_DETAIL_NULL_CREATION_FUNCTOR_HPP
Modified: branches/bcbboost/boost/interprocess/detail/os_file_functions.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/os_file_functions.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/os_file_functions.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -159,8 +159,6 @@
return (acquired = true);
}
-
-
inline bool release_file_lock(file_handle_t hnd)
{
const unsigned long len = 0xffffffff;
Modified: branches/bcbboost/boost/interprocess/detail/segment_manager_helper.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/segment_manager_helper.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/segment_manager_helper.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -31,11 +31,9 @@
#include <exception>
#endif
-/*!\file
- Describes the object placed in a memory segment that provides
- named object allocation capabilities for single-segment and
- multi-segment allocations.
-*/
+//!\file
+//!Describes the object placed in a memory segment that provides
+//!named object allocation capabilities.
namespace boost{
namespace interprocess{
@@ -133,22 +131,22 @@
{ return m_num_char; }
std::size_t name_offset() const
- {
+ {
return value_offset() + get_rounded_size(m_value_bytes, sizeof_char());
}
void *value() const
- {
+ {
return detail::char_ptr_cast(this) + value_offset();
}
std::size_t value_offset() const
- {
+ {
return get_rounded_size(sizeof(block_header), m_value_alignment);
}
template<class CharType>
- bool less(const block_header &b) const
+ bool less_comp(const block_header &b) const
{
return m_num_char < b.m_num_char ||
(m_num_char < b.m_num_char &&
@@ -157,7 +155,7 @@
}
template<class CharType>
- bool equal(const block_header &b) const
+ bool equal_comp(const block_header &b) const
{
return m_num_char == b.m_num_char &&
std::char_traits<CharType>::compare
@@ -294,10 +292,10 @@
}
bool operator <(const intrusive_value_type_impl<Hook, CharType> & other) const
- { return this->get_block_header()->template less<CharType>(*other.get_block_header()); }
+ { return (this->get_block_header())->template less_comp<CharType>(*other.get_block_header()); }
bool operator ==(const intrusive_value_type_impl<Hook, CharType> & other) const
- { return this->get_block_header()->template equal<CharType>(*other.get_block_header()); }
+ { return (this->get_block_header())->template equal_comp<CharType>(*other.get_block_header()); }
static intrusive_value_type_impl *get_intrusive_value_type(block_header *hdr)
{
@@ -395,8 +393,8 @@
template<class VoidPointer>
struct index_data
{
- typedef VoidPointer void_ptr;
- void_ptr m_ptr;
+ typedef VoidPointer void_pointer;
+ void_pointer m_ptr;
index_data(void *ptr) : m_ptr(ptr){}
void *value() const
Modified: branches/bcbboost/boost/interprocess/detail/type_traits.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/type_traits.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/type_traits.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -141,12 +141,31 @@
static yes_type is_same_tester(V*, V*);
static no_type is_same_tester(...);
- static T t;
- static U u;
+ static T *t;
+ static U *u;
- static const bool value = sizeof(yes_type) == sizeof(is_same_tester(&t,&u));
+ static const bool value = sizeof(yes_type) == sizeof(is_same_tester(t,u));
};
/*
+template <template<class P> typename T, template<typename P2> typename U>
+struct is_same
+{
+ typedef char yes_type;
+ struct no_type
+ {
+ char padding[8];
+ };
+
+ template <template<class P3> typename V>
+ static yes_type is_same_tester(V<P3>*, V<P3>*);
+ static no_type is_same_tester(...);
+
+ static T<int> *t;
+ static U<int> *u;
+
+ static const bool value = sizeof(yes_type) == sizeof(is_same_tester(t,u));
+};*/
+/*
template< typename T >
struct is_pointer_impl
{
Modified: branches/bcbboost/boost/interprocess/detail/utilities.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/utilities.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/utilities.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -105,9 +105,10 @@
template <class Allocator>
struct scoped_array_deallocator
{
- typedef typename Allocator::pointer pointer;
+ typedef typename Allocator::pointer pointer;
+ typedef typename Allocator::size_type size_type;
- scoped_array_deallocator(pointer p, Allocator& a, std::size_t length)
+ scoped_array_deallocator(pointer p, Allocator& a, size_type length)
: m_ptr(p), m_alloc(a), m_length(length) {}
~scoped_array_deallocator()
@@ -119,7 +120,20 @@
private:
pointer m_ptr;
Allocator& m_alloc;
- std::size_t m_length;
+ size_type m_length;
+};
+
+template <class Allocator>
+struct null_scoped_array_deallocator
+{
+ typedef typename Allocator::pointer pointer;
+ typedef typename Allocator::size_type size_type;
+
+ null_scoped_array_deallocator(pointer, Allocator&, size_type)
+ {}
+
+ void release()
+ {}
};
//!A deleter for scoped_ptr that destroys
@@ -127,17 +141,22 @@
template <class Allocator>
struct scoped_destructor_n
{
- typedef typename Allocator::pointer pointer;
+ typedef typename Allocator::pointer pointer;
typedef typename Allocator::value_type value_type;
+ typedef typename Allocator::size_type size_type;
pointer m_p;
- std::size_t m_n;
+ size_type m_n;
- scoped_destructor_n(pointer p, std::size_t n)
- : m_p(p), m_n(n){}
+ scoped_destructor_n(pointer p, size_type n)
+ : m_p(p), m_n(n)
+ {}
void release()
{ m_p = 0; }
+
+ void increment_size(size_type inc)
+ { m_n += inc; }
~scoped_destructor_n()
{
@@ -148,6 +167,24 @@
}
};
+//!A deleter for scoped_ptr that destroys
+//!an object using a STL allocator.
+template <class Allocator>
+struct null_scoped_destructor_n
+{
+ typedef typename Allocator::pointer pointer;
+ typedef typename Allocator::size_type size_type;
+
+ null_scoped_destructor_n(pointer, size_type)
+ {}
+
+ void increment_size(size_type)
+ {}
+
+ void release()
+ {}
+};
+
template <class A>
class allocator_destroyer
{
@@ -187,9 +224,9 @@
++m_itbeg;
}
}
-
- void release()
- { m_itbeg = multiallocation_iterator(); }
+
+ void increment()
+ { ++m_itbeg; }
};
@@ -223,7 +260,7 @@
{ m_itbeg = multiallocation_iterator(); }
};
-/*!Forces a cast from any pointer to char * pointer*/
+//!Forces a cast from any pointer to char *pointer
template<class T>
inline char* char_ptr_cast(T *ptr)
{
@@ -282,8 +319,8 @@
static const std::size_t value = 0;
};
-/*!Obtains a generic pointer of the same type that
- can point to other pointed type: Ptr<?> -> Ptr<NewValueType>*/
+//!Obtains a generic pointer of the same type that
+//!can point to other pointed type: Ptr<?> -> Ptr<NewValueType>
template<class T, class U>
struct pointer_to_other;
@@ -316,9 +353,9 @@
} //namespace detail {
-/*!Trait class to detect if an index is a node
- index. This allows more efficient operations
- when deallocating named objects.*/
+//!Trait class to detect if an index is a node
+//!index. This allows more efficient operations
+//!when deallocating named objects.
template <class Index>
struct is_node_index
{
@@ -326,24 +363,16 @@
};
-/*!Trait class to detect if an index is an intrusive
- index. This will embed the derivation hook in each
- allocation header, to provide memory for the intrusive
- container.*/
+//!Trait class to detect if an index is an intrusive
+//!index. This will embed the derivation hook in each
+//!allocation header, to provide memory for the intrusive
+//!container.
template <class Index>
struct is_intrusive_index
{
enum { value = false };
};
-/*!Trait class to detect if an smart pointer has
- multi-segment addressing capabilities.*/
-template <class Ptr>
-struct is_multisegment_ptr
-{
- enum { value = false };
-};
-
template <class SizeType>
SizeType
get_next_capacity(const SizeType max_size
Modified: branches/bcbboost/boost/interprocess/detail/win32_api.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/win32_api.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/win32_api.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -11,22 +11,21 @@
#ifndef BOOST_INTERPROCESS_WIN32_SYNC_PRIMITIVES_HPP
#define BOOST_INTERPROCESS_WIN32_SYNC_PRIMITIVES_HPP
+#include <boost/interprocess/detail/config_begin.hpp>
+#include <boost/interprocess/detail/workaround.hpp>
+#include <stddef.h>
+
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
+# pragma comment( lib, "advapi32.lib" )
#endif
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
#if (defined BOOST_WINDOWS) && !(defined BOOST_DISABLE_WIN32)
# include <stddef.h>
# include <stdarg.h>
# include <boost/detail/interlocked.hpp>
-# if !defined(__MINGW32__)
-# pragma comment( lib, "advapi32.lib" )//auto-unlink security features
-# endif
#else
-# error "This file can only be included in Windows OS"
+# error "This file can only be included in Windows OS"
#endif
//The structures used in Interprocess with the
@@ -248,10 +247,9 @@
extern "C" __declspec(dllimport) int __stdcall LockFileEx(void *hnd, unsigned long flags, unsigned long reserved, unsigned long size_low, unsigned long size_high, interprocess_overlapped* overlapped);
extern "C" __declspec(dllimport) int __stdcall UnlockFileEx(void *hnd, unsigned long reserved, unsigned long size_low, unsigned long size_high, interprocess_overlapped* overlapped);
extern "C" __declspec(dllimport) int __stdcall WriteFile(void *hnd, const void *buffer, unsigned long bytes_to_write, unsigned long *bytes_written, interprocess_overlapped* overlapped);
-extern "C" __declspec(dllimport) int __stdcall InitializeSecurityDescriptor
- (void *pSecurityDescriptor, unsigned long dwRevision);
-extern "C" __declspec(dllimport) int __stdcall SetSecurityDescriptorDacl
- ( void *pSecurityDescriptor, int bDaclPresent, interprocess_acl *pDacl, int bDaclDefaulted);
+extern "C" __declspec(dllimport) int __stdcall InitializeSecurityDescriptor(interprocess_security_descriptor *pSecurityDescriptor, unsigned long dwRevision);
+extern "C" __declspec(dllimport) int __stdcall SetSecurityDescriptorDacl(interprocess_security_descriptor *pSecurityDescriptor, int bDaclPresent, interprocess_acl *pDacl, int bDaclDefaulted);
+
/*
extern "C" __declspec(dllimport) long __stdcall InterlockedIncrement( long volatile * );
extern "C" __declspec(dllimport) long __stdcall InterlockedDecrement( long volatile * );
@@ -362,7 +360,7 @@
static inline void * open_file_mapping (unsigned long access, const char *name)
{ return OpenFileMappingA (access, 0, name); }
-static inline void *map_view_of_file_ex(void *handle, unsigned long file_access, unsigned long highoffset, unsigned long lowoffset, std::size_t numbytes, void *base_addr)
+static inline void *map_view_of_file_ex(void *handle, unsigned long file_access, unsigned long highoffset, unsigned long lowoffset, size_t numbytes, void *base_addr)
{ return MapViewOfFileEx(handle, file_access, highoffset, lowoffset, numbytes, base_addr); }
static inline void *create_file(const char *name, unsigned long access, unsigned long creation_flags, unsigned long attributes = 0)
@@ -374,7 +372,7 @@
static inline void get_system_info(system_info *info)
{ GetSystemInfo(info); }
-static inline int flush_view_of_file(void *base_addr, std::size_t numbytes)
+static inline int flush_view_of_file(void *base_addr, size_t numbytes)
{ return FlushViewOfFile(base_addr, numbytes); }
static inline bool get_file_size(void *handle, __int64 &size)
Modified: branches/bcbboost/boost/interprocess/detail/workaround.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/detail/workaround.hpp (original)
+++ branches/bcbboost/boost/interprocess/detail/workaround.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -48,6 +48,10 @@
#define BOOST_INTERPROCESS_POSIX_TIMEOUTS
#endif
+ #if defined(_POSIX_SEMAPHORES) && (_POSIX_SEMAPHORES - 0 > 0)
+ #define BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ #endif
+
#endif
#if __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ > 2)
Modified: branches/bcbboost/boost/interprocess/errors.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/errors.hpp (original)
+++ branches/bcbboost/boost/interprocess/errors.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -43,9 +43,8 @@
# endif //ifdef BOOST_HAS_UNISTD_H
#endif //#if (defined BOOST_WINDOWS) && !(defined BOOST_DISABLE_WIN32)
-/*!\file
- Describes the error numbering of interprocess classes
-*/
+//!\file
+//!Describes the error numbering of interprocess classes
namespace boost {
namespace interprocess {
Modified: branches/bcbboost/boost/interprocess/exceptions.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/exceptions.hpp (original)
+++ branches/bcbboost/boost/interprocess/exceptions.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -21,16 +21,15 @@
#include <stdexcept>
#include <new>
-/*!\file
- Describes exceptions thrown by interprocess classes
-*/
+//!\file
+//!Describes exceptions thrown by interprocess classes
namespace boost {
namespace interprocess {
-/*!This class is the base class of all exceptions
- thrown by boost::interprocess*/
+//!This class is the base class of all exceptions
+//!thrown by boost::interprocess
class interprocess_exception : public std::exception
{
public:
@@ -79,8 +78,8 @@
/// @endcond
};
-/*!This is the exception thrown by shared interprocess_mutex family when a deadlock situation
- is detected or when using a interprocess_condition the interprocess_mutex is not locked*/
+//!This is the exception thrown by shared interprocess_mutex family when a deadlock situation
+//!is detected or when using a interprocess_condition the interprocess_mutex is not locked
class lock_exception : public interprocess_exception
{
public:
@@ -92,8 +91,8 @@
{ return "boost::interprocess::lock_exception"; }
};
-/*!This is the exception thrown by named interprocess_semaphore when a deadlock situation
- is detected or when an error is detected in the post/wait operation*/
+//!This is the exception thrown by named interprocess_semaphore when a deadlock situation
+//!is detected or when an error is detected in the post/wait operation
/*
class sem_exception : public interprocess_exception
{
@@ -106,8 +105,8 @@
{ return "boost::interprocess::sem_exception"; }
};
*/
-/*!This is the exception thrown by synchronization objects when there is
- an error in a wait() function*/
+//!This is the exception thrown by synchronization objects when there is
+//!an error in a wait() function
/*
class wait_exception : public interprocess_exception
{
@@ -117,8 +116,8 @@
};
*/
-/*!This exception is thrown when a named object is created
- in "open_only" mode and the resource was not already created*/
+//!This exception is thrown when a named object is created
+//!in "open_only" mode and the resource was not already created
/*
class not_previously_created : public interprocess_exception
{
@@ -127,7 +126,9 @@
{ return "boost::interprocess::not_previously_created"; }
};
*/
-/*!This exception is thrown when a memory request can't be fulfilled.*/
+
+//!This exception is thrown when a memory request can't be
+//!fulfilled.
class bad_alloc : public interprocess_exception
{
public:
Modified: branches/bcbboost/boost/interprocess/file_mapping.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/file_mapping.hpp (original)
+++ branches/bcbboost/boost/interprocess/file_mapping.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,16 +23,15 @@
#include <cstdio> //std::remove
#include <string>
-/*!\file
- Describes file_mapping and mapped region classes
-*/
+//!\file
+//!Describes file_mapping and mapped region classes
namespace boost {
namespace interprocess {
-/*!A class that wraps a file-mapping that can be used to
- create mapped regions from the mapped files*/
+//!A class that wraps a file-mapping that can be used to
+//!create mapped regions from the mapped files
class file_mapping
{
/// @cond
@@ -42,18 +41,19 @@
/// @endcond
public:
- /*!Constructs an empty file mapping. Does not throw*/
+ //!Constructs an empty file mapping.
+ //!Does not throw
file_mapping();
- /*!Opens a file mapping of file "filename", starting in offset
- "file_offset", and the mapping's size will be "size". The mapping
- can be opened for read-only "read_only" or read-write "read_write"
- modes. Throws interprocess_exception on error.*/
+ //!Opens a file mapping of file "filename", starting in offset
+ //!"file_offset", and the mapping's size will be "size". The mapping
+ //!can be opened for read-only "read_only" or read-write "read_write"
+ //!modes. Throws interprocess_exception on error.
file_mapping(const char *filename, mode_t mode);
- /*!Moves the ownership of "moved"'s shared memory object to *this.
- After the call, "moved" does not represent any shared memory object.
- Does not throw*/
+ //!Moves the ownership of "moved"'s shared memory object to *this.
+ //!After the call, "moved" does not represent any shared memory object.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
file_mapping(detail::moved_object<file_mapping> &moved)
{ this->swap(moved.get()); }
@@ -62,9 +62,9 @@
{ this->swap(moved); }
#endif
- /*!Moves the ownership of "moved"'s shared memory to *this.
- After the call, "moved" does not represent any shared memory.
- Does not throw*/
+ //!Moves the ownership of "moved"'s shared memory to *this.
+ //!After the call, "moved" does not represent any shared memory.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
file_mapping &operator=
(detail::moved_object<file_mapping> &moved)
@@ -82,25 +82,29 @@
}
#endif
- /*!Swaps to file_mappings. Does not throw*/
+ //!Swaps to file_mappings.
+ //!Does not throw.
void swap(file_mapping &other);
- /*!Returns access mode*/
+ //!Returns access mode
+ //!used in the constructor
mode_t get_mode() const;
- /*!Get mapping handle*/
+ //!Obtains the mapping handle
+ //!to be used with mapped_region
mapping_handle_t get_mapping_handle() const;
- /*!Destroys the file mapping. All mapped regions created from this are still
- valid. Does not throw*/
+ //!Destroys the file mapping. All mapped regions created from this are still
+ //!valid. Does not throw
~file_mapping();
- /*!Returns the name of the file.*/
+ //!Returns the name of the file
+ //!used in the constructor.
const char *get_name() const;
/// @cond
private:
- /*!Closes a previously opened file mapping. Never throws.*/
+ //!Closes a previously opened file mapping. Never throws.
void priv_close();
file_handle_t m_handle;
mode_t m_mode;
Modified: branches/bcbboost/boost/interprocess/indexes/flat_map_index.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/indexes/flat_map_index.hpp (original)
+++ branches/bcbboost/boost/interprocess/indexes/flat_map_index.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -18,10 +18,9 @@
#include <boost/interprocess/containers/flat_map.hpp>
#include <boost/interprocess/allocators/allocator.hpp>
-/*!\file
- Describes index adaptor of boost::map container, to use it
- as name/shared memory index
-*/
+//!\file
+//!Describes index adaptor of boost::map container, to use it
+//!as name/shared memory index
//[flat_map_index
namespace boost { namespace interprocess {
Modified: branches/bcbboost/boost/interprocess/indexes/iset_index.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/indexes/iset_index.hpp (original)
+++ branches/bcbboost/boost/interprocess/indexes/iset_index.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -21,39 +21,34 @@
#include <boost/intrusive/set.hpp>
-/*!\file
- Describes index adaptor of boost::intrusive::set container, to use it
- as name/shared memory index
-*/
+//!\file
+//!Describes index adaptor of boost::intrusive::set container, to use it
+//!as name/shared memory index
-namespace boost { namespace interprocess {
+namespace boost {
+namespace interprocess {
/// @cond
-/*!Helper class to define typedefs from IndexTraits*/
+
+//!Helper class to define typedefs from IndexTraits
template <class MapConfig>
struct iset_index_aux
{
typedef typename
- MapConfig::segment_manager_base segment_manager_base;
+ MapConfig::segment_manager_base segment_manager_base;
typedef typename
- segment_manager_base::void_pointer void_pointer;
-
- typedef boost::intrusive::set_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , void_pointer> derivation_hook;
+ segment_manager_base::void_pointer void_pointer;
+ typedef typename bi::make_set_base_hook
+ <bi::void_pointer<void_pointer> >::type derivation_hook;
-// typedef typename MapConfig::intrusive_value_type intrusive_value_type;
-// typedef intrusive_value_type<derivation_hook>::type value_type;
typedef typename MapConfig::template
- intrusive_value_type<derivation_hook>::type value_type;
-
- typedef std::less<value_type> value_compare;
-
- typedef boost::intrusive::set
- <typename derivation_hook::template
- value_traits<value_type>, std::less<value_type> > index_t;
+ intrusive_value_type<derivation_hook>::type value_type;
+ typedef std::less<value_type> value_compare;
+ typedef typename bi::make_set
+ < value_type
+ , bi::base_hook<derivation_hook>
+ >::type index_t;
};
/// @endcond
@@ -107,14 +102,14 @@
public:
- /*!Constructor. Takes a pointer to the
- segment manager. Can throw*/
+ //!Constructor. Takes a pointer to the
+ //!segment manager. Can throw
iset_index(typename MapConfig::segment_manager_base *)
: index_type(/*typename index_aux::value_compare()*/)
{}
- /*!This reserves memory to optimize the insertion of n
- elements in the index*/
+ //!This reserves memory to optimize the insertion of n
+ //!elements in the index
void reserve(std::size_t)
{ /*Does nothing, map has not reserve or rehash*/ }
@@ -134,8 +129,9 @@
};
/// @cond
-/*!Trait class to detect if an index is an intrusive
- index.*/
+
+//!Trait class to detect if an index is an intrusive
+//!index.
template<class MapConfig>
struct is_intrusive_index
<boost::interprocess::iset_index<MapConfig> >
@@ -144,7 +140,8 @@
};
/// @endcond
-}} //namespace boost { namespace interprocess {
+} //namespace interprocess {
+} //namespace boost
#include <boost/interprocess/detail/config_end.hpp>
Modified: branches/bcbboost/boost/interprocess/indexes/iunordered_set_index.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/indexes/iunordered_set_index.hpp (original)
+++ branches/bcbboost/boost/interprocess/indexes/iunordered_set_index.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -41,20 +41,18 @@
typedef typename
segment_manager_base::void_pointer void_pointer;
- typedef boost::intrusive::unordered_set_base_hook
- < boost::intrusive::tag
- , boost::intrusive::safe_link
- , void_pointer> derivation_hook;
+ typedef typename bi::make_unordered_set_base_hook
+ < bi::void_pointer<void_pointer> >::type derivation_hook;
typedef typename MapConfig::template
- intrusive_value_type<derivation_hook>::type value_type;
+ intrusive_value_type<derivation_hook>::type value_type;
typedef typename MapConfig::
- intrusive_compare_key_type intrusive_compare_key_type;
+ intrusive_compare_key_type intrusive_compare_key_type;
- typedef std::equal_to<value_type> value_equal;
+ typedef std::equal_to<value_type> value_equal;
- typedef typename MapConfig::char_type char_type;
+ typedef typename MapConfig::char_type char_type;
struct equal_function
{
@@ -98,14 +96,14 @@
}
};
- typedef boost::intrusive::unordered_set
- <typename derivation_hook::template
- value_traits<value_type>, hash_function, equal_function, true> index_t;
-
- typedef typename index_t::bucket_type bucket_type;
-
+ typedef typename bi::make_unordered_set
+ < value_type
+ , bi::hash<hash_function>
+ , bi::equal<equal_function>
+ >::type index_t;
+ typedef typename index_t::bucket_type bucket_type;
typedef allocator
- <bucket_type, segment_manager_base> allocator_type;
+ <bucket_type, segment_manager_base> allocator_type;
struct allocator_holder
{
@@ -148,6 +146,7 @@
typedef typename index_type::value_type value_type;
typedef typename index_type::bucket_ptr bucket_ptr;
typedef typename index_type::bucket_type bucket_type;
+ typedef typename index_type::bucket_traits bucket_traits;
typedef typename index_type::size_type size_type;
/// @cond
@@ -176,10 +175,21 @@
return old_size;
std::size_t received_size;
if(!alloc.allocation_command
- (shrink_in_place | nothrow_allocation, old_size, new_size, received_size, buckets).first){
+ (try_shrink_in_place | nothrow_allocation, old_size, new_size, received_size, buckets).first){
return old_size;
}
+ for( bucket_type *p = detail::get_pointer(buckets) + received_size
+ , *pend = detail::get_pointer(buckets) + old_size
+ ; p != pend
+ ; ++p){
+ p->~bucket_type();
+ }
+
+ bucket_ptr shunk_p = alloc.allocation_command
+ (shrink_in_place | nothrow_allocation, received_size, received_size, received_size, buckets).first;
+ BOOST_ASSERT(buckets == shunk_p);
+
bucket_ptr buckets_init = buckets + received_size;
for(std::size_t i = 0; i < (old_size - received_size); ++i){
get_pointer(buckets_init++)->~bucket_type();
@@ -231,7 +241,7 @@
//!segment manager. Can throw
iunordered_set_index(segment_manager_base *mngr)
: allocator_holder(mngr)
- , index_type(&get_this_pointer()->init_bucket, 1)
+ , index_type(bucket_traits(&get_this_pointer()->init_bucket, 1))
{}
~iunordered_set_index()
@@ -265,7 +275,7 @@
}
//Rehashing does not throw, since neither the hash nor the
//comparison function can throw
- this->rehash(new_p, new_n);
+ this->rehash(bucket_traits(new_p, new_n));
if(new_p != old_p && old_p != bucket_ptr(&this->init_bucket)){
destroy_buckets(this->alloc, old_p, old_n);
}
@@ -275,34 +285,32 @@
//!previously allocated.
void shrink_to_fit()
{
- //size_type cur_size = this->size();
+ size_type cur_size = this->size();
size_type cur_count = this->bucket_count();
bucket_ptr old_p = this->bucket_pointer();
size_type sug_count;
if(!this->size() && old_p != bucket_ptr(&this->init_bucket)){
sug_count = 1;
- this->rehash(bucket_ptr(&this->init_bucket), 1);
+ this->rehash(bucket_traits(bucket_ptr(&this->init_bucket), 1));
destroy_buckets(this->alloc, old_p, cur_count);
}
else{
- /*
- sug_count = index_type::suggested_upper_bucket_count(cur_size);
+ sug_count = index_type::suggested_upper_bucket_count(cur_size);
- if(sug_count >= cur_count)
- return;
+ if(sug_count >= cur_count)
+ return;
- try{
- shrink_buckets(old_p, cur_count, this->alloc, sug_count);
- }
- catch(...){
- return;
- }
+ try{
+ shrink_buckets(old_p, cur_count, this->alloc, sug_count);
+ }
+ catch(...){
+ return;
+ }
- //Rehashing does not throw, since neither the hash nor the
- //comparison function can throw
- this->rehash(old_p, sug_count);
- */
+ //Rehashing does not throw, since neither the hash nor the
+ //comparison function can throw
+ this->rehash(bucket_traits(old_p, sug_count));
}
}
Modified: branches/bcbboost/boost/interprocess/indexes/map_index.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/indexes/map_index.hpp (original)
+++ branches/bcbboost/boost/interprocess/indexes/map_index.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -18,15 +18,16 @@
#include <utility>
#include <boost/interprocess/containers/map.hpp>
#include <boost/interprocess/allocators/private_adaptive_pool.hpp>
-//#include <boost/interprocess/allocators/allocator.hpp>
-/*!\file
- Describes index adaptor of boost::map container, to use it
- as name/shared memory index
-*/
-namespace boost { namespace interprocess {
+//!\file
+//!Describes index adaptor of boost::map container, to use it
+//!as name/shared memory index
+
+namespace boost {
+namespace interprocess {
+namespace detail{
-/*!Helper class to define typedefs from IndexTraits*/
+//!Helper class to define typedefs from IndexTraits
template <class MapConfig>
struct map_index_aux
{
@@ -38,36 +39,38 @@
typedef private_adaptive_pool
<value_type,
typename MapConfig::
- segment_manager_base> allocator_type;
+ segment_manager_base> allocator_type;
typedef boost::interprocess::map
<key_type, mapped_type,
key_less, allocator_type> index_t;
};
-/*!Index type based in boost::interprocess::map. Just derives from boost::interprocess::map
- and defines the interface needed by managed memory segments*/
+} //namespace detail {
+
+//!Index type based in boost::interprocess::map. Just derives from boost::interprocess::map
+//!and defines the interface needed by managed memory segments
template <class MapConfig>
class map_index
//Derive class from map specialization
- : public map_index_aux<MapConfig>::index_t
+ : public detail::map_index_aux<MapConfig>::index_t
{
/// @cond
- typedef map_index_aux<MapConfig> index_aux;
- typedef typename index_aux::index_t base_type;
+ typedef detail::map_index_aux<MapConfig> index_aux;
+ typedef typename index_aux::index_t base_type;
typedef typename MapConfig::
segment_manager_base segment_manager_base;
/// @endcond
public:
- /*!Constructor. Takes a pointer to the
- segment manager. Can throw*/
+ //!Constructor. Takes a pointer to the
+ //!segment manager. Can throw
map_index(segment_manager_base *segment_mngr)
: base_type(typename index_aux::key_less(),
segment_mngr){}
- /*!This reserves memory to optimize the insertion of n
- elements in the index*/
+ //!This reserves memory to optimize the insertion of n
+ //!elements in the index
void reserve(std::size_t)
{ /*Does nothing, map has not reserve or rehash*/ }
@@ -78,9 +81,10 @@
};
/// @cond
-/*!Trait class to detect if an index is a node
- index. This allows more efficient operations
- when deallocating named objects.*/
+
+//!Trait class to detect if an index is a node
+//!index. This allows more efficient operations
+//!when deallocating named objects.
template<class MapConfig>
struct is_node_index
<boost::interprocess::map_index<MapConfig> >
Modified: branches/bcbboost/boost/interprocess/indexes/null_index.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/indexes/null_index.hpp (original)
+++ branches/bcbboost/boost/interprocess/indexes/null_index.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -15,14 +15,16 @@
#include <boost/interprocess/offset_ptr.hpp>
-/*!\file
- Describes a null index adaptor, so that if we don't want to construct
- named objects, we can use this null index type to save resources.
-*/
-
-namespace boost { namespace interprocess {
-
-/*!Null index type*/
+//!\file
+//!Describes a null index adaptor, so that if we don't want to construct
+//!named objects, we can use this null index type to save resources.
+
+namespace boost {
+namespace interprocess {
+
+//!Null index type
+//!used to save compilation time when
+//!named indexes are not needed.
template <class MapConfig>
class null_index
{
@@ -35,19 +37,27 @@
typedef void * iterator;
typedef const void * const_iterator;
+ //!begin() is equal
+ //!to end()
const_iterator begin() const
{ return const_iterator(0); }
+ //!begin() is equal
+ //!to end()
iterator begin()
{ return iterator(0); }
+ //!begin() is equal
+ //!to end()
const_iterator end() const
{ return const_iterator(0); }
+ //!begin() is equal
+ //!to end()
iterator end()
{ return iterator(0); }
- /*!Dummy function*/
+ //!Empty constructor
null_index(segment_manager_base *){}
};
Modified: branches/bcbboost/boost/interprocess/indexes/unordered_map_index.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/indexes/unordered_map_index.hpp (original)
+++ branches/bcbboost/boost/interprocess/indexes/unordered_map_index.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,14 +20,15 @@
#include <boost/interprocess/detail/utilities.hpp>
#include <boost/interprocess/allocators/private_adaptive_pool.hpp>
-/*!\file
- Describes index adaptor of boost::unordered_map container, to use it
- as name/shared memory index
-*/
+//!\file
+//!Describes index adaptor of boost::unordered_map container, to use it
+//!as name/shared memory index
-namespace boost { namespace interprocess {
+namespace boost {
+namespace interprocess {
-/*!Helper class to define typedefs from IndexTraits*/
+//!Helper class to define typedefs from
+//!IndexTraits
template <class MapConfig>
struct unordered_map_index_aux
{
@@ -54,8 +55,8 @@
key_equal, allocator_type> index_t;
};
-/*!Index type based in unordered_map. Just derives from unordered_map and
- defines the interface needed by managed memory segments*/
+//!Index type based in unordered_map. Just derives from unordered_map and
+//!defines the interface needed by managed memory segments
template <class MapConfig>
class unordered_map_index
//Derive class from unordered_map specialization
@@ -69,16 +70,16 @@
/// @endcond
public:
- /*!Constructor. Takes a pointer to the
- segment manager. Can throw*/
+ //!Constructor. Takes a pointer to the
+ //!segment manager. Can throw
unordered_map_index(segment_manager_base *segment_mngr)
: base_type(0,
typename index_aux::hasher(),
typename index_aux::key_equal(),
segment_mngr){}
- /*!This reserves memory to optimize the insertion of n
- elements in the index*/
+ //!This reserves memory to optimize the insertion of n
+ //!elements in the index
void reserve(std::size_t n)
{ base_type::rehash(n); }
@@ -89,9 +90,10 @@
};
/// @cond
-/*!Trait class to detect if an index is a node
- index. This allows more efficient operations
- when deallocating named objects.*/
+
+//!Trait class to detect if an index is a node
+//!index. This allows more efficient operations
+//!when deallocating named objects.
template<class MapConfig>
struct is_node_index
<boost::interprocess::unordered_map_index<MapConfig> >
Modified: branches/bcbboost/boost/interprocess/interprocess_fwd.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/interprocess_fwd.hpp (original)
+++ branches/bcbboost/boost/interprocess/interprocess_fwd.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,17 @@
// Standard predeclarations
//////////////////////////////////////////////////////////////////////////////
+/// @cond
+
+namespace boost{
+namespace intrusive{
+}}
+
+namespace boost{
+namespace interprocess{
+namespace bi = boost::intrusive;
+}}
+
namespace std {
template <class T>
@@ -40,6 +51,8 @@
} //namespace std {
+/// @endcond
+
namespace boost { namespace interprocess {
//////////////////////////////////////////////////////////////////////////////
@@ -134,44 +147,26 @@
class offset_ptr;
//////////////////////////////////////////////////////////////////////////////
-// intersegment_ptr
-//////////////////////////////////////////////////////////////////////////////
-
-template <class Mutex>
-struct flat_map_intersegment;
-
-template <class T/*, class PT = flat_map_intersegment<interprocess_mutex> */>
-class intersegment_ptr;
-
-//////////////////////////////////////////////////////////////////////////////
// Memory allocation algorithms
//////////////////////////////////////////////////////////////////////////////
//Single segment memory allocation algorithms
template<class MutexFamily, class VoidMutex = offset_ptr<void> >
-class seq_fit;
-
-template<class MutexFamily, class VoidMutex = offset_ptr<void> >
class simple_seq_fit;
template<class MutexFamily, class VoidMutex = offset_ptr<void> >
class rbtree_best_fit;
-//Single segment memory allocation algorithms
-template<class MutexFamily, class VoidMutex = intersegment_ptr<void> >
-class multi_seq_fit;
-
-template<class MutexFamily, class VoidMutex = intersegment_ptr<void> >
-class multi_simple_seq_fit;
-
//////////////////////////////////////////////////////////////////////////////
// Index Types
//////////////////////////////////////////////////////////////////////////////
template<class IndexConfig> class flat_map_index;
-template<class IndexConfig> class map_index;
template<class IndexConfig> class iset_index;
+template<class IndexConfig> class iunordered_set_index;
+template<class IndexConfig> class map_index;
template<class IndexConfig> class null_index;
+template<class IndexConfig> class unordered_map_index;
//////////////////////////////////////////////////////////////////////////////
// Segment manager
@@ -204,7 +199,7 @@
wmanaged_external_buffer;
//////////////////////////////////////////////////////////////////////////////
-// Shared memory managed memory classes
+// managed memory classes
//////////////////////////////////////////////////////////////////////////////
template <class CharType
@@ -369,6 +364,12 @@
template<class T, class VoidPointer>
class intrusive_ptr;
+template<class T, class VoidAllocator, class Deleter>
+class shared_ptr;
+
+template<class T, class VoidAllocator, class Deleter>
+class weak_ptr;
+
//////////////////////////////////////////////////////////////////////////////
// IPC
//////////////////////////////////////////////////////////////////////////////
Modified: branches/bcbboost/boost/interprocess/ipc/message_queue.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/ipc/message_queue.hpp (original)
+++ branches/bcbboost/boost/interprocess/ipc/message_queue.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -30,15 +30,15 @@
#include <cstring> //memcpy
-/*!\file
- Describes an inter-process message queue. This class allows sending
- messages between processes and allows blocking, non-blocking and timed
- sending and receiving.
-*/
+//!\file
+//!Describes an inter-process message queue. This class allows sending
+//!messages between processes and allows blocking, non-blocking and timed
+//!sending and receiving.
namespace boost{ namespace interprocess{
-/*!A class that allows sending messages between processes.*/
+//!A class that allows sending messages
+//!between processes.
class message_queue
{
/// @cond
@@ -50,94 +50,101 @@
public:
- /*!Creates a process shared message queue with name "name". For this message queue,
- the maximum number of messages will be "max_num_msg" and the maximum message size
- will be "max_msg_size".*/
+ //!Creates a process shared message queue with name "name". For this message queue,
+ //!the maximum number of messages will be "max_num_msg" and the maximum message size
+ //!will be "max_msg_size".
message_queue(create_only_t create_only,
const char *name,
std::size_t max_num_msg,
std::size_t max_msg_size);
- /*!Opens or creates a process shared message queue with name "name".
- If the queue is created, the maximum number of messages will be "max_num_msg"
- and the maximum message size will be "max_msg_size". If queue was previously
- created the queue will be opened and "max_num_msg" and "max_msg_size" parameters
- are ignored.*/
+ //!Opens or creates a process shared message queue with name "name".
+ //!If the queue is created, the maximum number of messages will be "max_num_msg"
+ //!and the maximum message size will be "max_msg_size". If queue was previously
+ //!created the queue will be opened and "max_num_msg" and "max_msg_size" parameters
+ //!are ignored.
message_queue(open_or_create_t open_or_create,
const char *name,
std::size_t max_num_msg,
std::size_t max_msg_size);
- /*!Opens a previously created process shared message queue with name "name".
- If the was not previously created or there are no free resources, the
- function returns false.*/
+ //!Opens a previously created process shared message queue with name "name".
+ //!If the was not previously created or there are no free resources, the
+ //!function returns false.
message_queue(open_only_t open_only,
const char *name);
- /*!Destructor. Never throws*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. All opened message queues are still
+ //!valid after destruction. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the message queue from the system
+ //!use remove().
~message_queue();
- /*!Sends a message stored in buffer "buffer" with size "buffer_size" in the
- message queue with priority "priority". If the message queue is full
- the sender is blocked. Throws interprocess_error on error.*/
+ //!Sends a message stored in buffer "buffer" with size "buffer_size" in the
+ //!message queue with priority "priority". If the message queue is full
+ //!the sender is blocked. Throws interprocess_error on error.*/
void send (const void *buffer, std::size_t buffer_size,
unsigned int priority);
- /*!Sends a message stored in buffer "buffer" with size "buffer_size" through the
- message queue with priority "priority". If the message queue is full
- the sender is not blocked and returns false, otherwise returns true.
- Throws interprocess_error on error.*/
+ //!Sends a message stored in buffer "buffer" with size "buffer_size" through the
+ //!message queue with priority "priority". If the message queue is full
+ //!the sender is not blocked and returns false, otherwise returns true.
+ //!Throws interprocess_error on error.
bool try_send (const void *buffer, std::size_t buffer_size,
unsigned int priority);
- /*!Sends a message stored in buffer "buffer" with size "buffer_size" in the
- message queue with priority "priority". If the message queue is full
- the sender is retries until time "abs_time" is reached. Returns true if
- the message has been successfully sent. Returns false if timeout is reached.
- Throws interprocess_error on error.*/
+ //!Sends a message stored in buffer "buffer" with size "buffer_size" in the
+ //!message queue with priority "priority". If the message queue is full
+ //!the sender is retries until time "abs_time" is reached. Returns true if
+ //!the message has been successfully sent. Returns false if timeout is reached.
+ //!Throws interprocess_error on error.
bool timed_send (const void *buffer, std::size_t buffer_size,
unsigned int priority, const boost::posix_time::ptime& abs_time);
- /*!Receives a message from the message queue. The message is stored in buffer
- "buffer", which has size "buffer_size". The received message has size
- "recvd_size" and priority "priority". If the message queue is full
- the sender is blocked. Throws interprocess_error on error.*/
+ //!Receives a message from the message queue. The message is stored in buffer
+ //!"buffer", which has size "buffer_size". The received message has size
+ //!"recvd_size" and priority "priority". If the message queue is full
+ //!the sender is blocked. Throws interprocess_error on error.
void receive (void *buffer, std::size_t buffer_size,
std::size_t &recvd_size,unsigned int &priority);
- /*!Receives a message from the message queue. The message is stored in buffer
- "buffer", which has size "buffer_size". The received message has size
- "recvd_size" and priority "priority". If the message queue is full
- the sender is not blocked and returns false, otherwise returns true.
- Throws interprocess_error on error.*/
+ //!Receives a message from the message queue. The message is stored in buffer
+ //!"buffer", which has size "buffer_size". The received message has size
+ //!"recvd_size" and priority "priority". If the message queue is full
+ //!the sender is not blocked and returns false, otherwise returns true.
+ //!Throws interprocess_error on error.
bool try_receive (void *buffer, std::size_t buffer_size,
std::size_t &recvd_size,unsigned int &priority);
- /*!Receives a message from the message queue. The message is stored in buffer
- "buffer", which has size "buffer_size". The received message has size
- "recvd_size" and priority "priority". If the message queue is full
- the sender is retries until time "abs_time" is reached. Returns true if
- the message has been successfully sent. Returns false if timeout is reached.
- Throws interprocess_error on error.*/
+ //!Receives a message from the message queue. The message is stored in buffer
+ //!"buffer", which has size "buffer_size". The received message has size
+ //!"recvd_size" and priority "priority". If the message queue is full
+ //!the sender is retries until time "abs_time" is reached. Returns true if
+ //!the message has been successfully sent. Returns false if timeout is reached.
+ //!Throws interprocess_error on error.
bool timed_receive (void *buffer, std::size_t buffer_size,
std::size_t &recvd_size,unsigned int &priority,
const boost::posix_time::ptime &abs_time);
- /*!Returns the maximum number of messages allowed by the queue. The message
- queue must be opened or created previously. Otherwise, returns 0.
- Never throws*/
+ //!Returns the maximum number of messages allowed by the queue. The message
+ //!queue must be opened or created previously. Otherwise, returns 0.
+ //!Never throws
std::size_t get_max_msg() const;
- /*!Returns the maximum size of message allowed by the queue. The message
- queue must be opened or created previously. Otherwise, returns 0.
- Never throws*/
+ //!Returns the maximum size of message allowed by the queue. The message
+ //!queue must be opened or created previously. Otherwise, returns 0.
+ //!Never throws
std::size_t get_max_msg_size() const;
- /*!Returns the number of messages currently stored.
- Never throws*/
+ //!Returns the number of messages currently stored.
+ //!Never throws
std::size_t get_num_msg();
- /*!Removes the message queue from the system. Never throws*/
+ //!Removes the message queue from the system.
+ //!Returns false on error. Never throws
static bool remove(const char *name);
/// @cond
@@ -152,7 +159,8 @@
const void *buffer, std::size_t buffer_size,
unsigned int priority, const ptime &abs_time);
- /*!Returns the needed memory size for the shared message queue. Never throws*/
+ //!Returns the needed memory size for the shared message queue.
+ //!Never throws
static std::size_t get_mem_size(std::size_t max_msg_size, std::size_t max_num_msg);
detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
@@ -163,17 +171,17 @@
namespace detail {
-/*!This header is the prefix of each message in the queue*/
+//!This header is the prefix of each message in the queue
class msg_hdr_t
{
public:
std::size_t len; // Message length
unsigned int priority;// Message priority
- /*!Returns the data buffer associated with this this message*/
+ //!Returns the data buffer associated with this this message
void * data(){ return this+1; } //
};
-/*!This functor is the predicate to order stored messages by priority*/
+//!This functor is the predicate to order stored messages by priority
class priority_functor
{
public:
@@ -182,75 +190,74 @@
{ return msg1->priority < msg2->priority; }
};
-/*!This header is placed in the beginning of the shared memory and contains
- the data to control the queue. This class initializes the shared memory
- in the following way: in ascending memory address with proper alignment
- fillings:
-
- -> mq_hdr_t:
- Main control block that controls the rest of the elements
-
- -> offset_ptr<msg_hdr_t> index [max_num_msg]
- An array of pointers with size "max_num_msg" called index. Each pointer
- points to a preallocated message. The elements of this array are
- reordered in runtime in the following way:
-
- When the current number of messages is "cur_num_msg", the first
- "cur_num_msg" pointers point to inserted messages and the rest
- point to free messages. The first "cur_num_msg" pointers are
- ordered by the priority of the pointed message and by insertion order
- if two messages have the same priority. So the next message to be
- used in a "receive" is pointed by index [cur_num_msg-1] and the first free
- message ready to be used in a "send" operation is index [cur_num_msg].
- This transforms index in a fixed size priority queue with an embedded free
- message queue.
-
- -> struct message_t
- {
- msg_hdr_t header;
- char[max_msg_size] data;
- } messages [max_num_msg];
-
- An array of buffers of preallocated messages, each one prefixed with the
- msg_hdr_t structure. Each of this message is pointed by one pointer of
- the index structure.
-*/
+//!This header is placed in the beginning of the shared memory and contains
+//!the data to control the queue. This class initializes the shared memory
+//!in the following way: in ascending memory address with proper alignment
+//!fillings:
+//!
+//!-> mq_hdr_t:
+//! Main control block that controls the rest of the elements
+//!
+//!-> offset_ptr<msg_hdr_t> index [max_num_msg]
+//! An array of pointers with size "max_num_msg" called index. Each pointer
+//! points to a preallocated message. The elements of this array are
+//! reordered in runtime in the following way:
+//!
+//! When the current number of messages is "cur_num_msg", the first
+//! "cur_num_msg" pointers point to inserted messages and the rest
+//! point to free messages. The first "cur_num_msg" pointers are
+//! ordered by the priority of the pointed message and by insertion order
+//! if two messages have the same priority. So the next message to be
+//! used in a "receive" is pointed by index [cur_num_msg-1] and the first free
+//! message ready to be used in a "send" operation is index [cur_num_msg].
+//! This transforms index in a fixed size priority queue with an embedded free
+//! message queue.
+//!
+//!-> struct message_t
+//! {
+//! msg_hdr_t header;
+//! char[max_msg_size] data;
+//! } messages [max_num_msg];
+//!
+//! An array of buffers of preallocated messages, each one prefixed with the
+//! msg_hdr_t structure. Each of this message is pointed by one pointer of
+//! the index structure.
class mq_hdr_t
: public detail::priority_functor
{
typedef offset_ptr<msg_hdr_t> msg_hdr_ptr_t;
public:
- /*!Constructor. This object must be constructed in the beginning of the
- shared memory of the size returned by the function "get_mem_size".
- This constructor initializes the needed resources and creates
- the internal structures like the priority index. This can throw.*/
+ //!Constructor. This object must be constructed in the beginning of the
+ //!shared memory of the size returned by the function "get_mem_size".
+ //!This constructor initializes the needed resources and creates
+ //!the internal structures like the priority index. This can throw.*/
mq_hdr_t(std::size_t max_num_msg, std::size_t max_msg_size)
: m_max_num_msg(max_num_msg),
m_max_msg_size(max_msg_size),
m_cur_num_msg(0)
{ this->initialize_memory(); }
- /*!Returns the inserted message with top priority*/
+ //!Returns the inserted message with top priority
msg_hdr_t * top_msg()
{ return mp_index[m_cur_num_msg-1].get(); }
- /*!Returns true if the message queue is full*/
+ //!Returns true if the message queue is full
bool is_full() const
{ return m_cur_num_msg == m_max_num_msg; }
- /*!Returns true if the message queue is empty*/
+ //!Returns true if the message queue is empty
bool is_empty() const
{ return !m_cur_num_msg; }
- /*!Frees the top priority message and saves it in the free message list*/
+ //!Frees the top priority message and saves it in the free message list
void free_top_msg()
{ --m_cur_num_msg; }
- /*!Returns the first free msg of the free message queue*/
+ //!Returns the first free msg of the free message queue
msg_hdr_t * free_msg()
{ return mp_index[m_cur_num_msg].get(); }
- /*!Inserts the first free message in the priority queue*/
+ //!Inserts the first free message in the priority queue
void queue_free_msg()
{
//Get free msg
@@ -266,9 +273,9 @@
++m_cur_num_msg;
}
- /*!Returns the number of bytes needed to construct a message queue with
- "max_num_size" maximum number of messages and "max_msg_size" maximum
- message size. Never throws.*/
+ //!Returns the number of bytes needed to construct a message queue with
+ //!"max_num_size" maximum number of messages and "max_msg_size" maximum
+ //!message size. Never throws.
static std::size_t get_mem_size
(std::size_t max_msg_size, std::size_t max_num_msg)
{
@@ -282,8 +289,8 @@
detail::managed_open_or_create_impl<shared_memory_object>::ManagedOpenOrCreateUserOffset;
}
- /*!Initializes the memory structures to preallocate messages and constructs the
- message index. Never throws.*/
+ //!Initializes the memory structures to preallocate messages and constructs the
+ //!message index. Never throws.
void initialize_memory()
{
const std::size_t
@@ -330,8 +337,8 @@
};
-/*!This is the atomic functor to be executed when creating or opening
- shared memory. Never throws*/
+//!This is the atomic functor to be executed when creating or opening
+//!shared memory. Never throws
class initialization_func_t
{
public:
@@ -384,11 +391,6 @@
detail::initialization_func_t (max_num_msg, max_msg_size))
{}
- /*!Opens or creates a process shared message queue with name "name".
- If the queue is created, the maximum number of messages will be "max_num_msg"
- and the maximum message size will be "max_msg_size". If queue was previously
- created the queue will be opened and "max_num_msg" and "max_msg_size" parameters
- are ignored. If there are no free resources, the function returns false.*/
inline message_queue::message_queue(open_or_create_t open_or_create,
const char *name,
std::size_t max_num_msg,
@@ -403,9 +405,6 @@
detail::initialization_func_t (max_num_msg, max_msg_size))
{}
- /*!Opens a previously created process shared message queue with name "name".
- If the was not previously created or there are no free resources, the
- function returns false.*/
inline message_queue::message_queue(open_only_t open_only,
const char *name)
//Create shared memory and execute functor atomically
Modified: branches/bcbboost/boost/interprocess/managed_external_buffer.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/managed_external_buffer.hpp (original)
+++ branches/bcbboost/boost/interprocess/managed_external_buffer.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -21,9 +21,8 @@
#include <boost/interprocess/detail/managed_memory_impl.hpp>
#include <boost/interprocess/detail/move.hpp>
-/*!\file
- Describes a named user memory allocation user class.
-*/
+//!\file
+//!Describes a named user memory allocation user class.
namespace boost {
namespace interprocess {
@@ -60,7 +59,7 @@
(open_only_t, void *addr, std::size_t size)
{
if(!base_t::open_impl(addr, size)){
- throw interprocess_exception();//return false;
+ throw interprocess_exception();
}
}
Modified: branches/bcbboost/boost/interprocess/managed_heap_memory.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/managed_heap_memory.hpp (original)
+++ branches/bcbboost/boost/interprocess/managed_heap_memory.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,9 +23,8 @@
#include <boost/interprocess/detail/managed_memory_impl.hpp>
#include <boost/detail/no_exceptions_support.hpp>
-/*!\file
- Describes a named heap memory allocation user class.
-*/
+//!\file
+//!Describes a named heap memory allocation user class.
namespace boost {
namespace interprocess {
@@ -85,7 +84,8 @@
//!Constructor. Never throws.
basic_managed_heap_memory(){}
- //!Destructor. Calls priv_close. Never throws.
+ //!Destructor. Liberates the heap memory holding the managed data.
+ //!Never throws.
~basic_managed_heap_memory()
{ this->priv_close(); }
Modified: branches/bcbboost/boost/interprocess/managed_mapped_file.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/managed_mapped_file.hpp (original)
+++ branches/bcbboost/boost/interprocess/managed_mapped_file.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,18 +23,15 @@
#include <boost/interprocess/detail/file_wrapper.hpp>
#include <boost/interprocess/detail/move.hpp>
-/*!\file
- Describes a named shared memory object allocation user class.
-*/
+//!\file
+//!Describes a named shared memory object allocation user class.
namespace boost {
-
namespace interprocess {
-
-/*!A basic shared memory named object creation class. Initializes the
- shared memory segment. Inherits all basic functionality from
- basic_managed_memory_impl<CharType, AllocationAlgorithm, IndexType>*/
+//!A basic shared memory named object creation class. Initializes the
+//!shared memory segment. Inherits all basic functionality from
+//!basic_managed_memory_impl<CharType, AllocationAlgorithm, IndexType>
template
<
class CharType,
@@ -57,28 +54,29 @@
/// @endcond
public: //functions
- /*!Creates shared memory and creates and places the segment manager.
- This can throw.*/
+
+ //!Creates shared memory and creates and places the segment manager.
+ //!This can throw.
basic_managed_mapped_file(create_only_t create_only, const char *name,
std::size_t size, const void *addr = 0)
: m_mfile(create_only, name, size, read_write, addr,
create_open_func_t(get_this_pointer(), detail::DoCreate))
{}
- /*!Creates shared memory and creates and places the segment manager if
- segment was not created. If segment was created it connects to the
- segment.
- This can throw.*/
+ //!Creates shared memory and creates and places the segment manager if
+ //!segment was not created. If segment was created it connects to the
+ //!segment.
+ //!This can throw.
basic_managed_mapped_file (open_or_create_t open_or_create,
const char *name, std::size_t size,
const void *addr = 0)
: m_mfile(open_or_create, name, size, read_write, addr,
create_open_func_t(get_this_pointer(),
- detail::DoCreateOrOpen))
+ detail::DoOpenOrCreate))
{}
- /*!Connects to a created shared memory and it's the segment manager.
- Never throws.*/
+ //!Connects to a created shared memory and it's the segment manager.
+ //!Never throws.
basic_managed_mapped_file (open_only_t open_only, const char* name,
const void *addr = 0)
: m_mfile(open_only, name, read_write, addr,
@@ -86,7 +84,8 @@
detail::DoOpen))
{}
- /*!Moves the ownership of "moved"'s managed memory to *this. Does not throw*/
+ //!Moves the ownership of "moved"'s managed memory to *this.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_managed_mapped_file
(detail::moved_object<basic_managed_mapped_file> &moved)
@@ -96,7 +95,8 @@
{ this->swap(moved); }
#endif
- /*!Moves the ownership of "moved"'s managed memory to *this. Does not throw*/
+ //!Moves the ownership of "moved"'s managed memory to *this.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_managed_mapped_file &operator=
(detail::moved_object<basic_managed_mapped_file> &moved)
@@ -106,30 +106,36 @@
{ this->swap(moved); return *this; }
#endif
- /*!Destructor. Never throws.*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~basic_managed_mapped_file()
{}
- /*!Swaps the ownership of the managed mapped memories managed by *this and other.
- Never throws.*/
+ //!Swaps the ownership of the managed mapped memories managed by *this and other.
+ //!Never throws.
void swap(basic_managed_mapped_file &other)
{
base_t::swap(other);
m_mfile.swap(other.m_mfile);
}
- /*!Flushes cached data to file. Never throws*/
+ //!Flushes cached data to file.
+ //!Never throws
bool flush()
{ return m_mfile.flush(); }
- /*!Tries to resize mapped file so that we have room for
- more objects.
- WARNING: The memory mapping can change. To be able to use
- this function, all pointers constructed in this buffer
- must be offset pointers. Otherwise, the result is undefined.
- Returns true if the growth has been successful, so you will
- have some extra bytes to allocate new objects. If returns
- false, the heap allocation has failed.*/
+ //!Tries to resize mapped file so that we have room for
+ //!more objects.
+ //!WARNING: The memory mapping can change. To be able to use
+ //!this function, all pointers constructed in this buffer
+ //!must be offset pointers. Otherwise, the result is undefined.
+ //!Returns true if the growth has been successful, so you will
+ //!have some extra bytes to allocate new objects. If returns
+ //!false, the heap allocation has failed.
/*
bool grow(std::size_t extra_bytes)
{
Modified: branches/bcbboost/boost/interprocess/managed_shared_memory.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/managed_shared_memory.hpp (original)
+++ branches/bcbboost/boost/interprocess/managed_shared_memory.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,17 +23,16 @@
#include <boost/interprocess/shared_memory_object.hpp>
#include <boost/interprocess/creation_tags.hpp>
-/*!\file
- Describes a named shared memory object allocation user class.
-*/
+//!\file
+//!Describes a named shared memory object allocation user class.
namespace boost {
namespace interprocess {
-/*!A basic shared memory named object creation class. Initializes the
- shared memory segment. Inherits all basic functionality from
- basic_managed_memory_impl<CharType, AllocationAlgorithm, IndexType>*/
+//!A basic shared memory named object creation class. Initializes the
+//!shared memory segment. Inherits all basic functionality from
+//!basic_managed_memory_impl<CharType, AllocationAlgorithm, IndexType>*/
template
<
class CharType,
@@ -59,7 +58,13 @@
/// @endcond
public: //functions
- //!Destructor. Calls close. Never throws.
+
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~basic_managed_shared_memory()
{}
@@ -82,7 +87,7 @@
: base_t()
, base2_t(open_or_create, name, size, read_write, addr,
create_open_func_t(get_this_pointer(),
- detail::DoCreateOrOpen))
+ detail::DoOpenOrCreate))
{}
//!Connects to a created shared memory and it's the segment manager.
@@ -95,7 +100,8 @@
detail::DoOpen))
{}
- //!Moves the ownership of "moved"'s managed memory to *this. Does not throw
+ //!Moves the ownership of "moved"'s managed memory to *this.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_managed_shared_memory
(detail::moved_object<basic_managed_shared_memory> &moved)
@@ -105,7 +111,8 @@
{ this->swap(moved); }
#endif
- //!Moves the ownership of "moved"'s managed memory to *this. Does not throw
+ //!Moves the ownership of "moved"'s managed memory to *this.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_managed_shared_memory &operator=
(detail::moved_object<basic_managed_shared_memory> &moved)
Modified: branches/bcbboost/boost/interprocess/managed_windows_shared_memory.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/managed_windows_shared_memory.hpp (original)
+++ branches/bcbboost/boost/interprocess/managed_windows_shared_memory.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,25 +23,23 @@
#include <boost/interprocess/windows_shared_memory.hpp>
#include <boost/interprocess/detail/move.hpp>
-/*!\file
- Describes a named shared memory object allocation user class.
-*/
+//!\file
+//!Describes a named shared memory object allocation user class.
namespace boost {
namespace interprocess {
-/*!A basic managed windows shared memory creation class. Initializes the
- shared memory segment. Inherits all basic functionality from
- basic_managed_memory_impl<CharType, AllocationAlgorithm, IndexType>
- Unlike basic_managed_shared_memory, it has
- no kernel persistence and the shared memory is destroyed
- when all processes destroy all their windows_shared_memory
- objects and mapped regions for the same shared memory
- or the processes end/crash.
-
- Warning: basic_managed_windows_shared_memory and
- basic_managed_shared_memory can't communicate between them.
-*/
+//!A basic managed windows shared memory creation class. Initializes the
+//!shared memory segment. Inherits all basic functionality from
+//!basic_managed_memory_impl<CharType, AllocationAlgorithm, IndexType>
+//!Unlike basic_managed_shared_memory, it has
+//!no kernel persistence and the shared memory is destroyed
+//!when all processes destroy all their windows_shared_memory
+//!objects and mapped regions for the same shared memory
+//!or the processes end/crash.
+//!
+//!Warning: basic_managed_windows_shared_memory and
+//!basic_managed_shared_memory can't communicate between them.
template
<
class CharType,
@@ -83,7 +81,7 @@
const void *addr = 0)
: m_wshm(open_or_create, name, size, read_write, addr,
create_open_func_t(get_this_pointer(),
- detail::DoCreateOrOpen))
+ detail::DoOpenOrCreate))
{}
//!Connects to a created shared memory and it's the segment manager.
@@ -95,7 +93,8 @@
detail::DoOpen))
{}
- //!Moves the ownership of "moved"'s managed memory to *this. Does not throw
+ //!Moves the ownership of "moved"'s managed memory to *this.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_managed_windows_shared_memory
(detail::moved_object<basic_managed_windows_shared_memory> &moved)
@@ -105,7 +104,8 @@
{ this->swap(moved); }
#endif
- //!Moves the ownership of "moved"'s managed memory to *this. Does not throw
+ //!Moves the ownership of "moved"'s managed memory to *this.
+ //!Does not throw
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
basic_managed_windows_shared_memory &operator=
(detail::moved_object<basic_managed_windows_shared_memory> &moved)
@@ -116,7 +116,11 @@
{ this->swap(moved); return *this; }
#endif
- //!Destructor. Never throws.
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. All mapped regions are still valid after
+ //!destruction. When all mapped regions and basic_managed_windows_shared_memory
+ //!objects referring the shared memory are destroyed, the
+ //!operating system will destroy the shared memory.
~basic_managed_windows_shared_memory()
{}
Modified: branches/bcbboost/boost/interprocess/mapped_region.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/mapped_region.hpp (original)
+++ branches/bcbboost/boost/interprocess/mapped_region.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -36,15 +36,14 @@
#endif //#if (defined BOOST_WINDOWS) && !(defined BOOST_DISABLE_WIN32)
-/*!\file
- Describes memory_mappable and mapped region classes
-*/
+//!\file
+//!Describes memory_mappable and mapped region classes
namespace boost {
namespace interprocess {
-/*!The mapped_region class represents a portion or region created from a
- memory_mappable object.*/
+//!The mapped_region class represents a portion or region created from a
+//!memory_mappable object.
class mapped_region
{
/// @cond
@@ -55,10 +54,10 @@
public:
- /*!Creates a mapping region of the mapped memory "mapping", starting in
- offset "offset", and the mapping's size will be "size". The mapping
- can be opened for read-only "read_only" or read-write
- "read_write.*/
+ //!Creates a mapping region of the mapped memory "mapping", starting in
+ //!offset "offset", and the mapping's size will be "size". The mapping
+ //!can be opened for read-only "read_only" or read-write
+ //!"read_write.
template<class MemoryMappable>
mapped_region(const MemoryMappable& mapping
,mode_t mode
@@ -66,54 +65,58 @@
,std::size_t size = 0
,const void *address = 0);
- /*!Default constructor. Address and size and offset will be 0. Does not throw*/
+ //!Default constructor. Address and size and offset will be 0.
+ //!Does not throw
mapped_region();
- /*!Move constructor. *this will be constructed taking ownership of "other"'s
- region and "other" will be left in default constructor state.*/
+ //!Move constructor. *this will be constructed taking ownership of "other"'s
+ //!region and "other" will be left in default constructor state.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
mapped_region(detail::moved_object<mapped_region> other);
#else
mapped_region(mapped_region &&other);
#endif
- /*!Destroys the mapped region. Does not throw*/
+ //!Destroys the mapped region.
+ //!Does not throw
~mapped_region();
- /*!Move assignment. If *this owns a memory mapped region, it will be
- destroyed and it will take ownership of "other"'s memory mapped region.*/
+ //!Move assignment. If *this owns a memory mapped region, it will be
+ //!destroyed and it will take ownership of "other"'s memory mapped region.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
mapped_region &operator=(detail::moved_object<mapped_region> other);
#else
mapped_region &operator=(mapped_region &&other);
#endif
- /*!Returns the size of the mapping. Note for windows users: If
- windows_shared_memory is mapped using 0 as the size, it returns 0
- because the size is unknown. Never throws.*/
+ //!Returns the size of the mapping. Note for windows users: If
+ //!windows_shared_memory is mapped using 0 as the size, it returns 0
+ //!because the size is unknown. Never throws.
std::size_t get_size() const;
- /*!Returns the base address of the mapping. Never throws.*/
+ //!Returns the base address of the mapping.
+ //!Never throws.
void* get_address() const;
- /*!Returns the offset of the mapping from the beginning of the
- mapped memory. Never throws.*/
+ //!Returns the offset of the mapping from the beginning of the
+ //!mapped memory. Never throws.
offset_t get_offset() const;
- /*!Flushes to the disk a byte range within the mapped memory.
- Never throws*/
+ //!Flushes to the disk a byte range within the mapped memory.
+ //!Never throws
bool flush(std::size_t mapping_offset = 0, std::size_t numbytes = 0);
- /*!Swaps the mapped_region with another mapped region*/
+ //!Swaps the mapped_region with another
+ //!mapped region
void swap(mapped_region &other);
- /*!Returns the size of the page. This size is the minimum memory that
- will be used by the system when mapping a memory mappable source.*/
+ //!Returns the size of the page. This size is the minimum memory that
+ //!will be used by the system when mapping a memory mappable source.
static std::size_t get_page_size();
/// @cond
private:
- /*!Closes a previously opened memory mapping. Never throws.*/
+ //!Closes a previously opened memory mapping. Never throws
void priv_close();
template<int dummy>
@@ -521,7 +524,8 @@
}
/// @cond
-/*!No-op functor*/
+
+//!No-op functor
struct null_mapped_region_function
{
bool operator()(void *, std::size_t , bool) const
Modified: branches/bcbboost/boost/interprocess/mem_algo/detail/simple_seq_fit_impl.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/mem_algo/detail/simple_seq_fit_impl.hpp (original)
+++ branches/bcbboost/boost/interprocess/mem_algo/detail/simple_seq_fit_impl.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -27,6 +27,7 @@
#include <boost/interprocess/detail/min_max.hpp>
#include <boost/interprocess/detail/type_traits.hpp>
#include <boost/interprocess/sync/scoped_lock.hpp>
+#include <boost/interprocess/mem_algo/detail/mem_algo_common.hpp>
#include <algorithm>
#include <utility>
#include <cstring>
@@ -34,16 +35,13 @@
#include <assert.h>
#include <new>
-/*!\file
- Describes sequential fit algorithm used to allocate objects in shared memory.
- This class is intended as a base class for single segment and multi-segment
- implementations.
-*/
+//!\file
+//!Describes sequential fit algorithm used to allocate objects in shared memory.
+//!This class is intended as a base class for single segment and multi-segment
+//!implementations.
namespace boost {
-
namespace interprocess {
-
namespace detail {
//!This class implements the simple sequential fit algorithm with a simply
@@ -59,13 +57,15 @@
simple_seq_fit_impl &operator=(const simple_seq_fit_impl &);
public:
- class multiallocation_iterator;
//!Shared interprocess_mutex family used for the rest of the Interprocess framework
typedef MutexFamily mutex_family;
//!Pointer type to be used with the rest of the Interprocess framework
typedef VoidPointer void_pointer;
+ typedef detail::basic_multiallocation_iterator
+ <void_pointer> multiallocation_iterator;
+
private:
class block_ctrl;
typedef typename detail::
@@ -89,18 +89,6 @@
std::size_t get_total_bytes() const
{ return this->m_size*Alignment; }
-
- static block_ctrl *get_block_from_addr(void *addr)
- {
- return reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(addr) - BlockCtrlBytes);
- }
-
- void *get_addr() const
- {
- return reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(this) + BlockCtrlBytes);
- }
};
//!Shared interprocess_mutex to protect memory allocate/deallocate
@@ -118,83 +106,12 @@
std::size_t m_size;
} m_header;
- friend class multiallocation_iterator;
+ friend class detail::basic_multiallocation_iterator<void_pointer>;
+ friend class detail::memory_algorithm_common<simple_seq_fit_impl>;
- public:
- class multiallocation_iterator
- : public std::iterator<std::bidirectional_iterator_tag, char *>
- {
- void unspecified_bool_type_func() const {}
- typedef void (multiallocation_iterator::*unspecified_bool_type)() const;
-
- public:
- typedef char * value_type;
- typedef value_type & reference;
- typedef value_type * pointer;
-
- multiallocation_iterator()
- : block_(0), n_elements_ (0)
- {}
-
- multiallocation_iterator(void *many_allocation, std::size_t n_elements)
- : block_(static_cast<block_ctrl*>(many_allocation)), n_elements_ (n_elements)
- {}
-
- multiallocation_iterator &operator=(const multiallocation_iterator &other)
- { block_ = other.block_; n_elements_ = other.n_elements_; return *this; }
-
- public:
- multiallocation_iterator& operator++()
- {
- --n_elements_;
- block_ = (block_ctrl*)((char*)block_ + block_->m_size*Alignment);
- return *this;
- }
-
- multiallocation_iterator operator++(int)
- {
- multiallocation_iterator result(block_, n_elements_);
- ++*this;
- return result;
- }
-
- multiallocation_iterator& operator--()
- {
- ++n_elements_;
- block_ = (block_ctrl*)((char*)block_ - block_->m_size*Alignment);
- return *this;
- }
-
- multiallocation_iterator operator--(int)
- {
- multiallocation_iterator result(block_, n_elements_);
- --*this;
- return result;
- }
-
- bool operator== (const multiallocation_iterator& other) const
- { return n_elements_ == other.n_elements_; }
-
- bool operator!= (const multiallocation_iterator& other) const
- { return !operator== (other); }
-
- value_type operator*() const
- {
- value_type v = (char*)block_ + BlockCtrlBytes;
- return v;
- }
-
- operator unspecified_bool_type() const
- { return n_elements_? &multiallocation_iterator::unspecified_bool_type_func : 0; }
-
- pointer operator->() const
- { return &operator*(); }
-
- private:
- block_ctrl *block_;
- std::size_t n_elements_;
- };
+ typedef detail::memory_algorithm_common<simple_seq_fit_impl> algo_impl_t;
+ public:
//!Constructor. "size" is the total size of the managed memory segment,
//!"extra_hdr_bytes" indicates the extra bytes beginning in the sizeof(simple_seq_fit_impl)
//!offset that the allocator should not use at all.
@@ -214,7 +131,7 @@
/// @cond
//!Multiple element allocation, same size
- multiallocation_iterator allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements);
+ multiallocation_iterator allocate_many(std::size_t elem_bytes, std::size_t num_elements);
//!Multiple element allocation, different size
multiallocation_iterator allocate_many(const std::size_t *elem_sizes, std::size_t n_elements, std::size_t sizeof_element);
@@ -257,10 +174,12 @@
void* allocate_aligned (std::size_t nbytes, std::size_t alignment);
private:
- std::pair<void*, bool>
- priv_allocation_command(allocation_type command, std::size_t limit_size,
- std::size_t preferred_size,std::size_t &received_size,
- void *reuse_ptr, std::size_t sizeof_object);
+
+ //!Obtains the pointer returned to the user from the block control
+ static void *priv_get_user_buffer(const block_ctrl *block);
+
+ //!Obtains the block control structure of the user buffer
+ static block_ctrl *priv_get_block(const void *ptr);
//!Real allocation algorithm with min allocation option
std::pair<void *, bool> priv_allocate(allocation_type command
@@ -269,13 +188,12 @@
,std::size_t &received_size
,void *reuse_ptr = 0);
- //!Common function to implement the previous two
- multiallocation_iterator priv_allocate_many
- (const std::size_t *elem_sizes, std::size_t n_elements, std::size_t sizeof_element);
-
- multiallocation_iterator priv_allocate_many
- ( std::size_t elem_size, std::size_t min_elements
- , std::size_t preferred_elements, std::size_t &received_elements);
+ std::pair<void *, bool> priv_allocation_command(allocation_type command
+ ,std::size_t min_size
+ ,std::size_t preferred_size
+ ,std::size_t &received_size
+ ,void *reuse_ptr
+ ,std::size_t sizeof_object);
//!Returns the number of total units that a user buffer
//!of "userbytes" bytes really occupies (including header)
@@ -285,6 +203,9 @@
//!Returns 0 if next block is not free.
block_ctrl *priv_next_block_if_free(block_ctrl *ptr);
+ //!Check if this block is free (not allocated)
+ bool priv_is_allocated_block(block_ctrl *ptr);
+
//!Returns previous block's if it's free.
//!Returns 0 if previous block is not free.
std::pair<block_ctrl*, block_ctrl*>priv_prev_block_if_free(block_ctrl *ptr);
@@ -302,13 +223,8 @@
,void *reuse_ptr
,bool only_preferred_backwards);
- //!Real shrink function implementation
- bool priv_shrink(void *ptr
- ,std::size_t max_size, std::size_t preferred_size
- ,std::size_t &received_size);
-
//!Real private aligned allocation function
- void* priv_allocate_aligned (std::size_t nbytes, std::size_t alignment);
+ //void* priv_allocate_aligned (std::size_t nbytes, std::size_t alignment);
//!Checks if block has enough memory and splits/unlinks the block
//!returning the address to the users
@@ -322,10 +238,15 @@
//!Makes a new memory portion available for allocation
void priv_add_segment(void *addr, std::size_t size);
- enum { Alignment = detail::alignment_of<detail::max_align>::value };
- enum { BlockCtrlBytes = detail::ct_rounded_size<sizeof(block_ctrl), Alignment>::value };
- enum { BlockCtrlSize = BlockCtrlBytes/Alignment };
- enum { MinBlockSize = BlockCtrlSize + Alignment };
+ void priv_mark_new_allocated_block(block_ctrl *block);
+
+ static const std::size_t Alignment = detail::alignment_of<detail::max_align>::value;
+ static const std::size_t BlockCtrlBytes = detail::ct_rounded_size<sizeof(block_ctrl), Alignment>::value;
+ static const std::size_t BlockCtrlUnits = BlockCtrlBytes/Alignment;
+ static const std::size_t MinBlockUnits = BlockCtrlUnits;
+ static const std::size_t MinBlockSize = MinBlockUnits*Alignment;
+ static const std::size_t AllocatedCtrlBytes = BlockCtrlBytes;
+ static const std::size_t AllocatedCtrlUnits = BlockCtrlUnits;
public:
static const std::size_t PayloadPerAllocation = BlockCtrlBytes;
@@ -376,10 +297,31 @@
new_block->m_next = 0;
new_block->m_size = (m_header.m_size - old_end)/Alignment;
m_header.m_allocated += new_block->m_size*Alignment;
- this->priv_deallocate(detail::char_ptr_cast(new_block) + BlockCtrlBytes);
+ this->priv_deallocate(priv_get_user_buffer(new_block));
+}
+
+template<class MutexFamily, class VoidPointer>
+inline void simple_seq_fit_impl<MutexFamily, VoidPointer>::
+ priv_mark_new_allocated_block(block_ctrl *new_block)
+{
+ new_block->m_next = 0;
+}
+
+template<class MutexFamily, class VoidPointer>
+inline
+typename simple_seq_fit_impl<MutexFamily, VoidPointer>::block_ctrl *
+ simple_seq_fit_impl<MutexFamily, VoidPointer>::priv_get_block(const void *ptr)
+{
+ return reinterpret_cast<block_ctrl*>(detail::char_ptr_cast(ptr) - AllocatedCtrlBytes);
}
template<class MutexFamily, class VoidPointer>
+inline
+void *simple_seq_fit_impl<MutexFamily, VoidPointer>::
+ priv_get_user_buffer(const typename simple_seq_fit_impl<MutexFamily, VoidPointer>::block_ctrl *block)
+{ return detail::char_ptr_cast(block) + AllocatedCtrlBytes; }
+
+template<class MutexFamily, class VoidPointer>
inline void simple_seq_fit_impl<MutexFamily, VoidPointer>::priv_add_segment(void *addr, std::size_t size)
{
//Check size
@@ -393,7 +335,7 @@
//Simulate this block was previously allocated
m_header.m_allocated += new_block->m_size*Alignment;
//Return block and insert it in the free block list
- this->priv_deallocate(detail::char_ptr_cast(new_block) + BlockCtrlBytes);
+ this->priv_deallocate(priv_get_user_buffer(new_block));
}
template<class MutexFamily, class VoidPointer>
@@ -438,9 +380,9 @@
//Iterate through all free portions
do{
//Just clear user the memory part reserved for the user
- std::memset( detail::char_ptr_cast(block) + BlockCtrlBytes
+ std::memset( priv_get_user_buffer(block)
, 0
- , block->m_size*Alignment - BlockCtrlBytes);
+ , block->get_user_bytes());
block = detail::get_pointer(block->m_next);
}
while(block != &m_header.m_root);
@@ -484,7 +426,7 @@
template<class MutexFamily, class VoidPointer>
inline void* simple_seq_fit_impl<MutexFamily, VoidPointer>::
allocate(std::size_t nbytes)
-{
+{
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
@@ -499,7 +441,8 @@
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
- return priv_allocate_aligned(nbytes, alignment);
+ return algo_impl_t::
+ allocate_aligned(this, nbytes, alignment);
}
template<class MutexFamily, class VoidPointer>
@@ -509,6 +452,11 @@
std::size_t preferred_size,std::size_t &received_size,
T *reuse_ptr)
{
+ if(command & try_shrink_in_place){
+ bool success =
+ algo_impl_t::try_shrink(this, reuse_ptr, limit_size, preferred_size, received_size);
+ return std::pair<T *, bool> ((success ? reuse_ptr : 0), true);
+ }
std::pair<void*, bool> ret = priv_allocation_command
(command, limit_size, preferred_size, received_size, reuse_ptr, sizeof(T));
BOOST_ASSERT(0 == ((std::size_t)ret.first % detail::alignment_of<T>::value));
@@ -518,7 +466,7 @@
template<class MutexFamily, class VoidPointer>
inline std::pair<void*, bool> simple_seq_fit_impl<MutexFamily, VoidPointer>::
priv_allocation_command (allocation_type command, std::size_t limit_size,
- std::size_t preferred_size,std::size_t &received_size,
+ std::size_t preferred_size, std::size_t &received_size,
void *reuse_ptr, std::size_t sizeof_object)
{
command &= ~expand_bwd;
@@ -550,8 +498,8 @@
//to be modified
//Obtain the real size of the block
block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ptr) - BlockCtrlBytes);
- return block->m_size*Alignment - BlockCtrlBytes;
+ (priv_get_block(detail::char_ptr_cast(ptr)));
+ return block->get_user_bytes();
}
template<class MutexFamily, class VoidPointer>
@@ -564,7 +512,7 @@
,bool only_preferred_backwards)
{
typedef std::pair<block_ctrl *, block_ctrl *> prev_block_t;
- block_ctrl *reuse = block_ctrl::get_block_from_addr(reuse_ptr);
+ block_ctrl *reuse = priv_get_block(reuse_ptr);
received_size = 0;
if(this->size(reuse_ptr) > min_size){
@@ -608,12 +556,12 @@
(detail::char_ptr_cast(reuse) - needs_backwards - BlockCtrlBytes);
new_block->m_next = 0;
new_block->m_size =
- BlockCtrlSize + (needs_backwards + extra_forward)/Alignment;
+ BlockCtrlUnits + (needs_backwards + extra_forward)/Alignment;
prev->m_size =
- (prev->get_total_bytes() - needs_backwards)/Alignment - BlockCtrlSize;
+ (prev->get_total_bytes() - needs_backwards)/Alignment - BlockCtrlUnits;
received_size = needs_backwards + extra_forward;
m_header.m_allocated += needs_backwards + BlockCtrlBytes;
- return new_block->get_addr();
+ return priv_get_user_buffer(new_block);
}
else{
//Just merge the whole previous block
@@ -625,7 +573,7 @@
prev_2_block->m_next = prev->m_next;
prev->m_size = reuse->m_size + prev->m_size;
prev->m_next = 0;
- return prev->get_addr();
+ priv_get_user_buffer(prev);
}
}
}
@@ -635,12 +583,13 @@
template<class MutexFamily, class VoidPointer>
inline typename simple_seq_fit_impl<MutexFamily, VoidPointer>::multiallocation_iterator
simple_seq_fit_impl<MutexFamily, VoidPointer>::
- allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements)
+ allocate_many(std::size_t elem_bytes, std::size_t num_elements)
{
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
- return priv_allocate_many(elem_size, min_elements, preferred_elements, received_elements);
+ return algo_impl_t::
+ allocate_many(this, elem_bytes, num_elements);
}
template<class MutexFamily, class VoidPointer>
@@ -651,121 +600,16 @@
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
- return priv_allocate_many(elem_sizes, n_elements, sizeof_element);
-}
-
-template<class MutexFamily, class VoidPointer>
-typename simple_seq_fit_impl<MutexFamily, VoidPointer>::multiallocation_iterator
- simple_seq_fit_impl<MutexFamily, VoidPointer>::priv_allocate_many
- (const std::size_t *elem_sizes, std::size_t n_elements, std::size_t sizeof_element)
-{
- //Calculate the total size of all requests
- std::size_t total_request_units;
- total_request_units = 0;
- for(std::size_t i = 0; i < n_elements; ++i){
- std::size_t preferred_units = priv_get_total_units(elem_sizes[i]*sizeof_element);
- total_request_units += preferred_units;
- }
-
- std::size_t total_bytes = total_request_units*Alignment - BlockCtrlBytes;
-
- std::size_t received_size;
- std::pair<void *, bool> ret = priv_allocate
- (allocate_new, total_bytes, total_bytes, received_size, 0);
- if(!ret.first){
- return multiallocation_iterator();
- }
-
- block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ret.first) - BlockCtrlBytes);
- std::size_t received_units = block->m_size;
- char *block_address = (char*)block;
-
- total_request_units = 0;
-
- {
- std::size_t preferred_units;
- //If all have the same size, we don't need calculate it
- //every iteration
- for(std::size_t i = 0; i < n_elements; ++i){
- //If all have different size, we have to calculate it each iteration
- preferred_units = priv_get_total_units(elem_sizes[i]*sizeof_element);
- //This is the position where the new block must be created
- block_ctrl *new_block = new(block_address)block_ctrl;
- //The last block should take all the remaining space
- if((i + 1) == n_elements){
- new_block->m_size = received_units - total_request_units;
- }
- else{
- new_block->m_size = preferred_units;
- }
- //assert(new_block->m_size >= BlockCtrlUnits);
- new_block->m_next = 0;
- block_address += new_block->m_size*Alignment;
- total_request_units += new_block->m_size;
- }
- assert(total_request_units == received_units);
- }
- return multiallocation_iterator(block, n_elements);
-}
-
-template<class MutexFamily, class VoidPointer>
-typename simple_seq_fit_impl<MutexFamily, VoidPointer>::multiallocation_iterator
- simple_seq_fit_impl<MutexFamily, VoidPointer>::priv_allocate_many
- ( std::size_t elem_size, std::size_t min_elements
- , std::size_t preferred_elements, std::size_t &received_elements)
-{
- //Calculate the total size of all requests
- const std::size_t elem_units = priv_get_total_units(elem_size);
- const std::size_t total_min_usr_units = min_elements*elem_units - BlockCtrlSize;
- const std::size_t total_preferred_usr_units = preferred_elements*elem_units - BlockCtrlSize;
-
- std::size_t received_size;
- std::pair<void *, bool> ret = priv_allocate
- ( allocate_new, total_min_usr_units*Alignment
- , total_preferred_usr_units*Alignment, received_size, 0);
- if(!ret.first){
- received_elements = (received_size + BlockCtrlBytes)/elem_units;
- return multiallocation_iterator();
- }
-
- block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ret.first) - BlockCtrlBytes);
- std::size_t received_units = block->m_size;
- char *block_address = (char*)block;
-
- received_elements = received_units/elem_units;
- if(received_elements > preferred_elements){
- received_elements = preferred_elements;
- }
- std::size_t total_request_units = 0;
- {
- for(std::size_t i = 0; i < received_elements; ++i){
- //If all have different size, we have to calculate it each iteration
- //This is the position where the new block must be created
- block_ctrl *new_block = new(block_address)block_ctrl;
- //The last block should take all the remaining space
- if((i + 1) == received_elements){
- new_block->m_size = received_units - (received_elements-1)*elem_units;
- }
- else{
- new_block->m_size = elem_units;
- }
- //assert(new_block->m_size >= BlockCtrlUnits);
- new_block->m_next = 0;
- block_address += new_block->m_size*Alignment;
- total_request_units += new_block->m_size;
- }
- assert(total_request_units == received_units);
- }
- return multiallocation_iterator(block, received_elements);
+ return algo_impl_t::allocate_many(this, elem_sizes, n_elements, sizeof_element);
}
template<class MutexFamily, class VoidPointer>
inline std::size_t simple_seq_fit_impl<MutexFamily, VoidPointer>::
priv_get_total_units(std::size_t userbytes)
{
- return detail::get_rounded_size(userbytes, Alignment)/Alignment + BlockCtrlSize;
+ std::size_t s = detail::get_rounded_size(userbytes, Alignment)/Alignment;
+ if(!s) ++s;
+ return BlockCtrlUnits + s;
}
template<class MutexFamily, class VoidPointer>
@@ -778,7 +622,7 @@
{
if(command & shrink_in_place){
bool success =
- this->priv_shrink(reuse_ptr, limit_size, preferred_size, received_size);
+ algo_impl_t::shrink(this, reuse_ptr, limit_size, preferred_size, received_size);
return std::pair<void *, bool> ((success ? reuse_ptr : 0), true);
}
typedef std::pair<void *, bool> return_type;
@@ -788,7 +632,7 @@
return return_type(0, false);
//Number of units to request (including block_ctrl header)
- std::size_t nunits = detail::get_rounded_size(preferred_size, Alignment)/Alignment + BlockCtrlSize;
+ std::size_t nunits = detail::get_rounded_size(preferred_size, Alignment)/Alignment + BlockCtrlUnits;
//Get the root and the first memory block
block_ctrl *prev = &m_header.m_root;
@@ -796,7 +640,7 @@
block_ctrl *root = &m_header.m_root;
block_ctrl *biggest_block = 0;
block_ctrl *prev_biggest_block = 0;
- std::size_t biggest_size = limit_size;
+ std::size_t biggest_size = 0;
//Expand in place
//reuse_ptr, limit_size, preferred_size, received_size
@@ -827,12 +671,15 @@
//Bad luck finding preferred_size, now if we have any biggest_block
//try with this block
if(biggest_block){
- received_size = biggest_block->m_size*Alignment - BlockCtrlSize;
- nunits = detail::get_rounded_size(limit_size, Alignment)/Alignment + BlockCtrlSize;
+ std::size_t limit_units = detail::get_rounded_size(limit_size, Alignment)/Alignment + BlockCtrlUnits;
+ if(biggest_block->m_size < limit_units)
+ return return_type(0, false);
+
+ received_size = biggest_block->m_size*Alignment - BlockCtrlUnits;
void *ret = this->priv_check_and_allocate
- (nunits, prev_biggest_block, biggest_block, received_size);
- if(ret)
- return return_type(ret, false);
+ (biggest_block->m_size, prev_biggest_block, biggest_block, received_size);
+ assert(ret != 0);
+ return return_type(ret, false);
}
}
//Now try to expand both sides with min size
@@ -843,6 +690,11 @@
return return_type(0, false);
}
+template<class MutexFamily, class VoidPointer> inline
+bool simple_seq_fit_impl<MutexFamily, VoidPointer>::priv_is_allocated_block
+ (typename simple_seq_fit_impl<MutexFamily, VoidPointer>::block_ctrl *block)
+{ return block->m_next == 0; }
+
template<class MutexFamily, class VoidPointer>
inline typename simple_seq_fit_impl<MutexFamily, VoidPointer>::block_ctrl *
simple_seq_fit_impl<MutexFamily, VoidPointer>::
@@ -907,8 +759,7 @@
,std::size_t &received_size)
{
//Obtain the real size of the block
- block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ptr) - BlockCtrlBytes);
+ block_ctrl *block = reinterpret_cast<block_ctrl*>(priv_get_block(ptr));
std::size_t old_block_size = block->m_size;
//All used blocks' next is marked with 0 so check it
@@ -925,7 +776,7 @@
if(min_size > preferred_size)
return false;
- std::size_t data_size = old_block_size - BlockCtrlSize;
+ std::size_t data_size = old_block_size - BlockCtrlUnits;
if(data_size >= min_size)
return true;
@@ -941,7 +792,7 @@
//Now we can expand this block further than before
received_size = merged_size*Alignment - BlockCtrlBytes;
- if(merged_size < (min_size + BlockCtrlSize)){
+ if(merged_size < (min_size + BlockCtrlUnits)){
return false;
}
@@ -961,7 +812,7 @@
prev->m_next = block;
//Now use check and allocate to do the allocation logic
- preferred_size += BlockCtrlSize;
+ preferred_size += BlockCtrlUnits;
std::size_t nunits = preferred_size < merged_size ? preferred_size : merged_size;
//This must success since nunits is less than merged_size!
@@ -974,114 +825,6 @@
return true;
}
-template<class MutexFamily, class VoidPointer>
-inline bool simple_seq_fit_impl<MutexFamily, VoidPointer>::
- priv_shrink (void *ptr
- ,std::size_t max_size
- ,std::size_t preferred_size
- ,std::size_t &received_size)
-{
- //Obtain the real size of the block
- block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ptr) - BlockCtrlBytes);
- std::size_t block_size = block->m_size;
-
- //All used blocks' next is marked with 0 so check it
- assert(block->m_next == 0);
-
- //Put this to a safe value
- received_size = block_size*Alignment - BlockCtrlBytes;
-
- //Now translate it to Alignment units
- max_size = max_size/Alignment;
- preferred_size = detail::get_rounded_size(preferred_size, Alignment)/Alignment;
-
- //Some parameter checks
- if(max_size < preferred_size)
- return false;
-
- std::size_t data_size = block_size - BlockCtrlSize;
-
- if(data_size < preferred_size)
- return false;
-
- if(data_size == preferred_size)
- return true;
-
- //We must be able to create at least a new empty block
- if((data_size - preferred_size) < BlockCtrlSize){
- return false;
- }
-
- //Now we can just rewrite the size of the old buffer
- block->m_size = preferred_size + BlockCtrlSize;
-
- //Update new size
- received_size = preferred_size*Alignment;
-
- //We create the new block
- block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(block) + block->m_size*Alignment);
-
- //Write control data to simulate this new block was previously allocated
- block->m_next = 0;
- block->m_size = data_size - preferred_size;
-
- //Now deallocate the new block to insert it in the free list
- this->priv_deallocate(detail::char_ptr_cast(block)+BlockCtrlBytes);
- return true;
-}
-
-template<class MutexFamily, class VoidPointer>
-inline void* simple_seq_fit_impl<MutexFamily, VoidPointer>::
- priv_allocate_aligned(std::size_t nbytes, std::size_t alignment)
-{
- //Ensure power of 2
- if ((alignment & (alignment - std::size_t(1u))) != 0){
- //Alignment is not power of two
- assert((alignment & (alignment - std::size_t(1u))) != 0);
- return 0;
- }
-
- std::size_t ignore;
- if(alignment <= Alignment){
- return priv_allocate(allocate_new, nbytes, nbytes, ignore).first;
- }
-
- std::size_t request =
- nbytes + alignment + MinBlockSize*Alignment - BlockCtrlBytes;
- void *buffer = priv_allocate(allocate_new, request, request, ignore).first;
- if(!buffer)
- return 0;
- else if ((((std::size_t)(buffer)) % alignment) == 0)
- return buffer;
-
- char *aligned_portion = (char*)
- ((std::size_t)((char*)buffer + alignment - 1) & -alignment);
-
- char *pos = ((aligned_portion - (char*)buffer) >= (MinBlockSize*Alignment)) ?
- aligned_portion : (aligned_portion + alignment);
-
-
- block_ctrl *first = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(buffer) - BlockCtrlBytes);
-
- block_ctrl *second = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(pos) - BlockCtrlBytes);
-
- std::size_t old_size = first->m_size;
-
- first->m_size = ((char*)second - (char*)first)/Alignment;
- second->m_size = old_size - first->m_size;
-
- //Write control data to simulate this new block was previously allocated
- second->m_next = 0;
-
- //Now deallocate the new block to insert it in the free list
- this->priv_deallocate(detail::char_ptr_cast(first) + BlockCtrlBytes);
- return detail::char_ptr_cast(second) + BlockCtrlBytes;
-}
-
template<class MutexFamily, class VoidPointer> inline
void* simple_seq_fit_impl<MutexFamily, VoidPointer>::priv_check_and_allocate
(std::size_t nunits
@@ -1089,7 +832,7 @@
,typename simple_seq_fit_impl<MutexFamily, VoidPointer>::block_ctrl* block
,std::size_t &received_size)
{
- std::size_t upper_nunits = nunits + BlockCtrlSize;
+ std::size_t upper_nunits = nunits + BlockCtrlUnits;
bool found = false;
if (block->m_size > upper_nunits){
@@ -1116,13 +859,13 @@
//We need block_ctrl for deallocation stuff, so
//return memory user can overwrite
m_header.m_allocated += block->m_size*Alignment;
- received_size = block->m_size*Alignment - BlockCtrlBytes;
+ received_size = block->get_user_bytes();
//Mark the block as allocated
block->m_next = 0;
//Check alignment
assert(((detail::char_ptr_cast(block) - detail::char_ptr_cast(this))
% Alignment) == 0 );
- return detail::char_ptr_cast(block)+BlockCtrlBytes;
+ return priv_get_user_buffer(block);
}
return 0;
}
@@ -1146,10 +889,9 @@
//by memory address to allow block merging.
//Pointer next always points to the first
//(lower address) block
- block_ctrl_ptr prev = &m_header.m_root;
- block_ctrl_ptr pos = m_header.m_root.m_next;
- block_ctrl_ptr block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(addr) - BlockCtrlBytes);
+ block_ctrl * prev = &m_header.m_root;
+ block_ctrl * pos = detail::get_pointer(m_header.m_root.m_next);
+ block_ctrl * block = reinterpret_cast<block_ctrl*>(priv_get_block(addr));
//All used blocks' next is marked with 0 so check it
assert(block->m_next == 0);
@@ -1170,7 +912,7 @@
//in each process
while((detail::get_pointer(pos) != &m_header.m_root) && (block > pos)){
prev = pos;
- pos = pos->m_next;
+ pos = detail::get_pointer(pos->m_next);
}
//Try to combine with upper block
Modified: branches/bcbboost/boost/interprocess/mem_algo/rbtree_best_fit.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/mem_algo/rbtree_best_fit.hpp (original)
+++ branches/bcbboost/boost/interprocess/mem_algo/rbtree_best_fit.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -19,6 +19,7 @@
#include <boost/interprocess/detail/workaround.hpp>
#include <boost/interprocess/interprocess_fwd.hpp>
+#include <boost/interprocess/mem_algo/detail/mem_algo_common.hpp>
#include <boost/interprocess/allocators/allocation_type.hpp>
#include <boost/interprocess/offset_ptr.hpp>
#include <boost/interprocess/sync/interprocess_mutex.hpp>
@@ -39,11 +40,10 @@
#include <assert.h>
#include <new>
-/*!\file
- Describes a best-fit algorithm based in an intrusive red-black tree used to allocate
- objects in shared memory. This class is intended as a base class for single segment
- and multi-segment implementations.
-*/
+//!\file
+//!Describes a best-fit algorithm based in an intrusive red-black tree used to allocate
+//!objects in shared memory. This class is intended as a base class for single segment
+//!and multi-segment implementations.
namespace boost {
namespace interprocess {
@@ -65,20 +65,25 @@
typedef MutexFamily mutex_family;
//!Pointer type to be used with the rest of the Interprocess framework
typedef VoidPointer void_pointer;
+ typedef detail::basic_multiallocation_iterator
+ <void_pointer> multiallocation_iterator;
/// @cond
- class multiallocation_iterator;
-
private:
struct block_ctrl;
typedef typename detail::
- pointer_to_other<void_pointer, block_ctrl>::type block_ctrl_ptr;
+ pointer_to_other<void_pointer, block_ctrl>::type block_ctrl_ptr;
+ typedef typename detail::
+ pointer_to_other<void_pointer, char>::type char_ptr;
- typedef boost::intrusive::set_base_hook
- < boost::intrusive::tag
- , boost::intrusive::normal_link
- , VoidPointer> TreeHook;
+ typedef typename bi::make_set_base_hook
+ < bi::void_pointer<VoidPointer>
+ , bi::link_mode<bi::normal_link> >::type TreeHook;
+
+ typedef detail::multi_allocation_next<void_pointer> multi_allocation_next_t;
+ typedef typename multi_allocation_next_t::
+ multi_allocation_next_ptr multi_allocation_next_ptr;
struct SizeHolder
{
@@ -113,11 +118,10 @@
};
//!Shared interprocess_mutex to protect memory allocate/deallocate
- typedef typename MutexFamily::mutex_type interprocess_mutex;
-
- typedef boost::intrusive::multiset
- <typename TreeHook::template value_traits<block_ctrl> > Imultiset;
- typedef typename Imultiset::iterator imultiset_iterator;
+ typedef typename MutexFamily::mutex_type interprocess_mutex;
+ typedef typename bi::make_multiset
+ <block_ctrl, bi::base_hook<TreeHook> >::type Imultiset;
+ typedef typename Imultiset::iterator imultiset_iterator;
//!This struct includes needed data and derives from
//!interprocess_mutex to allow EBO when using null interprocess_mutex
@@ -133,84 +137,12 @@
std::size_t m_size;
} m_header;
- friend class multiallocation_iterator;
-
+ friend class detail::basic_multiallocation_iterator<void_pointer>;
+ friend class detail::memory_algorithm_common<rbtree_best_fit>;
+
+ typedef detail::memory_algorithm_common<rbtree_best_fit> algo_impl_t;
public:
- class multiallocation_iterator
- : public std::iterator<std::bidirectional_iterator_tag, char *>
- {
- void unspecified_bool_type_func() const {}
- typedef void (multiallocation_iterator::*unspecified_bool_type)() const;
-
- public:
- typedef char * value_type;
- typedef value_type & reference;
- typedef value_type * pointer;
-
- multiallocation_iterator()
- : block_(0), n_elements_ (0)
- {}
-
- multiallocation_iterator(void *many_allocation, std::size_t n_elements)
- : block_(static_cast<block_ctrl*>(many_allocation)), n_elements_ (n_elements)
- {}
-
- multiallocation_iterator &operator=(const multiallocation_iterator &other)
- { block_ = other.block_; n_elements_ = other.n_elements_; return *this; }
-
- public:
- multiallocation_iterator& operator++()
- {
- --n_elements_;
- block_ = (block_ctrl*)((char*)block_ + block_->m_size*Alignment);
- return *this;
- }
-
- multiallocation_iterator operator++(int)
- {
- multiallocation_iterator result(block_, n_elements_);
- ++*this;
- return result;
- }
-
- multiallocation_iterator& operator--()
- {
- ++n_elements_;
- block_ = (block_ctrl*)((char*)block_ - block_->m_prev_size*Alignment);
- return *this;
- }
-
- multiallocation_iterator operator--(int)
- {
- multiallocation_iterator result(block_, n_elements_);
- --*this;
- return result;
- }
-
- bool operator== (const multiallocation_iterator& other) const
- { return n_elements_ == other.n_elements_; }
-
- bool operator!= (const multiallocation_iterator& other) const
- { return !operator== (other); }
-
- value_type operator*() const
- {
- value_type v = (char*)priv_get_user_buffer(block_);
- return v;
- }
-
- operator unspecified_bool_type() const
- { return n_elements_? &multiallocation_iterator::unspecified_bool_type_func : 0; }
-
- pointer operator->() const
- { return &operator*(); }
-
- private:
- block_ctrl *block_;
- std::size_t n_elements_;
- };
-
/// @endcond
//!Constructor. "size" is the total size of the managed memory segment,
@@ -234,7 +166,7 @@
//Experimental. Dont' use
//!Multiple element allocation, same size
- multiallocation_iterator allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements);
+ multiallocation_iterator allocate_many(std::size_t elem_bytes, std::size_t num_elements);
//!Multiple element allocation, different size
multiallocation_iterator allocate_many(const std::size_t *elem_sizes, std::size_t n_elements, std::size_t sizeof_element);
@@ -292,14 +224,6 @@
,void *reuse_ptr = 0
,std::size_t backwards_multiple = 1);
- //!Common function to implement multiple allocation
- multiallocation_iterator priv_allocate_many
- (const std::size_t *elem_sizes, std::size_t n_elements, std::size_t sizeof_elements);
-
- multiallocation_iterator priv_allocate_many
- ( std::size_t elem_size, std::size_t min_elements
- , std::size_t preferred_elements, std::size_t &received_elements);
-
//!Obtains the block control structure of the user buffer
static block_ctrl *priv_get_block(const void *ptr);
@@ -310,18 +234,6 @@
//!of "userbytes" bytes really occupies (including header)
static std::size_t priv_get_total_units(std::size_t userbytes);
- //!Translates a size to a number of units (ceiling the result)
- static std::size_t priv_ceil_units(std::size_t size);
-
- //!Translates a size to a number of units (flooring the result)
- static std::size_t priv_floor_units(std::size_t size);
-
- //!Rounds the size (ceiling) to a multiple of units
- static std::size_t priv_multiple_of_units(std::size_t size);
-
- //!Asserts if the alignment is not correct
- static void priv_check_alignment(const void *ptr);
-
//!Real expand function implementation
bool priv_expand(void *ptr
,const std::size_t min_size, const std::size_t preferred_size
@@ -336,16 +248,11 @@
,bool only_preferred_backwards
,std::size_t backwards_multiple);
- //!Real shrink function implementation
- bool priv_shrink(void *ptr
- ,const std::size_t max_size, const std::size_t preferred_size
- ,std::size_t &received_size);
-
//!Set the size in the tail of the block
void priv_tail_size(block_ctrl *ptr, std::size_t size);
//!Real private aligned allocation function
- void* priv_allocate_aligned (std::size_t nbytes, std::size_t alignment);
+ //void* priv_allocate_aligned (std::size_t nbytes, std::size_t alignment);
//!Get the size in the tail of the block
std::size_t priv_tail_size(block_ctrl *ptr);
@@ -376,15 +283,17 @@
//!Makes a new memory portion available for allocation
void priv_add_segment(void *addr, std::size_t size);
- enum { Alignment = detail::alignment_of<detail::max_align>::value };
- enum { AlignmentMask = (Alignment - 1) };
- enum { BlockCtrlBytes = detail::ct_rounded_size<sizeof(block_ctrl), Alignment>::value };
- enum { BlockCtrlUnits = BlockCtrlBytes/Alignment };
- enum { AllocatedCtrlBytes = detail::ct_rounded_size<sizeof(SizeHolder), Alignment>::value };
- enum { AllocatedCtrlUnits = AllocatedCtrlBytes/Alignment };
- enum { EndCtrlBlockBytes = detail::ct_rounded_size<sizeof(SizeHolder), Alignment>::value };
- enum { EndCtrlBlockUnits = EndCtrlBlockBytes/Alignment };
- enum { MinBlockUnits = BlockCtrlUnits };
+ void priv_mark_new_allocated_block(block_ctrl *block);
+
+ static const std::size_t Alignment = detail::alignment_of<detail::max_align>::value;
+ static const std::size_t AlignmentMask = (Alignment - 1);
+ static const std::size_t BlockCtrlBytes = detail::ct_rounded_size<sizeof(block_ctrl), Alignment>::value;
+ static const std::size_t BlockCtrlUnits = BlockCtrlBytes/Alignment;
+ static const std::size_t AllocatedCtrlBytes = detail::ct_rounded_size<sizeof(SizeHolder), Alignment>::value;
+ static const std::size_t AllocatedCtrlUnits = AllocatedCtrlBytes/Alignment;
+ static const std::size_t EndCtrlBlockBytes = detail::ct_rounded_size<sizeof(SizeHolder), Alignment>::value;
+ static const std::size_t EndCtrlBlockUnits = EndCtrlBlockBytes/Alignment;
+ static const std::size_t MinBlockUnits = BlockCtrlUnits;
//Make sure the maximum alignment is power of two
BOOST_STATIC_ASSERT((0 == (Alignment & (Alignment - std::size_t(1u)))));
@@ -404,7 +313,7 @@
//Now write calculate the offset of the first big block that will
//cover the whole segment
- std::size_t block1_off = priv_multiple_of_units(sizeof(*this)+extra_hdr_bytes);
+ std::size_t block1_off = algo_impl_t::multiple_of_units(sizeof(*this)+extra_hdr_bytes);
assert(get_min_size(extra_hdr_bytes) <= size);
priv_add_segment(detail::char_ptr_cast(this) + block1_off, size - block1_off);
@@ -423,7 +332,7 @@
{
//Get the address of the first block
std::size_t block1_off =
- priv_multiple_of_units(sizeof(*this) + m_header.m_extra_hdr_bytes);
+ algo_impl_t::multiple_of_units(sizeof(*this) + m_header.m_extra_hdr_bytes);
block_ctrl *first_block = reinterpret_cast<block_ctrl *>
(detail::char_ptr_cast(this) + block1_off);
@@ -449,11 +358,9 @@
new_end_block->m_size = (detail::char_ptr_cast(first_block) -
detail::char_ptr_cast(new_end_block))/Alignment;
assert(first_block == priv_next_block(new_end_block));
- priv_mark_as_allocated_block(new_end_block);
new_end_block->m_end = 1;
+ priv_mark_new_allocated_block(new_end_block);
- //This will update the link of the first block
- priv_tail_size(new_end_block, new_end_block->m_size);
assert(new_end_block == priv_prev_block(first_block));
//The old end block is the new block
@@ -463,9 +370,8 @@
detail::char_ptr_cast(new_block))/Alignment;
new_block->m_prev_size = old_end_prev;
assert(new_block->m_size >= BlockCtrlUnits);
- priv_tail_size(new_block, new_block->m_size);
+ priv_mark_new_allocated_block(new_block);
assert(priv_next_block(new_block) == new_end_block);
- priv_mark_as_allocated_block(new_block);
m_header.m_allocated += new_block->m_size*Alignment;
@@ -519,6 +425,14 @@
}
template<class MutexFamily, class VoidPointer>
+inline void rbtree_best_fit<MutexFamily, VoidPointer>::
+ priv_mark_new_allocated_block(block_ctrl *new_block)
+{
+ priv_tail_size(new_block, new_block->m_size);
+ priv_mark_as_allocated_block(new_block);
+}
+
+template<class MutexFamily, class VoidPointer>
inline std::size_t rbtree_best_fit<MutexFamily, VoidPointer>::get_size() const
{ return m_header.m_size; }
@@ -526,14 +440,14 @@
inline std::size_t rbtree_best_fit<MutexFamily, VoidPointer>::get_free_memory() const
{
return m_header.m_size - m_header.m_allocated -
- priv_multiple_of_units(sizeof(*this) + m_header.m_extra_hdr_bytes);
+ algo_impl_t::multiple_of_units(sizeof(*this) + m_header.m_extra_hdr_bytes);
}
template<class MutexFamily, class VoidPointer>
inline std::size_t rbtree_best_fit<MutexFamily, VoidPointer>::
get_min_size (std::size_t extra_hdr_bytes)
{
- return (priv_ceil_units(sizeof(rbtree_best_fit) + extra_hdr_bytes) +
+ return (algo_impl_t::ceil_units(sizeof(rbtree_best_fit) + extra_hdr_bytes) +
MinBlockUnits + EndCtrlBlockUnits)*Alignment;
}
@@ -545,7 +459,7 @@
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
std::size_t block1_off =
- priv_multiple_of_units(sizeof(*this)+m_header.m_extra_hdr_bytes);
+ algo_impl_t::multiple_of_units(sizeof(*this)+m_header.m_extra_hdr_bytes);
return m_header.m_allocated == 0 &&
m_header.m_imultiset.begin() != m_header.m_imultiset.end() &&
@@ -576,7 +490,7 @@
}
std::size_t block1_off =
- priv_multiple_of_units(sizeof(*this)+m_header.m_extra_hdr_bytes);
+ algo_impl_t::multiple_of_units(sizeof(*this)+m_header.m_extra_hdr_bytes);
//Check free bytes are less than size
if(free_memory > (m_header.m_size - block1_off)){
@@ -599,11 +513,11 @@
template<class MutexFamily, class VoidPointer>
inline void* rbtree_best_fit<MutexFamily, VoidPointer>::
allocate_aligned(std::size_t nbytes, std::size_t alignment)
-{
+{
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
- return priv_allocate_aligned(nbytes, alignment);
+ return algo_impl_t::allocate_aligned(this, nbytes, alignment);
}
template<class MutexFamily, class VoidPointer>
@@ -613,6 +527,11 @@
std::size_t preferred_size,std::size_t &received_size,
T *reuse_ptr)
{
+ if(command & try_shrink_in_place){
+ bool success =
+ algo_impl_t::try_shrink(this, reuse_ptr, limit_size, preferred_size, received_size);
+ return std::pair<T *, bool> ((success ? reuse_ptr : 0), true);
+ }
std::pair<void*, bool> ret = priv_allocation_command
(command, limit_size, preferred_size, received_size, reuse_ptr, sizeof(T));
BOOST_ASSERT(0 == ((std::size_t)ret.first % detail::alignment_of<T>::value));
@@ -701,7 +620,7 @@
//Sanity check
assert(reuse->m_size == priv_tail_size(reuse));
- priv_check_alignment(reuse);
+ algo_impl_t::check_alignment(reuse);
block_ctrl *prev_block;
@@ -712,7 +631,7 @@
//Some sanity checks
assert(prev_block->m_size == priv_tail_size(prev_block));
- priv_check_alignment(prev_block);
+ algo_impl_t::check_alignment(prev_block);
//Let's calculate the number of extra bytes of data before the current
//block's begin. The value is a multiple of backwards_multiple
@@ -748,14 +667,13 @@
(detail::char_ptr_cast(reuse) - needs_backwards_aligned);
//Erase old previous block, since we will change it
- m_header.m_imultiset.erase(Imultiset::iterator_to(*prev_block));
+ m_header.m_imultiset.erase(Imultiset::s_iterator_to(*prev_block));
//Free old previous buffer
new_block->m_size =
AllocatedCtrlUnits + (needs_backwards_aligned + received_size)/Alignment;
assert(new_block->m_size >= BlockCtrlUnits);
- priv_tail_size(new_block, new_block->m_size);
- priv_mark_as_allocated_block(new_block);
+ priv_mark_new_allocated_block(new_block);
prev_block->m_size = (detail::char_ptr_cast(new_block) -
detail::char_ptr_cast(prev_block))/Alignment;
@@ -769,7 +687,7 @@
m_header.m_allocated += needs_backwards_aligned;
//Check alignment
- priv_check_alignment(new_block);
+ algo_impl_t::check_alignment(new_block);
//If the backwards expansion has remaining bytes in the
//first bytes, fill them with a pattern
@@ -783,7 +701,7 @@
else if(prev_block->m_size >= needs_backwards_aligned/Alignment &&
0 == (prev_block->m_size % lcm)) {
//Erase old previous block, since we will change it
- m_header.m_imultiset.erase(Imultiset::iterator_to(*prev_block));
+ m_header.m_imultiset.erase(Imultiset::s_iterator_to(*prev_block));
//Just merge the whole previous block
const std::size_t needs_backwards_aligned = prev_block->m_size*Alignment;
@@ -794,9 +712,7 @@
//Now update sizes
prev_block->m_size = prev_block->m_size + reuse->m_size;
assert(prev_block->m_size >= BlockCtrlUnits);
- priv_tail_size(prev_block, prev_block->m_size);
- priv_mark_as_allocated_block(prev_block);
- priv_check_alignment(prev_block);
+ priv_mark_new_allocated_block(prev_block);
//If the backwards expansion has remaining bytes in the
//first bytes, fill them with a pattern
@@ -814,134 +730,14 @@
}
template<class MutexFamily, class VoidPointer>
-inline void* rbtree_best_fit<MutexFamily, VoidPointer>::
- priv_allocate_aligned(std::size_t nbytes, std::size_t alignment)
-{
- //Ensure power of 2
- if ((alignment & (alignment - std::size_t(1u))) != 0){
- //Alignment is not power of two
- assert((alignment & (alignment - std::size_t(1u))) != 0);
- return 0;
- }
-
- std::size_t real_size;
- if(alignment <= Alignment){
- return priv_allocate(allocate_new, nbytes, nbytes, real_size).first;
- }
-
- //We can find a aligned portion if we allocate a chunk that has alignment
- //nbytes + alignment bytes or more.
- std::size_t minimum_allocation = max_value(nbytes + alignment, std::size_t(MinBlockUnits*Alignment));
- //Since we will split that chunk, we must request a bit more memory
- //if the alignment is near the beginning of the buffer, because otherwise,
- //there is no space for a new chunk before the alignment.
- //
- // ____ Aligned here
- // |
- // -----------------------------------------------------
- // | MBU |
- // -----------------------------------------------------
- std::size_t request =
- minimum_allocation + (MinBlockUnits*Alignment - AllocatedCtrlBytes);
-
- //Now allocate the buffer
- void *buffer = priv_allocate(allocate_new, request, request, real_size).first;
- if(!buffer){
- return 0;
- }
- else if ((((std::size_t)(buffer)) % alignment) == 0){
- //If we are lucky and the buffer is aligned, just split it and
- //return the high part
- block_ctrl *first = priv_get_block(buffer);
- std::size_t old_size = first->m_size;
- const std::size_t first_min_units =
- max_value(priv_ceil_units(nbytes) + AllocatedCtrlUnits, std::size_t(MinBlockUnits));
- //We can create a new block in the end of the segment
- if(old_size >= (first_min_units + MinBlockUnits)){
- block_ctrl *second = new((char*)first + Alignment*first_min_units) block_ctrl;
- first->m_size = first_min_units;
- second->m_size = old_size - first->m_size;
- BOOST_ASSERT(second->m_size >= MinBlockUnits);
- priv_tail_size(first, first->m_size);
- priv_tail_size(second, second->m_size);
- priv_mark_as_allocated_block(second);
- this->priv_deallocate(priv_get_user_buffer(second));
- }
- return buffer;
- }
-
- //Buffer not aligned, find the aligned part.
- //
- // ____ Aligned here
- // |
- // -----------------------------------------------------
- // | MBU +more | ACB |
- // -----------------------------------------------------
- char *pos = (char*)
- ((std::size_t)((char*)buffer +
- //This is the minimum size of (2)
- (MinBlockUnits*Alignment - AllocatedCtrlBytes) +
- //This is the next MBU for the aligned memory
- AllocatedCtrlBytes +
- //This is the alignment trick
- alignment - 1) & -alignment);
-
- //Now obtain the address of the blocks
- block_ctrl *first = priv_get_block(buffer);
- block_ctrl *second = priv_get_block(pos);
-
- //Set the new size of the first block
- std::size_t old_size = first->m_size;
- first->m_size = ((char*)second - (char*)first)/Alignment;
- priv_tail_size(first, first->m_size);
- priv_mark_as_allocated_block(first);
-
- //Now check if we can create a new buffer in the end
- //
- // __"second" block
- // | __Aligned here
- // | | __"third" block
- // -----------|-----|-----|------------------------------
- // | MBU +more | ACB | (3) | BCU |
- // -----------------------------------------------------
- //This size will be the minimum size to be able to create a
- //new chunk in the end.
- const std::size_t second_min_units = max_value(std::size_t(MinBlockUnits),
- priv_ceil_units(nbytes) + AllocatedCtrlUnits );
-
- //Check if we can create a new block (of size MinBlockUnits) in the end of the segment
- if((old_size - first->m_size) >= (second_min_units + MinBlockUnits)){
- //Now obtain the address of the end block
- block_ctrl *third = new ((char*)second + Alignment*second_min_units)block_ctrl;
- second->m_size = second_min_units;
- third->m_size = old_size - first->m_size - second->m_size;
- BOOST_ASSERT(third->m_size >= MinBlockUnits);
- priv_tail_size(second, second->m_size);
- priv_tail_size(third, third->m_size);
- priv_mark_as_allocated_block(second);
- priv_mark_as_allocated_block(third);
- this->priv_deallocate(priv_get_user_buffer(third));
- }
- else{
- second->m_size = old_size - first->m_size;
- priv_tail_size(second, second->m_size);
- priv_mark_as_allocated_block(second);
- }
-
- this->priv_deallocate(priv_get_user_buffer(first));
- return priv_get_user_buffer(second);
-}
-
-template<class MutexFamily, class VoidPointer>
inline typename rbtree_best_fit<MutexFamily, VoidPointer>::multiallocation_iterator
rbtree_best_fit<MutexFamily, VoidPointer>::
- allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements)
+ allocate_many(std::size_t elem_bytes, std::size_t num_elements)
{
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
- received_elements = min_elements;
- return priv_allocate_many(elem_size, min_elements, preferred_elements, received_elements);
+ return algo_impl_t::allocate_many(this, elem_bytes, num_elements);
}
template<class MutexFamily, class VoidPointer>
@@ -952,7 +748,7 @@
//-----------------------
boost::interprocess::scoped_lock<interprocess_mutex> guard(m_header);
//-----------------------
- return priv_allocate_many(elem_sizes, n_elements, sizeof_element);
+ return algo_impl_t::allocate_many(this, elem_sizes, n_elements, sizeof_element);
}
template<class MutexFamily, class VoidPointer>
@@ -969,9 +765,10 @@
if(command & shrink_in_place){
bool success =
- this->priv_shrink(reuse_ptr, limit_size, preferred_size, received_size);
+ algo_impl_t::shrink(this, reuse_ptr, limit_size, preferred_size, received_size);
return std::pair<void *, bool> ((success ? reuse_ptr : 0), true);
}
+
typedef std::pair<void *, bool> return_type;
received_size = 0;
@@ -1019,112 +816,6 @@
}
template<class MutexFamily, class VoidPointer>
-typename rbtree_best_fit<MutexFamily, VoidPointer>::multiallocation_iterator
- rbtree_best_fit<MutexFamily, VoidPointer>::priv_allocate_many
- (const std::size_t *elem_sizes, std::size_t n_elements, std::size_t sizeof_element)
-{
- //Calculate the total size of all requests
- std::size_t total_request_units;
- total_request_units = 0;
- for(std::size_t i = 0; i < n_elements; ++i){
- std::size_t preferred_units = priv_get_total_units(elem_sizes[i]*sizeof_element);
- total_request_units += preferred_units;
- }
-
- std::size_t total_bytes = total_request_units*Alignment - AllocatedCtrlBytes;
-
- std::size_t received_size;
- std::pair<void *, bool> ret = priv_allocate
- (allocate_new, total_bytes, total_bytes, received_size, 0);
- if(!ret.first){
- return multiallocation_iterator();
- }
-
- block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ret.first) - AllocatedCtrlBytes);
- std::size_t received_units = block->m_size;
- char *block_address = (char*)block;
-
- total_request_units = 0;
-
- {
- std::size_t preferred_units;
- //If all have the same size, we don't need calculate it
- //every iteration
- for(std::size_t i = 0; i < n_elements; ++i){
- //If all have different size, we have to calculate it each iteration
- preferred_units = priv_get_total_units(elem_sizes[i]*sizeof_element);
- //This is the position where the new block must be created
- block_ctrl *new_block = new(block_address)block_ctrl;
- //The last block should take all the remaining space
- if((i + 1) == n_elements){
- new_block->m_size = received_units - total_request_units;
- }
- else{
- new_block->m_size = preferred_units;
- }
- priv_tail_size(new_block, new_block->m_size);
- priv_mark_as_allocated_block(new_block);
- block_address += new_block->m_size*Alignment;
- total_request_units += new_block->m_size;
- }
- assert(total_request_units == received_units);
- }
- return multiallocation_iterator(block, n_elements);
-}
-
-template<class MutexFamily, class VoidPointer>
-typename rbtree_best_fit<MutexFamily, VoidPointer>::multiallocation_iterator
- rbtree_best_fit<MutexFamily, VoidPointer>::priv_allocate_many
- ( std::size_t elem_size, std::size_t min_elements
- , std::size_t preferred_elements, std::size_t &received_elements)
-{
- //Calculate the total size of all requests
- const std::size_t elem_units = priv_get_total_units(elem_size);
- const std::size_t total_min_usr_units = min_elements*elem_units - AllocatedCtrlUnits;
- const std::size_t total_preferred_usr_units = preferred_elements*elem_units - AllocatedCtrlUnits;
-
- std::size_t received_size;
- std::pair<void *, bool> ret = priv_allocate
- ( allocate_new, total_min_usr_units*Alignment
- , total_preferred_usr_units*Alignment, received_size, 0);
- if(!ret.first){
- received_elements = (received_size + AllocatedCtrlBytes)/elem_units;
- return multiallocation_iterator();
- }
-
- block_ctrl *block = reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(ret.first) - AllocatedCtrlBytes);
- std::size_t received_units = block->m_size;
- char *block_address = (char*)block;
-
- received_elements = received_units/elem_units;
- if(received_elements > preferred_elements){
- received_elements = preferred_elements;
- }
- std::size_t total_request_units = 0;
- {
- for(std::size_t i = 0; i < received_elements; ++i){
- //If all have different size, we have to calculate it each iteration
- //This is the position where the new block must be created
- block_ctrl *new_block = new(block_address)block_ctrl;
- //The last block should take all the remaining space
- if((i + 1) == received_elements){
- new_block->m_size = received_units - (received_elements-1)*elem_units;
- }
- else{
- new_block->m_size = elem_units;
- }
- priv_tail_size(new_block, new_block->m_size);
- priv_mark_as_allocated_block(new_block);
- block_address += new_block->m_size*Alignment;
- total_request_units += new_block->m_size;
- }
- assert(total_request_units == received_units);
- }
- return multiallocation_iterator(block, received_elements);
-}
-template<class MutexFamily, class VoidPointer>
inline
typename rbtree_best_fit<MutexFamily, VoidPointer>::block_ctrl *
rbtree_best_fit<MutexFamily, VoidPointer>::priv_get_block(const void *ptr)
@@ -1149,44 +840,6 @@
}
template<class MutexFamily, class VoidPointer>
-inline
-std::size_t rbtree_best_fit<MutexFamily, VoidPointer>::
- priv_ceil_units(std::size_t size)
-{
- return detail::get_rounded_size(size, Alignment)/Alignment;
-}
-
-template<class MutexFamily, class VoidPointer>
-inline
-std::size_t rbtree_best_fit<MutexFamily, VoidPointer>::
- priv_floor_units(std::size_t size)
-{ return size/Alignment; }
-
-template<class MutexFamily, class VoidPointer>
-inline
-std::size_t rbtree_best_fit<MutexFamily, VoidPointer>::
- priv_multiple_of_units(std::size_t size)
-{ return detail::get_rounded_size(size, Alignment); }
-
-template<class MutexFamily, class VoidPointer>
-inline
-void rbtree_best_fit<MutexFamily, VoidPointer>::
- priv_check_alignment(const void *ptr)
-{
- const std::size_t remaining(std::size_t(ptr) & AlignmentMask);
- if(remaining){
- const void *p = (void*)(std::size_t(ptr) & ~AlignmentMask);
- (void)p;
- for(std::size_t i = 1; i < remaining; ++i){
- BOOST_ASSERT(detail::char_ptr_cast(p)[i] == (char)i);
- }
- }
- else{
- BOOST_ASSERT(((std::size_t)ptr) % Alignment == 0);
- }
-}
-
-template<class MutexFamily, class VoidPointer>
bool rbtree_best_fit<MutexFamily, VoidPointer>::
priv_expand (void *ptr
,const std::size_t min_size
@@ -1207,8 +860,8 @@
return true;
//Now translate it to Alignment units
- const std::size_t min_user_units = priv_ceil_units(min_size);
- const std::size_t preferred_user_units = priv_ceil_units(preferred_size);
+ const std::size_t min_user_units = algo_impl_t::ceil_units(min_size);
+ const std::size_t preferred_user_units = algo_impl_t::ceil_units(preferred_size);
//Some parameter checks
assert(min_user_units <= preferred_user_units);
@@ -1240,7 +893,7 @@
//Check if we can split the next one in two parts
if((merged_units - intended_units) >= BlockCtrlUnits){
//Now we have to update the data in the tree
- m_header.m_imultiset.erase(Imultiset::iterator_to(*next_block));
+ m_header.m_imultiset.erase(Imultiset::s_iterator_to(*next_block));
//This block is bigger than needed, split it in
//two blocks, the first one will be merged and
@@ -1267,7 +920,7 @@
//There is no free space to create a new node: just merge both blocks
else{
//Now we have to update the data in the tree
- m_header.m_imultiset.erase(Imultiset::iterator_to(*next_block));
+ m_header.m_imultiset.erase(Imultiset::s_iterator_to(*next_block));
//Write the new length
block->m_size = merged_units;
@@ -1280,80 +933,6 @@
return true;
}
-template<class MutexFamily, class VoidPointer>
-bool rbtree_best_fit<MutexFamily, VoidPointer>::
- priv_shrink (void *ptr
- ,const std::size_t max_size
- ,const std::size_t preferred_size
- ,std::size_t &received_size)
-{
- //Obtain the real block
- block_ctrl *block = priv_get_block(ptr);
- std::size_t old_block_units = block->m_size;
-
- //The block must be marked as allocated
- assert(priv_is_allocated_block(block));
-
- //Check if alignment and block size are right
- priv_check_alignment(ptr);
-
- //Put this to a safe value
- received_size = (old_block_units - AllocatedCtrlUnits)*Alignment;
-
- //Now translate it to Alignment units
- const std::size_t max_user_units = priv_floor_units(max_size);
- const std::size_t preferred_user_units = priv_ceil_units(preferred_size);
-
- //Check if rounded max and preferred are possible correct
- if(max_user_units < preferred_user_units)
- return false;
-
- //Check if the block is smaller than the requested minimum
- std::size_t old_user_units = old_block_units - AllocatedCtrlUnits;
-
- if(old_user_units < preferred_user_units)
- return false;
-
- //If the block is smaller than the requested minimum
- if(old_user_units == preferred_user_units)
- return true;
-
- std::size_t shrunk_user_units =
- ((BlockCtrlUnits - AllocatedCtrlUnits) > preferred_user_units)
- ? (BlockCtrlUnits - AllocatedCtrlUnits)
- : preferred_user_units;
-
- //Some parameter checks
- if(max_user_units < shrunk_user_units)
- return false;
-
- //We must be able to create at least a new empty block
- if((old_user_units - shrunk_user_units) < BlockCtrlUnits ){
- return false;
- }
-
- //Now we can just rewrite the size of the old buffer
- block->m_size = shrunk_user_units + AllocatedCtrlUnits;
- assert(block->m_size >= BlockCtrlUnits);
- priv_tail_size(block, block->m_size);
-
- //Update new size
- received_size = shrunk_user_units*Alignment;
-
- //We create the new block
- block_ctrl *new_block = new(reinterpret_cast<block_ctrl*>
- (detail::char_ptr_cast(block) + block->m_size*Alignment)) block_ctrl;
-
- //Write control data to simulate this new block was previously allocated
- //and deallocate it
- priv_mark_as_allocated_block(new_block);
- new_block->m_size = old_block_units - block->m_size;
- assert(new_block->m_size >= BlockCtrlUnits);
- priv_tail_size(new_block, new_block->m_size);
- this->priv_deallocate(priv_get_user_buffer(new_block));
- return true;
-}
-
template<class MutexFamily, class VoidPointer> inline
void rbtree_best_fit<MutexFamily, VoidPointer>::priv_tail_size
(typename rbtree_best_fit<MutexFamily, VoidPointer>::block_ctrl *ptr, std::size_t size)
@@ -1404,8 +983,8 @@
,std::size_t &received_size)
{
std::size_t upper_nunits = nunits + BlockCtrlUnits;
- imultiset_iterator ittree = Imultiset::iterator_to(*block);
-
+ imultiset_iterator it_old = Imultiset::s_iterator_to(*block);
+/*
if (block->m_size >= upper_nunits){
//Now we have to update the data in the tree
m_header.m_imultiset.erase(ittree);
@@ -1436,7 +1015,49 @@
assert(0);
return 0;
}
+*/
+ if (block->m_size >= upper_nunits){
+ //This block is bigger than needed, split it in
+ //two blocks, the first's size will be "units" and
+ //the second's size "block->m_size-units"
+ std::size_t block_old_size = block->m_size;
+ block->m_size = nunits;
+ assert(block->m_size >= BlockCtrlUnits);
+ priv_tail_size(block, block->m_size);
+
+ //This is the remaining block
+ block_ctrl *new_block = new(reinterpret_cast<block_ctrl*>
+ (detail::char_ptr_cast(block) + Alignment*nunits))block_ctrl;
+ new_block->m_size = block_old_size - nunits;
+ assert(new_block->m_size >= BlockCtrlUnits);
+ priv_tail_size(new_block, new_block->m_size);
+ priv_mark_as_free_block(new_block);
+ imultiset_iterator it_hint;
+ if(it_old == m_header.m_imultiset.begin()
+ || (--imultiset_iterator(it_old))->m_size < new_block->m_size){
+ //option a: slow but secure
+ //m_header.m_imultiset.insert(m_header.m_imultiset.erase(it_old), *new_block);
+ //option b: Construct an empty node and swap
+ //Imultiset::init_node(*new_block);
+ //block->swap_nodes(*new_block);
+ //option c: replace the node directly
+ m_header.m_imultiset.replace_node(Imultiset::s_iterator_to(*it_old), *new_block);
+ }
+ else{
+ //Now we have to update the data in the tree
+ m_header.m_imultiset.erase(it_old);
+ m_header.m_imultiset.insert(m_header.m_imultiset.begin(), *new_block);
+ }
+
+ }
+ else if (block->m_size >= nunits){
+ m_header.m_imultiset.erase(it_old);
+ }
+ else{
+ assert(0);
+ return 0;
+ }
//We need block_ctrl for deallocation stuff, so
//return memory user can overwrite
m_header.m_allocated += block->m_size*Alignment;
@@ -1446,7 +1067,7 @@
priv_mark_as_allocated_block(block);
//Check alignment
- priv_check_alignment(block);
+ algo_impl_t::check_alignment(block);
//Clear the memory occupied by the tree hook, since this won't be
//cleared with zero_free_memory
@@ -1477,7 +1098,7 @@
assert(block->m_size == priv_tail_size(block));
//Check if alignment and block size are right
- priv_check_alignment(addr);
+ algo_impl_t::check_alignment(addr);
std::size_t block_old_size = Alignment*block->m_size;
assert(m_header.m_allocated >= block_old_size);
@@ -1496,7 +1117,7 @@
block->m_size += next_block->m_size;
assert(block->m_size >= BlockCtrlUnits);
priv_tail_size(block, block->m_size);
- m_header.m_imultiset.erase(Imultiset::iterator_to(*next_block));
+ m_header.m_imultiset.erase(Imultiset::s_iterator_to(*next_block));
}
//Get the previous block
@@ -1510,7 +1131,7 @@
prev_block->m_size += block->m_size;
assert(prev_block->m_size >= BlockCtrlUnits);
priv_tail_size(prev_block, prev_block->m_size);
- m_header.m_imultiset.erase(Imultiset::iterator_to(*prev_block));
+ m_header.m_imultiset.erase(Imultiset::s_iterator_to(*prev_block));
block_to_insert = prev_block;
}
Modified: branches/bcbboost/boost/interprocess/mem_algo/simple_seq_fit.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/mem_algo/simple_seq_fit.hpp (original)
+++ branches/bcbboost/boost/interprocess/mem_algo/simple_seq_fit.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -22,15 +22,14 @@
#include <boost/interprocess/mem_algo/detail/simple_seq_fit_impl.hpp>
#include <boost/interprocess/offset_ptr.hpp>
-/*!\file
- Describes sequential fit algorithm used to allocate objects in shared memory.
-*/
+//!\file
+//!Describes sequential fit algorithm used to allocate objects in shared memory.
namespace boost {
namespace interprocess {
-/*!This class implements the simple sequential fit algorithm with a simply
- linked list of free buffers.*/
+//!This class implements the simple sequential fit algorithm with a simply
+//!linked list of free buffers.
template<class MutexFamily, class VoidPointer>
class simple_seq_fit
: public detail::simple_seq_fit_impl<MutexFamily, VoidPointer>
@@ -40,9 +39,9 @@
/// @endcond
public:
- /*!Constructor. "size" is the total size of the managed memory segment,
- "extra_hdr_bytes" indicates the extra bytes beginning in the sizeof(simple_seq_fit)
- offset that the allocator should not use at all.*/
+ //!Constructor. "size" is the total size of the managed memory segment,
+ //!"extra_hdr_bytes" indicates the extra bytes beginning in the sizeof(simple_seq_fit)
+ //!offset that the allocator should not use at all.*/
simple_seq_fit (std::size_t size, std::size_t extra_hdr_bytes)
: base_t(size, extra_hdr_bytes){}
};
Modified: branches/bcbboost/boost/interprocess/offset_ptr.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/offset_ptr.hpp (original)
+++ branches/bcbboost/boost/interprocess/offset_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -25,10 +25,10 @@
#include <boost/assert.hpp>
#include <iterator>
-/*!\file
- Describes a smart pointer that stores the offset between this pointer and
- target pointee, called offset_ptr.
-*/
+//!\file
+//!Describes a smart pointer that stores the offset between this pointer and
+//!target pointee, called offset_ptr.
+
namespace boost {
//Predeclarations
@@ -40,12 +40,12 @@
namespace interprocess {
-/*!A smart pointer that stores the offset between between the pointer and the
- the object it points. This allows offset allows special properties, since
- the pointer is independent from the address address of the pointee, if the
- pointer and the pointee are still separated by the same offset. This feature
- converts offset_ptr in a smart pointer that can be placed in shared memory and
- memory mapped files mapped in different addresses in every process.*/
+//!A smart pointer that stores the offset between between the pointer and the
+//!the object it points. This allows offset allows special properties, since
+//!the pointer is independent from the address address of the pointee, if the
+//!pointer and the pointee are still separated by the same offset. This feature
+//!converts offset_ptr in a smart pointer that can be placed in shared memory and
+//!memory mapped files mapped in different addresses in every process.
template <class PointedType>
class offset_ptr
{
@@ -98,113 +98,134 @@
public: //Public Functions
- /*!Constructor from raw pointer (allows "0" pointer conversion). Never throws.*/
+ //!Constructor from raw pointer (allows "0" pointer conversion).
+ //!Never throws.
offset_ptr(pointer ptr = 0) { this->set_offset(ptr); }
- /*!Constructor from other pointer. Never throws.*/
+ //!Constructor from other pointer.
+ //!Never throws.
template <class T>
offset_ptr(T *ptr)
{ pointer p (ptr); (void)p; this->set_offset(p); }
- /*!Constructor from other offset_ptr */
+ //!Constructor from other offset_ptr
+ //!Never throws.
offset_ptr(const offset_ptr& ptr)
{ this->set_offset(ptr.get()); }
- /*!Constructor from other offset_ptr. If pointers of pointee types are
- convertible, offset_ptrs will be convertibles. Never throws.*/
+ //!Constructor from other offset_ptr. If pointers of pointee types are
+ //!convertible, offset_ptrs will be convertibles. Never throws.
template<class T2>
offset_ptr(const offset_ptr<T2> &ptr)
{ pointer p(ptr.get()); (void)p; this->set_offset(p); }
- /*!Emulates static_cast operator. Never throws. */
+ //!Emulates static_cast operator.
+ //!Never throws.
template<class Y>
offset_ptr(const offset_ptr<Y> & r, detail::static_cast_tag)
{ this->set_offset(static_cast<PointedType*>(r.get())); }
- /*!Emulates const_cast operator. Never throws.*/
+ //!Emulates const_cast operator.
+ //!Never throws.
template<class Y>
offset_ptr(const offset_ptr<Y> & r, detail::const_cast_tag)
{ this->set_offset(const_cast<PointedType*>(r.get())); }
- /*!Emulates dynamic_cast operator. Never throws.*/
+ //!Emulates dynamic_cast operator.
+ //!Never throws.
template<class Y>
offset_ptr(const offset_ptr<Y> & r, detail::dynamic_cast_tag)
{ this->set_offset(dynamic_cast<PointedType*>(r.get())); }
- /*!Emulates reinterpret_cast operator. Never throws.*/
+ //!Emulates reinterpret_cast operator.
+ //!Never throws.
template<class Y>
offset_ptr(const offset_ptr<Y> & r, detail::reinterpret_cast_tag)
{ this->set_offset(reinterpret_cast<PointedType*>(r.get())); }
- /*!Obtains raw pointer from offset. Never throws.*/
+ //!Obtains raw pointer from offset.
+ //!Never throws.
pointer get()const
{ return (pointer)this->get_pointer(); }
- /*!Pointer-like -> operator. It can return 0 pointer. Never throws.*/
+ //!Pointer-like -> operator. It can return 0 pointer.
+ //!Never throws.
pointer operator->() const
{ return this->get(); }
- /*!Dereferencing operator, if it is a null offset_ptr behavior
- is undefined. Never throws.*/
+ //!Dereferencing operator, if it is a null offset_ptr behavior
+ //! is undefined. Never throws.
reference operator* () const
{ return *(this->get()); }
- /*!Indexing operator. Never throws.*/
+ //!Indexing operator.
+ //!Never throws.
reference operator[](std::ptrdiff_t idx) const
{ return this->get()[idx]; }
- /*!Assignment from pointer (saves extra conversion). Never throws.*/
+ //!Assignment from pointer (saves extra conversion).
+ //!Never throws.
offset_ptr& operator= (pointer from)
{ this->set_offset(from); return *this; }
- /*!Assignment from other offset_ptr. Never throws.*/
+ //!Assignment from other offset_ptr.
+ //!Never throws.
offset_ptr& operator= (const offset_ptr & pt)
{ pointer p(pt.get()); (void)p; this->set_offset(p); return *this; }
- /*!Assignment from related offset_ptr. If pointers of pointee types
- are assignable, offset_ptrs will be assignable. Never throws.*/
+ //!Assignment from related offset_ptr. If pointers of pointee types
+ //! are assignable, offset_ptrs will be assignable. Never throws.
template <class T2>
offset_ptr& operator= (const offset_ptr<T2> & pt)
{ pointer p(pt.get()); this->set_offset(p); return *this; }
- /*!offset_ptr + std::ptrdiff_t. Never throws.*/
+ //!offset_ptr + std::ptrdiff_t.
+ //!Never throws.
offset_ptr operator+ (std::ptrdiff_t offset) const
{ return offset_ptr(this->get()+offset); }
- /*!offset_ptr - std::ptrdiff_t. Never throws.*/
+ //!offset_ptr - std::ptrdiff_t.
+ //!Never throws.
offset_ptr operator- (std::ptrdiff_t offset) const
{ return offset_ptr(this->get()-offset); }
- /*!offset_ptr += std::ptrdiff_t. Never throws.*/
+ //!offset_ptr += std::ptrdiff_t.
+ //!Never throws.
offset_ptr &operator+= (std::ptrdiff_t offset)
{ this->inc_offset(offset * sizeof (PointedType)); return *this; }
- /*!offset_ptr -= std::ptrdiff_t. Never throws.*/
+ //!offset_ptr -= std::ptrdiff_t.
+ //!Never throws.
offset_ptr &operator-= (std::ptrdiff_t offset)
{ this->dec_offset(offset * sizeof (PointedType)); return *this; }
- /*!++offset_ptr. Never throws.*/
+ //!++offset_ptr.
+ //!Never throws.
offset_ptr& operator++ (void)
{ this->inc_offset(sizeof (PointedType)); return *this; }
- /*!offset_ptr++. Never throws.*/
+ //!offset_ptr++.
+ //!Never throws.
offset_ptr operator++ (int)
{ offset_ptr temp(*this); ++*this; return temp; }
- /*!--offset_ptr. Never throws.*/
+ //!--offset_ptr.
+ //!Never throws.
offset_ptr& operator-- (void)
{ this->dec_offset(sizeof (PointedType)); return *this; }
- /*!offset_ptr--. Never throws.*/
+ //!offset_ptr--.
+ //!Never throws.
offset_ptr operator-- (int)
{ offset_ptr temp(*this); --*this; return temp; }
- /*!safe bool conversion operator. Never throws.*/
+ //!safe bool conversion operator.
+ //!Never throws.
operator unspecified_bool_type() const
{ return this->get()? &self_t::unspecified_bool_type_func : 0; }
- /*!Not operator. Not needed in theory, but improves portability.
- Never throws.*/
+ //!Not operator. Not needed in theory, but improves portability.
+ //!Never throws
bool operator! () const
{ return this->get() == 0; }
/*
@@ -217,65 +238,76 @@
*/
};
-/*!offset_ptr<T1> == offset_ptr<T2>. Never throws.*/
+//!offset_ptr<T1> == offset_ptr<T2>.
+//!Never throws.
template<class T1, class T2>
inline bool operator== (const offset_ptr<T1> &pt1,
const offset_ptr<T2> &pt2)
{ return pt1.get() == pt2.get(); }
-/*!offset_ptr<T1> != offset_ptr<T2>. Never throws.*/
+//!offset_ptr<T1> != offset_ptr<T2>.
+//!Never throws.
template<class T1, class T2>
inline bool operator!= (const offset_ptr<T1> &pt1,
const offset_ptr<T2> &pt2)
{ return pt1.get() != pt2.get(); }
-/*!offset_ptr<T1> < offset_ptr<T2>. Never throws.*/
+//!offset_ptr<T1> < offset_ptr<T2>.
+//!Never throws.
template<class T1, class T2>
inline bool operator< (const offset_ptr<T1> &pt1,
const offset_ptr<T2> &pt2)
{ return pt1.get() < pt2.get(); }
-/*!offset_ptr<T1> <= offset_ptr<T2>. Never throws.*/
+//!offset_ptr<T1> <= offset_ptr<T2>.
+//!Never throws.
template<class T1, class T2>
inline bool operator<= (const offset_ptr<T1> &pt1,
const offset_ptr<T2> &pt2)
{ return pt1.get() <= pt2.get(); }
-/*!offset_ptr<T1> > offset_ptr<T2>. Never throws.*/
+//!offset_ptr<T1> > offset_ptr<T2>.
+//!Never throws.
template<class T1, class T2>
inline bool operator> (const offset_ptr<T1> &pt1,
const offset_ptr<T2> &pt2)
{ return pt1.get() > pt2.get(); }
-/*!offset_ptr<T1> >= offset_ptr<T2>. Never throws.*/
+//!offset_ptr<T1> >= offset_ptr<T2>.
+//!Never throws.
template<class T1, class T2>
inline bool operator>= (const offset_ptr<T1> &pt1,
const offset_ptr<T2> &pt2)
{ return pt1.get() >= pt2.get(); }
-/*!operator<< */
+//!operator<<
+//!for offset ptr
template<class E, class T, class Y>
inline std::basic_ostream<E, T> & operator<<
(std::basic_ostream<E, T> & os, offset_ptr<Y> const & p)
{ return os << p.get(); }
-/*!operator>> */
+//!operator>>
+//!for offset ptr
template<class E, class T, class Y>
inline std::basic_istream<E, T> & operator>>
(std::basic_istream<E, T> & os, offset_ptr<Y> & p)
{ Y * tmp; return os >> tmp; p = tmp; }
-/*!std::ptrdiff_t + offset_ptr */
+//!std::ptrdiff_t + offset_ptr
+//!operation
template<class T>
inline offset_ptr<T> operator+(std::ptrdiff_t diff, const offset_ptr<T>& right)
{ return right + diff; }
-/*!offset_ptr - offset_ptr */
+//!offset_ptr - offset_ptr
+//!operation
template<class T, class T2>
inline std::ptrdiff_t operator- (const offset_ptr<T> &pt, const offset_ptr<T2> &pt2)
{ return pt.get()- pt2.get(); }
-/*!swap specialization */
+//!swap specialization
+//!for offset_ptr
template<class T>
inline void swap (boost::interprocess::offset_ptr<T> &pt,
boost::interprocess::offset_ptr<T> &pt2)
@@ -343,8 +375,8 @@
//#if !defined(_MSC_VER) || (_MSC_VER >= 1400)
namespace interprocess {
//#endif
-/*!get_pointer() enables boost::mem_fn to recognize offset_ptr.
- Never throws.*/
+//!get_pointer() enables boost::mem_fn to recognize offset_ptr.
+//!Never throws.
template<class T>
inline T * get_pointer(boost::interprocess::offset_ptr<T> const & p)
{ return p.get(); }
Modified: branches/bcbboost/boost/interprocess/segment_manager.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/segment_manager.hpp (original)
+++ branches/bcbboost/boost/interprocess/segment_manager.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -30,6 +30,8 @@
#include <boost/interprocess/offset_ptr.hpp>
#include <boost/interprocess/indexes/iset_index.hpp>
#include <boost/interprocess/exceptions.hpp>
+#include <boost/interprocess/allocators/allocator.hpp>
+#include <boost/interprocess/smart_ptr/deleter.hpp>
#include <cstddef> //std::size_t
#include <string> //char_traits
#include <new> //std::nothrow
@@ -118,10 +120,9 @@
//Experimental. Dont' use.
//!Allocates n_elements of
//!elem_size bytes. Throws bad_alloc on failure.
- multiallocation_iterator allocate_many
- (std::size_t elem_bytes, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements)
+ multiallocation_iterator allocate_many(std::size_t elem_bytes, std::size_t num_elements)
{
- multiallocation_iterator ret = MemoryAlgorithm::allocate_many(elem_bytes, min_elements, preferred_elements, received_elements);
+ multiallocation_iterator ret = MemoryAlgorithm::allocate_many(elem_bytes, num_elements);
if(!ret) throw bad_alloc();
return ret;
}
@@ -138,8 +139,8 @@
//!Allocates n_elements of
//!elem_size bytes. Returns a default constructed iterator on failure.
- multiallocation_iterator allocate_many(std::size_t elem_size, std::size_t min_elements, std::size_t preferred_elements, std::size_t &received_elements, std::nothrow_t)
- { return MemoryAlgorithm::allocate_many(elem_size, min_elements, preferred_elements, received_elements); }
+ multiallocation_iterator allocate_many(std::size_t elem_bytes, std::size_t num_elements, std::nothrow_t)
+ { return MemoryAlgorithm::allocate_many(elem_bytes, num_elements); }
//!Allocates n_elements, each one of
//!element_lenghts[i]*sizeof_element bytes.
@@ -208,7 +209,8 @@
bool check_sanity()
{ return MemoryAlgorithm::check_sanity(); }
- //!Writes to zero free memory (memory not yet allocated) of the memory algorithm
+ //!Writes to zero free memory (memory not yet allocated)
+ //!of the memory algorithm
void zero_free_memory()
{ MemoryAlgorithm::zero_free_memory(); }
@@ -612,6 +614,35 @@
(m_header.m_unique_index.end(), unique_transform());
}
+ //!This is the default allocator to allocate types T
+ //!from this managed segment
+ template<class T>
+ struct allocator
+ {
+ typedef boost::interprocess::allocator<T, segment_manager> type;
+ };
+
+ //!Returns an instance of the default allocator for type T
+ //!initialized that allocates memory from this segment manager.
+ template<class T>
+ typename allocator<T>::type
+ get_allocator()
+ { return typename allocator<T>::type(this); }
+
+ //!This is the default deleter to delete types T
+ //!from this managed segment.
+ template<class T>
+ struct deleter
+ {
+ typedef boost::interprocess::deleter<T, segment_manager> type;
+ };
+
+ //!Returns an instance of the default allocator for type T
+ //!initialized that allocates memory from this segment manager.
+ template<class T>
+ typename deleter<T>::type
+ get_deleter()
+ { return typename deleter<T>::type(this); }
/// @cond
//!Generic named/anonymous new function. Offers all the possibilities,
Modified: branches/bcbboost/boost/interprocess/shared_memory_object.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/shared_memory_object.hpp (original)
+++ branches/bcbboost/boost/interprocess/shared_memory_object.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -63,7 +63,7 @@
//!access mode "mode". If the file previously exists, it tries to open it with mode "mode".
//!Otherwise throws an error.
shared_memory_object(open_or_create_t, const char *name, mode_t mode)
- { this->priv_open_or_create(detail::DoCreateOrOpen, name, mode); }
+ { this->priv_open_or_create(detail::DoOpenOrCreate, name, mode); }
//!Tries to open a shared memory object with name "name", with the access mode "mode".
//!If the file does not previously exist, it throws an error.
@@ -105,15 +105,20 @@
//!Swaps the shared_memory_objects. Does not throw
void swap(shared_memory_object &other);
- //!Erases a shared memory object from the system. Never throws
+ //!Erases a shared memory object from the system.
+ //!Returns false on error. Never throws
static bool remove(const char *name);
//!Sets the size of the shared memory mapping
void truncate(offset_t length);
- //!Closes the shared memory mapping. All mapped regions are still
- //!valid after destruction. The shared memory object still exists and
- //!can be newly opened.
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. All mapped regions are still
+ //!valid after destruction. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~shared_memory_object();
//!Returns the name of the file.
@@ -207,7 +212,7 @@
case detail::DoCreate:
m_handle = detail::create_new_file(shmfile.c_str(), mode, true);
break;
- case detail::DoCreateOrOpen:
+ case detail::DoOpenOrCreate:
m_handle = detail::create_or_open_file(shmfile.c_str(), mode, true);
break;
default:
@@ -275,7 +280,7 @@
mode_t mode)
{
bool slash_added = filename[0] != '/';
- //First add precedding "/"
+ //First add preceding "/"
m_filename.clear();
if(slash_added){
m_filename = '/';
@@ -302,7 +307,7 @@
case detail::DoCreate:
oflag |= (O_CREAT | O_EXCL);
break;
- case detail::DoCreateOrOpen:
+ case detail::DoOpenOrCreate:
oflag |= O_CREAT;
break;
default:
@@ -334,7 +339,7 @@
{
try{
std::string file_str;
- //First add precedding "/"
+ //First add preceding "/"
if(filename[0] != '/'){
file_str = '/';
}
Modified: branches/bcbboost/boost/interprocess/smart_ptr/detail/shared_count.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/detail/shared_count.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/detail/shared_count.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -4,7 +4,7 @@
//
// (C) Copyright Peter Dimov and Multi Media Ltd. 2001, 2002, 2003
// (C) Copyright Peter Dimov 2004-2005
-// (C) Copyright Ion Gaztanaga 2006. Distributed under the Boost
+// (C) Copyright Ion Gaztanaga 2006-2007. 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)
//
@@ -24,7 +24,6 @@
#include <boost/interprocess/detail/workaround.hpp>
#include <boost/checked_delete.hpp>
-#include <boost/throw_exception.hpp>
#include <boost/interprocess/smart_ptr/detail/bad_weak_ptr.hpp>
#include <boost/interprocess/smart_ptr/detail/sp_counted_impl.hpp>
#include <boost/interprocess/detail/utilities.hpp>
@@ -35,36 +34,36 @@
namespace interprocess {
namespace detail{
-template<class T, class A, class D>
+template<class T, class VoidAllocator, class Deleter>
class weak_count;
-template<class T, class A, class D>
+template<class T, class VoidAllocator, class Deleter>
class shared_count
{
public:
typedef typename detail::pointer_to_other
- <typename A::pointer, T>::type pointer;
+ <typename VoidAllocator::pointer, T>::type pointer;
private:
- typedef sp_counted_impl_pd<A, D> counted_impl;
+ typedef sp_counted_impl_pd<VoidAllocator, Deleter> counted_impl;
typedef typename detail::pointer_to_other
- <typename A::pointer, counted_impl>::type counted_impl_ptr;
+ <typename VoidAllocator::pointer, counted_impl>::type counted_impl_ptr;
typedef typename detail::pointer_to_other
- <typename A::pointer, sp_counted_base>::type counted_base_ptr;
- typedef typename A::template rebind
+ <typename VoidAllocator::pointer, sp_counted_base>::type counted_base_ptr;
+ typedef typename VoidAllocator::template rebind
<counted_impl>::other counted_impl_allocator;
typedef typename detail::pointer_to_other
- <typename A::pointer, const D>::type const_deleter_pointer;
+ <typename VoidAllocator::pointer, const Deleter>::type const_deleter_pointer;
typedef typename detail::pointer_to_other
- <typename A::pointer, const A>::type const_allocator_pointer;
+ <typename VoidAllocator::pointer, const VoidAllocator>::type const_allocator_pointer;
pointer m_px;
counted_impl_ptr m_pi;
- template <class T2, class A2, class D2>
+ template <class T2, class VoidAllocator2, class Deleter2>
friend class weak_count;
- template <class T2, class A2, class D2>
+ template <class T2, class VoidAllocator2, class Deleter2>
friend class shared_count;
public:
@@ -74,7 +73,7 @@
{}
template <class Ptr>
- shared_count(const Ptr &p, const A &a, D d)
+ shared_count(const Ptr &p, const VoidAllocator &a, Deleter d)
: m_px(p), m_pi(0)
{
BOOST_TRY{
@@ -85,7 +84,7 @@
scoped_ptr<counted_impl,
scoped_ptr_dealloc_functor<counted_impl_allocator> >
deallocator(m_pi, alloc);
- //It's more correct to use A::construct but
+ //It's more correct to use VoidAllocator::construct but
//this needs copy constructor and we don't like it
new(detail::get_pointer(m_pi))counted_impl(p, a, d);
deallocator.release();
@@ -110,18 +109,18 @@
//this is a test
template<class Y>
- explicit shared_count(shared_count<Y, A, D> const & r)
+ explicit shared_count(shared_count<Y, VoidAllocator, Deleter> const & r)
: m_px(r.m_px), m_pi(r.m_pi) // nothrow
{ if( m_pi != 0 ) m_pi->add_ref_copy(); }
//this is a test
template<class Y>
- explicit shared_count(const pointer & ptr, shared_count<Y, A, D> const & r)
+ explicit shared_count(const pointer & ptr, shared_count<Y, VoidAllocator, Deleter> const & r)
: m_px(ptr), m_pi(r.m_pi) // nothrow
{ if( m_pi != 0 ) m_pi->add_ref_copy(); }
/*
- explicit shared_count(weak_count<Y, A, D> const & r)
+ explicit shared_count(weak_count<Y, VoidAllocator, Deleter> const & r)
// throws bad_weak_ptr when r.use_count() == 0
: m_pi( r.m_pi )
{
@@ -131,12 +130,12 @@
}
*/
template<class Y>
- explicit shared_count(weak_count<Y, A, D> const & r)
+ explicit shared_count(weak_count<Y, VoidAllocator, Deleter> const & r)
// throws bad_weak_ptr when r.use_count() == 0
: m_px(r.m_px), m_pi( r.m_pi )
{
if( m_pi == 0 || !m_pi->add_ref_lock() ){
- boost::throw_exception( boost::interprocess::bad_weak_ptr() );
+ throw( boost::interprocess::bad_weak_ptr() );
}
}
@@ -159,7 +158,7 @@
}
template<class Y>
- shared_count & operator= (shared_count<Y, A, D> const & r) // nothrow
+ shared_count & operator= (shared_count<Y, VoidAllocator, Deleter> const & r) // nothrow
{
m_px = r.m_px;
counted_impl_ptr tmp = r.m_pi;
@@ -186,45 +185,45 @@
// const_allocator_pointer get_allocator() const
// { return m_pi ? m_pi->get_allocator() : 0; }
- template<class T2, class A2, class D2>
- bool internal_equal (shared_count<T2, A2, D2> const & other) const
+ template<class T2, class VoidAllocator2, class Deleter2>
+ bool internal_equal (shared_count<T2, VoidAllocator2, Deleter2> const & other) const
{ return this->m_pi == other.m_pi; }
- template<class T2, class A2, class D2>
- bool internal_less (shared_count<T2, A2, D2> const & other) const
+ template<class T2, class VoidAllocator2, class Deleter2>
+ bool internal_less (shared_count<T2, VoidAllocator2, Deleter2> const & other) const
{ return std::less<counted_base_ptr>()(this->m_pi, other.m_pi); }
};
-template<class T, class A, class D, class T2, class A2, class D2> inline
-bool operator==(shared_count<T, A, D> const & a, shared_count<T2, A2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class T2, class VoidAllocator2, class Deleter2> inline
+bool operator==(shared_count<T, VoidAllocator, Deleter> const & a, shared_count<T2, VoidAllocator2, Deleter2> const & b)
{ return a.internal_equal(b); }
-template<class T, class A, class D, class T2, class A2, class D2> inline
-bool operator<(shared_count<T, A, D> const & a, shared_count<T2, A2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class T2, class VoidAllocator2, class Deleter2> inline
+bool operator<(shared_count<T, VoidAllocator, Deleter> const & a, shared_count<T2, VoidAllocator2, Deleter2> const & b)
{ return a.internal_less(b); }
-template<class T, class A, class D>
+template<class T, class VoidAllocator, class Deleter>
class weak_count
{
public:
typedef typename detail::pointer_to_other
- <typename A::pointer, T>::type pointer;
+ <typename VoidAllocator::pointer, T>::type pointer;
private:
- typedef sp_counted_impl_pd<A, D> counted_impl;
+ typedef sp_counted_impl_pd<VoidAllocator, Deleter> counted_impl;
typedef typename detail::pointer_to_other
- <typename A::pointer, counted_impl>::type counted_impl_ptr;
+ <typename VoidAllocator::pointer, counted_impl>::type counted_impl_ptr;
typedef typename detail::pointer_to_other
- <typename A::pointer, sp_counted_base>::type counted_base_ptr;
+ <typename VoidAllocator::pointer, sp_counted_base>::type counted_base_ptr;
pointer m_px;
counted_impl_ptr m_pi;
- template <class T2, class A2, class D2>
+ template <class T2, class VoidAllocator2, class Deleter2>
friend class weak_count;
- template <class T2, class A2, class D2>
+ template <class T2, class VoidAllocator2, class Deleter2>
friend class shared_count;
public:
@@ -233,7 +232,7 @@
{}
template <class Y>
- explicit weak_count(shared_count<Y, A, D> const & r)
+ explicit weak_count(shared_count<Y, VoidAllocator, Deleter> const & r)
: m_px(r.m_px), m_pi(r.m_pi) // nothrow
{ if(m_pi != 0) m_pi->weak_add_ref(); }
@@ -242,7 +241,7 @@
{ if(m_pi != 0) m_pi->weak_add_ref(); }
template<class Y>
- weak_count(weak_count<Y, A, D> const & r)
+ weak_count(weak_count<Y, VoidAllocator, Deleter> const & r)
: m_px(r.m_px), m_pi(r.m_pi) // nothrow
{ if(m_pi != 0) m_pi->weak_add_ref(); }
@@ -250,7 +249,7 @@
{ if(m_pi != 0) m_pi->weak_release(); }
template<class Y>
- weak_count & operator= (shared_count<Y, A, D> const & r) // nothrow
+ weak_count & operator= (shared_count<Y, VoidAllocator, Deleter> const & r) // nothrow
{
m_px = r.m_px;
counted_impl_ptr tmp = r.m_pi;
@@ -273,7 +272,7 @@
{ m_px = ptr; }
template<class Y>
- weak_count & operator= (weak_count<Y, A, D> const& r) // nothrow
+ weak_count & operator= (weak_count<Y, VoidAllocator, Deleter> const& r) // nothrow
{
counted_impl_ptr tmp = r.m_pi;
if(tmp != 0) tmp->weak_add_ref();
@@ -288,21 +287,21 @@
long use_count() const // nothrow
{ return m_pi != 0? m_pi->use_count() : 0; }
- template<class T2, class A2, class D2>
- bool internal_equal (weak_count<T2, A2, D2> const & other) const
+ template<class T2, class VoidAllocator2, class Deleter2>
+ bool internal_equal (weak_count<T2, VoidAllocator2, Deleter2> const & other) const
{ return this->m_pi == other.m_pi; }
- template<class T2, class A2, class D2>
- bool internal_less (weak_count<T2, A2, D2> const & other) const
+ template<class T2, class VoidAllocator2, class Deleter2>
+ bool internal_less (weak_count<T2, VoidAllocator2, Deleter2> const & other) const
{ return std::less<counted_base_ptr>()(this->m_pi, other.m_pi); }
};
-template<class T, class A, class D, class T2, class A2, class D2> inline
-bool operator==(weak_count<T, A, D> const & a, weak_count<T2, A2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class T2, class VoidAllocator2, class Deleter2> inline
+bool operator==(weak_count<T, VoidAllocator, Deleter> const & a, weak_count<T2, VoidAllocator2, Deleter2> const & b)
{ return a.internal_equal(b); }
-template<class T, class A, class D, class T2, class A2, class D2> inline
-bool operator<(weak_count<T, A, D> const & a, weak_count<T2, A2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class T2, class VoidAllocator2, class Deleter2> inline
+bool operator<(weak_count<T, VoidAllocator, Deleter> const & a, weak_count<T2, VoidAllocator2, Deleter2> const & b)
{ return a.internal_less(b); }
} // namespace detail
Modified: branches/bcbboost/boost/interprocess/smart_ptr/enable_shared_from_this.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/enable_shared_from_this.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/enable_shared_from_this.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -21,6 +21,9 @@
#include <boost/interprocess/smart_ptr/weak_ptr.hpp>
#include <boost/interprocess/smart_ptr/shared_ptr.hpp>
+//!\file
+//!Describes an utility to form a shared pointer from this
+
namespace boost{
namespace interprocess{
Modified: branches/bcbboost/boost/interprocess/smart_ptr/intrusive_ptr.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/intrusive_ptr.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/intrusive_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -14,9 +14,8 @@
#ifndef BOOST_INTERPROCESS_INTRUSIVE_PTR_HPP_INCLUDED
#define BOOST_INTERPROCESS_INTRUSIVE_PTR_HPP_INCLUDED
-/*!\file
- Describes an intrusive ownership pointer.
-*/
+//!\file
+//!Describes an intrusive ownership pointer.
#include <boost/interprocess/detail/config_begin.hpp>
#include <boost/interprocess/detail/workaround.hpp>
@@ -31,27 +30,27 @@
namespace boost {
namespace interprocess {
-/*!The intrusive_ptr class template stores a pointer to an object
- with an embedded reference count. intrusive_ptr is parameterized on
- T (the type of the object pointed to) and VoidPointer(a void pointer type
- that defines the type of pointer that intrusive_ptr will store).
- intrusive_ptr<T, void *> defines a class with a T* member whereas
- intrusive_ptr<T, offset_ptr<void> > defines a class with a offset_ptr<T> member.
- Relies on unqualified calls to:
-
- void intrusive_ptr_add_ref(T * p);
- void intrusive_ptr_release(T * p);
-
- with (p != 0)
-
- The object is responsible for destroying itself.*/
+//!The intrusive_ptr class template stores a pointer to an object
+//!with an embedded reference count. intrusive_ptr is parameterized on
+//!T (the type of the object pointed to) and VoidPointer(a void pointer type
+//!that defines the type of pointer that intrusive_ptr will store).
+//!intrusive_ptr<T, void *> defines a class with a T* member whereas
+//!intrusive_ptr<T, offset_ptr<void> > defines a class with a offset_ptr<T> member.
+//!Relies on unqualified calls to:
+//!
+//! void intrusive_ptr_add_ref(T * p);
+//! void intrusive_ptr_release(T * p);
+//!
+//! with (p != 0)
+//!
+//!The object is responsible for destroying itself.
template<class T, class VoidPointer>
class intrusive_ptr
{
public:
- /*!Provides the type of the internal stored pointer.*/
+ //!Provides the type of the internal stored pointer.
typedef typename detail::pointer_to_other<VoidPointer, T>::type pointer;
- /*!Provides the type of the stored pointer.*/
+ //!Provides the type of the stored pointer.
typedef T element_type;
/// @cond
@@ -62,28 +61,29 @@
/// @endcond
public:
- /*!Constructor. Initializes internal pointer to 0. Does not throw*/
+ //!Constructor. Initializes internal pointer to 0.
+ //!Does not throw
intrusive_ptr(): m_ptr(0)
{}
- /*!Constructor. Copies pointer and if "p" is not zero and
- "add_ref" is true calls intrusive_ptr_add_ref(get_pointer(p)).
- Does not throw*/
+ //!Constructor. Copies pointer and if "p" is not zero and
+ //!"add_ref" is true calls intrusive_ptr_add_ref(get_pointer(p)).
+ //!Does not throw
intrusive_ptr(const pointer &p, bool add_ref = true): m_ptr(p)
{
if(m_ptr != 0 && add_ref) intrusive_ptr_add_ref(detail::get_pointer(m_ptr));
}
- /*!Copy constructor. Copies the internal pointer and if "p" is not
- zero calls intrusive_ptr_add_ref(get_pointer(p)). Does not throw*/
+ //!Copy constructor. Copies the internal pointer and if "p" is not
+ //!zero calls intrusive_ptr_add_ref(get_pointer(p)). Does not throw
intrusive_ptr(intrusive_ptr const & rhs)
: m_ptr(rhs.m_ptr)
{
if(m_ptr != 0) intrusive_ptr_add_ref(detail::get_pointer(m_ptr));
}
- /*!Constructor from related. Copies the internal pointer and if "p" is not
- zero calls intrusive_ptr_add_ref(get_pointer(p)). Does not throw*/
+ //!Constructor from related. Copies the internal pointer and if "p" is not
+ //!zero calls intrusive_ptr_add_ref(get_pointer(p)). Does not throw
template<class U> intrusive_ptr
(intrusive_ptr<U, VP> const & rhs)
: m_ptr(rhs.get())
@@ -91,23 +91,23 @@
if(m_ptr != 0) intrusive_ptr_add_ref(detail::get_pointer(m_ptr));
}
- /*!Destructor. If internal pointer is not 0, calls
- intrusive_ptr_release(get_pointer(m_ptr)). Does not throw*/
+ //!Destructor. If internal pointer is not 0, calls
+ //!intrusive_ptr_release(get_pointer(m_ptr)). Does not throw
~intrusive_ptr()
{
if(m_ptr != 0) intrusive_ptr_release(detail::get_pointer(m_ptr));
}
- /*!Assignment operator. Equivalent to intrusive_ptr(r).swap(*this).
- Does not throw*/
+ //!Assignment operator. Equivalent to intrusive_ptr(r).swap(*this).
+ //!Does not throw
intrusive_ptr & operator=(intrusive_ptr const & rhs)
{
this_type(rhs).swap(*this);
return *this;
}
- /*!Assignment from related. Equivalent to intrusive_ptr(r).swap(*this).
- Does not throw*/
+ //!Assignment from related. Equivalent to intrusive_ptr(r).swap(*this).
+ //!Does not throw
template<class U> intrusive_ptr & operator=
(intrusive_ptr<U, VP> const & rhs)
{
@@ -115,43 +115,51 @@
return *this;
}
- /*!Assignment from pointer. Equivalent to intrusive_ptr(r).swap(*this).
- Does not throw*/
+ //!Assignment from pointer. Equivalent to intrusive_ptr(r).swap(*this).
+ //!Does not throw
intrusive_ptr & operator=(pointer rhs)
{
this_type(rhs).swap(*this);
return *this;
}
- /*!Returns a reference to the internal pointer. Does not throw*/
+ //!Returns a reference to the internal pointer.
+ //!Does not throw
pointer &get()
{ return m_ptr; }
- /*!Returns a reference to the internal pointer. Does not throw*/
+ //!Returns a reference to the internal pointer.
+ //!Does not throw
const pointer &get() const
{ return m_ptr; }
- /*!Returns *get(). Does not throw*/
+ //!Returns *get().
+ //!Does not throw
T & operator*() const
{ return *m_ptr; }
- /*!Returns *get(). Does not throw*/
+ //!Returns *get().
+ //!Does not throw
const pointer &operator->() const
{ return m_ptr; }
- /*!Returns get(). Does not throw*/
+ //!Returns get().
+ //!Does not throw
pointer &operator->()
{ return m_ptr; }
- /*!Conversion to boolean. Does not throw*/
+ //!Conversion to boolean.
+ //!Does not throw
operator unspecified_bool_type () const
{ return m_ptr == 0? 0: &this_type::m_ptr; }
- /*!Not operator. Does not throw*/
+ //!Not operator.
+ //!Does not throw
bool operator! () const
{ return m_ptr == 0; }
- /*!Exchanges the contents of the two smart pointers. Does not throw*/
+ //!Exchanges the contents of the two smart pointers.
+ //!Does not throw
void swap(intrusive_ptr & rhs)
{ detail::do_swap(m_ptr, rhs.m_ptr); }
@@ -161,43 +169,50 @@
/// @endcond
};
-/*Returns a.get() == b.get(). Does not throw*/
+//!Returns a.get() == b.get().
+//!Does not throw
template<class T, class U, class VP> inline
bool operator==(intrusive_ptr<T, VP> const & a,
intrusive_ptr<U, VP> const & b)
{ return a.get() == b.get(); }
-/*Returns a.get() != b.get(). Does not throw*/
+//!Returns a.get() != b.get().
+//!Does not throw
template<class T, class U, class VP> inline
bool operator!=(intrusive_ptr<T, VP> const & a,
intrusive_ptr<U, VP> const & b)
{ return a.get() != b.get(); }
-/*Returns a.get() == b. Does not throw*/
+//!Returns a.get() == b.
+//!Does not throw
template<class T, class VP> inline
bool operator==(intrusive_ptr<T, VP> const & a,
const typename intrusive_ptr<T, VP>::pointer &b)
{ return a.get() == b; }
-/*Returns a.get() != b. Does not throw*/
+//!Returns a.get() != b.
+//!Does not throw
template<class T, class VP> inline
bool operator!=(intrusive_ptr<T, VP> const & a,
const typename intrusive_ptr<T, VP>::pointer &b)
{ return a.get() != b; }
-/*Returns a == b.get(). Does not throw*/
+//!Returns a == b.get().
+//!Does not throw
template<class T, class VP> inline
bool operator==(const typename intrusive_ptr<T, VP>::pointer &a,
intrusive_ptr<T, VP> const & b)
{ return a == b.get(); }
-/*Returns a != b.get(). Does not throw*/
+//!Returns a != b.get().
+//!Does not throw
template<class T, class VP> inline
bool operator!=(const typename intrusive_ptr<T, VP>::pointer &a,
intrusive_ptr<T, VP> const & b)
{ return a != b.get(); }
-/*Returns a.get() < b.get(). Does not throw*/
+//!Returns a.get() < b.get().
+//!Does not throw
template<class T, class VP> inline
bool operator<(intrusive_ptr<T, VP> const & a,
intrusive_ptr<T, VP> const & b)
@@ -206,7 +221,8 @@
(a.get(), b.get());
}
-/*!Exchanges the contents of the two intrusive_ptrs. Does not throw*/
+//!Exchanges the contents of the two intrusive_ptrs.
+//!Does not throw
template<class T, class VP> inline
void swap(intrusive_ptr<T, VP> & lhs,
intrusive_ptr<T, VP> & rhs)
@@ -218,7 +234,8 @@
(std::basic_ostream<E, T> & os, intrusive_ptr<Y, VP> const & p)
{ os << p.get(); return os; }
-/*Returns p.get(). Does not throw*/
+//!Returns p.get().
+//!Does not throw
template<class T, class VP>
inline typename boost::interprocess::intrusive_ptr<T, VP>::pointer
get_pointer(intrusive_ptr<T, VP> p)
@@ -260,7 +277,8 @@
/// @cond
#if defined(_MSC_VER) && (_MSC_VER < 1400)
-/*Returns p.get(). Does not throw*/
+//!Returns p.get().
+//!Does not throw
template<class T, class VP>
inline T *get_pointer(boost::interprocess::intrusive_ptr<T, VP> p)
{ return p.get(); }
Modified: branches/bcbboost/boost/interprocess/smart_ptr/scoped_ptr.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/scoped_ptr.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/scoped_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,6 +20,9 @@
#include <boost/interprocess/detail/pointer_type.hpp>
#include <boost/assert.hpp>
+//!\file
+//!Describes the smart pointer scoped_ptr
+
namespace boost {
namespace interprocess {
Modified: branches/bcbboost/boost/interprocess/smart_ptr/shared_ptr.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/shared_ptr.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/shared_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -4,9 +4,10 @@
//
// (C) Copyright Greg Colvin and Beman Dawes 1998, 1999.
// (C) Copyright Peter Dimov 2001, 2002, 2003
-// (C) Copyright Ion Gaztanaga 2006. 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 Ion Gaztanaga 2006-2007.
+// 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)
//
// See http://www.boost.org/libs/interprocess for documentation.
//
@@ -18,14 +19,14 @@
#include <boost/interprocess/detail/config_begin.hpp>
#include <boost/interprocess/detail/workaround.hpp>
-#include <boost/assert.hpp>
#include <boost/interprocess/detail/utilities.hpp>
#include <boost/interprocess/detail/cast_tags.hpp>
#include <boost/assert.hpp>
-#include <boost/throw_exception.hpp>
#include <boost/interprocess/smart_ptr/detail/shared_count.hpp>
#include <boost/interprocess/detail/mpl.hpp>
#include <boost/interprocess/detail/type_traits.hpp>
+#include <boost/interprocess/allocators/allocator.hpp>
+#include <boost/interprocess/smart_ptr/deleter.hpp>
#include <boost/static_assert.hpp>
#include <algorithm> // for std::swap
@@ -33,75 +34,87 @@
#include <typeinfo> // for std::bad_cast
#include <iosfwd> // for std::basic_ostream
+//!\file
+//!Describes the smart pointer shared_ptr
+
namespace boost{
namespace interprocess{
-template<class T, class VA, class D> class weak_ptr;
-template<class T, class VA, class D> class enable_shared_from_this;
+template<class T, class VoidAllocator, class Deleter> class weak_ptr;
+template<class T, class VoidAllocator, class Deleter> class enable_shared_from_this;
namespace detail{
-template<class T, class VA, class D>
+template<class T, class VoidAllocator, class Deleter>
inline void sp_enable_shared_from_this
- (shared_count<T, VA, D> const & pn,
- const typename pointer_to_other <typename shared_count<T, VA, D>::pointer,
- enable_shared_from_this<T, VA, D> >::type &pe,
- const typename shared_count<T, VA, D>::pointer &px)
+ (shared_count<T, VoidAllocator, Deleter> const & pn,
+ const typename pointer_to_other <typename shared_count<T, VoidAllocator, Deleter>::pointer,
+ enable_shared_from_this<T, VoidAllocator, Deleter> >::type &pe,
+ const typename shared_count<T, VoidAllocator, Deleter>::pointer &px)
{
if(pe != 0)
pe->_internal_weak_this._internal_assign(pn);
}
/*
-template<class T, class VA, class D>
-inline void sp_enable_shared_from_this(shared_count<T, VA, D> const &, ...)
+template<class T, class VoidAllocator, class Deleter>
+inline void sp_enable_shared_from_this(shared_count<T, VoidAllocator, Deleter> const &, ...)
{}
*/
} // namespace detail
-/*!shared_ptr stores a pointer to a dynamically allocated object.
- The object pointed to is guaranteed to be deleted when the last shared_ptr pointing to
- it is destroyed or reset. shared_ptr is parameterized on
- T (the type of the object pointed to), VA (the void allocator to be used
- to allocate the auxiliary data) and D (the deleter whose
- operator() will be used to delete the object.
- The internal pointer will be of the same pointer type as typename
- VA::pointer type (that is, if typename VA::pointer is
- offset_ptr<void>, the internal pointer will be offset_ptr<T>).*/
-template<class T, class VA, class D>
+//!shared_ptr stores a pointer to a dynamically allocated object.
+//!The object pointed to is guaranteed to be deleted when the last shared_ptr pointing to
+//!it is destroyed or reset.
+//!
+//!shared_ptr is parameterized on
+//!T (the type of the object pointed to), VoidAllocator (the void allocator to be used
+//!to allocate the auxiliary data) and Deleter (the deleter whose
+//!operator() will be used to delete the object.
+//!
+//!The internal pointer will be of the same pointer type as typename
+//!VoidAllocator::pointer type (that is, if typename VoidAllocator::pointer is
+//!offset_ptr<void>, the internal pointer will be offset_ptr<T>).
+//!
+//!Because the implementation uses reference counting, cycles of shared_ptr
+//!instances will not be reclaimed. For example, if main() holds a
+//!shared_ptr to A, which directly or indirectly holds a shared_ptr back
+//!to A, A's use count will be 2. Destruction of the original shared_ptr
+//!will leave A dangling with a use count of 1.
+//!Use weak_ptr to "break cycles."
+template<class T, class VoidAllocator, class Deleter>
class shared_ptr
{
/// @cond
private:
- typedef shared_ptr<T, VA, D> this_type;
+ typedef shared_ptr<T, VoidAllocator, Deleter> this_type;
/// @endcond
public:
- /*!Provides the type of the stored pointer.*/
+
typedef T element_type;
- /*!Provides the type of the stored pointer.*/
typedef T value_type;
- /*!Provides the type of the internal stored pointer.*/
typedef typename detail::pointer_to_other
- <typename VA::pointer, T>::type pointer;
-
+ <typename VoidAllocator::pointer, T>::type pointer;
typedef typename detail::add_reference
<value_type>::type reference;
typedef typename detail::add_reference
<const value_type>::type const_reference;
typedef typename detail::pointer_to_other
- <typename VA::pointer, const D>::type const_deleter_pointer;
+ <typename VoidAllocator::pointer, const Deleter>::type const_deleter_pointer;
typedef typename detail::pointer_to_other
- <typename VA::pointer, const VA>::type const_allocator_pointer;
+ <typename VoidAllocator::pointer, const VoidAllocator>::type const_allocator_pointer;
- /*!Constructs an empty shared_ptr. Use_count() == 0 && get() == 0.*/
+ public:
+ //!Constructs an empty shared_ptr.
+ //!Use_count() == 0 && get()== 0.
shared_ptr()
: m_pn() // never throws
{}
- /*!Constructs a shared_ptr that owns the pointer p. Auxiliary data will be allocated
- with a copy of a and the object will be deleted with a copy of d.
- Requirements: D and A's copy constructor must not throw.*/
- explicit shared_ptr(const pointer&p, const VA &a = VA(), const D &d = D())
+ //!Constructs a shared_ptr that owns the pointer p. Auxiliary data will be allocated
+ //!with a copy of a and the object will be deleted with a copy of d.
+ //!Requirements: Deleter and A's copy constructor must not throw.
+ explicit shared_ptr(const pointer&p, const VoidAllocator &a = VoidAllocator(), const Deleter &d = Deleter())
: m_pn(p, a, d)
{
//Check that the pointer passed is of the same type that
@@ -112,57 +125,64 @@
//detail::sp_enable_shared_from_this( m_pn, p, p );
}
- /*!If r is empty, constructs an empty shared_ptr. Otherwise, constructs
- a shared_ptr that shares ownership with r. Never throws.*/
+ //!If r is empty, constructs an empty shared_ptr. Otherwise, constructs
+ //!a shared_ptr that shares ownership with r. Never throws.
template<class Y>
- shared_ptr(shared_ptr<Y, VA, D> const & r)
+ shared_ptr(shared_ptr<Y, VoidAllocator, Deleter> const & r)
: m_pn(r.m_pn) // never throws
{}
- /*!Constructs a shared_ptr that shares ownership with r and stores
- a copy of the pointer stored in r.*/
+ //!Constructs a shared_ptr that shares ownership with r and stores
+ //!a copy of the pointer stored in r.
template<class Y>
- explicit shared_ptr(weak_ptr<Y, VA, D> const & r)
+ explicit shared_ptr(weak_ptr<Y, VoidAllocator, Deleter> const & r)
: m_pn(r.m_pn) // may throw
{}
+ /// @cond
template<class Y>
- shared_ptr(shared_ptr<Y, VA, D> const & r, detail::static_cast_tag)
+ shared_ptr(shared_ptr<Y, VoidAllocator, Deleter> const & r, detail::static_cast_tag)
: m_pn( pointer(static_cast<T*>(detail::get_pointer(r.m_pn.get_pointer())))
, r.m_pn)
{}
template<class Y>
- shared_ptr(shared_ptr<Y, VA, D> const & r, detail::const_cast_tag)
+ shared_ptr(shared_ptr<Y, VoidAllocator, Deleter> const & r, detail::const_cast_tag)
: m_pn( pointer(const_cast<T*>(detail::get_pointer(r.m_pn.get_pointer())))
, r.m_pn)
{}
template<class Y>
- shared_ptr(shared_ptr<Y, VA, D> const & r, detail::dynamic_cast_tag)
+ shared_ptr(shared_ptr<Y, VoidAllocator, Deleter> const & r, detail::dynamic_cast_tag)
: m_pn( pointer(dynamic_cast<T*>(detail::get_pointer(r.m_pn.get_pointer())))
, r.m_pn)
{
if(!m_pn.get_pointer()){ // need to allocate new counter -- the cast failed
- m_pn = detail::shared_count<T, VA, D>();
+ m_pn = detail::shared_count<T, VoidAllocator, Deleter>();
}
}
+ /// @endcond
- /*!Equivalent to shared_ptr(r).swap(*this). Never throws*/
+ //!Equivalent to shared_ptr(r).swap(*this).
+ //!Never throws
template<class Y>
- shared_ptr & operator=(shared_ptr<Y, VA, D> const & r)
+ shared_ptr & operator=(shared_ptr<Y, VoidAllocator, Deleter> const & r)
{
m_pn = r.m_pn; // shared_count::op= doesn't throw
return *this;
}
+ //!This is equivalent to:
+ //!this_type().swap(*this);
void reset()
{
this_type().swap(*this);
}
+ //!This is equivalent to:
+ //!this_type(p, a, d).swap(*this);
template<class Pointer>
- void reset(const Pointer &p, const VA &a = VA(), const D &d = D())
+ void reset(const Pointer &p, const VoidAllocator &a = VoidAllocator(), const Deleter &d = Deleter())
{
//Check that the pointer passed is of the same type that
//the pointer the allocator defines or it's a raw pointer
@@ -172,42 +192,57 @@
this_type(p, a, d).swap(*this);
}
+ //!Returns a reference to the
+ //!pointed type
reference operator* () const // never throws
{ BOOST_ASSERT(m_pn.get_pointer() != 0); return *m_pn.get_pointer(); }
+ //!Returns the pointer pointing
+ //!to the owned object
pointer operator-> () const // never throws
{ BOOST_ASSERT(m_pn.get_pointer() != 0); return m_pn.get_pointer(); }
- pointer &operator-> () // never throws
- { BOOST_ASSERT(m_pn.get_pointer() != 0); return m_pn.get_pointer(); }
-
- const pointer &get() const // never throws
- { return m_pn.get_pointer(); }
-
- pointer &get() // never throws
+ //!Returns the pointer pointing
+ //!to the owned object
+ pointer get() const // never throws
{ return m_pn.get_pointer(); }
+ /// @cond
// implicit conversion to "bool"
void unspecified_bool_type_func() const {}
typedef void (this_type::*unspecified_bool_type)() const;
operator unspecified_bool_type() const // never throws
{ return !m_pn.get_pointer() ? 0 : &this_type::unspecified_bool_type_func; }
+ /// @endcond
+ //!Not operator.
+ //!Returns true if this->get() != 0, false otherwise
bool operator! () const // never throws
{ return !m_pn.get_pointer(); }
+ //!Returns use_count() == 1.
+ //!unique() might be faster than use_count()
bool unique() const // never throws
{ return m_pn.unique(); }
+ //!Returns the number of shared_ptr objects, *this included,
+ //!that share ownership with *this, or an unspecified nonnegative
+ //!value when *this is empty.
+ //!use_count() is not necessarily efficient. Use only for
+ //!debugging and testing purposes, not for production code.
long use_count() const // never throws
{ return m_pn.use_count(); }
- void swap(shared_ptr<T, VA, D> & other) // never throws
+ //!Exchanges the contents of the two
+ //!smart pointers.
+ void swap(shared_ptr<T, VoidAllocator, Deleter> & other) // never throws
{ m_pn.swap(other.m_pn); }
- template<class T2, class A2, class D2>
- bool _internal_less(shared_ptr<T2, A2, D2> const & rhs) const
+ /// @cond
+
+ template<class T2, class A2, class Deleter2>
+ bool _internal_less(shared_ptr<T2, A2, Deleter2> const & rhs) const
{ return m_pn < rhs.m_pn; }
const_deleter_pointer get_deleter() const
@@ -216,60 +251,87 @@
// const_allocator_pointer get_allocator() const
// { return m_pn.get_allocator(); }
- /// @cond
private:
- template<class T2, class A2, class D2> friend class shared_ptr;
- template<class T2, class A2, class D2> friend class weak_ptr;
+ template<class T2, class A2, class Deleter2> friend class shared_ptr;
+ template<class T2, class A2, class Deleter2> friend class weak_ptr;
- detail::shared_count<T, VA, D> m_pn; // reference counter
+ detail::shared_count<T, VoidAllocator, Deleter> m_pn; // reference counter
/// @endcond
}; // shared_ptr
-template<class T, class VA, class D, class U, class VA2, class D2> inline
-bool operator==(shared_ptr<T, VA, D> const & a, shared_ptr<U, VA2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class U, class VoidAllocator2, class Deleter2> inline
+bool operator==(shared_ptr<T, VoidAllocator, Deleter> const & a, shared_ptr<U, VoidAllocator2, Deleter2> const & b)
{ return a.get() == b.get(); }
-template<class T, class VA, class D, class U, class VA2, class D2> inline
-bool operator!=(shared_ptr<T, VA, D> const & a, shared_ptr<U, VA2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class U, class VoidAllocator2, class Deleter2> inline
+bool operator!=(shared_ptr<T, VoidAllocator, Deleter> const & a, shared_ptr<U, VoidAllocator2, Deleter2> const & b)
{ return a.get() != b.get(); }
-template<class T, class VA, class D, class U, class VA2, class D2> inline
-bool operator<(shared_ptr<T, VA, D> const & a, shared_ptr<U, VA2, D2> const & b)
+template<class T, class VoidAllocator, class Deleter, class U, class VoidAllocator2, class Deleter2> inline
+bool operator<(shared_ptr<T, VoidAllocator, Deleter> const & a, shared_ptr<U, VoidAllocator2, Deleter2> const & b)
{ return a._internal_less(b); }
-template<class T, class VA, class D> inline
-void swap(shared_ptr<T, VA, D> & a, shared_ptr<T, VA, D> & b)
+template<class T, class VoidAllocator, class Deleter> inline
+void swap(shared_ptr<T, VoidAllocator, Deleter> & a, shared_ptr<T, VoidAllocator, Deleter> & b)
{ a.swap(b); }
-template<class T, class VA, class D, class U> inline
-shared_ptr<T, VA, D> static_pointer_cast(shared_ptr<U, VA, D> const & r)
-{ return shared_ptr<T, VA, D>(r, detail::static_cast_tag()); }
-
-template<class T, class VA, class D, class U> inline
-shared_ptr<T, VA, D> const_pointer_cast(shared_ptr<U, VA, D> const & r)
-{ return shared_ptr<T, VA, D>(r, detail::const_cast_tag()); }
-
-template<class T, class VA, class D, class U> inline
-shared_ptr<T, VA, D> dynamic_pointer_cast(shared_ptr<U, VA, D> const & r)
-{ return shared_ptr<T, VA, D>(r, detail::dynamic_cast_tag()); }
+template<class T, class VoidAllocator, class Deleter, class U> inline
+shared_ptr<T, VoidAllocator, Deleter> static_pointer_cast(shared_ptr<U, VoidAllocator, Deleter> const & r)
+{ return shared_ptr<T, VoidAllocator, Deleter>(r, detail::static_cast_tag()); }
+
+template<class T, class VoidAllocator, class Deleter, class U> inline
+shared_ptr<T, VoidAllocator, Deleter> const_pointer_cast(shared_ptr<U, VoidAllocator, Deleter> const & r)
+{ return shared_ptr<T, VoidAllocator, Deleter>(r, detail::const_cast_tag()); }
+
+template<class T, class VoidAllocator, class Deleter, class U> inline
+shared_ptr<T, VoidAllocator, Deleter> dynamic_pointer_cast(shared_ptr<U, VoidAllocator, Deleter> const & r)
+{ return shared_ptr<T, VoidAllocator, Deleter>(r, detail::dynamic_cast_tag()); }
// get_pointer() enables boost::mem_fn to recognize shared_ptr
-template<class T, class VA, class D> inline
-T * get_pointer(shared_ptr<T, VA, D> const & p)
+template<class T, class VoidAllocator, class Deleter> inline
+T * get_pointer(shared_ptr<T, VoidAllocator, Deleter> const & p)
{ return p.get(); }
// operator<<
-template<class E, class T, class Y, class VA, class D> inline
+template<class E, class T, class Y, class VoidAllocator, class Deleter> inline
std::basic_ostream<E, T> & operator<<
- (std::basic_ostream<E, T> & os, shared_ptr<Y, VA, D> const & p)
+ (std::basic_ostream<E, T> & os, shared_ptr<Y, VoidAllocator, Deleter> const & p)
{ os << p.get(); return os; }
+
+//!Returns the type of a shared pointer
+//!of type T with the allocator boost::interprocess::allocator allocator
+//!and boost::interprocess::deleter deleter
+//!that can be constructed in the given managed segment type.
+template<class T, class ManagedMemory>
+struct managed_shared_ptr
+{
+ typedef typename ManagedMemory::template allocator<void>::type void_allocator;
+ typedef typename ManagedMemory::template deleter<T>::type deleter;
+ typedef shared_ptr< T, void_allocator, deleter> type;
+};
+
+//!Returns an instance of a shared pointer constructed
+//!with the default allocator and deleter from a pointer
+//!of type T that has been allocated in the passed managed segment
+template<class T, class ManagedMemory>
+inline typename managed_shared_ptr<T, ManagedMemory>::type
+ make_managed_shared_ptr(T *constructed_object, ManagedMemory &managed_memory)
+{
+ return typename managed_shared_ptr<T, ManagedMemory>::type
+ ( constructed_object
+ , managed_memory.template get_allocator<void>()
+ , managed_memory.template get_deleter<T>()
+ );
+}
+
+
/*
// get_deleter (experimental)
-template<class T, class VA, class D>
-typename detail::pointer_to_other<shared_ptr<T, VA, D>, D>::type
- get_deleter(shared_ptr<T, VA, D> const & p)
-{ return static_cast<D *>(p._internal_get_deleter(typeid(D))); }
+template<class T, class VoidAllocator, class Deleter>
+typename detail::pointer_to_other<shared_ptr<T, VoidAllocator, Deleter>, Deleter>::type
+ get_deleter(shared_ptr<T, VoidAllocator, Deleter> const & p)
+{ return static_cast<Deleter *>(p._internal_get_deleter(typeid(Deleter))); }
*/
} // namespace interprocess
@@ -277,8 +339,8 @@
#if defined(_MSC_VER) && (_MSC_VER < 1400)
// get_pointer() enables boost::mem_fn to recognize shared_ptr
-template<class T, class VA, class D> inline
-T * get_pointer(boost::interprocess::shared_ptr<T, VA, D> const & p)
+template<class T, class VoidAllocator, class Deleter> inline
+T * get_pointer(boost::interprocess::shared_ptr<T, VoidAllocator, Deleter> const & p)
{ return p.get(); }
#endif
Modified: branches/bcbboost/boost/interprocess/smart_ptr/unique_ptr.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/unique_ptr.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/unique_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -3,7 +3,7 @@
//////////////////////////////////////////////////////////////////////////////
//
// This file is the adaptation for Interprocess of
-// Howard Hinnant's unique_ptr emulation
+// Howard Hinnant's unique_ptr emulation code.
//
// (C) Copyright Ion Gaztanaga 2006. Distributed under the Boost
// Software License, Version 1.0. (See accompanying file
@@ -26,45 +26,15 @@
#include <boost/static_assert.hpp>
#include <boost/interprocess/detail/mpl.hpp>
#include <boost/interprocess/detail/type_traits.hpp>
-//#include <boost/type_traits.hpp>
-//#include <boost/utility/enable_if.hpp>
+#include <boost/interprocess/smart_ptr/deleter.hpp>
#include <cstddef>
+//!\file
+//!Describes the smart pointer unique_ptr
+
namespace boost{
namespace interprocess{
-template <class T>
-struct default_delete
-{
- default_delete() {}
- template <class U> default_delete(const default_delete<U>&) {}
- void operator() (T* ptr) const
- {
- BOOST_STATIC_ASSERT(sizeof(T) > 0);
- delete ptr;
- }
-};
-
-template <class T>
-struct default_delete<T[]>
-{
- void operator() (T* ptr) const
- {
- BOOST_STATIC_ASSERT(sizeof(T) > 0);
- delete [] ptr;
- }
-};
-
-template <class T, std::size_t N>
-struct default_delete<T[N]>
-{
- void operator() (T* ptr, std::size_t) const
- {
- BOOST_STATIC_ASSERT(sizeof(T) > 0);
- delete [] ptr;
- }
-};
-
/// @cond
template <class T, class D> class unique_ptr;
@@ -81,7 +51,34 @@
} //namespace detail {
/// @endcond
-template <class T, class D = default_delete<T> >
+//!Template unique_ptr stores a pointer to an object and deletes that object
+//!using the associated deleter when it is itself destroyed (such as when
+//!leaving block scope.
+//!
+//!The unique_ptr provides a semantics of strict ownership. A unique_ptr owns the
+//!object it holds a pointer to.
+//!
+//!A unique_ptr is not CopyConstructible, nor CopyAssignable, however it is
+//!MoveConstructible and Move-Assignable.
+//!
+//!The uses of unique_ptr include providing exception safety for dynamically
+//!allocated memory, passing ownership of dynamically allocated memory to a
+//!function, and returning dynamically allocated memory from a function
+//!
+//!A client-supplied template argument D must be a
+//!function pointer or functor for which, given a value d of type D and a pointer
+//!ptr to a type T*, the expression d(ptr) is
+//!valid and has the effect of deallocating the pointer as appropriate for that
+//!deleter. D may also be an lvalue-reference to a deleter.
+//!
+//!If the deleter D maintains state, it is intended that this state stay with
+//!the associated pointer as ownership is transferred
+//!from unique_ptr to unique_ptr. The deleter state need never be copied,
+//!only moved or swapped as pointer ownership
+//!is moved around. That is, the deleter need only be MoveConstructible,
+//!MoveAssignable, and Swappable, and need not be CopyConstructible
+//!(unless copied into the unique_ptr) nor CopyAssignable.
+template <class T, class D>
class unique_ptr
{
/// @cond
@@ -95,51 +92,93 @@
typedef D deleter_type;
typedef typename detail::pointer_type<T, D>::type pointer;
- // constructors
+ //!Requires: D must be default constructible, and that construction must not
+ //!throw an exception. D must not be a reference type.
+ //!
+ //!Effects: Constructs a unique_ptr which owns nothing.
+ //!
+ //!Postconditions: get() == 0. get_deleter() returns a reference to a
+ //!default constructed deleter D.
+ //!
+ //!Throws: nothing.
unique_ptr()
- : ptr_(pointer())
+ : ptr_(pointer(0))
{}
+ //!Requires: The expression D()(p) must be well formed. The default constructor
+ //!of D must not throw an exception.
+ //!
+ //!D must not be a reference type.
+ //!
+ //!Effects: Constructs a unique_ptr which owns p.
+ //!
+ //!Postconditions: get() == p. get_deleter() returns a reference to a default constructed deleter D.
+ //!
+ //!Throws: nothing.
explicit unique_ptr(pointer p)
: ptr_(p)
{}
+ //!Requires: The expression d(p) must be well formed.
+ //!
+ //!Postconditions: get() == p. get_deleter() returns a reference to the
+ //!internally stored deleter. If D is a
+ //!reference type then get_deleter() returns a reference to the lvalue d.
+ //!
+ //!Throws: nothing.
unique_ptr(pointer p
,typename detail::if_<detail::is_reference<D>
,D
,typename detail::add_reference<const D>::type>::type d)
: ptr_(p, d)
{}
-/*
- unique_ptr(const unique_ptr& u)
- : ptr_(const_cast<unique_ptr&>(u).release(), u.get_deleter())
- {}
-*/
+
+ //!Requires: If the deleter is not a reference type, construction of the
+ //!deleter D from an lvalue D must not throw an exception.
+ //!
+ //!Effects: Constructs a unique_ptr which owns the pointer which u owns
+ //!(if any). If the deleter is not a reference type, it is move constructed
+ //!from us deleter, otherwise the reference is copy constructed from us deleter.
+ //!
+ //!After the construction, u no longer owns a pointer.
+ //![ Note: The deleter constructor can be implemented with
+ //!std::forward<D>. end note ]
+ //!
+ //!Postconditions: get() == value u.get() had before the construction.
+ //!get_deleter() returns a reference to the internally stored deleter which
+ //!was constructed from u.get_deleter(). If D is a reference type then get_-
+ //!deleter() and u.get_deleter() both reference the same lvalue deleter.
+ //!
+ //!Throws: nothing.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
unique_ptr(detail::moved_object<unique_ptr> u)
- : ptr_(u.get().release(), u.get().get_deleter())
+ : ptr_(u.get().release(), move(u.get().get_deleter()))
{}
#else
unique_ptr(unique_ptr &&u)
- : ptr_(u.release(), u.get_deleter())
+ : ptr_(u.release(), forward<D>(u.get_deleter()))
{}
#endif
-/*
- template <class U, class E>
- unique_ptr(const unique_ptr<U, E>& u,
- typename boost::enable_if_c<
- detail::is_convertible<typename unique_ptr<U, E>::pointer, pointer>::value &&
- detail::is_convertible<E, D>::value &&
- (
- !detail::is_reference<D>::value ||
- detail::is_same<D, E>::value
- )
- ,
- nat
- >::type = nat())
- : ptr_(const_cast<unique_ptr<U,E>&>(u).release(), u.get_deleter())
- {}
-*/
+
+ //!Requires: If D is not a reference type, construction of the deleter
+ //!D from an rvalue of type E must be well formed
+ //!and not throw an exception. If D is a reference type, then E must be
+ //!the same type as D (diagnostic required). unique_ptr<U, E>::pointer
+ //!must be implicitly convertible to pointer.
+ //!
+ //!Effects: Constructs a unique_ptr which owns the pointer which u owns
+ //!(if any). If the deleter is not a reference
+ //!type, it is move constructed from us deleter, otherwise the reference
+ //!is copy constructed from us deleter.
+ //!
+ //!After the construction, u no longer owns a pointer.
+ //!
+ //!postconditions get() == value u.get() had before the construction,
+ //!modulo any required offset adjustments
+ //!resulting from the cast from U* to T*. get_deleter() returns a reference to the internally stored deleter which
+ //!was constructed from u.get_deleter().
+ //!
+ //!Throws: nothing.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
template <class U, class E>
unique_ptr(const detail::moved_object<unique_ptr<U, E> >& u,
@@ -153,7 +192,7 @@
,
nat
>::type = nat())
- : ptr_(const_cast<unique_ptr<U,E>&>(u.get()).release(), u.get().get_deleter())
+ : ptr_(const_cast<unique_ptr<U,E>&>(u.get()).release(), move(u.get().get_deleter()))
{}
#else
template <class U, class E>
@@ -168,66 +207,145 @@
,
nat
>::type = nat())
- : ptr_(const_cast<unique_ptr<U,E>&>(u).release(), u.get_deleter())
+ : ptr_(const_cast<unique_ptr<U,E>&>(u).release(), forward<D>(u.get_deleter()))
{}
#endif
- // destructor
+ //!Effects: If get() == 0 there are no effects. Otherwise get_deleter()(get()).
+ //!
+ //!Throws: nothing.
~unique_ptr()
{ reset(); }
// assignment
- unique_ptr& operator=(const unique_ptr& cu)
+
+ //!Requires: Assignment of the deleter D from an rvalue D must not throw an exception.
+ //!
+ //!Effects: reset(u.release()) followed by a move assignment from us deleter to
+ //!this deleter.
+ //!
+ //!Postconditions: This unique_ptr now owns the pointer which u owned, and u no
+ //!longer owns it.
+ //!
+ //!Returns: *this.
+ //!
+ //!Throws: nothing.
+ #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
+ unique_ptr& operator=(const detail::moved_object<unique_ptr>& u)
+ {
+ reset(u.get().release());
+ ptr_.second() = move(u.get().get_deleter());
+ return *this;
+ }
+ #else
+ unique_ptr(unique_ptr && u)
{
- unique_ptr& u = const_cast<unique_ptr&>(cu);
reset(u.release());
- ptr_.second() = u.get_deleter();
+ ptr_.second() = move(u.get_deleter());
return *this;
}
+ #endif
+ //!Requires: Assignment of the deleter D from an rvalue D must not
+ //!throw an exception. U* must be implicitly convertible to T*.
+ //!
+ //!Effects: reset(u.release()) followed by a move assignment from
+ //!us deleter to this deleter. If either D or E is
+ //!a reference type, then the referenced lvalue deleter participates
+ //!in the move assignment.
+ //!
+ //!Postconditions: This unique_ptr now owns the pointer which u owned,
+ //!and u no longer owns it.
+ //!
+ //!Returns: *this.
+ //!
+ //!Throws: nothing.
template <class U, class E>
- unique_ptr& operator=(const unique_ptr<U, E>& cu)
+ #ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
+ unique_ptr& operator=(const detail::moved_object<unique_ptr<U, E> >& mu)
+ {
+ reset(mu.get().release());
+ ptr_.second() = move(mu.get().get_deleter());
+ return *this;
+ }
+ #else
+ unique_ptr(unique_ptr<U, E> && u)
{
- unique_ptr<U, E>& u = const_cast<unique_ptr<U, E>&>(cu);
reset(u.release());
- ptr_.second() = u.get_deleter();
+ ptr_.second() = move(u.get_deleter());
return *this;
}
+ #endif
+ //!Assigns from the literal 0 or NULL.
+ //!
+ //!Effects: reset().
+ //!
+ //!Postcondition: get() == 0
+ //!
+ //!Returns: *this.
+ //!
+ //!Throws: nothing.
unique_ptr& operator=(int nat::*)
{
reset();
return *this;
}
- // observers
+ //!Requires: get() != 0.
+ //!Returns: *get().
+ //!Throws: nothing.
typename detail::add_reference<T>::type operator*() const
{ return *ptr_.first(); }
+ //!Requires: get() != 0.
+ //!Returns: get().
+ //!Throws: nothing.
pointer operator->() const
{ return ptr_.first(); }
+ //!Returns: The stored pointer.
+ //!Throws: nothing.
pointer get() const
{ return ptr_.first(); }
+ //!Returns: A reference to the stored deleter.
+ //!
+ //!Throws: nothing.
deleter_reference get_deleter()
{ return ptr_.second(); }
+ //!Returns: A const reference to the stored deleter.
+ //!
+ //!Throws: nothing.
deleter_const_reference get_deleter() const
{ return ptr_.second(); }
+ //!Returns: An unspecified value that, when used in boolean
+ //!contexts, is equivalent to get() != 0.
+ //!
+ //!Throws: nothing.
operator int nat::*() const
{ return ptr_.first() ? &nat::for_bool_ : 0; }
- // modifiers
+ //!Postcondition: get() == 0.
+ //!
+ //!Returns: The value get() had at the start of the call to release.
+ //!
+ //!Throws: nothing.
pointer release()
{
pointer tmp = ptr_.first();
- ptr_.first() = pointer();
+ ptr_.first() = 0;
return tmp;
}
- void reset(pointer p = pointer())
+ //!Effects: If p == get() there are no effects. Otherwise get_deleter()(get()).
+ //!
+ //!Postconditions: get() == p.
+ //!
+ //!Throws: nothing.
+ void reset(pointer p = 0)
{
if (ptr_.first() != p){
if (ptr_.first())
@@ -236,6 +354,11 @@
}
}
+ //!Requires: The deleter D is Swappable and will not throw an exception under swap.
+ //!
+ //!Effects: The stored pointers of this and u are exchanged. The stored deleters are swapd (unqualified).
+ //!
+ //!Throws: nothing.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void swap(unique_ptr& u)
{ ptr_.swap(u.ptr_); }
@@ -255,7 +378,6 @@
unique_ptr(const unique_ptr&);
template <class U, class E> unique_ptr(unique_ptr<U, E>&);
template <class U> unique_ptr(U&, typename detail::unique_ptr_error<U>::type = 0);
-
unique_ptr& operator=(unique_ptr&);
template <class U, class E> unique_ptr& operator=(unique_ptr<U, E>&);
@@ -313,10 +435,10 @@
pointer release()
{
pointer tmp = ptr_.first();
- ptr_.first() = pointer();
+ ptr_.first() = 0;
return tmp;
}
- void reset(pointer p = pointer())
+ void reset(pointer p = 0)
{
if (ptr_.first() != p)
{
@@ -354,7 +476,7 @@
static const std::size_t size = N;
// constructors
- unique_ptr() : ptr_(pointer()) {}
+ unique_ptr() : ptr_(0) {}
explicit unique_ptr(pointer p) : ptr_(p) {}
unique_ptr(pointer p, typename if_<
boost::is_reference<D>,
@@ -392,10 +514,10 @@
pointer release()
{
pointer tmp = ptr_.first();
- ptr_.first() = pointer();
+ ptr_.first() = 0;
return tmp;
}
- void reset(pointer p = pointer())
+ void reset(pointer p = 0)
{
if (ptr_.first() != p)
{
@@ -449,7 +571,8 @@
{ return x.get() >= y.get(); }
/// @cond
-/*!This class has move constructor*/
+
+//!This class has move constructor
template <class T, class D>
struct is_movable<unique_ptr<T, D> >
{
@@ -457,6 +580,35 @@
};
/// @endcond
+
+//!Returns the type of a unique pointer
+//!of type T with boost::interprocess::deleter deleter
+//!that can be constructed in the given managed segment type.
+template<class T, class ManagedMemory>
+struct managed_unique_ptr
+{
+ typedef unique_ptr
+ < T
+ , typename ManagedMemory::template deleter<T>::type
+ > type;
+};
+
+//!Returns an instance of the a unique pointer constructed
+//!with boost::interproces::deleter from a pointer
+//!of type T that has been allocated in the passed managed segment
+template<class T, class ManagedMemory>
+inline typename detail::return_type
+ <typename managed_unique_ptr<T, ManagedMemory>::type
+ >::type
+ make_managed_unique_ptr(T *constructed_object, ManagedMemory &managed_memory)
+{
+ typename managed_unique_ptr<T, ManagedMemory>::type to_return
+ ( constructed_object
+ , managed_memory.template get_deleter<T>()
+ );
+ return to_return;
+}
+
} //namespace interprocess{
} //namespace boost{
Modified: branches/bcbboost/boost/interprocess/smart_ptr/weak_ptr.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/smart_ptr/weak_ptr.hpp (original)
+++ branches/bcbboost/boost/interprocess/smart_ptr/weak_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -3,9 +3,10 @@
// This file is the adaptation for Interprocess of boost/weak_ptr.hpp
//
// (C) Copyright Peter Dimov 2001, 2002, 2003
-// (C) Copyright Ion Gaztanaga 2006. 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 Ion Gaztanaga 2006-2007.
+// 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)
//
// See http://www.boost.org/libs/interprocess for documentation.
//
@@ -19,10 +20,32 @@
#include <boost/interprocess/smart_ptr/shared_ptr.hpp>
#include <boost/detail/no_exceptions_support.hpp>
+#include <boost/interprocess/allocators/allocator.hpp>
+#include <boost/interprocess/smart_ptr/deleter.hpp>
+
+//!\file
+//!Describes the smart pointer weak_ptr.
namespace boost{
namespace interprocess{
+//!The weak_ptr class template stores a "weak reference" to an object
+//!that's already managed by a shared_ptr. To access the object, a weak_ptr
+//!can be converted to a shared_ptr using the shared_ptr constructor or the
+//!member function lock. When the last shared_ptr to the object goes away
+//!and the object is deleted, the attempt to obtain a shared_ptr from the
+//!weak_ptr instances that refer to the deleted object will fail: the constructor
+//!will throw an exception of type bad_weak_ptr, and weak_ptr::lock will
+//!return an empty shared_ptr.
+//!
+//!Every weak_ptr meets the CopyConstructible and Assignable requirements
+//!of the C++ Standard Library, and so can be used in standard library containers.
+//!Comparison operators are supplied so that weak_ptr works with the standard
+//!library's associative containers.
+//!
+//!weak_ptr operations never throw exceptions.
+//!
+//!The class template is parameterized on T, the type of the object pointed to.
template<class T, class A, class D>
class weak_ptr
{
@@ -42,6 +65,8 @@
typedef T element_type;
typedef T value_type;
+ //!Effects: Constructs an empty weak_ptr.
+ //!Postconditions: use_count() == 0.
weak_ptr()
: m_pn() // never throws
{}
@@ -61,6 +86,14 @@
//
// It is not possible to avoid spurious access violations since
// in multithreaded programs r.m_px may be invalidated at any point.
+
+ //!Effects: If r is empty, constructs an empty weak_ptr; otherwise,
+ //!constructs a weak_ptr that shares ownership with r as if by storing a
+ //!copy of the pointer stored in r.
+ //!
+ //!Postconditions: use_count() == r.use_count().
+ //!
+ //!Throws: nothing.
template<class Y>
weak_ptr(weak_ptr<Y, A, D> const & r)
: m_pn(r.m_pn) // never throws
@@ -71,11 +104,24 @@
m_pn.set_pointer(ref.get());
}
+ //!Effects: If r is empty, constructs an empty weak_ptr; otherwise,
+ //!constructs a weak_ptr that shares ownership with r as if by storing a
+ //!copy of the pointer stored in r.
+ //!
+ //!Postconditions: use_count() == r.use_count().
+ //!
+ //!Throws: nothing.
template<class Y>
weak_ptr(shared_ptr<Y, A, D> const & r)
: m_pn(r.m_pn) // never throws
{}
+ //!Effects: Equivalent to weak_ptr(r).swap(*this).
+ //!
+ //!Throws: nothing.
+ //!
+ //!Notes: The implementation is free to meet the effects (and the
+ //!implied guarantees) via different means, without creating a temporary.
template<class Y>
weak_ptr & operator=(weak_ptr<Y, A, D> const & r) // never throws
{
@@ -87,10 +133,19 @@
return *this;
}
+ //!Effects: Equivalent to weak_ptr(r).swap(*this).
+ //!
+ //!Throws: nothing.
+ //!
+ //!Notes: The implementation is free to meet the effects (and the
+ //!implied guarantees) via different means, without creating a temporary.
template<class Y>
weak_ptr & operator=(shared_ptr<Y, A, D> const & r) // never throws
{ m_pn = r.m_pn; return *this; }
+ //!Returns: expired()? shared_ptr<T>(): shared_ptr<T>(*this).
+ //!
+ //!Throws: nothing.
shared_ptr<T, A, D> lock() const // never throws
{
// optimization: avoid throw overhead
@@ -108,18 +163,37 @@
BOOST_CATCH_END
}
+ //!Returns: 0 if *this is empty; otherwise, the number of shared_ptr objects
+ //!that share ownership with *this.
+ //!
+ //!Throws: nothing.
+ //!
+ //!Notes: use_count() is not necessarily efficient. Use only for debugging and
+ //!testing purposes, not for production code.
long use_count() const // never throws
{ return m_pn.use_count(); }
-
+
+ //!Returns: Returns: use_count() == 0.
+ //!
+ //!Throws: nothing.
+ //!
+ //!Notes: expired() may be faster than use_count().
bool expired() const // never throws
{ return m_pn.use_count() == 0; }
+ //!Effects: Equivalent to:
+ //!weak_ptr().swap(*this).
void reset() // never throws in 1.30+
{ this_type().swap(*this); }
+ //!Effects: Exchanges the contents of the two
+ //!smart pointers.
+ //!
+ //!Throws: nothing.
void swap(this_type & other) // never throws
{ detail::do_swap(m_pn, other.m_pn); }
+ /// @cond
template<class T2, class A2, class D2>
bool _internal_less(weak_ptr<T2, A2, D2> const & rhs) const
{ return m_pn < rhs.m_pn; }
@@ -128,7 +202,6 @@
void _internal_assign(const detail::shared_count<Y, A, D> & pn2)
{ m_pn = pn2; }
- /// @cond
private:
template<class T2, class A2, class D2> friend class shared_ptr;
@@ -146,6 +219,34 @@
void swap(weak_ptr<T, A, D> & a, weak_ptr<T, A, D> & b)
{ a.swap(b); }
+//!Returns the type of a weak pointer
+//!of type T with the allocator boost::interprocess::allocator allocator
+//!and boost::interprocess::deleter deleter
+//!that can be constructed in the given managed segment type.
+template<class T, class ManagedMemory>
+struct managed_weak_ptr
+{
+ typedef weak_ptr
+ < T
+ , typename ManagedMemory::template allocator<void>::type
+ , typename ManagedMemory::template deleter<T>::type
+ > type;
+};
+
+//!Returns an instance of the a weak pointer constructed
+//!with the default allocator and deleter from a pointer
+//!of type T that has been allocated in the passed managed segment
+template<class T, class ManagedMemory>
+inline typename managed_weak_ptr<T, ManagedMemory>::type
+ make_managed_weak_ptr(T *constructed_object, ManagedMemory &managed_memory)
+{
+ return typename managed_weak_ptr<T, ManagedMemory>::type
+ ( constructed_object
+ , managed_memory.template get_allocator<void>()
+ , managed_memory.template get_deleter<T>()
+ );
+}
+
} // namespace interprocess
} // namespace boost
Modified: branches/bcbboost/boost/interprocess/sync/file_lock.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/file_lock.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/file_lock.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -22,16 +22,15 @@
#include <boost/interprocess/detail/os_file_functions.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
-/*!\file
- Describes a class that wraps file locking capabilities.
-*/
+//!\file
+//!Describes a class that wraps file locking capabilities.
namespace boost {
namespace interprocess {
-/*!A file lock, is a mutual exclusion utility similar to a mutex using a
- file. A file lock has sharable and exclusive locking capabilities and
- can be used with scoped_lock and sharable_lock classes.*/
+//!A file lock, is a mutual exclusion utility similar to a mutex using a
+//!file. A file lock has sharable and exclusive locking capabilities and
+//!can be used with scoped_lock and sharable_lock classes.
class file_lock
{
/// @cond
@@ -41,67 +40,67 @@
file_lock &operator=(const file_lock &);
/// @endcond
public:
- /*!Opens a file lock. Throws interprocess_exception if the file does not
- exist or there are no operating system resources.*/
+ //!Opens a file lock. Throws interprocess_exception if the file does not
+ //!exist or there are no operating system resources.
file_lock(const char *name);
- /*!Closes a file lock. Does not throw.*/
+ //!Closes a file lock. Does not throw.
~file_lock();
//Exclusive locking
- /*!Effects: The calling thread tries to obtain exclusive ownership of the mutex,
- and if another thread has exclusive, or sharable ownership of
- the mutex, it waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain exclusive ownership of the mutex,
+ //! and if another thread has exclusive, or sharable ownership of
+ //! the mutex, it waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock();
- /*!Effects: The calling thread tries to acquire exclusive ownership of the mutex
- without waiting. If no other thread has exclusive, or sharable
- ownership of the mutex this succeeds.
- Returns: If it can acquire exclusive ownership immediately returns true.
- If it has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire exclusive ownership of the mutex
+ //! without waiting. If no other thread has exclusive, or sharable
+ //! ownership of the mutex this succeeds.
+ //!Returns: If it can acquire exclusive ownership immediately returns true.
+ //! If it has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock();
- /*!Effects: The calling thread tries to acquire exclusive ownership of the mutex
- waiting if necessary until no other thread has has exclusive, or sharable
- ownership of the mutex or abs_time is reached.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire exclusive ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive, or sharable
+ //! ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The calling thread releases the exclusive ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The calling thread releases the exclusive ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock();
//Sharable locking
- /*!Effects: The calling thread tries to obtain sharable ownership of the mutex,
- and if another thread has exclusive ownership of the mutex, waits until
- it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain sharable ownership of the mutex,
+ //! and if another thread has exclusive ownership of the mutex, waits until
+ //! it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock_sharable();
- /*!Effects: The calling thread tries to acquire sharable ownership of the mutex
- without waiting. If no other thread has has exclusive ownership of the
- mutex this succeeds.
- Returns: If it can acquire sharable ownership immediately returns true. If it
- has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire sharable ownership of the mutex
+ //! without waiting. If no other thread has has exclusive ownership of the
+ //! mutex this succeeds.
+ //!Returns: If it can acquire sharable ownership immediately returns true. If it
+ //! has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock_sharable();
- /*!Effects: The calling thread tries to acquire sharable ownership of the mutex
- waiting if necessary until no other thread has has exclusive ownership of
- the mutex or abs_time is reached.
- Returns: If acquires sharable ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire sharable ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive ownership of
+ //! the mutex or abs_time is reached.
+ //!Returns: If acquires sharable ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock_sharable(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have sharable ownership of the mutex.
- Effects: The calling thread releases the sharable ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have sharable ownership of the mutex.
+ //!Effects: The calling thread releases the sharable ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_sharable();
/// @cond
private:
Modified: branches/bcbboost/boost/interprocess/sync/interprocess_barrier.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/interprocess_barrier.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/interprocess_barrier.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -52,31 +52,31 @@
namespace boost {
namespace interprocess {
-/*!An object of class barrier is a synchronization primitive that
- can be placed in shared memory used to cause a set of threads from
- different processes to wait until they each perform a certain
- function or each reach a particular point in their execution.*/
+//!An object of class barrier is a synchronization primitive that
+//!can be placed in shared memory used to cause a set of threads from
+//!different processes to wait until they each perform a certain
+//!function or each reach a particular point in their execution.
class barrier
{
public:
- /*!Constructs a barrier object that will cause count threads
- to block on a call to wait(). */
+ //!Constructs a barrier object that will cause count threads
+ //!to block on a call to wait().
barrier(unsigned int count);
- /*!Destroys *this. If threads are still executing their wait()
- operations, the behavior for these threads is undefined.*/
+ //!Destroys *this. If threads are still executing their wait()
+ //!operations, the behavior for these threads is undefined.
~barrier();
- /*!Effects: Wait until N threads call wait(), where N equals the count
- provided to the constructor for the barrier object.
- Note that if the barrier is destroyed before wait() can return,
- the behavior is undefined.
- Returns: Exactly one of the N threads will receive a return value
- of true, the others will receive a value of false. Precisely which
- thread receives the return value of true will be implementation-defined.
- Applications can use this value to designate one thread as a leader that
- will take a certain action, and the other threads emerging from the barrier
- can wait for that action to take place.*/
+ //!Effects: Wait until N threads call wait(), where N equals the count
+ //!provided to the constructor for the barrier object.
+ //!Note that if the barrier is destroyed before wait() can return,
+ //!the behavior is undefined.
+ //!Returns: Exactly one of the N threads will receive a return value
+ //!of true, the others will receive a value of false. Precisely which
+ //!thread receives the return value of true will be implementation-defined.
+ //!Applications can use this value to designate one thread as a leader that
+ //!will take a certain action, and the other threads emerging from the barrier
+ //!can wait for that action to take place.
bool wait();
/// @cond
Modified: branches/bcbboost/boost/interprocess/sync/interprocess_condition.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/interprocess_condition.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/interprocess_condition.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -38,9 +38,8 @@
#define BOOST_INTERPROCESS_USE_GENERIC_EMULATION
#endif
-/*!\file
- Describes process-shared variables interprocess_condition class
-*/
+//!\file
+//!Describes process-shared variables interprocess_condition class
namespace boost {
@@ -60,23 +59,24 @@
friend class named_condition;
/// @endcond
public:
- /*!Constructs a interprocess_condition*/
+ //!Constructs a interprocess_condition. On error throws interprocess_exception.
interprocess_condition();
- /*!Destroys *this*/
+ //!Destroys *this
+ //!liberating system resources.
~interprocess_condition();
- /*!If there is a thread waiting on *this, change that
- thread's state to ready. Otherwise there is no effect.*/
+ //!If there is a thread waiting on *this, change that
+ //!thread's state to ready. Otherwise there is no effect.
void notify_one();
- /*!Change the state of all threads waiting on *this to ready.
- If there are no waiting threads, notify_all() has no effect.*/
+ //!Change the state of all threads waiting on *this to ready.
+ //!If there are no waiting threads, notify_all() has no effect.
void notify_all();
- /*!Releases the lock on the interprocess_mutex object associated with lock, blocks
- the current thread of execution until readied by a call to
- this->notify_one() or this->notify_all(), and then reacquires the lock.*/
+ //!Releases the lock on the interprocess_mutex object associated with lock, blocks
+ //!the current thread of execution until readied by a call to
+ //!this->notify_one() or this->notify_all(), and then reacquires the lock.
template <typename L>
void wait(L& lock)
{
@@ -85,7 +85,8 @@
do_wait(*lock.mutex());
}
- /*!The same as: while (!pred()) wait(lock)*/
+ //!The same as:
+ //!while (!pred()) wait(lock)
template <typename L, typename Pr>
void wait(L& lock, Pr pred)
{
@@ -96,11 +97,11 @@
do_wait(*lock.mutex());
}
- /*!Releases the lock on the interprocess_mutex object associated with lock, blocks
- the current thread of execution until readied by a call to
- this->notify_one() or this->notify_all(), or until time abs_time is reached,
- and then reacquires the lock.
- Returns: false if time abs_time is reached, otherwise true.*/
+ //!Releases the lock on the interprocess_mutex object associated with lock, blocks
+ //!the current thread of execution until readied by a call to
+ //!this->notify_one() or this->notify_all(), or until time abs_time is reached,
+ //!and then reacquires the lock.
+ //!Returns: false if time abs_time is reached, otherwise true.
template <typename L>
bool timed_wait(L& lock, const boost::posix_time::ptime &abs_time)
{
@@ -110,9 +111,9 @@
return do_timed_wait(abs_time, *lock.mutex());
}
- /*!The same as: while (!pred()) {
- if (!timed_wait(lock, abs_time)) return pred();
- } return true;*/
+ //!The same as: while (!pred()) {
+ //! if (!timed_wait(lock, abs_time)) return pred();
+ //! } return true;
template <typename L, typename Pr>
bool timed_wait(L& lock, const boost::posix_time::ptime &abs_time, Pr pred)
{
Modified: branches/bcbboost/boost/interprocess/sync/interprocess_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/interprocess_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/interprocess_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -48,18 +48,17 @@
#define BOOST_INTERPROCESS_USE_GENERIC_EMULATION
#endif
-/*!\file
- Describes a mutex class that can be placed in memory shared by
- several processes.
-*/
+//!\file
+//!Describes a mutex class that can be placed in memory shared by
+//!several processes.
namespace boost {
namespace interprocess {
class interprocess_condition;
-/*!Wraps a interprocess_mutex that can be placed in shared memory and can be
- shared between processes. Allows timed lock tries*/
+//!Wraps a interprocess_mutex that can be placed in shared memory and can be
+//!shared between processes. Allows timed lock tries
class interprocess_mutex
{
/// @cond
@@ -70,38 +69,39 @@
/// @endcond
public:
- /*!Constructor. Throws interprocess_exception on error.*/
+ //!Constructor.
+ //!Throws interprocess_exception on error.
interprocess_mutex();
- /*!Destructor. If any process uses the mutex after the destructor is called
- the result is undefined. Does not throw.*/
+ //!Destructor. If any process uses the mutex after the destructor is called
+ //!the result is undefined. Does not throw.
~interprocess_mutex();
- /*!Effects: The calling thread tries to obtain ownership of the mutex, and
- if another thread has ownership of the mutex, it waits until it can
- obtain the ownership. If a thread takes ownership of the mutex the
- mutex must be unlocked by the same mutex.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain ownership of the mutex, and
+ //! if another thread has ownership of the mutex, it waits until it can
+ //! obtain the ownership. If a thread takes ownership of the mutex the
+ //! mutex must be unlocked by the same mutex.
+ //!Throws: interprocess_exception on error.
void lock();
- /*!Effects: The calling thread tries to obtain ownership of the mutex, and
- if another thread has ownership of the mutex returns immediately.
- Returns: If the thread acquires ownership of the mutex, returns true, if
- the another thread has ownership of the mutex, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain ownership of the mutex, and
+ //! if another thread has ownership of the mutex returns immediately.
+ //!Returns: If the thread acquires ownership of the mutex, returns true, if
+ //! the another thread has ownership of the mutex, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock();
- /*!Effects: The calling thread will try to obtain exclusive ownership of the
- mutex if it can do so in until the specified time is reached. If the
- mutex supports recursive locking, the mutex must be unlocked the same
- number of times it is locked.
- Returns: If the thread acquires ownership of the mutex, returns true, if
- the timeout expires returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread will try to obtain exclusive ownership of the
+ //! mutex if it can do so in until the specified time is reached. If the
+ //! mutex supports recursive locking, the mutex must be unlocked the same
+ //! number of times it is locked.
+ //!Returns: If the thread acquires ownership of the mutex, returns true, if
+ //! the timeout expires returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*!Effects: The calling thread releases the exclusive ownership of the mutex.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread releases the exclusive ownership of the mutex.
+ //!Throws: interprocess_exception on error.
void unlock();
/// @cond
private:
Modified: branches/bcbboost/boost/interprocess/sync/interprocess_recursive_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/interprocess_recursive_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/interprocess_recursive_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -49,17 +49,16 @@
#define BOOST_INTERPROCESS_USE_GENERIC_EMULATION
#endif
-/*!\file
- Describes interprocess_recursive_mutex and shared_recursive_try_mutex classes
-*/
+//!\file
+//!Describes interprocess_recursive_mutex and shared_recursive_try_mutex classes
namespace boost {
namespace interprocess {
-/*!Wraps a interprocess_mutex that can be placed in shared memory and can be
- shared between processes. Allows several locking calls by the same
- process. Allows timed lock tries*/
+//!Wraps a interprocess_mutex that can be placed in shared memory and can be
+//!shared between processes. Allows several locking calls by the same
+//!process. Allows timed lock tries
class interprocess_recursive_mutex
{
/// @cond
@@ -68,37 +67,38 @@
interprocess_recursive_mutex &operator=(const interprocess_recursive_mutex &);
/// @endcond
public:
- /*!Constructor. Throws interprocess_exception on error.*/
+ //!Constructor.
+ //!Throws interprocess_exception on error.
interprocess_recursive_mutex();
- /*!Destructor. If any process uses the mutex after the destructor is called
- the result is undefined. Does not throw.*/
+ //!Destructor. If any process uses the mutex after the destructor is called
+ //!the result is undefined. Does not throw.
~interprocess_recursive_mutex();
- /*!Effects: The calling thread tries to obtain ownership of the mutex, and
- if another thread has ownership of the mutex, it waits until it can
- obtain the ownership. If a thread takes ownership of the mutex the
- mutex must be unlocked by the same mutex. The mutex must be unlocked
- the same number of times it is locked.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain ownership of the mutex, and
+ //! if another thread has ownership of the mutex, it waits until it can
+ //! obtain the ownership. If a thread takes ownership of the mutex the
+ //! mutex must be unlocked by the same mutex. The mutex must be unlocked
+ //! the same number of times it is locked.
+ //!Throws: interprocess_exception on error.
void lock(void);
- /*! Tries to lock the interprocess_mutex, returns false when interprocess_mutex
- is already locked, returns true when success. The mutex must be unlocked
- the same number of times it is locked.
- Throws: interprocess_exception if a severe error is found*/
+ //!Tries to lock the interprocess_mutex, returns false when interprocess_mutex
+ //!is already locked, returns true when success. The mutex must be unlocked
+ //!the same number of times it is locked.
+ //!Throws: interprocess_exception if a severe error is found
bool try_lock(void);
- /*! Tries to lock the interprocess_mutex, if interprocess_mutex can't be locked before
- abs_time time, returns false. The mutex must be unlocked
- the same number of times it is locked.
- Throws: interprocess_exception if a severe error is found*/
+ //!Tries to lock the interprocess_mutex, if interprocess_mutex can't be locked before
+ //!abs_time time, returns false. The mutex must be unlocked
+ //! the same number of times it is locked.
+ //!Throws: interprocess_exception if a severe error is found
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*!Effects: The calling thread releases the exclusive ownership of the mutex.
- If the mutex supports recursive locking, the mutex must be unlocked the
- same number of times it is locked.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread releases the exclusive ownership of the mutex.
+ //! If the mutex supports recursive locking, the mutex must be unlocked the
+ //! same number of times it is locked.
+ //!Throws: interprocess_exception on error.
void unlock(void);
/// @cond
private:
Modified: branches/bcbboost/boost/interprocess/sync/interprocess_semaphore.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/interprocess_semaphore.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/interprocess_semaphore.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -39,16 +39,15 @@
#define BOOST_INTERPROCESS_USE_GENERIC_EMULATION
#endif
-/*!\file
- Describes a interprocess_semaphore class for inter-process synchronization
-*/
+//!\file
+//!Describes a interprocess_semaphore class for inter-process synchronization
namespace boost {
namespace interprocess {
-/*!Wraps a interprocess_semaphore that can be placed in shared memory and can be
- shared between processes. Allows timed lock tries*/
+//!Wraps a interprocess_semaphore that can be placed in shared memory and can be
+//!shared between processes. Allows timed lock tries
class interprocess_semaphore
{
/// @cond
@@ -57,36 +56,37 @@
interprocess_semaphore &operator=(const interprocess_semaphore &);
/// @endcond
public:
- /*!Creates a interprocess_semaphore with the given initial count.
- interprocess_exception if there is an error.*/
+ //!Creates a interprocess_semaphore with the given initial count.
+ //!interprocess_exception if there is an error.*/
interprocess_semaphore(int initialCount);
- /*!Destroys the interprocess_semaphore. Does not throw*/
+ //!Destroys the interprocess_semaphore.
+ //!Does not throw
~interprocess_semaphore();
- /*!Increments the interprocess_semaphore count. If there are processes/threads blocked waiting
- for the interprocess_semaphore, then one of these processes will return successfully from
- its wait function. If there is an error an interprocess_exception exception is thrown.*/
+ //!Increments the interprocess_semaphore count. If there are processes/threads blocked waiting
+ //!for the interprocess_semaphore, then one of these processes will return successfully from
+ //!its wait function. If there is an error an interprocess_exception exception is thrown.
void post();
- /*!Decrements the interprocess_semaphore. If the interprocess_semaphore value is not greater than zero,
- then the calling process/thread blocks until it can decrement the counter.
- If there is an error an interprocess_exception exception is thrown.*/
+ //!Decrements the interprocess_semaphore. If the interprocess_semaphore value is not greater than zero,
+ //!then the calling process/thread blocks until it can decrement the counter.
+ //!If there is an error an interprocess_exception exception is thrown.
void wait();
- /*!Decrements the interprocess_semaphore if the interprocess_semaphore's value is greater than zero
- and returns true. If the value is not greater than zero returns false.
- If there is an error an interprocess_exception exception is thrown.*/
+ //!Decrements the interprocess_semaphore if the interprocess_semaphore's value is greater than zero
+ //!and returns true. If the value is not greater than zero returns false.
+ //!If there is an error an interprocess_exception exception is thrown.
bool try_wait();
- /*!Decrements the interprocess_semaphore if the interprocess_semaphore's value is greater
- than zero and returns true. Otherwise, waits for the interprocess_semaphore
- to the posted or the timeout expires. If the timeout expires, the
- function returns false. If the interprocess_semaphore is posted the function
- returns true. If there is an error throws sem_exception*/
+ //!Decrements the interprocess_semaphore if the interprocess_semaphore's value is greater
+ //!than zero and returns true. Otherwise, waits for the interprocess_semaphore
+ //!to the posted or the timeout expires. If the timeout expires, the
+ //!function returns false. If the interprocess_semaphore is posted the function
+ //!returns true. If there is an error throws sem_exception
bool timed_wait(const boost::posix_time::ptime &abs_time);
- /*!Returns the interprocess_semaphore count*/
+ //!Returns the interprocess_semaphore count
// int get_count() const;
/// @cond
private:
Modified: branches/bcbboost/boost/interprocess/sync/interprocess_upgradable_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/interprocess_upgradable_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/interprocess_upgradable_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,16 +23,14 @@
#include <limits.h>
-/*!\file
- Describes interprocess_upgradable_mutex class
-*/
+//!\file
+//!Describes interprocess_upgradable_mutex class
namespace boost {
-
namespace interprocess {
-/*!Wraps a interprocess_upgradable_mutex that can be placed in shared memory and can be
- shared between processes. Allows timed lock tries*/
+//!Wraps a interprocess_upgradable_mutex that can be placed in shared memory and can be
+//!shared between processes. Allows timed lock tries
class interprocess_upgradable_mutex
{
//Non-copyable
@@ -42,156 +40,158 @@
friend class interprocess_condition;
public:
- /*!Constructs the upgradable lock. Throws interprocess_exception on error.*/
+ //!Constructs the upgradable lock.
+ //!Throws interprocess_exception on error.
interprocess_upgradable_mutex();
- /*!Destroys the upgradable lock. Does not throw.*/
+ //!Destroys the upgradable lock.
+ //!Does not throw.
~interprocess_upgradable_mutex();
//Exclusive locking
- /*!Effects: The calling thread tries to obtain exclusive ownership of the mutex,
- and if another thread has exclusive, sharable or upgradable ownership of
- the mutex, it waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain exclusive ownership of the mutex,
+ //! and if another thread has exclusive, sharable or upgradable ownership of
+ //! the mutex, it waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock();
- /*!Effects: The calling thread tries to acquire exclusive ownership of the mutex
- without waiting. If no other thread has exclusive, sharable or upgradable
- ownership of the mutex this succeeds.
- Returns: If it can acquire exclusive ownership immediately returns true.
- If it has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire exclusive ownership of the mutex
+ //! without waiting. If no other thread has exclusive, sharable or upgradable
+ //! ownership of the mutex this succeeds.
+ //!Returns: If it can acquire exclusive ownership immediately returns true.
+ //! If it has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock();
- /*!Effects: The calling thread tries to acquire exclusive ownership of the mutex
- waiting if necessary until no other thread has has exclusive, sharable or
- upgradable ownership of the mutex or abs_time is reached.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire exclusive ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive, sharable or
+ //! upgradable ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The calling thread releases the exclusive ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The calling thread releases the exclusive ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock();
//Sharable locking
- /*!Effects: The calling thread tries to obtain sharable ownership of the mutex,
- and if another thread has exclusive or upgradable ownership of the mutex,
- waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain sharable ownership of the mutex,
+ //! and if another thread has exclusive or upgradable ownership of the mutex,
+ //! waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock_sharable();
- /*!Effects: The calling thread tries to acquire sharable ownership of the mutex
- without waiting. If no other thread has has exclusive or upgradable ownership
- of the mutex this succeeds.
- Returns: If it can acquire sharable ownership immediately returns true. If it
- has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire sharable ownership of the mutex
+ //! without waiting. If no other thread has has exclusive or upgradable ownership
+ //! of the mutex this succeeds.
+ //!Returns: If it can acquire sharable ownership immediately returns true. If it
+ //! has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock_sharable();
- /*!Effects: The calling thread tries to acquire sharable ownership of the mutex
- waiting if necessary until no other thread has has exclusive or upgradable
- ownership of the mutex or abs_time is reached.
- Returns: If acquires sharable ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire sharable ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive or upgradable
+ //! ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires sharable ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock_sharable(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have sharable ownership of the mutex.
- Effects: The calling thread releases the sharable ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have sharable ownership of the mutex.
+ //!Effects: The calling thread releases the sharable ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_sharable();
//Upgradable locking
- /*!Effects: The calling thread tries to obtain upgradable ownership of the mutex,
- and if another thread has exclusive or upgradable ownership of the mutex,
- waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain upgradable ownership of the mutex,
+ //! and if another thread has exclusive or upgradable ownership of the mutex,
+ //! waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock_upgradable();
- /*!Effects: The calling thread tries to acquire upgradable ownership of the mutex
- without waiting. If no other thread has has exclusive or upgradable ownership
- of the mutex this succeeds.
- Returns: If it can acquire upgradable ownership immediately returns true.
- If it has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire upgradable ownership of the mutex
+ //! without waiting. If no other thread has has exclusive or upgradable ownership
+ //! of the mutex this succeeds.
+ //!Returns: If it can acquire upgradable ownership immediately returns true.
+ //! If it has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock_upgradable();
- /*!Effects: The calling thread tries to acquire upgradable ownership of the mutex
- waiting if necessary until no other thread has has exclusive or upgradable
- ownership of the mutex or abs_time is reached.
- Returns: If acquires upgradable ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire upgradable ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive or upgradable
+ //! ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires upgradable ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock_upgradable(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The calling thread releases the upgradable ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The calling thread releases the upgradable ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_upgradable();
//Demotions
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The thread atomically releases exclusive ownership and acquires
- upgradable ownership. This operation is non-blocking.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The thread atomically releases exclusive ownership and acquires
+ //! upgradable ownership. This operation is non-blocking.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_and_lock_upgradable();
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The thread atomically releases exclusive ownership and acquires
- sharable ownership. This operation is non-blocking.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The thread atomically releases exclusive ownership and acquires
+ //! sharable ownership. This operation is non-blocking.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_and_lock_sharable();
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and acquires
- sharable ownership. This operation is non-blocking.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and acquires
+ //! sharable ownership. This operation is non-blocking.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_upgradable_and_lock_sharable();
//Promotions
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and acquires
- exclusive ownership. This operation will block until all threads with
- sharable ownership releas it.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and acquires
+ //! exclusive ownership. This operation will block until all threads with
+ //! sharable ownership release their sharable lock.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_upgradable_and_lock();
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and tries to
- acquire exclusive ownership. This operation will fail if there are threads
- with sharable ownership, but it will maintain upgradable ownership.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and tries to
+ //! acquire exclusive ownership. This operation will fail if there are threads
+ //! with sharable ownership, but it will maintain upgradable ownership.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error.
bool try_unlock_upgradable_and_lock();
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and tries to acquire
- exclusive ownership, waiting if necessary until abs_time. This operation will
- fail if there are threads with sharable ownership or timeout reaches, but it
- will maintain upgradable ownership.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error. */
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and tries to acquire
+ //! exclusive ownership, waiting if necessary until abs_time. This operation will
+ //! fail if there are threads with sharable ownership or timeout reaches, but it
+ //! will maintain upgradable ownership.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error. */
bool timed_unlock_upgradable_and_lock(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have sharable ownership of the mutex.
- Effects: The thread atomically releases sharable ownership and tries to acquire
- exclusive ownership. This operation will fail if there are threads with sharable
- or upgradable ownership, but it will maintain sharable ownership.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have sharable ownership of the mutex.
+ //!Effects: The thread atomically releases sharable ownership and tries to acquire
+ //! exclusive ownership. This operation will fail if there are threads with sharable
+ //! or upgradable ownership, but it will maintain sharable ownership.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error.
bool try_unlock_sharable_and_lock();
- /*!Precondition: The thread must have sharable ownership of the mutex.
- Effects: The thread atomically releases sharable ownership and tries to acquire
- upgradable ownership. This operation will fail if there are threads with sharable
- or upgradable ownership, but it will maintain sharable ownership.
- Returns: If acquires upgradable ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have sharable ownership of the mutex.
+ //!Effects: The thread atomically releases sharable ownership and tries to acquire
+ //! upgradable ownership. This operation will fail if there are threads with sharable
+ //! or upgradable ownership, but it will maintain sharable ownership.
+ //!Returns: If acquires upgradable ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error.
bool try_unlock_sharable_and_lock_upgradable();
/// @cond
Modified: branches/bcbboost/boost/interprocess/sync/lock_options.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/lock_options.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/lock_options.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -18,9 +18,8 @@
#include <boost/interprocess/detail/config_begin.hpp>
#include <boost/interprocess/detail/workaround.hpp>
-/*!\file
- Describes the lock options with associated with interprocess_mutex lock constructors.
-*/
+//!\file
+//!Describes the lock options with associated with interprocess_mutex lock constructors.
namespace boost {
@@ -30,11 +29,11 @@
namespace interprocess {
namespace detail{
- /*!Type to indicate to a mutex lock constructor that must not lock the mutex.*/
+ //!Type to indicate to a mutex lock constructor that must not lock the mutex.
struct defer_lock_type{};
- /*!Type to indicate to a mutex lock constructor that must try to lock the mutex.*/
+ //!Type to indicate to a mutex lock constructor that must try to lock the mutex.
struct try_to_lock_type {};
- /*!Type to indicate to a mutex lock constructor that the mutex is already locked.*/
+ //!Type to indicate to a mutex lock constructor that the mutex is already locked.
struct accept_ownership_type{};
} //namespace detail{
Modified: branches/bcbboost/boost/interprocess/sync/mutex_family.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/mutex_family.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/mutex_family.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -22,24 +22,23 @@
#include <boost/interprocess/sync/interprocess_recursive_mutex.hpp>
#include <boost/interprocess/sync/null_mutex.hpp>
-/*!\file
- Describes a shared interprocess_mutex family fit algorithm used to allocate objects in shared memory.
-*/
+//!\file
+//!Describes a shared interprocess_mutex family fit algorithm used to allocate objects in shared memory.
namespace boost {
namespace interprocess {
-/*!Describes interprocess_mutex family to use with Interprocess framework
- based on boost::interprocess synchronization objects.*/
+//!Describes interprocess_mutex family to use with Interprocess framework
+//!based on boost::interprocess synchronization objects.
struct mutex_family
{
typedef boost::interprocess::interprocess_mutex mutex_type;
typedef boost::interprocess::interprocess_recursive_mutex recursive_mutex_type;
};
-/*!Describes interprocess_mutex family to use with Interprocess frameworks
- based on null operation synchronization objects.*/
+//!Describes interprocess_mutex family to use with Interprocess frameworks
+//!based on null operation synchronization objects.
struct null_mutex_family
{
typedef boost::interprocess::null_mutex mutex_type;
Modified: branches/bcbboost/boost/interprocess/sync/named_condition.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/named_condition.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/named_condition.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -8,8 +8,8 @@
//
//////////////////////////////////////////////////////////////////////////////
-#ifndef BOOST_NAMED_CONDITION_HPP
-#define BOOST_NAMED_CONDITION_HPP
+#ifndef BOOST_INTERPROCESS_NAMED_CONDITION_HPP
+#define BOOST_INTERPROCESS_NAMED_CONDITION_HPP
#if (defined _MSC_VER) && (_MSC_VER >= 1200)
# pragma once
@@ -23,10 +23,15 @@
#include <boost/interprocess/sync/interprocess_condition.hpp>
#include <boost/interprocess/detail/managed_open_or_create_impl.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
+#include <boost/interprocess/sync/emulation/named_creation_functor.hpp>
+#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+#include <boost/interprocess/sync/interprocess_mutex.hpp>
+#include <boost/interprocess/sync/scoped_lock.hpp>
+#endif
+
-/*!\file
- Describes process-shared variables interprocess_condition class
-*/
+//!\file
+//!Describes process-shared variables interprocess_condition class
namespace boost {
@@ -41,102 +46,114 @@
named_condition &operator=(const named_condition &);
/// @endcond
public:
- /*!Creates a global condition with a name.*/
+ //!Creates a global condition with a name.
+ //!If the condition can't be created throws interprocess_exception
named_condition(create_only_t create_only, const char *name);
- /*!Opens or creates a global condition with a name.
- If the condition is created, this call is equivalent to create().
- If the condition is already created, this call is equivalent to open().
- Does not throw*/
+ //!Opens or creates a global condition with a name.
+ //!If the condition is created, this call is equivalent to
+ //!named_condition(create_only_t, ... )
+ //!If the condition is already created, this call is equivalent
+ //!named_condition(open_only_t, ... )
+ //!Does not throw
named_condition(open_or_create_t open_or_create, const char *name);
- /*!Opens a global condition with a name if that condition is previously.
- created. If it is not previously created this function return false.
- Does not throw*/
+ //!Opens a global condition with a name if that condition is previously
+ //!created. If it is not previously created this function throws
+ //!interprocess_exception.
named_condition(open_only_t open_only, const char *name);
- /*!Destroys *this*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~named_condition();
- /*!If there is a thread waiting on *this, change that
- thread's state to ready. Otherwise there is no effect.*/
+ //!If there is a thread waiting on *this, change that
+ //!thread's state to ready. Otherwise there is no effect.*/
void notify_one();
- /*!Change the state of all threads waiting on *this to ready.
- If there are no waiting threads, notify_all() has no effect.*/
+ //!Change the state of all threads waiting on *this to ready.
+ //!If there are no waiting threads, notify_all() has no effect.
void notify_all();
- /*!Releases the lock on the interprocess_mutex object associated with lock, blocks
- the current thread of execution until readied by a call to
- this->notify_one() or this->notify_all(), and then reacquires the lock.*/
+ //!Releases the lock on the interprocess_mutex object associated with lock, blocks
+ //!the current thread of execution until readied by a call to
+ //!this->notify_one() or this->notify_all(), and then reacquires the lock.
template <typename L>
void wait(L& lock);
- /*!The same as: while (!pred()) wait(lock)*/
+ //!The same as:
+ //!while (!pred()) wait(lock)
template <typename L, typename Pr>
void wait(L& lock, Pr pred);
- /*!Releases the lock on the interprocess_mutex object associated with lock, blocks
- the current thread of execution until readied by a call to
- this->notify_one() or this->notify_all(), or until time abs_time is reached,
- and then reacquires the lock.
- Returns: false if time abs_time is reached, otherwise true.*/
+ //!Releases the lock on the interprocess_mutex object associated with lock, blocks
+ //!the current thread of execution until readied by a call to
+ //!this->notify_one() or this->notify_all(), or until time abs_time is reached,
+ //!and then reacquires the lock.
+ //!Returns: false if time abs_time is reached, otherwise true.
template <typename L>
bool timed_wait(L& lock, const boost::posix_time::ptime &abs_time);
- /*!The same as: while (!pred()) {
- if (!timed_wait(lock, abs_time)) return pred();
- } return true;*/
+ //!The same as: while (!pred()) {
+ //! if (!timed_wait(lock, abs_time)) return pred();
+ //! } return true;
template <typename L, typename Pr>
bool timed_wait(L& lock, const boost::posix_time::ptime &abs_time, Pr pred);
+ //!Erases a named condition from the system.
+ //!Returns false on error. Never throws.
static bool remove(const char *name);
/// @cond
private:
- interprocess_condition *condition() const
- { return static_cast<interprocess_condition*>(m_shmem.get_address()); }
+ struct condition_holder
+ {
+ interprocess_condition cond_;
+ //If named_mutex is implemented using semaphores
+ //we need to store an additional mutex
+ #ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ interprocess_mutex mutex_;
+ #endif
+ };
- detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
+ interprocess_condition *condition() const
+ { return &static_cast<condition_holder*>(m_shmem.get_address())->cond_; }
- class construct_func_t;
- /// @endcond
-};
+ #ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ interprocess_mutex *mutex() const
+ { return &static_cast<condition_holder*>(m_shmem.get_address())->mutex_; }
+
+ template <class Lock>
+ void do_wait(Lock& lock)
+ {
+ scoped_lock<interprocess_mutex> internal_lock(*this->mutex());
+ lock.unlock();
+ this->condition()->wait(internal_lock);
+ lock.lock();
+ }
-/// @cond
-class named_condition::construct_func_t
-{
- public:
- enum CreationType { open_only, open_or_create, create_only };
+ template <class Lock>
+ bool do_timed_wait(Lock& lock, const boost::posix_time::ptime &abs_time)
+ {
+ scoped_lock<interprocess_mutex> internal_lock(*this->mutex());
+ lock.unlock();
+ bool r = this->condition()->timed_wait(internal_lock, abs_time);
+ lock.lock();
+ return r;
+ }
+ #endif //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
- construct_func_t(CreationType type)
- : m_creation_type(type){}
+ detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
- bool operator()(void *address, std::size_t, bool created) const
- {
- switch(m_creation_type){
- case open_only:
- return true;
- break;
- case create_only:
- case open_or_create:
- if(created){
- new(address)interprocess_condition;
- }
- return true;
- break;
-
- default:
- return false;
- break;
- }
- return true;
- }
- private:
- CreationType m_creation_type;
+ template <class T, class Arg> friend class boost::interprocess::detail::named_creation_functor;
+ typedef detail::named_creation_functor<condition_holder> construct_func_t;
+ /// @endcond
};
-/// @endcond
inline named_condition::~named_condition()
{}
@@ -144,23 +161,23 @@
inline named_condition::named_condition(create_only_t, const char *name)
: m_shmem (create_only
,name
- ,sizeof(interprocess_condition) +
+ ,sizeof(condition_holder) +
detail::managed_open_or_create_impl<shared_memory_object>::
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::create_only))
+ ,construct_func_t(detail::DoCreate))
{}
inline named_condition::named_condition(open_or_create_t, const char *name)
: m_shmem (open_or_create
,name
- ,sizeof(interprocess_condition) +
+ ,sizeof(condition_holder) +
detail::managed_open_or_create_impl<shared_memory_object>::
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::open_or_create))
+ ,construct_func_t(detail::DoOpenOrCreate))
{}
inline named_condition::named_condition(open_only_t, const char *name)
@@ -168,9 +185,65 @@
,name
,read_write
,0
- ,construct_func_t(construct_func_t::open_only))
+ ,construct_func_t(detail::DoOpen))
{}
+#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+
+inline void named_condition::notify_one()
+{
+ scoped_lock<interprocess_mutex> internal_lock(*this->mutex());
+ this->condition()->notify_one();
+}
+
+inline void named_condition::notify_all()
+{
+ scoped_lock<interprocess_mutex> internal_lock(*this->mutex());
+ this->condition()->notify_all();
+}
+
+template <typename L>
+inline void named_condition::wait(L& lock)
+{
+ if (!lock)
+ throw lock_exception();
+ this->do_wait(lock);
+}
+
+template <typename L, typename Pr>
+inline void named_condition::wait(L& lock, Pr pred)
+{
+ if (!lock)
+ throw lock_exception();
+ while (!pred())
+ this->do_wait(lock);
+}
+
+template <typename L>
+inline bool named_condition::timed_wait
+ (L& lock, const boost::posix_time::ptime &abs_time)
+{
+ if (!lock)
+ throw lock_exception();
+ return this->do_timed_wait(lock, abs_time);
+}
+
+template <typename L, typename Pr>
+inline bool named_condition::timed_wait
+ (L& lock, const boost::posix_time::ptime &abs_time, Pr pred)
+{
+ if (!lock)
+ throw lock_exception();
+
+ while (!pred()){
+ if(!this->do_timed_wait(lock, abs_time)){
+ return pred();
+ }
+ }
+ return true;
+}
+
+#else //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
inline void named_condition::notify_one()
{ this->condition()->notify_one(); }
@@ -187,8 +260,7 @@
}
template <typename L, typename Pr>
-inline void named_condition::wait
- (L& lock, Pr pred)
+inline void named_condition::wait(L& lock, Pr pred)
{
if (!lock)
throw lock_exception();
@@ -202,8 +274,7 @@
(L& lock, const boost::posix_time::ptime &abs_time)
{
if (!lock)
- throw lock_exception();
-
+ throw lock_exception();
return this->condition()->do_timed_wait(abs_time, *lock.mutex()->mutex());
}
@@ -212,22 +283,24 @@
(L& lock, const boost::posix_time::ptime &abs_time, Pr pred)
{
if (!lock)
- throw lock_exception();
+ throw lock_exception();
while (!pred()){
- if (!this->condition()->do_timed_wait(abs_time, *lock.mutex()->mutex()))
- return pred();
+ if (!this->condition()->do_timed_wait(abs_time, *lock.mutex()->mutex()))
+ return pred();
}
return true;
}
+#endif //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+
inline bool named_condition::remove(const char *name)
{ return shared_memory_object::remove(name); }
} //namespace interprocess
-} // namespace boost
+} //namespace boost
#include <boost/interprocess/detail/config_end.hpp>
-#endif // BOOST_NAMED_CONDITION_HPP
+#endif // BOOST_INTERPROCESS_NAMED_CONDITION_HPP
Modified: branches/bcbboost/boost/interprocess/sync/named_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/named_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/named_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -19,14 +19,19 @@
#include <boost/interprocess/detail/workaround.hpp>
#include <boost/interprocess/creation_tags.hpp>
#include <boost/interprocess/exceptions.hpp>
-#include <boost/interprocess/shared_memory_object.hpp>
-#include <boost/interprocess/sync/interprocess_mutex.hpp>
-#include <boost/interprocess/detail/managed_open_or_create_impl.hpp>
-#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
-
-/*!\file
- Describes a named mutex class for inter-process synchronization
-*/
+#include <boost/interprocess/sync/emulation/named_creation_functor.hpp>
+
+#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ #include <boost/interprocess/sync/posix/semaphore_wrapper.hpp>
+#else
+ #include <boost/interprocess/shared_memory_object.hpp>
+ #include <boost/interprocess/sync/interprocess_mutex.hpp>
+ #include <boost/interprocess/detail/managed_open_or_create_impl.hpp>
+ #include <boost/interprocess/detail/posix_time_types_wrk.hpp>
+#endif
+
+//!\file
+//!Describes a named mutex class for inter-process synchronization
namespace boost {
@@ -34,100 +39,117 @@
class named_condition;
-/*!A mutex with a global name, so it can be found from different
- processes. This mutex can't be placed in shared memory, and
- each process should have it's own named_mutex.*/
+//!A mutex with a global name, so it can be found from different
+//!processes. This mutex can't be placed in shared memory, and
+//!each process should have it's own named_mutex.
class named_mutex
{
/// @cond
+
//Non-copyable
named_mutex();
named_mutex(const named_mutex &);
named_mutex &operator=(const named_mutex &);
friend class named_condition;
/// @endcond
+
public:
- /*!Creates a global interprocess_mutex with a name.*/
+ //!Creates a global interprocess_mutex with a name.
+ //!Throws interprocess_exception on error.
named_mutex(create_only_t create_only, const char *name);
- /*!Opens or creates a global mutex with a name.
- If the mutex is created, this call is equivalent to create().
- If the mutex is already created, this call is equivalent to open().
- Does not throw*/
+ //!Opens or creates a global mutex with a name.
+ //!If the mutex is created, this call is equivalent to
+ //!named_mutex(create_only_t, ... )
+ //!If the mutex is already created, this call is equivalent
+ //!named_mutex(open_only_t, ... )
+ //!Does not throw
named_mutex(open_or_create_t open_or_create, const char *name);
- /*!Opens a global mutex with a name if that mutex is previously.
- created. If it is not previously created this function return false.
- Does not throw*/
+ //!Opens a global mutex with a name if that mutex is previously
+ //!created. If it is not previously created this function throws
+ //!interprocess_exception.
named_mutex(open_only_t open_only, const char *name);
- /*!Closes the named mutex. Does not throw*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~named_mutex();
- /*!Unlocks a previously locked interprocess_mutex.*/
+ //!Unlocks a previously locked
+ //!interprocess_mutex.
void unlock();
- /*!Locks interprocess_mutex, sleeps when interprocess_mutex is already locked.
- Throws interprocess_exception if a severe error is found*/
+ //!Locks interprocess_mutex, sleeps when interprocess_mutex is already locked.
+ //!Throws interprocess_exception if a severe error is found
void lock();
- /*! Tries to lock the interprocess_mutex, returns false when interprocess_mutex
- is already locked, returns true when success.
- Throws interprocess_exception if a severe error is found*/
+ //!Tries to lock the interprocess_mutex, returns false when interprocess_mutex
+ //!is already locked, returns true when success.
+ //!Throws interprocess_exception if a severe error is found
bool try_lock();
- /*! Tries to lock the interprocess_mutex until time abs_time,
- Returns false when timeout expires, returns true when locks.
- Throws interprocess_exception if a severe error is found*/
+ //!Tries to lock the interprocess_mutex until time abs_time,
+ //!Returns false when timeout expires, returns true when locks.
+ //!Throws interprocess_exception if a severe error is found
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*! Erases a named mutex from the system*/
+ //!Erases a named mutex from the system.
+ //!Returns false on error. Never throws.
static bool remove(const char *name);
/// @cond
private:
+ #ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ detail::named_semaphore_wrapper m_sem;
+ #else //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
interprocess_mutex *mutex() const
{ return static_cast<interprocess_mutex*>(m_shmem.get_address()); }
detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
-
- class construct_func_t;
+ typedef detail::named_creation_functor<interprocess_mutex> construct_func_t;
+ #endif
/// @endcond
};
/// @cond
-class named_mutex::construct_func_t
-{
- public:
- enum CreationType { open_only, open_or_create, create_only };
- construct_func_t(CreationType type)
- : m_creation_type(type){}
+#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
- bool operator()(void *address, std::size_t, bool created) const
- {
- switch(m_creation_type){
- case open_only:
- return true;
- break;
- case create_only:
- case open_or_create:
- if(created){
- new(address)interprocess_mutex;
- }
- return true;
- break;
-
- default:
- return false;
- break;
- }
- return true;
- }
- private:
- CreationType m_creation_type;
-};
-/// @endcond
+inline named_mutex::named_mutex(create_only_t, const char *name)
+ : m_sem(detail::DoCreate, name, read_write, 1)
+{}
+
+inline named_mutex::named_mutex(open_or_create_t, const char *name)
+ : m_sem(detail::DoOpenOrCreate, name, read_write, 1)
+{}
+
+inline named_mutex::named_mutex(open_only_t, const char *name)
+ : m_sem(detail::DoOpen, name, read_write, 1)
+{}
+
+inline named_mutex::~named_mutex()
+{}
+
+inline void named_mutex::lock()
+{ m_sem.wait(); }
+
+inline void named_mutex::unlock()
+{ m_sem.post(); }
+
+inline bool named_mutex::try_lock()
+{ return m_sem.try_wait(); }
+
+inline bool named_mutex::timed_lock(const boost::posix_time::ptime &abs_time)
+{ return m_sem.timed_wait(abs_time); }
+
+inline bool named_mutex::remove(const char *name)
+{ return detail::named_semaphore_wrapper::remove(name); }
+
+#else //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
inline named_mutex::~named_mutex()
{}
@@ -140,7 +162,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::create_only))
+ ,construct_func_t(detail::DoCreate))
{}
inline named_mutex::named_mutex(open_or_create_t, const char *name)
@@ -151,7 +173,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::open_or_create))
+ ,construct_func_t(detail::DoOpenOrCreate))
{}
inline named_mutex::named_mutex(open_only_t, const char *name)
@@ -159,7 +181,7 @@
,name
,read_write
,0
- ,construct_func_t(construct_func_t::open_only))
+ ,construct_func_t(detail::DoOpen))
{}
inline void named_mutex::lock()
@@ -177,6 +199,10 @@
inline bool named_mutex::remove(const char *name)
{ return shared_memory_object::remove(name); }
+#endif //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+
+/// @endcond
+
} //namespace interprocess {
} //namespace boost {
Modified: branches/bcbboost/boost/interprocess/sync/named_recursive_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/named_recursive_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/named_recursive_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,17 +23,17 @@
#include <boost/interprocess/shared_memory_object.hpp>
#include <boost/interprocess/detail/managed_open_or_create_impl.hpp>
#include <boost/interprocess/sync/interprocess_recursive_mutex.hpp>
+#include <boost/interprocess/sync/emulation/named_creation_functor.hpp>
-/*!\file
- Describes a named interprocess_mutex class for inter-process synchronization
-*/
+//!\file
+//!Describes a named named_recursive_mutex class for inter-process synchronization
namespace boost {
namespace interprocess {
-/*!A recursive mutex with a global name, so it can be found from different
- processes. This mutex can't be placed in shared memory, and
- each process should have it's own named_recursive_mutex.*/
+//!A recursive mutex with a global name, so it can be found from different
+//!processes. This mutex can't be placed in shared memory, and
+//!each process should have it's own named_recursive_mutex.
class named_recursive_mutex
{
/// @cond
@@ -43,41 +43,52 @@
named_recursive_mutex &operator=(const named_recursive_mutex &);
/// @endcond
public:
- /*!Creates a global interprocess_mutex with a name.*/
+
+ //!Creates a global recursive_mutex with a name.
+ //!If the recursive_mutex can't be created throws interprocess_exception
named_recursive_mutex(create_only_t create_only, const char *name);
- /*!Opens or creates a global interprocess_mutex with a name.
- If the interprocess_mutex is created, this call is equivalent to create().
- If the interprocess_mutex is already created, this call is equivalent to open().
- Does not throw*/
+ //!Opens or creates a global recursive_mutex with a name.
+ //!If the recursive_mutex is created, this call is equivalent to
+ //!named_recursive_mutex(create_only_t, ... )
+ //!If the recursive_mutex is already created, this call is equivalent
+ //!named_recursive_mutex(open_only_t, ... )
+ //!Does not throw
named_recursive_mutex(open_or_create_t open_or_create, const char *name);
- /*!Opens a global interprocess_mutex with a name if that interprocess_mutex is previously.
- created. If it is not previously created this function return false.
- Does not throw*/
+ //!Opens a global recursive_mutex with a name if that recursive_mutex is previously
+ //!created. If it is not previously created this function throws
+ //!interprocess_exception.
named_recursive_mutex(open_only_t open_only, const char *name);
- /*!Destroys named interprocess_mutex. Does not throw*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~named_recursive_mutex();
- /*!Unlocks a previously locked interprocess_mutex.*/
+ //!Unlocks a previously locked
+ //!named_recursive_mutex.
void unlock();
- /*!Locks interprocess_mutex, sleeps when interprocess_mutex is already locked.
- Throws interprocess_exception if a severe error is found*/
+ //!Locks named_recursive_mutex, sleeps when named_recursive_mutex is already locked.
+ //!Throws interprocess_exception if a severe error is found.
void lock();
- /*! Tries to lock the interprocess_mutex, returns false when interprocess_mutex
- is already locked, returns true when success.
- Throws interprocess_exception if a severe error is found*/
+ //!Tries to lock the named_recursive_mutex, returns false when named_recursive_mutex
+ //!is already locked, returns true when success.
+ //!Throws interprocess_exception if a severe error is found.
bool try_lock();
- /*! Tries to lock the interprocess_mutex until time abs_time,
- Returns false when timeout expires, returns true when locks.
- Throws interprocess_exception if a severe error is found*/
+ //!Tries to lock the named_recursive_mutex until time abs_time,
+ //!Returns false when timeout expires, returns true when locks.
+ //!Throws interprocess_exception if a severe error is found
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*! Erases a named recursive mutex from the system*/
+ //!Erases a named recursive mutex
+ //!from the system
static bool remove(const char *name);
/// @cond
@@ -86,45 +97,10 @@
{ return static_cast<interprocess_recursive_mutex*>(m_shmem.get_address()); }
detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
-
- class construct_func_t;
+ typedef detail::named_creation_functor<interprocess_recursive_mutex> construct_func_t;
/// @endcond
};
-/// @cond
-class named_recursive_mutex::construct_func_t
-{
- public:
- enum CreationType { open_only, open_or_create, create_only };
-
- construct_func_t(CreationType type)
- : m_creation_type(type){}
-
- bool operator()(void *address, std::size_t, bool created) const
- {
- switch(m_creation_type){
- case open_only:
- return true;
- break;
- case create_only:
- case open_or_create:
- if(created){
- new(address)interprocess_recursive_mutex;
- }
- return true;
- break;
-
- default:
- return false;
- break;
- }
- return true;
- }
- private:
- CreationType m_creation_type;
-};
-/// @endcond
-
inline named_recursive_mutex::~named_recursive_mutex()
{}
@@ -136,7 +112,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::create_only))
+ ,construct_func_t(detail::DoCreate))
{}
inline named_recursive_mutex::named_recursive_mutex(open_or_create_t, const char *name)
@@ -147,7 +123,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::open_or_create))
+ ,construct_func_t(detail::DoOpenOrCreate))
{}
inline named_recursive_mutex::named_recursive_mutex(open_only_t, const char *name)
@@ -155,7 +131,7 @@
,name
,read_write
,0
- ,construct_func_t(construct_func_t::open_only))
+ ,construct_func_t(detail::DoOpen))
{}
inline void named_recursive_mutex::lock()
Modified: branches/bcbboost/boost/interprocess/sync/named_semaphore.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/named_semaphore.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/named_semaphore.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,113 +20,139 @@
#include <boost/interprocess/creation_tags.hpp>
#include <boost/interprocess/exceptions.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
+
+#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+#include <boost/interprocess/sync/posix/semaphore_wrapper.hpp>
+#else
#include <boost/interprocess/shared_memory_object.hpp>
#include <boost/interprocess/detail/managed_open_or_create_impl.hpp>
#include <boost/interprocess/sync/interprocess_semaphore.hpp>
+#include <boost/interprocess/sync/emulation/named_creation_functor.hpp>
+#endif
-/*!\file
- Describes a named semaphore class for inter-process synchronization
-*/
+//!\file
+//!Describes a named semaphore class for inter-process synchronization
namespace boost {
-
namespace interprocess {
-/*!A interprocess_semaphore with a global name, so it can be found from different
- processes. Allows several resource sharing patterns and efficient
- acknowledgment mechanisms.*/
+//!A semaphore with a global name, so it can be found from different
+//!processes. Allows several resource sharing patterns and efficient
+//!acknowledgment mechanisms.
class named_semaphore
{
/// @cond
+
//Non-copyable
named_semaphore();
named_semaphore(const named_semaphore &);
named_semaphore &operator=(const named_semaphore &);
/// @endcond
+
public:
- /*!Creates a global interprocess_semaphore with a name, and an initial count.
- It will return an false if the interprocess_semaphore is already created.*/
+ //!Creates a global semaphore with a name, and an initial count.
+ //!If the semaphore can't be created throws interprocess_exception
named_semaphore(create_only_t, const char *name, int initialCount);
- /*!Opens or creates a global interprocess_semaphore with a name, and an initial count.
- If the interprocess_semaphore is created, this call is equivalent to create().
- If the interprocess_semaphore is already created, this call is equivalent to open()
- and initialCount is ignored.*/
+ //!Opens or creates a global semaphore with a name, and an initial count.
+ //!If the semaphore is created, this call is equivalent to
+ //!named_semaphore(create_only_t, ...)
+ //!If the semaphore is already created, this call is equivalent to
+ //!named_semaphore(open_only_t, ... )
+ //!and initialCount is ignored.
named_semaphore(open_or_create_t, const char *name, int initialCount);
- /*!Opens a global interprocess_semaphore with a name if that interprocess_semaphore is previously.
- created. If it is not previously created this function return false.*/
+ //!Opens a global semaphore with a name if that semaphore is previously.
+ //!created. If it is not previously created this function throws
+ //!interprocess_exception.
named_semaphore(open_only_t, const char *name);
- /*!Destroys the named semaphore. Does not throw*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~named_semaphore();
- /*!Increments the interprocess_semaphore count. If there are processes/threads blocked waiting
- for the interprocess_semaphore, then one of these processes will return successfully from
- its wait function. If there is an error an interprocess_exception exception is thrown.*/
+ //!Increments the semaphore count. If there are processes/threads blocked waiting
+ //!for the semaphore, then one of these processes will return successfully from
+ //!its wait function. If there is an error an interprocess_exception exception is thrown.
void post();
- /*!Decrements the interprocess_semaphore. If the interprocess_semaphore value is not greater than zero,
- then the calling process/thread blocks until it can decrement the counter.
- If there is an error an interprocess_exception exception is thrown.*/
+ //!Decrements the semaphore. If the semaphore value is not greater than zero,
+ //!then the calling process/thread blocks until it can decrement the counter.
+ //!If there is an error an interprocess_exception exception is thrown.
void wait();
- /*!Decrements the interprocess_semaphore if the interprocess_semaphore's value is greater than zero
- and returns true. If the value is not greater than zero returns false.
- If there is an error an interprocess_exception exception is thrown.*/
+ //!Decrements the semaphore if the semaphore's value is greater than zero
+ //!and returns true. If the value is not greater than zero returns false.
+ //!If there is an error an interprocess_exception exception is thrown.
bool try_wait();
- /*!Decrements the interprocess_semaphore if the interprocess_semaphore's value is greater
- than zero and returns true. Otherwise, waits for the interprocess_semaphore
- to the posted or the timeout expires. If the timeout expires, the
- function returns false. If the interprocess_semaphore is posted the function
- returns true. If there is an error throws sem_exception*/
+ //!Decrements the semaphore if the semaphore's value is greater
+ //!than zero and returns true. Otherwise, waits for the semaphore
+ //!to the posted or the timeout expires. If the timeout expires, the
+ //!function returns false. If the semaphore is posted the function
+ //!returns true. If there is an error throws sem_exception
bool timed_wait(const boost::posix_time::ptime &abs_time);
- /*!Erases a named semaphore from the system*/
+ //!Erases a named semaphore from the system.
+ //!Returns false on error. Never throws.
static bool remove(const char *name);
/// @cond
private:
+ #ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ detail::named_semaphore_wrapper m_sem;
+ #else //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+ interprocess_semaphore *semaphore() const
+ { return static_cast<interprocess_semaphore*>(m_shmem.get_address()); }
+
detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
- class construct_func_t;
+ typedef detail::named_creation_functor<interprocess_semaphore, int> construct_func_t;
+ #endif
/// @endcond
};
/// @cond
-class named_semaphore::construct_func_t
-{
- public:
- enum CreationType { open_only, open_or_create, create_only };
- construct_func_t(CreationType type, int init_count)
- : m_creation_type(type), m_init_count(init_count){}
+#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
- bool operator()(void *address, std::size_t, bool created) const
- {
- switch(m_creation_type){
- case open_only:
- return true;
- break;
- case create_only:
- case open_or_create:
- if(created){
- new(address)interprocess_semaphore(m_init_count);
- }
- return true;
- break;
-
- default:
- return false;
- break;
- }
- return true;
- }
- private:
- CreationType m_creation_type;
- int m_init_count;
-};
-/// @endcond
+inline named_semaphore::named_semaphore
+ (create_only_t, const char *name, int initialCount)
+ : m_sem(detail::DoCreate, name, read_write, initialCount)
+{}
+
+inline named_semaphore::named_semaphore
+ (open_or_create_t, const char *name, int initialCount)
+ : m_sem(detail::DoOpenOrCreate, name, read_write, initialCount)
+{}
+
+inline named_semaphore::named_semaphore
+ (open_only_t, const char *name)
+ : m_sem(detail::DoOpen, name, read_write, 1)
+{}
+
+inline named_semaphore::~named_semaphore()
+{}
+
+inline void named_semaphore::wait()
+{ m_sem.wait(); }
+
+inline void named_semaphore::post()
+{ m_sem.post(); }
+
+inline bool named_semaphore::try_wait()
+{ return m_sem.try_wait(); }
+
+inline bool named_semaphore::timed_wait(const boost::posix_time::ptime &abs_time)
+{ return m_sem.timed_wait(abs_time); }
+
+inline bool named_semaphore::remove(const char *name)
+{ return detail::named_semaphore_wrapper::remove(name); }
+
+#else //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
inline named_semaphore::~named_semaphore()
{}
@@ -140,7 +166,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::create_only, initialCount))
+ ,construct_func_t(detail::DoCreate, initialCount))
{}
inline named_semaphore::named_semaphore
@@ -152,7 +178,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::open_or_create, initialCount))
+ ,construct_func_t(detail::DoOpenOrCreate, initialCount))
{}
inline named_semaphore::named_semaphore
@@ -161,26 +187,29 @@
,name
,read_write
,0
- ,construct_func_t(construct_func_t::open_only, 0))
+ ,construct_func_t(detail::DoOpen, 0))
{}
inline void named_semaphore::post()
-{ static_cast<interprocess_semaphore*>(m_shmem.get_address())->post(); }
+{ semaphore()->post(); }
inline void named_semaphore::wait()
-{ static_cast<interprocess_semaphore*>(m_shmem.get_address())->wait(); }
+{ semaphore()->wait(); }
inline bool named_semaphore::try_wait()
-{ return static_cast<interprocess_semaphore*>(m_shmem.get_address())->try_wait(); }
+{ return semaphore()->try_wait(); }
inline bool named_semaphore::timed_wait(const boost::posix_time::ptime &abs_time)
-{ return static_cast<interprocess_semaphore*>(m_shmem.get_address())->timed_wait(abs_time); }
+{ return semaphore()->timed_wait(abs_time); }
inline bool named_semaphore::remove(const char *name)
{ return shared_memory_object::remove(name); }
-} //namespace interprocess {
+#endif //#ifdef BOOST_INTERPROCESS_POSIX_SEMAPHORES
+
+/// @endcond
+} //namespace interprocess {
} //namespace boost {
Modified: branches/bcbboost/boost/interprocess/sync/named_upgradable_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/named_upgradable_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/named_upgradable_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,19 +23,19 @@
#include <boost/interprocess/detail/managed_open_or_create_impl.hpp>
#include <boost/interprocess/sync/interprocess_upgradable_mutex.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
+#include <boost/interprocess/sync/emulation/named_creation_functor.hpp>
-/*!\file
- Describes a named upgradable mutex class for inter-process synchronization
-*/
+//!\file
+//!Describes a named upgradable mutex class for inter-process synchronization
namespace boost {
namespace interprocess {
class named_condition;
-/*!A upgradable mutex with a global name, so it can be found from different
- processes. This mutex can't be placed in shared memory, and
- each process should have it's own named upgradable mutex.*/
+//!A upgradable mutex with a global name, so it can be found from different
+//!processes. This mutex can't be placed in shared memory, and
+//!each process should have it's own named upgradable mutex.
class named_upgradable_mutex
{
/// @cond
@@ -46,164 +46,174 @@
friend class named_condition;
/// @endcond
public:
- /*!Creates a global interprocess_mutex with a name.*/
+
+ //!Creates a global upgradable mutex with a name.
+ //!If the upgradable mutex can't be created throws interprocess_exception
named_upgradable_mutex(create_only_t create_only, const char *name);
- /*!Opens or creates a global upgradable mutex with a name.
- If the upgradable mutex is created, this call is equivalent to create().
- If the upgradable mutex is already created, this call is equivalent to open().
- Throws interprocess_exception on error.*/
+ //!Opens or creates a global upgradable mutex with a name, and an initial count.
+ //!If the upgradable mutex is created, this call is equivalent to
+ //!named_upgradable_mutex(create_only_t, ...)
+ //!If the upgradable mutex is already created, this call is equivalent to
+ //!named_upgradable_mutex(open_only_t, ... ).
named_upgradable_mutex(open_or_create_t open_or_create, const char *name);
- /*!Opens a global upgradable mutex with a name if that mutex is previously.
- created. If it is not previously created this function return false.
- Throws interprocess_exception on error.*/
+ //!Opens a global upgradable mutex with a name if that upgradable mutex
+ //!is previously.
+ //!created. If it is not previously created this function throws
+ //!interprocess_exception.
named_upgradable_mutex(open_only_t open_only, const char *name);
- /*!Closes the named upgradable mutex. Does not throw*/
+ //!Destroys *this and indicates that the calling process is finished using
+ //!the resource. The destructor function will deallocate
+ //!any system resources allocated by the system for use by this process for
+ //!this resource. The resource can still be opened again calling
+ //!the open constructor overload. To erase the resource from the system
+ //!use remove().
~named_upgradable_mutex();
//Exclusive locking
- /*!Effects: The calling thread tries to obtain exclusive ownership of the mutex,
- and if another thread has exclusive, sharable or upgradable ownership of
- the mutex, it waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain exclusive ownership of the mutex,
+ //! and if another thread has exclusive, sharable or upgradable ownership of
+ //! the mutex, it waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock();
- /*!Effects: The calling thread tries to acquire exclusive ownership of the mutex
- without waiting. If no other thread has exclusive, sharable or upgradable
- ownership of the mutex this succeeds.
- Returns: If it can acquire exclusive ownership immediately returns true.
- If it has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire exclusive ownership of the mutex
+ //! without waiting. If no other thread has exclusive, sharable or upgradable
+ //! ownership of the mutex this succeeds.
+ //!Returns: If it can acquire exclusive ownership immediately returns true.
+ //! If it has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock();
- /*!Effects: The calling thread tries to acquire exclusive ownership of the mutex
- waiting if necessary until no other thread has has exclusive, sharable or
- upgradable ownership of the mutex or abs_time is reached.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire exclusive ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive, sharable or
+ //! upgradable ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The calling thread releases the exclusive ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The calling thread releases the exclusive ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock();
//Sharable locking
- /*!Effects: The calling thread tries to obtain sharable ownership of the mutex,
- and if another thread has exclusive or upgradable ownership of the mutex,
- waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain sharable ownership of the mutex,
+ //! and if another thread has exclusive or upgradable ownership of the mutex,
+ //! waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock_sharable();
- /*!Effects: The calling thread tries to acquire sharable ownership of the mutex
- without waiting. If no other thread has has exclusive or upgradable ownership
- of the mutex this succeeds.
- Returns: If it can acquire sharable ownership immediately returns true. If it
- has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire sharable ownership of the mutex
+ //! without waiting. If no other thread has has exclusive or upgradable ownership
+ //! of the mutex this succeeds.
+ //!Returns: If it can acquire sharable ownership immediately returns true. If it
+ //! has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock_sharable();
- /*!Effects: The calling thread tries to acquire sharable ownership of the mutex
- waiting if necessary until no other thread has has exclusive or upgradable
- ownership of the mutex or abs_time is reached.
- Returns: If acquires sharable ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire sharable ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive or upgradable
+ //! ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires sharable ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock_sharable(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have sharable ownership of the mutex.
- Effects: The calling thread releases the sharable ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have sharable ownership of the mutex.
+ //!Effects: The calling thread releases the sharable ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_sharable();
//Upgradable locking
- /*!Effects: The calling thread tries to obtain upgradable ownership of the mutex,
- and if another thread has exclusive or upgradable ownership of the mutex,
- waits until it can obtain the ownership.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to obtain upgradable ownership of the mutex,
+ //! and if another thread has exclusive or upgradable ownership of the mutex,
+ //! waits until it can obtain the ownership.
+ //!Throws: interprocess_exception on error.
void lock_upgradable();
- /*!Effects: The calling thread tries to acquire upgradable ownership of the mutex
- without waiting. If no other thread has has exclusive or upgradable ownership
- of the mutex this succeeds.
- Returns: If it can acquire upgradable ownership immediately returns true.
- If it has to wait, returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire upgradable ownership of the mutex
+ //! without waiting. If no other thread has has exclusive or upgradable ownership
+ //! of the mutex this succeeds.
+ //!Returns: If it can acquire upgradable ownership immediately returns true.
+ //! If it has to wait, returns false.
+ //!Throws: interprocess_exception on error.
bool try_lock_upgradable();
- /*!Effects: The calling thread tries to acquire upgradable ownership of the mutex
- waiting if necessary until no other thread has has exclusive or upgradable
- ownership of the mutex or abs_time is reached.
- Returns: If acquires upgradable ownership, returns true. Otherwise returns false.
- Throws: interprocess_exception on error.*/
+ //!Effects: The calling thread tries to acquire upgradable ownership of the mutex
+ //! waiting if necessary until no other thread has has exclusive or upgradable
+ //! ownership of the mutex or abs_time is reached.
+ //!Returns: If acquires upgradable ownership, returns true. Otherwise returns false.
+ //!Throws: interprocess_exception on error.
bool timed_lock_upgradable(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The calling thread releases the upgradable ownership of the mutex.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The calling thread releases the upgradable ownership of the mutex.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_upgradable();
//Demotions
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The thread atomically releases exclusive ownership and acquires
- upgradable ownership. This operation is non-blocking.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The thread atomically releases exclusive ownership and acquires
+ //! upgradable ownership. This operation is non-blocking.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_and_lock_upgradable();
- /*!Precondition: The thread must have exclusive ownership of the mutex.
- Effects: The thread atomically releases exclusive ownership and acquires
- sharable ownership. This operation is non-blocking.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have exclusive ownership of the mutex.
+ //!Effects: The thread atomically releases exclusive ownership and acquires
+ //! sharable ownership. This operation is non-blocking.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_and_lock_sharable();
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and acquires
- sharable ownership. This operation is non-blocking.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and acquires
+ //! sharable ownership. This operation is non-blocking.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_upgradable_and_lock_sharable();
//Promotions
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and acquires
- exclusive ownership. This operation will block until all threads with
- sharable ownership releas it.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and acquires
+ //! exclusive ownership. This operation will block until all threads with
+ //! sharable ownership releas it.
+ //!Throws: An exception derived from interprocess_exception on error.
void unlock_upgradable_and_lock();
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and tries to
- acquire exclusive ownership. This operation will fail if there are threads
- with sharable ownership, but it will maintain upgradable ownership.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and tries to
+ //! acquire exclusive ownership. This operation will fail if there are threads
+ //! with sharable ownership, but it will maintain upgradable ownership.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error.
bool try_unlock_upgradable_and_lock();
- /*!Precondition: The thread must have upgradable ownership of the mutex.
- Effects: The thread atomically releases upgradable ownership and tries to acquire
- exclusive ownership, waiting if necessary until abs_time. This operation will
- fail if there are threads with sharable ownership or timeout reaches, but it
- will maintain upgradable ownership.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error. */
+ //!Precondition: The thread must have upgradable ownership of the mutex.
+ //!Effects: The thread atomically releases upgradable ownership and tries to acquire
+ //! exclusive ownership, waiting if necessary until abs_time. This operation will
+ //! fail if there are threads with sharable ownership or timeout reaches, but it
+ //! will maintain upgradable ownership.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error.
bool timed_unlock_upgradable_and_lock(const boost::posix_time::ptime &abs_time);
- /*!Precondition: The thread must have sharable ownership of the mutex.
- Effects: The thread atomically releases sharable ownership and tries to acquire
- exclusive ownership. This operation will fail if there are threads with sharable
- or upgradable ownership, but it will maintain sharable ownership.
- Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
- Throws: An exception derived from interprocess_exception on error.*/
+ //!Precondition: The thread must have sharable ownership of the mutex.
+ //!Effects: The thread atomically releases sharable ownership and tries to acquire
+ //! exclusive ownership. This operation will fail if there are threads with sharable
+ //! or upgradable ownership, but it will maintain sharable ownership.
+ //!Returns: If acquires exclusive ownership, returns true. Otherwise returns false.
+ //!Throws: An exception derived from interprocess_exception on error.
bool try_unlock_sharable_and_lock();
bool try_unlock_sharable_and_lock_upgradable();
- /*! Erases a named upgradable mutex from the system*/
+ //!Erases a named upgradable mutex from the system.
+ //!Returns false on error. Never throws.
static bool remove(const char *name);
/// @cond
@@ -212,43 +222,10 @@
{ return static_cast<interprocess_upgradable_mutex*>(m_shmem.get_address()); }
detail::managed_open_or_create_impl<shared_memory_object> m_shmem;
-
- class construct_func_t;
+ typedef detail::named_creation_functor<interprocess_upgradable_mutex> construct_func_t;
/// @endcond
};
-/// @cond
-class named_upgradable_mutex::construct_func_t
-{
- public:
- enum CreationType { open_only, open_or_create, create_only };
- construct_func_t(CreationType type)
- : m_creation_type(type){}
-
- bool operator()(void *address, std::size_t, bool created) const
- {
- switch(m_creation_type){
- case open_only:
- return true;
- break;
- case create_only:
- case open_or_create:
- if(created){
- new(address)interprocess_upgradable_mutex;
- }
- return true;
- break;
-
- default:
- return false;
- break;
- }
- return true;
- }
- private:
- CreationType m_creation_type;
-};
-/// @endcond
inline named_upgradable_mutex::~named_upgradable_mutex()
{}
@@ -261,7 +238,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::create_only))
+ ,construct_func_t(detail::DoCreate))
{}
inline named_upgradable_mutex::named_upgradable_mutex
@@ -273,7 +250,7 @@
ManagedOpenOrCreateUserOffset
,read_write
,0
- ,construct_func_t(construct_func_t::open_or_create))
+ ,construct_func_t(detail::DoOpenOrCreate))
{}
inline named_upgradable_mutex::named_upgradable_mutex
@@ -282,7 +259,7 @@
,name
,read_write
,0
- ,construct_func_t(construct_func_t::open_only))
+ ,construct_func_t(detail::DoOpen))
{}
inline void named_upgradable_mutex::lock()
Modified: branches/bcbboost/boost/interprocess/sync/null_mutex.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/null_mutex.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/null_mutex.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -19,9 +19,8 @@
#include <boost/interprocess/detail/workaround.hpp>
-/*!\file
- Describes null_mutex classes
-*/
+//!\file
+//!Describes null_mutex classes
namespace boost {
@@ -30,8 +29,8 @@
namespace interprocess {
-/*!Implements a mutex that simulates a mutex without doing any operation and
- simulates a successful operation.*/
+//!Implements a mutex that simulates a mutex without doing any operation and
+//!simulates a successful operation.
class null_mutex
{
/// @cond
@@ -40,97 +39,102 @@
/// @endcond
public:
- /*!Constructor. Empty.*/
+ //!Constructor.
+ //!Empty.
null_mutex(){}
- /*!Destructor. Empty.*/
+ //!Destructor.
+ //!Empty.
~null_mutex(){}
- /*!Simulates a mutex lock() operation. Empty function. Does not throw.*/
+ //!Simulates a mutex lock() operation. Empty function.
void lock(){}
- /*!Simulates a mutex try_lock() operation. Returns always true. Does not throw.*/
+ //!Simulates a mutex try_lock() operation.
+ //!Equivalent to "return true;"
bool try_lock()
{ return true; }
- /*!Simulates a mutex timed_lock() operation. Returns always true. Does not throw.*/
+ //!Simulates a mutex timed_lock() operation.
+ //!Equivalent to "return true;"
bool timed_lock(const boost::posix_time::ptime &)
{ return true; }
- /*!Simulates a mutex unlock() operation. Empty function. Does not throw.*/
+ //!Simulates a mutex unlock() operation.
+ //!Empty function.
void unlock(){}
- /*!Simulates a mutex lock_sharable() operation. Empty function.
- Does not throw.*/
+ //!Simulates a mutex lock_sharable() operation.
+ //!Empty function.
void lock_sharable(){}
- /*!Simulates a mutex try_lock_sharable() operation. Returns always true.
- Does not throw.*/
+ //!Simulates a mutex try_lock_sharable() operation.
+ //!Equivalent to "return true;"
bool try_lock_sharable()
{ return true; }
- /*!Simulates a mutex timed_lock_sharable() operation. Returns always true.
- Does not throw.*/
+ //!Simulates a mutex timed_lock_sharable() operation.
+ //!Equivalent to "return true;"
bool timed_lock_sharable(const boost::posix_time::ptime &)
{ return true; }
- /*!Simulates a mutex unlock_sharable() operation. Empty function.
- Does not throw.*/
+ //!Simulates a mutex unlock_sharable() operation.
+ //!Empty function.
void unlock_sharable(){}
- /*!Simulates a mutex lock_upgradable() operation. Empty function.
- Does not throw.*/
+ //!Simulates a mutex lock_upgradable() operation.
+ //!Empty function.
void lock_upgradable(){}
- /*!Simulates a mutex try_lock_upgradable() operation. Returns always true.
- Does not throw.*/
+ //!Simulates a mutex try_lock_upgradable() operation.
+ //!Equivalent to "return true;"
bool try_lock_upgradable()
{ return true; }
- /*!Simulates a mutex timed_lock_upgradable() operation. Returns always true.
- Does not throw.*/
+ //!Simulates a mutex timed_lock_upgradable() operation.
+ //!Equivalent to "return true;"
bool timed_lock_upgradable(const boost::posix_time::ptime &)
{ return true; }
- /*!Simulates a mutex unlock_upgradable() operation. Empty function.
- Does not throw.*/
+ //!Simulates a mutex unlock_upgradable() operation.
+ //!Empty function.
void unlock_upgradable(){}
- /*!Simulates unlock_and_lock_upgradable(). Empty function.
- Does not throw.*/
+ //!Simulates unlock_and_lock_upgradable().
+ //!Empty function.
void unlock_and_lock_upgradable(){}
- /*!Simulates unlock_and_lock_sharable(). Empty function.
- Does not throw.*/
+ //!Simulates unlock_and_lock_sharable().
+ //!Empty function.
void unlock_and_lock_sharable(){}
- /*!Simulates unlock_upgradable_and_lock_sharable(). Empty function.
- Does not throw.*/
+ //!Simulates unlock_upgradable_and_lock_sharable().
+ //!Empty function.
void unlock_upgradable_and_lock_sharable(){}
//Promotions
- /*!Simulates unlock_upgradable_and_lock(). Empty function.
- Does not throw.*/
+ //!Simulates unlock_upgradable_and_lock().
+ //!Empty function.
void unlock_upgradable_and_lock(){}
- /*!Simulates try_unlock_upgradable_and_lock(). Returns always true.
- Does not throw.*/
+ //!Simulates try_unlock_upgradable_and_lock().
+ //!Equivalent to "return true;"
bool try_unlock_upgradable_and_lock()
{ return true; }
- /*!Simulates timed_unlock_upgradable_and_lock(). Returns always true.
- Does not throw.*/
+ //!Simulates timed_unlock_upgradable_and_lock().
+ //!Equivalent to "return true;"
bool timed_unlock_upgradable_and_lock(const boost::posix_time::ptime &)
{ return true; }
- /*!Simulates try_unlock_sharable_and_lock(). Returns always true.
- Does not throw.*/
+ //!Simulates try_unlock_sharable_and_lock().
+ //!Equivalent to "return true;"
bool try_unlock_sharable_and_lock()
{ return true; }
- /*!Simulates try_unlock_sharable_and_lock_upgradable(). Returns always true.
- Does not throw.*/
+ //!Simulates try_unlock_sharable_and_lock_upgradable().
+ //!Equivalent to "return true;"
bool try_unlock_sharable_and_lock_upgradable()
{ return true; }
};
Modified: branches/bcbboost/boost/interprocess/sync/posix/pthread_helpers.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/posix/pthread_helpers.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/posix/pthread_helpers.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -28,10 +28,10 @@
#if defined BOOST_INTERPROCESS_POSIX_PROCESS_SHARED
- /*!Makes pthread_mutexattr_t cleanup easy when using exceptions*/
+ //!Makes pthread_mutexattr_t cleanup easy when using exceptions
struct mutexattr_wrapper
{
- /*!Constructor*/
+ //!Constructor
mutexattr_wrapper(bool recursive = false)
{
if(pthread_mutexattr_init(&m_attr)!=0 ||
@@ -41,19 +41,19 @@
throw boost::interprocess::interprocess_exception();
}
- /*!Destructor*/
+ //!Destructor
~mutexattr_wrapper() { pthread_mutexattr_destroy(&m_attr); }
- /*!This allows using mutexattr_wrapper as pthread_mutexattr_t*/
+ //!This allows using mutexattr_wrapper as pthread_mutexattr_t
operator pthread_mutexattr_t&() { return m_attr; }
pthread_mutexattr_t m_attr;
};
- /*!Makes pthread_condattr_t cleanup easy when using exceptions*/
+ //!Makes pthread_condattr_t cleanup easy when using exceptions
struct condattr_wrapper
{
- /*!Constructor*/
+ //!Constructor
condattr_wrapper()
{
if(pthread_condattr_init(&m_attr)!=0 ||
@@ -61,20 +61,20 @@
throw boost::interprocess::interprocess_exception();
}
- /*!Destructor*/
+ //!Destructor
~condattr_wrapper() { pthread_condattr_destroy(&m_attr); }
- /*!This allows using condattr_wrapper as pthread_condattr_t*/
+ //!This allows using condattr_wrapper as pthread_condattr_t
operator pthread_condattr_t&(){ return m_attr; }
pthread_condattr_t m_attr;
};
- /*!Makes initialized pthread_mutex_t cleanup easy when using exceptions*/
+ //!Makes initialized pthread_mutex_t cleanup easy when using exceptions
class mutex_initializer
{
public:
- /*!Constructor. Takes interprocess_mutex attributes to initialize the interprocess_mutex*/
+ //!Constructor. Takes interprocess_mutex attributes to initialize the interprocess_mutex
mutex_initializer(pthread_mutex_t &mut, pthread_mutexattr_t &mut_attr)
: mp_mut(&mut)
{
@@ -90,7 +90,7 @@
pthread_mutex_t *mp_mut;
};
- /*!Makes initialized pthread_cond_t cleanup easy when using exceptions*/
+ //!Makes initialized pthread_cond_t cleanup easy when using exceptions
class condition_initializer
{
public:
@@ -113,10 +113,10 @@
#if defined BOOST_INTERPROCESS_POSIX_BARRIERS
- /*!Makes pthread_barrierattr_t cleanup easy when using exceptions*/
+ //!Makes pthread_barrierattr_t cleanup easy when using exceptions
struct barrierattr_wrapper
{
- /*!Constructor*/
+ //!Constructor
barrierattr_wrapper()
{
if(pthread_barrierattr_init(&m_attr)!=0 ||
@@ -124,20 +124,20 @@
throw boost::interprocess::interprocess_exception();
}
- /*!Destructor*/
+ //!Destructor
~barrierattr_wrapper() { pthread_barrierattr_destroy(&m_attr); }
- /*!This allows using mutexattr_wrapper as pthread_barrierattr_t*/
+ //!This allows using mutexattr_wrapper as pthread_barrierattr_t
operator pthread_barrierattr_t&() { return m_attr; }
pthread_barrierattr_t m_attr;
};
- /*!Makes initialized pthread_barrier_t cleanup easy when using exceptions*/
+ //!Makes initialized pthread_barrier_t cleanup easy when using exceptions
class barrier_initializer
{
public:
- /*!Constructor. Takes barrier attributes to initialize the barrier*/
+ //!Constructor. Takes barrier attributes to initialize the barrier
barrier_initializer(pthread_barrier_t &mut,
pthread_barrierattr_t &mut_attr,
int count)
Modified: branches/bcbboost/boost/interprocess/sync/posix/semaphore_wrapper.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/posix/semaphore_wrapper.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/posix/semaphore_wrapper.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -11,90 +11,247 @@
#ifndef BOOST_INTERPROCESS_POSIX_SEMAPHORE_WRAPPER_HPP
#define BOOST_INTERPROCESS_POSIX_SEMAPHORE_WRAPPER_HPP
-#include <boost/interprocess/sync/posix/ptime_to_timespec.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
#include <boost/interprocess/exceptions.hpp>
+#include <boost/interprocess/creation_tags.hpp>
+#include <boost/interprocess/detail/os_file_functions.hpp>
+#include <string>
+#include <semaphore.h>
+
+#ifdef BOOST_INTERPROCESS_POSIX_TIMEOUTS
+#include <boost/interprocess/sync/posix/ptime_to_timespec.hpp>
+#else
+#include <boost/interprocess/detail/os_thread_functions.hpp>
+#endif
namespace boost {
namespace interprocess {
namespace detail {
-class semaphore_wrapper
+inline bool semaphore_open
+ (sem_t *&handle, detail::create_enum_t type, const char *origname, mode_t mode,
+ unsigned int count)
{
- semaphore_wrapper();
- semaphore_wrapper(const semaphore_wrapper&);
- semaphore_wrapper &operator= (const semaphore_wrapper &);
- public:
- semaphore_wrapper(int initialCount)
- {
- int ret = sem_init(&m_sem, 1, initialCount);
- if(ret != 0){
- throw interprocess_exception(system_error_code());
- }
+ bool slash_added = origname[0] != '/';
+ //First add preceding "/"
+ std::string name;
+
+ if(slash_added){
+ name = '/';
+ }
+ name += origname;
+
+ //Create new mapping
+ int oflag = 0;
+ if(mode == read_only){
+ oflag |= O_RDONLY;
+ }
+ else if(mode == read_write){
+ oflag |= O_RDWR;
+ }
+ else{
+ error_info err(mode_error);
+ throw interprocess_exception(err);
+ }
+
+ switch(type){
+ case detail::DoOpen:
+ //No addition
+ break;
+ case detail::DoCreate:
+ oflag |= (O_CREAT | O_EXCL);
+ break;
+ case detail::DoOpenOrCreate:
+ oflag |= O_CREAT;
+ break;
+ default:
+ {
+ error_info err = other_error;
+ throw interprocess_exception(err);
+ }
}
- ~semaphore_wrapper()
- {
- int ret = sem_destroy(&m_sem);
- if(ret != 0){
- assert(0);
- }
+ //Open file using POSIX API
+ if(oflag & O_CREAT)
+ handle = sem_open(name.c_str(), oflag, S_IRWXO | S_IRWXG | S_IRWXU, count);
+ else
+ handle = sem_open(name.c_str(), oflag);
+
+ //Check for error
+ if(handle == SEM_FAILED){
+ throw interprocess_exception(error_info(errno));
}
- void post()
- {
- int ret = sem_post(&m_sem);
- if(ret != 0){
- throw interprocess_exception(system_error_code());
- }
+ if(slash_added){
+ name.erase(name.begin());
}
- void wait()
- {
- int ret = sem_wait(&m_sem);
- if(ret != 0){
- throw interprocess_exception(system_error_code());
+ return true;
+}
+
+inline void semaphore_close(sem_t *handle)
+{
+ int ret = sem_close(handle);
+ if(ret != 0){
+ assert(0);
+ }
+}
+
+inline bool semaphore_unlink(const char *name)
+{
+ try{
+ std::string str;
+ //First add preceding "/"
+ if(name[0] != '/'){
+ str = '/';
}
+ str += name;
+ return 0 != sem_unlink(str.c_str());
+ }
+ catch(...){
+ return false;
}
+}
- bool try_wait()
- {
- int res = sem_trywait(&m_sem);
+inline void semaphore_init(sem_t *handle, int initialCount)
+{
+ int ret = sem_init(handle, 1, initialCount);
+ if(ret != 0){
+ throw interprocess_exception(system_error_code());
+ }
+}
+
+inline void semaphore_destroy(sem_t *handle)
+{
+ int ret = sem_destroy(handle);
+ if(ret != 0){
+ assert(0);
+ }
+}
+
+inline void semaphore_post(sem_t *handle)
+{
+ int ret = sem_post(handle);
+ if(ret != 0){
+ throw interprocess_exception(system_error_code());
+ }
+}
+
+inline void semaphore_wait(sem_t *handle)
+{
+ int ret = sem_wait(handle);
+ if(ret != 0){
+ throw interprocess_exception(system_error_code());
+ }
+}
+
+inline bool semaphore_try_wait(sem_t *handle)
+{
+ int res = sem_trywait(handle);
+ if(res == 0)
+ return true;
+ if(system_error_code() == EAGAIN){
+ return false;
+ }
+ throw interprocess_exception(system_error_code());
+ return false;
+}
+
+inline bool semaphore_timed_wait(sem_t *handle, const boost::posix_time::ptime &abs_time)
+{
+ #ifdef BOOST_INTERPROCESS_POSIX_TIMEOUTS
+ timespec tspec = detail::ptime_to_timespec(abs_time);
+ for (;;){
+ int res = sem_timedwait(handle, &tspec);
if(res == 0)
return true;
- if(system_error_code() == EAGAIN){
+ if (res > 0){
+ //buggy glibc, copy the returned error code to errno
+ errno = res;
+ }
+ if(system_error_code() == ETIMEDOUT){
return false;
}
throw interprocess_exception(system_error_code());
- return false;
}
-
- bool timed_wait(const boost::posix_time::ptime &abs_time)
- {
- timespec tspec = detail::ptime_to_timespec(abs_time);
- for (;;){
- int res = sem_timedwait(&m_sem, &tspec);
- if(res == 0)
- return true;
- if (res > 0){
- //buggy glibc, copy the returned error code to errno
- errno = res;
- }
- if(system_error_code() == ETIMEDOUT){
- return false;
- }
- throw interprocess_exception(system_error_code());
- }
- return false;
+ return false;
+ #else //#ifdef BOOST_INTERPROCESS_POSIX_TIMEOUTS
+ boost::posix_time::ptime now;
+ while((now = microsec_clock::universal_time()) < abs_time){
+ if(semaphore_try_wait(handle))
+ return true;
+ thread_yield();
}
+ return false;
+ #endif //#ifdef BOOST_INTERPROCESS_POSIX_TIMEOUTS
+}
/*
- int get_count()const
- {
- int count;
- sem_getvalue(&m_sem, &ret);
- return count;
- }
+inline int semaphore_get_count(sem_t *handle)
+{
+ int count;
+ sem_getvalue(handle, &ret);
+ return count;
+}
*/
+
+class named_semaphore_wrapper
+{
+ named_semaphore_wrapper();
+ named_semaphore_wrapper(const named_semaphore_wrapper&);
+ named_semaphore_wrapper &operator= (const named_semaphore_wrapper &);
+
+ public:
+ named_semaphore_wrapper
+ (detail::create_enum_t type, const char *name, mode_t mode, unsigned int count)
+ { semaphore_open(mp_sem, type, name, mode, count); }
+
+ ~named_semaphore_wrapper()
+ { semaphore_close(mp_sem); }
+
+ void post()
+ { semaphore_post(mp_sem); }
+
+ void wait()
+ { semaphore_wait(mp_sem); }
+
+ bool try_wait()
+ { return semaphore_try_wait(mp_sem); }
+
+ bool timed_wait(const boost::posix_time::ptime &abs_time)
+ { return semaphore_timed_wait(mp_sem, abs_time); }
+
+ static bool remove(const char *name)
+ { return semaphore_unlink(name); }
+
+ private:
+ sem_t *mp_sem;
+};
+
+class semaphore_wrapper
+{
+ semaphore_wrapper();
+ semaphore_wrapper(const semaphore_wrapper&);
+ semaphore_wrapper &operator= (const semaphore_wrapper &);
+
+ public:
+ semaphore_wrapper(int initialCount)
+ { semaphore_init(&m_sem, initialCount); }
+
+ ~semaphore_wrapper()
+ { semaphore_destroy(&m_sem); }
+
+ void post()
+ { semaphore_post(&m_sem); }
+
+ void wait()
+ { semaphore_wait(&m_sem); }
+
+ bool try_wait()
+ { return semaphore_try_wait(&m_sem); }
+
+ bool timed_wait(const boost::posix_time::ptime &abs_time)
+ { return semaphore_timed_wait(&m_sem, abs_time); }
+
private:
sem_t m_sem;
};
Modified: branches/bcbboost/boost/interprocess/sync/scoped_lock.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/scoped_lock.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/scoped_lock.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -27,9 +27,8 @@
#include <boost/interprocess/detail/move.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
-/*!\file
- Describes the scoped_lock class.
-*/
+//!\file
+//!Describes the scoped_lock class.
namespace boost {
namespace interprocess {
@@ -40,16 +39,16 @@
template<class M>
class upgradable_lock;
-/*!scoped_lock is meant to carry out the tasks for locking, unlocking, try-locking
- and timed-locking (recursive or not) for the Mutex. The Mutex need not supply all
- of this functionality. If the client of scoped_lock<Mutex> does not use
- functionality which the Mutex does not supply, no harm is done. Mutex ownership
- transfer is supported through the syntax of move semantics. Ownership transfer
- is allowed both by construction and assignment. The scoped_lock does not support
- copy semantics. A compile time error results if copy construction or copy
- assignment is attempted. Mutex ownership can also be moved from an
- upgradable_lock and sharable_lock via constructor. In this role, scoped_lock
- shares the same functionality as a write_lock.*/
+//!scoped_lock is meant to carry out the tasks for locking, unlocking, try-locking
+//!and timed-locking (recursive or not) for the Mutex. The Mutex need not supply all
+//!of this functionality. If the client of scoped_lock<Mutex> does not use
+//!functionality which the Mutex does not supply, no harm is done. Mutex ownership
+//!transfer is supported through the syntax of move semantics. Ownership transfer
+//!is allowed both by construction and assignment. The scoped_lock does not support
+//!copy semantics. A compile time error results if copy construction or copy
+//!assignment is attempted. Mutex ownership can also be moved from an
+//!upgradable_lock and sharable_lock via constructor. In this role, scoped_lock
+//!shares the same functionality as a write_lock.
template <class Mutex>
class scoped_lock
{
@@ -63,69 +62,69 @@
public:
typedef Mutex mutex_type;
- /*!Effects: Default constructs a scoped_lock.
- Postconditions: owns() == false and mutex() == 0.*/
+ //!Effects: Default constructs a scoped_lock.
+ //!Postconditions: owns() == false and mutex() == 0.
scoped_lock()
: mp_mutex(0), m_locked(false)
{}
- /*!Effects: m.lock().
- Postconditions: owns() == true and mutex() == &m.
- Notes: The constructor will take ownership of the mutex. If another thread
- already owns the mutex, this thread will block until the mutex is released.
- Whether or not this constructor handles recursive locking depends upon the mutex.*/
+ //!Effects: m.lock().
+ //!Postconditions: owns() == true and mutex() == &m.
+ //!Notes: The constructor will take ownership of the mutex. If another thread
+ //! already owns the mutex, this thread will block until the mutex is released.
+ //! Whether or not this constructor handles recursive locking depends upon the mutex.
explicit scoped_lock(mutex_type& m)
: mp_mutex(&m), m_locked(false)
{ mp_mutex->lock(); m_locked = true; }
- /*!Postconditions: owns() == false, and mutex() == &m.
- Notes: The constructor will not take ownership of the mutex. There is no effect
- required on the referenced mutex.*/
+ //!Postconditions: owns() == false, and mutex() == &m.
+ //!Notes: The constructor will not take ownership of the mutex. There is no effect
+ //! required on the referenced mutex.
scoped_lock(mutex_type& m, detail::defer_lock_type)
: mp_mutex(&m), m_locked(false)
{}
- /*!Postconditions: owns() == true, and mutex() == &m.
- Notes: The constructor will suppose that the mutex is already locked. There
- is no effect required on the referenced mutex.*/
+ //!Postconditions: owns() == true, and mutex() == &m.
+ //!Notes: The constructor will suppose that the mutex is already locked. There
+ //! is no effect required on the referenced mutex.
scoped_lock(mutex_type& m, detail::accept_ownership_type)
: mp_mutex(&m), m_locked(true)
{}
- /*!Effects: m.try_lock().
- Postconditions: mutex() == &m. owns() == the return value of the
- m.try_lock() executed within the constructor.
- Notes: The constructor will take ownership of the mutex if it can do
- so without waiting. Whether or not this constructor handles recursive
- locking depends upon the mutex. If the mutex_type does not support try_lock,
- this constructor will fail at compile time if instantiated, but otherwise
- have no effect.*/
+ //!Effects: m.try_lock().
+ //!Postconditions: mutex() == &m. owns() == the return value of the
+ //! m.try_lock() executed within the constructor.
+ //!Notes: The constructor will take ownership of the mutex if it can do
+ //! so without waiting. Whether or not this constructor handles recursive
+ //! locking depends upon the mutex. If the mutex_type does not support try_lock,
+ //! this constructor will fail at compile time if instantiated, but otherwise
+ //! have no effect.
scoped_lock(mutex_type& m, detail::try_to_lock_type)
: mp_mutex(&m), m_locked(mp_mutex->try_lock())
{}
- /*!Effects: m.timed_lock(abs_time).
- Postconditions: mutex() == &m. owns() == the return value of the
- m.timed_lock(abs_time) executed within the constructor.
- Notes: The constructor will take ownership of the mutex if it can do
- it until abs_time is reached. Whether or not this constructor
- handles recursive locking depends upon the mutex. If the mutex_type
- does not support try_lock, this constructor will fail at compile
- time if instantiated, but otherwise have no effect.*/
+ //!Effects: m.timed_lock(abs_time).
+ //!Postconditions: mutex() == &m. owns() == the return value of the
+ //! m.timed_lock(abs_time) executed within the constructor.
+ //!Notes: The constructor will take ownership of the mutex if it can do
+ //! it until abs_time is reached. Whether or not this constructor
+ //! handles recursive locking depends upon the mutex. If the mutex_type
+ //! does not support try_lock, this constructor will fail at compile
+ //! time if instantiated, but otherwise have no effect.
scoped_lock(mutex_type& m, const boost::posix_time::ptime& abs_time)
: mp_mutex(&m), m_locked(mp_mutex->timed_lock(abs_time))
{}
- /*!Postconditions: mutex() == the value scop.mutex() had before the
- constructor executes. s1.mutex() == 0. owns() == the value of
- scop.owns() before the constructor executes. scop.owns().
- Notes: If the scop scoped_lock owns the mutex, ownership is moved
- to thisscoped_lock with no blocking. If the scop scoped_lock does not
- own the mutex, then neither will this scoped_lock. Only a moved
- scoped_lock's will match this signature. An non-moved scoped_lock
- can be moved with the expression: "move(lock);". This
- constructor does not alter the state of the mutex, only potentially
- who owns it.*/
+ //!Postconditions: mutex() == the value scop.mutex() had before the
+ //! constructor executes. s1.mutex() == 0. owns() == the value of
+ //! scop.owns() before the constructor executes. scop.owns().
+ //!Notes: If the scop scoped_lock owns the mutex, ownership is moved
+ //! to thisscoped_lock with no blocking. If the scop scoped_lock does not
+ //! own the mutex, then neither will this scoped_lock. Only a moved
+ //! scoped_lock's will match this signature. An non-moved scoped_lock
+ //! can be moved with the expression: "move(lock);". This
+ //! constructor does not alter the state of the mutex, only potentially
+ //! who owns it.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit scoped_lock(detail::moved_object<scoped_lock<Mutex> > scop)
: mp_mutex(0), m_locked(scop.get().owns())
@@ -136,18 +135,18 @@
{ mp_mutex = scop.release(); }
#endif
- /*!Effects: If upgr.owns() then calls unlock_upgradable_and_lock() on the
- referenced mutex. upgr.release() is called.
- Postconditions: mutex() == the value upgr.mutex() had before the construction.
- upgr.mutex() == 0. owns() == upgr.owns() before the construction.
- upgr.owns() == false after the construction.
- Notes: If upgr is locked, this constructor will lock this scoped_lock while
- unlocking upgr. If upgr is unlocked, then this scoped_lock will be
- unlocked as well. Only a moved upgradable_lock's will match this
- signature. An non-moved upgradable_lock can be moved with
- the expression: "move(lock);" This constructor may block if
- other threads hold a sharable_lock on this mutex (sharable_lock's can
- share ownership with an upgradable_lock).*/
+ //!Effects: If upgr.owns() then calls unlock_upgradable_and_lock() on the
+ //! referenced mutex. upgr.release() is called.
+ //!Postconditions: mutex() == the value upgr.mutex() had before the construction.
+ //! upgr.mutex() == 0. owns() == upgr.owns() before the construction.
+ //! upgr.owns() == false after the construction.
+ //!Notes: If upgr is locked, this constructor will lock this scoped_lock while
+ //! unlocking upgr. If upgr is unlocked, then this scoped_lock will be
+ //! unlocked as well. Only a moved upgradable_lock's will match this
+ //! signature. An non-moved upgradable_lock can be moved with
+ //! the expression: "move(lock);" This constructor may block if
+ //! other threads hold a sharable_lock on this mutex (sharable_lock's can
+ //! share ownership with an upgradable_lock).
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit scoped_lock(detail::moved_object<upgradable_lock<Mutex> > upgr)
: mp_mutex(0), m_locked(false)
@@ -172,21 +171,21 @@
}
#endif
- /*!Effects: If upgr.owns() then calls try_unlock_upgradable_and_lock() on the
- referenced mutex:
- a)if try_unlock_upgradable_and_lock() returns true then mutex() obtains
- the value from upgr.release() and owns() is set to true.
- b)if try_unlock_upgradable_and_lock() returns false then upgr is
- unaffected and this scoped_lock construction as the same effects as
- a default construction.
- c)Else upgr.owns() is false. mutex() obtains the value from upgr.release()
- and owns() is set to false
- Notes: This construction will not block. It will try to obtain mutex
- ownership from upgr immediately, while changing the lock type from a
- "read lock" to a "write lock". If the "read lock" isn't held in the
- first place, the mutex merely changes type to an unlocked "write lock".
- If the "read lock" is held, then mutex transfer occurs only if it can
- do so in a non-blocking manner.*/
+ //!Effects: If upgr.owns() then calls try_unlock_upgradable_and_lock() on the
+ //!referenced mutex:
+ //! a)if try_unlock_upgradable_and_lock() returns true then mutex() obtains
+ //! the value from upgr.release() and owns() is set to true.
+ //! b)if try_unlock_upgradable_and_lock() returns false then upgr is
+ //! unaffected and this scoped_lock construction as the same effects as
+ //! a default construction.
+ //! c)Else upgr.owns() is false. mutex() obtains the value from upgr.release()
+ //! and owns() is set to false
+ //!Notes: This construction will not block. It will try to obtain mutex
+ //! ownership from upgr immediately, while changing the lock type from a
+ //! "read lock" to a "write lock". If the "read lock" isn't held in the
+ //! first place, the mutex merely changes type to an unlocked "write lock".
+ //! If the "read lock" is held, then mutex transfer occurs only if it can
+ //! do so in a non-blocking manner.*/
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
scoped_lock(detail::moved_object<upgradable_lock<Mutex> > upgr
,detail::try_to_lock_type)
@@ -219,20 +218,20 @@
}
#endif
- /*!Effects: If upgr.owns() then calls timed_unlock_upgradable_and_lock(abs_time)
- on the referenced mutex:
- a)if timed_unlock_upgradable_and_lock(abs_time) returns true then mutex()
- obtains the value from upgr.release() and owns() is set to true.
- b)if timed_unlock_upgradable_and_lock(abs_time) returns false then upgr
- is unaffected and this scoped_lock construction as the same effects
- as a default construction.
- c)Else upgr.owns() is false. mutex() obtains the value from upgr.release()
- and owns() is set to false
- Notes: This construction will not block. It will try to obtain mutex ownership
- from upgr immediately, while changing the lock type from a "read lock" to a
- "write lock". If the "read lock" isn't held in the first place, the mutex
- merely changes type to an unlocked "write lock". If the "read lock" is held,
- then mutex transfer occurs only if it can do so in a non-blocking manner.*/
+ //!Effects: If upgr.owns() then calls timed_unlock_upgradable_and_lock(abs_time)
+ //! on the referenced mutex:
+ //! a)if timed_unlock_upgradable_and_lock(abs_time) returns true then mutex()
+ //! obtains the value from upgr.release() and owns() is set to true.
+ //! b)if timed_unlock_upgradable_and_lock(abs_time) returns false then upgr
+ //! is unaffected and this scoped_lock construction as the same effects
+ //! as a default construction.
+ //! c)Else upgr.owns() is false. mutex() obtains the value from upgr.release()
+ //! and owns() is set to false
+ //!Notes: This construction will not block. It will try to obtain mutex ownership
+ //! from upgr immediately, while changing the lock type from a "read lock" to a
+ //! "write lock". If the "read lock" isn't held in the first place, the mutex
+ //! merely changes type to an unlocked "write lock". If the "read lock" is held,
+ //! then mutex transfer occurs only if it can do so in a non-blocking manner.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
scoped_lock(detail::moved_object<upgradable_lock<Mutex> > upgr
,boost::posix_time::ptime &abs_time)
@@ -265,21 +264,21 @@
}
#endif
- /*!Effects: If shar.owns() then calls try_unlock_sharable_and_lock() on the
- referenced mutex.
- a)if try_unlock_sharable_and_lock() returns true then mutex() obtains
- the value from shar.release() and owns() is set to true.
- b)if try_unlock_sharable_and_lock() returns false then shar is
- unaffected and this scoped_lock construction has the same
- effects as a default construction.
- c)Else shar.owns() is false. mutex() obtains the value from
- shar.release() and owns() is set to false
- Notes: This construction will not block. It will try to obtain mutex
- ownership from shar immediately, while changing the lock type from a
- "read lock" to a "write lock". If the "read lock" isn't held in the
- first place, the mutex merely changes type to an unlocked "write lock".
- If the "read lock" is held, then mutex transfer occurs only if it can
- do so in a non-blocking manner.*/
+ //!Effects: If shar.owns() then calls try_unlock_sharable_and_lock() on the
+ //!referenced mutex.
+ //! a)if try_unlock_sharable_and_lock() returns true then mutex() obtains
+ //! the value from shar.release() and owns() is set to true.
+ //! b)if try_unlock_sharable_and_lock() returns false then shar is
+ //! unaffected and this scoped_lock construction has the same
+ //! effects as a default construction.
+ //! c)Else shar.owns() is false. mutex() obtains the value from
+ //! shar.release() and owns() is set to false
+ //!Notes: This construction will not block. It will try to obtain mutex
+ //! ownership from shar immediately, while changing the lock type from a
+ //! "read lock" to a "write lock". If the "read lock" isn't held in the
+ //! first place, the mutex merely changes type to an unlocked "write lock".
+ //! If the "read lock" is held, then mutex transfer occurs only if it can
+ //! do so in a non-blocking manner.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
scoped_lock(detail::moved_object<sharable_lock<Mutex> > shar
,detail::try_to_lock_type)
@@ -312,20 +311,20 @@
}
#endif
- /*!Effects: if (owns()) mp_mutex->unlock().
- Notes: The destructor behavior ensures that the mutex lock is not leaked.*/
+ //!Effects: if (owns()) mp_mutex->unlock().
+ //!Notes: The destructor behavior ensures that the mutex lock is not leaked.*/
~scoped_lock()
{
try{ if(m_locked && mp_mutex) mp_mutex->unlock(); }
catch(...){}
}
- /*!Effects: If owns() before the call, then unlock() is called on mutex().
- *this gets the state of scop and scop gets set to a default constructed state.
- Notes: With a recursive mutex it is possible that both this and scop own
- the same mutex before the assignment. In this case, this will own the
- mutex after the assignment (and scop will not), but the mutex's lock
- count will be decremented by one.*/
+ //!Effects: If owns() before the call, then unlock() is called on mutex().
+ //! *this gets the state of scop and scop gets set to a default constructed state.
+ //!Notes: With a recursive mutex it is possible that both this and scop own
+ //! the same mutex before the assignment. In this case, this will own the
+ //! mutex after the assignment (and scop will not), but the mutex's lock
+ //! count will be decremented by one.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
scoped_lock &operator=(detail::moved_object<scoped_lock<Mutex> > scop)
{
@@ -346,11 +345,11 @@
}
#endif
- /*!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
- exception. Calls lock() on the referenced mutex.
- Postconditions: owns() == true.
- Notes: The scoped_lock changes from a state of not owning the mutex, to
- owning the mutex, blocking if necessary.*/
+ //!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
+ //! exception. Calls lock() on the referenced mutex.
+ //!Postconditions: owns() == true.
+ //!Notes: The scoped_lock changes from a state of not owning the mutex, to
+ //! owning the mutex, blocking if necessary.
void lock()
{
if(!mp_mutex || m_locked)
@@ -359,13 +358,13 @@
m_locked = true;
}
- /*!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
- exception. Calls try_lock() on the referenced mutex.
- Postconditions: owns() == the value returned from mutex()->try_lock().
- Notes: The scoped_lock changes from a state of not owning the mutex, to
- owning the mutex, but only if blocking was not required. If the
- mutex_type does not support try_lock(), this function will fail at
- compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
+ //! exception. Calls try_lock() on the referenced mutex.
+ //!Postconditions: owns() == the value returned from mutex()->try_lock().
+ //!Notes: The scoped_lock changes from a state of not owning the mutex, to
+ //! owning the mutex, but only if blocking was not required. If the
+ //! mutex_type does not support try_lock(), this function will fail at
+ //! compile time if instantiated, but otherwise have no effect.*/
bool try_lock()
{
if(!mp_mutex || m_locked)
@@ -374,13 +373,13 @@
return m_locked;
}
- /*!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
- exception. Calls timed_lock(abs_time) on the referenced mutex.
- Postconditions: owns() == the value returned from mutex()-> timed_lock(abs_time).
- Notes: The scoped_lock changes from a state of not owning the mutex, to
- owning the mutex, but only if it can obtain ownership by the specified
- time. If the mutex_type does not support timed_lock (), this function
- will fail at compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
+ //! exception. Calls timed_lock(abs_time) on the referenced mutex.
+ //!Postconditions: owns() == the value returned from mutex()-> timed_lock(abs_time).
+ //!Notes: The scoped_lock changes from a state of not owning the mutex, to
+ //! owning the mutex, but only if it can obtain ownership by the specified
+ //! time. If the mutex_type does not support timed_lock (), this function
+ //! will fail at compile time if instantiated, but otherwise have no effect.*/
bool timed_lock(const boost::posix_time::ptime& abs_time)
{
if(!mp_mutex || m_locked)
@@ -389,11 +388,11 @@
return m_locked;
}
- /*!Effects: If mutex() == 0 or if not locked, throws a lock_exception()
- exception. Calls unlock() on the referenced mutex.
- Postconditions: owns() == false.
- Notes: The scoped_lock changes from a state of owning the mutex, to not
- owning the mutex.*/
+ //!Effects: If mutex() == 0 or if not locked, throws a lock_exception()
+ //! exception. Calls unlock() on the referenced mutex.
+ //!Postconditions: owns() == false.
+ //!Notes: The scoped_lock changes from a state of owning the mutex, to not
+ //! owning the mutex.*/
void unlock()
{
if(!mp_mutex || !m_locked)
@@ -402,22 +401,24 @@
m_locked = false;
}
- /*!Effects: Returns true if this scoped_lock has acquired the referenced mutex.*/
+ //!Effects: Returns true if this scoped_lock has acquired
+ //!the referenced mutex.
bool owns() const
{ return m_locked && mp_mutex; }
- /*!Conversion to bool. Returns owns().*/
+ //!Conversion to bool.
+ //!Returns owns().
operator unspecified_bool_type() const
{ return m_locked? &this_type::m_locked : 0; }
- /*!Effects: Returns a pointer to the referenced mutex, or 0 if
- there is no mutex to reference.*/
+ //!Effects: Returns a pointer to the referenced mutex, or 0 if
+ //!there is no mutex to reference.
mutex_type* mutex() const
{ return mp_mutex; }
- /*!Effects: Returns a pointer to the referenced mutex, or 0 if there is no
- mutex to reference.
- Postconditions: mutex() == 0 and owns() == false.*/
+ //!Effects: Returns a pointer to the referenced mutex, or 0 if there is no
+ //! mutex to reference.
+ //!Postconditions: mutex() == 0 and owns() == false.
mutex_type* release()
{
mutex_type *mut = mp_mutex;
@@ -426,8 +427,8 @@
return mut;
}
- /*!Effects: Swaps state with moved lock.
- Throws: Nothing.*/
+ //!Effects: Swaps state with moved lock.
+ //!Throws: Nothing.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void swap(detail::moved_object<scoped_lock<mutex_type> > other)
{
@@ -450,7 +451,8 @@
};
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class M>
struct is_movable<scoped_lock<M> >
{
Modified: branches/bcbboost/boost/interprocess/sync/sharable_lock.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/sharable_lock.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/sharable_lock.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -28,10 +28,9 @@
//Ig#include <boost/utility.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
-/*!\file
- Describes the upgradable_lock class that serves to acquire the upgradable
- lock of a mutex.
-*/
+//!\file
+//!Describes the upgradable_lock class that serves to acquire the upgradable
+//!lock of a mutex.
namespace boost {
namespace interprocess {
@@ -42,14 +41,14 @@
template<class M>
class upgradable_lock;
-/*!sharable_lock is meant to carry out the tasks for sharable-locking
- (such as read-locking), unlocking, try-sharable-locking and timed-sharable-locking
- (recursive or not) for the Mutex. The Mutex need not supply all of this
- functionality. If the client of sharable_lock<Mutex> does not use functionality which
- the Mutex does not supply, no harm is done. Mutex ownership can be shared among
- sharable_locks, and a single upgradable_lock. sharable_lock does not support
- copy semantics. But sharable_lock supports ownership transfer from an sharable_lock,
- upgradable_lock and scoped_lock via trasfer_lock syntax.*/
+//!sharable_lock is meant to carry out the tasks for sharable-locking
+//!(such as read-locking), unlocking, try-sharable-locking and timed-sharable-locking
+//!(recursive or not) for the Mutex. The Mutex need not supply all of this
+//!functionality. If the client of sharable_lock<Mutex> does not use functionality which
+//!the Mutex does not supply, no harm is done. Mutex ownership can be shared among
+//!sharable_locks, and a single upgradable_lock. sharable_lock does not support
+//!copy semantics. But sharable_lock supports ownership transfer from an sharable_lock,
+//!upgradable_lock and scoped_lock via trasfer_lock syntax.*/
template <class SharableMutex>
class sharable_lock
{
@@ -66,70 +65,70 @@
/// @endcond
public:
- /*!Effects: Default constructs a sharable_lock.
- Postconditions: owns() == false and mutex() == 0.*/
+ //!Effects: Default constructs a sharable_lock.
+ //!Postconditions: owns() == false and mutex() == 0.
sharable_lock()
: mp_mutex(0), m_locked(false)
{}
- /*!Effects: m.lock_sharable().
- Postconditions: owns() == true and mutex() == &m.
- Notes: The constructor will take sharable-ownership of the mutex. If
- another thread already owns the mutex with exclusive ownership
- (scoped_lock), this thread will block until the mutex is released.
- If another thread owns the mutex with sharable or upgradable ownership,
- then no blocking will occur. Whether or not this constructor handles
- recursive locking depends upon the mutex.*/
+ //!Effects: m.lock_sharable().
+ //!Postconditions: owns() == true and mutex() == &m.
+ //!Notes: The constructor will take sharable-ownership of the mutex. If
+ //! another thread already owns the mutex with exclusive ownership
+ //! (scoped_lock), this thread will block until the mutex is released.
+ //! If another thread owns the mutex with sharable or upgradable ownership,
+ //! then no blocking will occur. Whether or not this constructor handles
+ //! recursive locking depends upon the mutex.
explicit sharable_lock(mutex_type& m)
: mp_mutex(&m), m_locked(false)
{ mp_mutex->lock_sharable(); m_locked = true; }
- /*!Postconditions: owns() == false, and mutex() == &m.
- Notes: The constructor will not take ownership of the mutex. There is no effect
- required on the referenced mutex.*/
+ //!Postconditions: owns() == false, and mutex() == &m.
+ //!Notes: The constructor will not take ownership of the mutex. There is no effect
+ //! required on the referenced mutex.
sharable_lock(mutex_type& m, detail::defer_lock_type)
: mp_mutex(&m), m_locked(false)
{}
- /*!Postconditions: owns() == true, and mutex() == &m.
- Notes: The constructor will suppose that the mutex is already sharable
- locked. There is no effect required on the referenced mutex.*/
+ //!Postconditions: owns() == true, and mutex() == &m.
+ //!Notes: The constructor will suppose that the mutex is already sharable
+ //! locked. There is no effect required on the referenced mutex.
sharable_lock(mutex_type& m, detail::accept_ownership_type)
: mp_mutex(&m), m_locked(true)
{}
- /*!Effects: m.try_lock_sharable()
- Postconditions: mutex() == &m. owns() == the return value of the
- m.try_lock_sharable() executed within the constructor.
- Notes: The constructor will take sharable-ownership of the mutex if it
- can do so without waiting. Whether or not this constructor handles
- recursive locking depends upon the mutex. If the mutex_type does not
- support try_lock_sharable, this constructor will fail at compile
- time if instantiated, but otherwise have no effect.*/
+ //!Effects: m.try_lock_sharable()
+ //!Postconditions: mutex() == &m. owns() == the return value of the
+ //! m.try_lock_sharable() executed within the constructor.
+ //!Notes: The constructor will take sharable-ownership of the mutex if it
+ //! can do so without waiting. Whether or not this constructor handles
+ //! recursive locking depends upon the mutex. If the mutex_type does not
+ //! support try_lock_sharable, this constructor will fail at compile
+ //! time if instantiated, but otherwise have no effect.
sharable_lock(mutex_type& m, detail::try_to_lock_type)
: mp_mutex(&m), m_locked(false)
{ m_locked = mp_mutex->try_lock_sharable(); }
- /*!Effects: m.timed_lock_sharable(abs_time)
- Postconditions: mutex() == &m. owns() == the return value of the
- m.timed_lock_sharable() executed within the constructor.
- Notes: The constructor will take sharable-ownership of the mutex if it
- can do so within the time specified. Whether or not this constructor
- handles recursive locking depends upon the mutex. If the mutex_type
- does not support timed_lock_sharable, this constructor will fail at
- compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: m.timed_lock_sharable(abs_time)
+ //!Postconditions: mutex() == &m. owns() == the return value of the
+ //! m.timed_lock_sharable() executed within the constructor.
+ //!Notes: The constructor will take sharable-ownership of the mutex if it
+ //! can do so within the time specified. Whether or not this constructor
+ //! handles recursive locking depends upon the mutex. If the mutex_type
+ //! does not support timed_lock_sharable, this constructor will fail at
+ //! compile time if instantiated, but otherwise have no effect.
sharable_lock(mutex_type& m, const boost::posix_time::ptime& abs_time)
: mp_mutex(&m), m_locked(false)
{ m_locked = mp_mutex->timed_lock_sharable(abs_time); }
- /*!Postconditions: mutex() == upgr.mutex(). owns() == the value of upgr.owns()
- before the construction. upgr.owns() == false after the construction.
- Notes: If the upgr sharable_lock owns the mutex, ownership is moved to this
- sharable_lock with no blocking. If the upgr sharable_lock does not own the mutex, then
- neither will this sharable_lock. Only a moved sharable_lock's will match this
- signature. An non-moved sharable_lock can be moved with the expression:
- "move(lock);". This constructor does not alter the state of the mutex,
- only potentially who owns it.*/
+ //!Postconditions: mutex() == upgr.mutex(). owns() == the value of upgr.owns()
+ //! before the construction. upgr.owns() == false after the construction.
+ //!Notes: If the upgr sharable_lock owns the mutex, ownership is moved to this
+ //! sharable_lock with no blocking. If the upgr sharable_lock does not own the mutex, then
+ //! neither will this sharable_lock. Only a moved sharable_lock's will match this
+ //! signature. An non-moved sharable_lock can be moved with the expression:
+ //! "move(lock);". This constructor does not alter the state of the mutex,
+ //! only potentially who owns it.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit sharable_lock(detail::moved_object<sharable_lock<mutex_type> > upgr)
: mp_mutex(0), m_locked(upgr.get().owns())
@@ -140,15 +139,15 @@
{ mp_mutex = upgr.release(); }
#endif
- /*!Effects: If upgr.owns() then calls unlock_upgradable_and_lock_sharable() on the
- referenced mutex.
- Postconditions: mutex() == the value upgr.mutex() had before the construction.
- upgr.mutex() == 0 owns() == the value of upgr.owns() before construction.
- upgr.owns() == false after the construction.
- Notes: If upgr is locked, this constructor will lock this sharable_lock while
- unlocking upgr. Only a moved sharable_lock's will match this
- signature. An non-moved upgradable_lock can be moved with the expression:
- "move(lock);".*/
+ //!Effects: If upgr.owns() then calls unlock_upgradable_and_lock_sharable() on the
+ //! referenced mutex.
+ //!Postconditions: mutex() == the value upgr.mutex() had before the construction.
+ //! upgr.mutex() == 0 owns() == the value of upgr.owns() before construction.
+ //! upgr.owns() == false after the construction.
+ //!Notes: If upgr is locked, this constructor will lock this sharable_lock while
+ //! unlocking upgr. Only a moved sharable_lock's will match this
+ //! signature. An non-moved upgradable_lock can be moved with the expression:
+ //! "move(lock);".*/
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit sharable_lock(detail::moved_object<upgradable_lock<mutex_type> > upgr)
: mp_mutex(0), m_locked(false)
@@ -173,16 +172,16 @@
}
#endif
- /*!Effects: If scop.owns() then calls unlock_and_lock_sharable() on the
- referenced mutex.
- Postconditions: mutex() == the value scop.mutex() had before the construction.
- scop.mutex() == 0 owns() == scop.owns() before the constructor. After the
- construction, scop.owns() == false.
- Notes: If scop is locked, this constructor will transfer the exclusive ownership
- to a sharable-ownership of this sharable_lock.
- Only a moved scoped_lock's will match this
- signature. An non-moved scoped_lock can be moved with the expression:
- "move(lock);".*/
+ //!Effects: If scop.owns() then calls unlock_and_lock_sharable() on the
+ //! referenced mutex.
+ //!Postconditions: mutex() == the value scop.mutex() had before the construction.
+ //! scop.mutex() == 0 owns() == scop.owns() before the constructor. After the
+ //! construction, scop.owns() == false.
+ //!Notes: If scop is locked, this constructor will transfer the exclusive ownership
+ //! to a sharable-ownership of this sharable_lock.
+ //! Only a moved scoped_lock's will match this
+ //! signature. An non-moved scoped_lock can be moved with the expression:
+ //! "move(lock);".*/
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit sharable_lock(detail::moved_object<scoped_lock<mutex_type> > scop)
: mp_mutex(0), m_locked(false)
@@ -207,8 +206,8 @@
}
#endif
- /*!Effects: if (owns()) mp_mutex->unlock_sharable().
- Notes: The destructor behavior ensures that the mutex lock is not leaked.*/
+ //!Effects: if (owns()) mp_mutex->unlock_sharable().
+ //!Notes: The destructor behavior ensures that the mutex lock is not leaked.
~sharable_lock()
{
try{
@@ -217,11 +216,11 @@
catch(...){}
}
- /*!Effects: If owns() before the call, then unlock_sharable() is called on mutex().
- *this gets the state of upgr and upgr gets set to a default constructed state.
- Notes: With a recursive mutex it is possible that both this and upgr own the mutex
- before the assignment. In this case, this will own the mutex after the assignment
- (and upgr will not), but the mutex's lock count will be decremented by one.*/
+ //!Effects: If owns() before the call, then unlock_sharable() is called on mutex().
+ //! *this gets the state of upgr and upgr gets set to a default constructed state.
+ //!Notes: With a recursive mutex it is possible that both this and upgr own the mutex
+ //! before the assignment. In this case, this will own the mutex after the assignment
+ //! (and upgr will not), but the mutex's lock count will be decremented by one.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
sharable_lock &operator=(detail::moved_object<sharable_lock<mutex_type> > upgr)
{
@@ -242,11 +241,11 @@
}
#endif
- /*!Effects: If mutex() == 0 or already locked, throws a lock_exception()
- exception. Calls lock_sharable() on the referenced mutex.
- Postconditions: owns() == true.
- Notes: The sharable_lock changes from a state of not owning the
- mutex, to owning the mutex, blocking if necessary.*/
+ //!Effects: If mutex() == 0 or already locked, throws a lock_exception()
+ //! exception. Calls lock_sharable() on the referenced mutex.
+ //!Postconditions: owns() == true.
+ //!Notes: The sharable_lock changes from a state of not owning the
+ //! mutex, to owning the mutex, blocking if necessary.
void lock()
{
if(!mp_mutex || m_locked)
@@ -255,14 +254,14 @@
m_locked = true;
}
- /*!Effects: If mutex() == 0 or already locked, throws a lock_exception()
- exception. Calls try_lock_sharable() on the referenced mutex.
- Postconditions: owns() == the value returned from
- mutex()->try_lock_sharable().
- Notes: The sharable_lock changes from a state of not owning the mutex,
- to owning the mutex, but only if blocking was not required. If the
- mutex_type does not support try_lock_sharable(), this function will
- fail at compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: If mutex() == 0 or already locked, throws a lock_exception()
+ //! exception. Calls try_lock_sharable() on the referenced mutex.
+ //!Postconditions: owns() == the value returned from
+ //! mutex()->try_lock_sharable().
+ //!Notes: The sharable_lock changes from a state of not owning the mutex,
+ //! to owning the mutex, but only if blocking was not required. If the
+ //! mutex_type does not support try_lock_sharable(), this function will
+ //! fail at compile time if instantiated, but otherwise have no effect.
bool try_lock()
{
if(!mp_mutex || m_locked)
@@ -271,15 +270,15 @@
return m_locked;
}
- /*!Effects: If mutex() == 0 or already locked, throws a lock_exception()
- exception. Calls timed_lock_sharable(abs_time) on the referenced mutex.
- Postconditions: owns() == the value returned from
- mutex()->timed_lock_sharable(elps_time).
- Notes: The sharable_lock changes from a state of not owning the mutex,
- to owning the mutex, but only if it can obtain ownership within the
- specified time interval. If the mutex_type does not support
- timed_lock_sharable(), this function will fail at compile time if
- instantiated, but otherwise have no effect.*/
+ //!Effects: If mutex() == 0 or already locked, throws a lock_exception()
+ //! exception. Calls timed_lock_sharable(abs_time) on the referenced mutex.
+ //!Postconditions: owns() == the value returned from
+ //! mutex()->timed_lock_sharable(elps_time).
+ //!Notes: The sharable_lock changes from a state of not owning the mutex,
+ //! to owning the mutex, but only if it can obtain ownership within the
+ //! specified time interval. If the mutex_type does not support
+ //! timed_lock_sharable(), this function will fail at compile time if
+ //! instantiated, but otherwise have no effect.
bool timed_lock(const boost::posix_time::ptime& abs_time)
{
if(!mp_mutex || m_locked)
@@ -288,11 +287,11 @@
return m_locked;
}
- /*!Effects: If mutex() == 0 or not locked, throws a lock_exception() exception.
- Calls unlock_sharable() on the referenced mutex.
- Postconditions: owns() == false.
- Notes: The sharable_lock changes from a state of owning the mutex, to
- not owning the mutex.*/
+ //!Effects: If mutex() == 0 or not locked, throws a lock_exception() exception.
+ //! Calls unlock_sharable() on the referenced mutex.
+ //!Postconditions: owns() == false.
+ //!Notes: The sharable_lock changes from a state of owning the mutex, to
+ //! not owning the mutex.
void unlock()
{
if(!mp_mutex || !m_locked)
@@ -301,22 +300,24 @@
m_locked = false;
}
- /*!Effects: Returns true if this scoped_lock has acquired the referenced mutex.*/
+ //!Effects: Returns true if this scoped_lock has
+ //!acquired the referenced mutex.
bool owns() const
{ return m_locked && mp_mutex; }
- /*!Conversion to bool. Returns owns().*/
+ //!Conversion to bool.
+ //!Returns owns().
operator unspecified_bool_type() const
{ return m_locked? &this_type::m_locked : 0; }
- /*!Effects: Returns a pointer to the referenced mutex, or 0 if
- there is no mutex to reference.*/
+ //!Effects: Returns a pointer to the referenced mutex, or 0 if
+ //!there is no mutex to reference.
mutex_type* mutex() const
{ return mp_mutex; }
- /*!Effects: Returns a pointer to the referenced mutex, or 0 if there is no
- mutex to reference.
- Postconditions: mutex() == 0 and owns() == false.*/
+ //!Effects: Returns a pointer to the referenced mutex, or 0 if there is no
+ //! mutex to reference.
+ //!Postconditions: mutex() == 0 and owns() == false.
mutex_type* release()
{
mutex_type *mut = mp_mutex;
@@ -325,8 +326,8 @@
return mut;
}
- /*!Effects: Swaps state with moved lock.
- Throws: Nothing.*/
+ //!Effects: Swaps state with moved lock.
+ //!Throws: Nothing.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void swap(detail::moved_object<sharable_lock<mutex_type> > other)
{
@@ -349,7 +350,8 @@
};
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class M>
struct is_movable<sharable_lock<M> >
{
Modified: branches/bcbboost/boost/interprocess/sync/upgradable_lock.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/sync/upgradable_lock.hpp (original)
+++ branches/bcbboost/boost/interprocess/sync/upgradable_lock.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -27,10 +27,9 @@
#include <boost/interprocess/detail/move.hpp>
#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
-/*!\file
- Describes the upgradable_lock class that serves to acquire the upgradable
- lock of a mutex.
-*/
+//!\file
+//!Describes the upgradable_lock class that serves to acquire the upgradable
+//!lock of a mutex.
namespace boost {
namespace interprocess {
@@ -41,15 +40,15 @@
template<class M>
class sharable_lock;
-/*!upgradable_lock is meant to carry out the tasks for read-locking, unlocking,
- try-read-locking and timed-read-locking (recursive or not) for the Mutex.
- Additionally the upgradable_lock can transfer ownership to a scoped_lock
- using trasfer_lock syntax. The Mutex need not supply all of the functionality.
- If the client of upgradable_lock<Mutex> does not use functionality which the
- Mutex does not supply, no harm is done. Mutex ownership can be shared among
- read_locks, and a single upgradable_lock. upgradable_lock does not support
- copy semantics. However upgradable_lock supports ownership transfer from
- a upgradable_locks or scoped_locks via trasfer_lock syntax.*/
+//!upgradable_lock is meant to carry out the tasks for read-locking, unlocking,
+//!try-read-locking and timed-read-locking (recursive or not) for the Mutex.
+//!Additionally the upgradable_lock can transfer ownership to a scoped_lock
+//!using trasfer_lock syntax. The Mutex need not supply all of the functionality.
+//!If the client of upgradable_lock<Mutex> does not use functionality which the
+//!Mutex does not supply, no harm is done. Mutex ownership can be shared among
+//!read_locks, and a single upgradable_lock. upgradable_lock does not support
+//!copy semantics. However upgradable_lock supports ownership transfer from
+//!a upgradable_locks or scoped_locks via trasfer_lock syntax.
template <class UpgradableMutex>
class upgradable_lock
{
@@ -66,8 +65,8 @@
/// @endcond
public:
- /*!Effects: Default constructs a upgradable_lock.
- Postconditions: owns() == false and mutex() == 0.*/
+ //!Effects: Default constructs a upgradable_lock.
+ //!Postconditions: owns() == false and mutex() == 0.
upgradable_lock()
: mp_mutex(0), m_locked(false)
{}
@@ -76,54 +75,54 @@
: mp_mutex(&m), m_locked(false)
{ mp_mutex->lock_upgradable(); m_locked = true; }
- /*!Postconditions: owns() == false, and mutex() == &m.
- Notes: The constructor will not take ownership of the mutex. There is no effect
- required on the referenced mutex.*/
+ //!Postconditions: owns() == false, and mutex() == &m.
+ //!Notes: The constructor will not take ownership of the mutex. There is no effect
+ //! required on the referenced mutex.
upgradable_lock(mutex_type& m, detail::defer_lock_type)
: mp_mutex(&m), m_locked(false)
{}
- /*!Postconditions: owns() == true, and mutex() == &m.
- Notes: The constructor will suppose that the mutex is already upgradable
- locked. There is no effect required on the referenced mutex.*/
+ //!Postconditions: owns() == true, and mutex() == &m.
+ //!Notes: The constructor will suppose that the mutex is already upgradable
+ //! locked. There is no effect required on the referenced mutex.
upgradable_lock(mutex_type& m, detail::accept_ownership_type)
: mp_mutex(&m), m_locked(true)
{}
- /*!Effects: m.try_lock_upgradable().
- Postconditions: mutex() == &m. owns() == the return value of the
- m.try_lock_upgradable() executed within the constructor.
- Notes: The constructor will take upgradable-ownership of the mutex
- if it can do so without waiting. Whether or not this constructor
- handles recursive locking depends upon the mutex. If the mutex_type
- does not support try_lock_upgradable, this constructor will fail at
- compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: m.try_lock_upgradable().
+ //!Postconditions: mutex() == &m. owns() == the return value of the
+ //! m.try_lock_upgradable() executed within the constructor.
+ //!Notes: The constructor will take upgradable-ownership of the mutex
+ //! if it can do so without waiting. Whether or not this constructor
+ //! handles recursive locking depends upon the mutex. If the mutex_type
+ //! does not support try_lock_upgradable, this constructor will fail at
+ //! compile time if instantiated, but otherwise have no effect.
upgradable_lock(mutex_type& m, detail::try_to_lock_type)
: mp_mutex(&m), m_locked(false)
{ m_locked = mp_mutex->try_lock_upgradable(); }
- /*!Effects: m.timed_lock_upgradable(abs_time)
- Postconditions: mutex() == &m. owns() == the return value of the
- m.timed_lock_upgradable() executed within the constructor.
- Notes: The constructor will take upgradable-ownership of the mutex if it
- can do so within the time specified. Whether or not this constructor
- handles recursive locking depends upon the mutex. If the mutex_type
- does not support timed_lock_upgradable, this constructor will fail
- at compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: m.timed_lock_upgradable(abs_time)
+ //!Postconditions: mutex() == &m. owns() == the return value of the
+ //! m.timed_lock_upgradable() executed within the constructor.
+ //!Notes: The constructor will take upgradable-ownership of the mutex if it
+ //! can do so within the time specified. Whether or not this constructor
+ //! handles recursive locking depends upon the mutex. If the mutex_type
+ //! does not support timed_lock_upgradable, this constructor will fail
+ //! at compile time if instantiated, but otherwise have no effect.
upgradable_lock(mutex_type& m, const boost::posix_time::ptime& abs_time)
: mp_mutex(&m), m_locked(false)
{ m_locked = mp_mutex->timed_lock_upgradable(abs_time); }
- /*!Effects: No effects on the underlying mutex.
- Postconditions: mutex() == the value upgr.mutex() had before the
- construction. upgr.mutex() == 0. owns() == upgr.owns() before the
- construction. upgr.owns() == false.
- Notes: If upgr is locked, this constructor will lock this upgradable_lock
- while unlocking upgr. If upgr is unlocked, then this upgradable_lock will
- be unlocked as well. Only a moved upgradable_lock's will match this
- signature. An non-moved upgradable_lock can be moved with the
- expression: "move(lock);". This constructor does not alter the
- state of the mutex, only potentially who owns it.*/
+ //!Effects: No effects on the underlying mutex.
+ //!Postconditions: mutex() == the value upgr.mutex() had before the
+ //! construction. upgr.mutex() == 0. owns() == upgr.owns() before the
+ //! construction. upgr.owns() == false.
+ //!Notes: If upgr is locked, this constructor will lock this upgradable_lock
+ //! while unlocking upgr. If upgr is unlocked, then this upgradable_lock will
+ //! be unlocked as well. Only a moved upgradable_lock's will match this
+ //! signature. An non-moved upgradable_lock can be moved with the
+ //! expression: "move(lock);". This constructor does not alter the
+ //! state of the mutex, only potentially who owns it.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit upgradable_lock(detail::moved_object<upgradable_lock<mutex_type> > upgr)
: mp_mutex(0), m_locked(upgr.get().owns())
@@ -134,15 +133,15 @@
{ mp_mutex = upgr.release(); }
#endif
- /*!Effects: If scop.owns(), m_.unlock_and_lock_upgradable().
- Postconditions: mutex() == the value scop.mutex() had before the construction.
- scop.mutex() == 0. owns() == scop.owns() before the constructor. After the
- construction, scop.owns() == false.
- Notes: If scop is locked, this constructor will transfer the exclusive-ownership
- to an upgradable-ownership of this upgradable_lock.
- Only a moved sharable_lock's will match this
- signature. An non-moved sharable_lock can be moved with the
- expression: "move(lock);".*/
+ //!Effects: If scop.owns(), m_.unlock_and_lock_upgradable().
+ //!Postconditions: mutex() == the value scop.mutex() had before the construction.
+ //! scop.mutex() == 0. owns() == scop.owns() before the constructor. After the
+ //! construction, scop.owns() == false.
+ //!Notes: If scop is locked, this constructor will transfer the exclusive-ownership
+ //! to an upgradable-ownership of this upgradable_lock.
+ //! Only a moved sharable_lock's will match this
+ //! signature. An non-moved sharable_lock can be moved with the
+ //! expression: "move(lock);".
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
explicit upgradable_lock(detail::moved_object<scoped_lock<mutex_type> > scop)
: mp_mutex(0), m_locked(false)
@@ -167,21 +166,21 @@
}
#endif
- /*!Effects: If shar.owns() then calls try_unlock_sharable_and_lock_upgradable()
- on the referenced mutex.
- a)if try_unlock_sharable_and_lock_upgradable() returns true then mutex()
- obtains the value from shar.release() and owns() is set to true.
- b)if try_unlock_sharable_and_lock_upgradable() returns false then shar is
- unaffected and this upgradable_lock construction has the same
- effects as a default construction.
- c)Else shar.owns() is false. mutex() obtains the value from shar.release()
- and owns() is set to false.
- Notes: This construction will not block. It will try to obtain mutex
- ownership from shar immediately, while changing the lock type from a
- "read lock" to an "upgradable lock". If the "read lock" isn't held
- in the first place, the mutex merely changes type to an unlocked
- "upgradable lock". If the "read lock" is held, then mutex transfer
- occurs only if it can do so in a non-blocking manner.*/
+ //!Effects: If shar.owns() then calls try_unlock_sharable_and_lock_upgradable()
+ //! on the referenced mutex.
+ //! a)if try_unlock_sharable_and_lock_upgradable() returns true then mutex()
+ //! obtains the value from shar.release() and owns() is set to true.
+ //! b)if try_unlock_sharable_and_lock_upgradable() returns false then shar is
+ //! unaffected and this upgradable_lock construction has the same
+ //! effects as a default construction.
+ //! c)Else shar.owns() is false. mutex() obtains the value from shar.release()
+ //! and owns() is set to false.
+ //!Notes: This construction will not block. It will try to obtain mutex
+ //! ownership from shar immediately, while changing the lock type from a
+ //! "read lock" to an "upgradable lock". If the "read lock" isn't held
+ //! in the first place, the mutex merely changes type to an unlocked
+ //! "upgradable lock". If the "read lock" is held, then mutex transfer
+ //! occurs only if it can do so in a non-blocking manner.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
upgradable_lock( detail::moved_object<sharable_lock<mutex_type> > shar
, detail::try_to_lock_type)
@@ -214,8 +213,8 @@
}
#endif
- /*!Effects: if (owns()) m_->unlock_upgradable().
- Notes: The destructor behavior ensures that the mutex lock is not leaked.*/
+ //!Effects: if (owns()) m_->unlock_upgradable().
+ //!Notes: The destructor behavior ensures that the mutex lock is not leaked.
~upgradable_lock()
{
try{
@@ -224,12 +223,12 @@
catch(...){}
}
- /*!Effects: If owns(), then unlock_upgradable() is called on mutex().
- *this gets the state of upgr and upgr gets set to a default constructed state.
- Notes: With a recursive mutex it is possible that both this and upgr own the
- mutex before the assignment. In this case, this will own the mutex
- after the assignment (and upgr will not), but the mutex's upgradable lock
- count will be decremented by one.*/
+ //!Effects: If owns(), then unlock_upgradable() is called on mutex().
+ //! *this gets the state of upgr and upgr gets set to a default constructed state.
+ //!Notes: With a recursive mutex it is possible that both this and upgr own the
+ //! mutex before the assignment. In this case, this will own the mutex
+ //! after the assignment (and upgr will not), but the mutex's upgradable lock
+ //! count will be decremented by one.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
upgradable_lock &operator=(detail::moved_object<upgradable_lock<mutex_type> > upgr)
{
@@ -250,11 +249,11 @@
}
#endif
- /*!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
- exception. Calls lock_upgradable() on the referenced mutex.
- Postconditions: owns() == true.
- Notes: The sharable_lock changes from a state of not owning the mutex,
- to owning the mutex, blocking if necessary.*/
+ //!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
+ //! exception. Calls lock_upgradable() on the referenced mutex.
+ //!Postconditions: owns() == true.
+ //!Notes: The sharable_lock changes from a state of not owning the mutex,
+ //! to owning the mutex, blocking if necessary.
void lock()
{
if(!mp_mutex || m_locked)
@@ -263,14 +262,14 @@
m_locked = true;
}
- /*!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
- exception. Calls try_lock_upgradable() on the referenced mutex.
- Postconditions: owns() == the value returned from
- mutex()->try_lock_upgradable().
- Notes: The upgradable_lock changes from a state of not owning the mutex,
- to owning the mutex, but only if blocking was not required. If the
- mutex_type does not support try_lock_upgradable(), this function will
- fail at compile time if instantiated, but otherwise have no effect.*/
+ //!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
+ //! exception. Calls try_lock_upgradable() on the referenced mutex.
+ //!Postconditions: owns() == the value returned from
+ //! mutex()->try_lock_upgradable().
+ //!Notes: The upgradable_lock changes from a state of not owning the mutex,
+ //! to owning the mutex, but only if blocking was not required. If the
+ //! mutex_type does not support try_lock_upgradable(), this function will
+ //! fail at compile time if instantiated, but otherwise have no effect.
bool try_lock()
{
if(!mp_mutex || m_locked)
@@ -279,15 +278,15 @@
return m_locked;
}
- /*!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
- exception. Calls timed_lock_upgradable(abs_time) on the referenced mutex.
- Postconditions: owns() == the value returned from
- mutex()->timed_lock_upgradable(abs_time).
- Notes: The upgradable_lock changes from a state of not owning the mutex,
- to owning the mutex, but only if it can obtain ownership within the
- specified time. If the mutex_type does not support
- timed_lock_upgradable(abs_time), this function will fail at compile
- time if instantiated, but otherwise have no effect.*/
+ //!Effects: If mutex() == 0 or if already locked, throws a lock_exception()
+ //! exception. Calls timed_lock_upgradable(abs_time) on the referenced mutex.
+ //!Postconditions: owns() == the value returned from
+ //! mutex()->timed_lock_upgradable(abs_time).
+ //!Notes: The upgradable_lock changes from a state of not owning the mutex,
+ //! to owning the mutex, but only if it can obtain ownership within the
+ //! specified time. If the mutex_type does not support
+ //! timed_lock_upgradable(abs_time), this function will fail at compile
+ //! time if instantiated, but otherwise have no effect.
bool timed_lock(const boost::posix_time::ptime& abs_time)
{
if(!mp_mutex || m_locked)
@@ -296,11 +295,11 @@
return m_locked;
}
- /*!Effects: If mutex() == 0 or if not locked, throws a lock_exception()
- exception. Calls unlock_upgradable() on the referenced mutex.
- Postconditions: owns() == false.
- Notes: The upgradable_lock changes from a state of owning the mutex,
- to not owning the mutex.*/
+ //!Effects: If mutex() == 0 or if not locked, throws a lock_exception()
+ //! exception. Calls unlock_upgradable() on the referenced mutex.
+ //!Postconditions: owns() == false.
+ //!Notes: The upgradable_lock changes from a state of owning the mutex,
+ //! to not owning the mutex.
void unlock()
{
if(!mp_mutex || !m_locked)
@@ -309,22 +308,24 @@
m_locked = false;
}
- /*!Effects: Returns true if this scoped_lock has acquired the referenced mutex.*/
+ //!Effects: Returns true if this scoped_lock has acquired the
+ //!referenced mutex.
bool owns() const
{ return m_locked && mp_mutex; }
- /*!Conversion to bool. Returns owns().*/
+ //!Conversion to bool.
+ //!Returns owns().
operator unspecified_bool_type() const
{ return m_locked? &this_type::m_locked : 0; }
- /*!Effects: Returns a pointer to the referenced mutex, or 0 if
- there is no mutex to reference.*/
+ //!Effects: Returns a pointer to the referenced mutex, or 0 if
+ //!there is no mutex to reference.
mutex_type* mutex() const
{ return mp_mutex; }
- /*!Effects: Returns a pointer to the referenced mutex, or 0 if there is no
- mutex to reference.
- Postconditions: mutex() == 0 and owns() == false.*/
+ //!Effects: Returns a pointer to the referenced mutex, or 0 if there is no
+ //! mutex to reference.
+ //!Postconditions: mutex() == 0 and owns() == false.
mutex_type* release()
{
mutex_type *mut = mp_mutex;
@@ -333,8 +334,8 @@
return mut;
}
- /*!Effects: Swaps state with moved lock.
- Throws: Nothing.*/
+ //!Effects: Swaps state with moved lock.
+ //!Throws: Nothing.
#ifndef BOOST_INTERPROCESS_RVALUE_REFERENCE
void swap(detail::moved_object<upgradable_lock<mutex_type> > other)
{
@@ -357,7 +358,8 @@
};
/// @cond
-/*!This class is movable*/
+
+//!This class is movable
template <class M>
struct is_movable<upgradable_lock<M> >
{
Modified: branches/bcbboost/boost/interprocess/windows_shared_memory.hpp
==============================================================================
--- branches/bcbboost/boost/interprocess/windows_shared_memory.hpp (original)
+++ branches/bcbboost/boost/interprocess/windows_shared_memory.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -56,7 +56,9 @@
/// @endcond
public:
- //!Default constructor. Represents an empty windows_shared_memory.
+
+ //!Default constructor.
+ //!Represents an empty windows_shared_memory.
windows_shared_memory();
//!Creates a new native shared memory with name "name" and mode "mode",
@@ -69,7 +71,7 @@
//!access mode "mode". If the file previously exists, it tries to open it with mode "mode".
//!Otherwise throws an error.
windows_shared_memory(open_or_create_t, const char *name, mode_t mode, std::size_t size)
- { this->priv_open_or_create(detail::DoCreateOrOpen, name, mode, size); }
+ { this->priv_open_or_create(detail::DoOpenOrCreate, name, mode, size); }
//!Tries to open a shared memory object with name "name", with the access mode "mode".
//!If the file does not previously exist, it throws an error.
@@ -200,7 +202,7 @@
(map_access, filename);
break;
case detail::DoCreate:
- case detail::DoCreateOrOpen:
+ case detail::DoOpenOrCreate:
{
__int64 s = size;
unsigned long high_size(s >> 32), low_size((boost::uint32_t)s);
Modified: branches/bcbboost/boost/intrusive/circular_list_algorithms.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/circular_list_algorithms.hpp (original)
+++ branches/bcbboost/boost/intrusive/circular_list_algorithms.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -52,6 +52,7 @@
public:
typedef typename NodeTraits::node_ptr node_ptr;
typedef typename NodeTraits::const_node_ptr const_node_ptr;
+ typedef NodeTraits node_traits;
//! <b>Effects</b>: Constructs an empty list, making this_node the only
//! node of the circular list:
Modified: branches/bcbboost/boost/intrusive/circular_slist_algorithms.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/circular_slist_algorithms.hpp (original)
+++ branches/bcbboost/boost/intrusive/circular_slist_algorithms.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -48,6 +48,7 @@
public:
typedef typename NodeTraits::node_ptr node_ptr;
typedef typename NodeTraits::const_node_ptr const_node_ptr;
+ typedef NodeTraits node_traits;
//! <b>Requires</b>: this_node must be in a circular list or be an empty circular list.
//!
Modified: branches/bcbboost/boost/intrusive/derivation_value_traits.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/derivation_value_traits.hpp (original)
+++ branches/bcbboost/boost/intrusive/derivation_value_traits.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,7 +13,7 @@
#ifndef BOOST_INTRUSIVE_DERIVATION_VALUE_TRAITS_HPP
#define BOOST_INTRUSIVE_DERIVATION_VALUE_TRAITS_HPP
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <iterator>
namespace boost {
@@ -22,7 +22,7 @@
//!This value traits template is used to create value traits
//!from user defined node traits where value_traits::value_type will
//!derive from node_traits::node
-template<class T, class NodeTraits, linking_policy Policy>
+template<class T, class NodeTraits, link_mode_type LinkMode = safe_link>
struct derivation_value_traits
{
public:
@@ -35,8 +35,7 @@
typedef typename boost::pointer_to_other<node_ptr, const T>::type const_pointer;
typedef typename std::iterator_traits<pointer>::reference reference;
typedef typename std::iterator_traits<const_pointer>::reference const_reference;
-
- enum { linking_policy = Policy };
+ static const link_mode_type link_mode = LinkMode;
static node_ptr to_node_ptr(reference value)
{ return node_ptr(&value); }
Modified: branches/bcbboost/boost/intrusive/detail/config_begin.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/config_begin.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/config_begin.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,12 +10,10 @@
//
/////////////////////////////////////////////////////////////////////////////
-#ifndef BOOST_INTRUSIVE_SELECT_COMPILER_INCLUDED
-#ifndef BOOST_COMPILER_CONFIG
+#ifndef BOOST_INTRUSIVE_CONFIG_INCLUDED
+#define BOOST_INTRUSIVE_CONFIG_INCLUDED
#include <boost/config.hpp>
#endif
-#define BOOST_INTRUSIVE_SELECT_COMPILER_INCLUDED
-#endif
#ifdef BOOST_MSVC
Modified: branches/bcbboost/boost/intrusive/detail/ebo_functor_holder.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/ebo_functor_holder.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/ebo_functor_holder.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -35,7 +35,7 @@
template<typename T>
class ebo_functor_holder_impl<T, false>
- : private T
+ : public T
{
public:
ebo_functor_holder_impl(){}
Modified: branches/bcbboost/boost/intrusive/detail/hashtable_node.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/hashtable_node.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/hashtable_node.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -18,14 +18,9 @@
#include <boost/intrusive/detail/assert.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/circular_list_algorithms.hpp>
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-#include <boost/iterator/iterator_facade.hpp>
-#endif
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
-#include <boost/utility/enable_if.hpp>
-#include <boost/type_traits/is_convertible.hpp>
-#endif
#include <boost/intrusive/detail/mpl.hpp>
+#include <boost/intrusive/detail/utilities.hpp>
+#include <boost/intrusive/detail/slist_node.hpp> //remove-me
#include <cstddef>
namespace boost {
@@ -52,27 +47,34 @@
const std::size_t prime_list_holder<Dummy>::prime_list_size
= sizeof(prime_list)/sizeof(std::size_t);
-template <class SlistImpl>
-struct bucket_type_impl
- : public SlistImpl
+template <class Slist>
+struct bucket_impl : public Slist
{
- bucket_type_impl()
+ bucket_impl()
{}
- bucket_type_impl(const bucket_type_impl &)
+ bucket_impl(const bucket_impl &)
{}
- bucket_type_impl &operator=(const bucket_type_impl&)
- { SlistImpl::clear(); }
+ ~bucket_impl()
+ {
+ //This bucket is still being used!
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(Slist::empty());
+ }
+
+ bucket_impl &operator=(const bucket_impl&)
+ {
+ //This bucket is still in use!
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(Slist::empty());
+ //Slist::clear();
+ }
- static typename std::iterator_traits
- <typename SlistImpl::const_iterator>::difference_type
- get_bucket_num
- ( typename SlistImpl::const_iterator it
- , const bucket_type_impl<SlistImpl> &first_bucket
- , const bucket_type_impl<SlistImpl> &last_bucket)
+ static typename Slist::difference_type get_bucket_num
+ ( typename Slist::const_iterator it
+ , const bucket_impl<Slist> &first_bucket
+ , const bucket_impl<Slist> &last_bucket)
{
- typename SlistImpl::const_iterator
+ typename Slist::const_iterator
first(first_bucket.cend()), last(last_bucket.cend());
//The end node is embedded in the singly linked list:
@@ -81,252 +83,130 @@
it.pointed_node() <= last.pointed_node())){
++it;
}
- //Now get the bucket_type_impl from the iterator
- const bucket_type_impl &b = static_cast<const bucket_type_impl&>
- (SlistImpl::container_from_end_iterator(it));
+ //Now get the bucket_impl from the iterator
+ const bucket_impl &b = static_cast<const bucket_impl&>
+ (Slist::container_from_end_iterator(it));
//Now just calculate the index b has in the bucket array
return &b - &first_bucket;
}
-
- static SlistImpl &bucket_to_slist(bucket_type_impl<SlistImpl> &b)
- { return static_cast<SlistImpl &>(b); }
-
- static const SlistImpl &bucket_to_slist(const bucket_type_impl<SlistImpl> &b)
- { return static_cast<const SlistImpl &>(b); }
-};
-
-template<class SlistImpl>
-struct bucket_info_impl
-{
- typedef typename boost::pointer_to_other
- < typename SlistImpl::pointer
- , bucket_type_impl<SlistImpl> >::type bucket_ptr;
- typedef typename SlistImpl::size_type size_type;
- bucket_ptr buckets_;
- size_type buckets_len_;
};
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-
-template<class Value, class SlistImpl>
-class hashtable_iterator
- : public boost::iterator_facade
- < hashtable_iterator<Value, SlistImpl>
- , Value
- , boost::forward_traversal_tag
- , Value&
- , typename std::iterator_traits<typename SlistImpl::iterator>::difference_type
- >
+template<class Slist>
+struct bucket_traits_impl
{
- typedef typename SlistImpl::iterator local_iterator;
- typedef typename SlistImpl::const_iterator const_local_iterator;
- typedef typename SlistImpl::value_traits::node_ptr node_ptr;
- typedef typename SlistImpl::value_traits::const_node_ptr const_node_ptr;
-
- typedef bucket_type_impl<SlistImpl> bucket_type;
+ /// @cond
typedef typename boost::pointer_to_other
- < typename SlistImpl::pointer, bucket_type>::type bucket_ptr;
- typedef typename boost::pointer_to_other
- < typename SlistImpl::pointer, const bucket_type>::type const_bucket_ptr;
- typedef detail::bucket_info_impl<SlistImpl> bucket_info_t;
- typedef typename boost::pointer_to_other
- <bucket_ptr, bucket_info_t>::type bucket_info_ptr;
- typedef typename boost::pointer_to_other
- <bucket_ptr, const bucket_info_t>::type const_bucket_info_ptr;
- typedef typename SlistImpl::size_type size_type;
- struct enabler {};
+ < typename Slist::pointer, bucket_impl<Slist> >::type bucket_ptr;
+ typedef typename Slist::size_type size_type;
+ /// @endcond
- public:
- hashtable_iterator ()
- {}
-
- explicit hashtable_iterator(local_iterator ptr, const_bucket_info_ptr bucket_info)
- : local_it_ (ptr), bucket_info_ (bucket_info)
- {}
-
-
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- hashtable_iterator(hashtable_iterator<OtherValue, SlistImpl> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,Value*>
- , enabler
- >::type = enabler()
- )
- : local_it_(other.local_it_), bucket_info_(other.bucket_info_)
- {}
- #else
- template <class OtherValue>
- hashtable_iterator(hashtable_iterator<OtherValue, SlistImpl> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : local_it_(other.local_it_), bucket_info_(other.bucket_info_)
+ bucket_traits_impl(bucket_ptr buckets, size_type len)
+ : buckets_(buckets), buckets_len_(len)
{}
- #endif
- const local_iterator &local() const
- { return local_it_; }
+ bucket_ptr bucket_begin() const
+ { return buckets_; }
- const_node_ptr pointed_node() const
- { return local_it_.pointed_node(); }
-
- const const_bucket_info_ptr &bucket_info() const
- { return bucket_info_; }
+ size_type bucket_count() const
+ { return buckets_len_; }
private:
- friend class boost::iterator_core_access;
- template <class, class> friend class hashtable_iterator;
-
- template <class OtherValue>
- bool equal(hashtable_iterator<OtherValue, SlistImpl> const& other) const
- { return other.local() == local_it_; }
-
- void increment()
- {
- size_type buckets_len = bucket_info_->buckets_len_;
- const_bucket_ptr buckets = bucket_info_->buckets_;
- const_local_iterator first = bucket_type::bucket_to_slist(buckets[0]).cend();
- const_local_iterator last = bucket_type::bucket_to_slist(buckets[buckets_len]).cend();
-
- ++local_it_;
- if(first.pointed_node() <= local_it_.pointed_node() &&
- local_it_.pointed_node() <= last.pointed_node()){
- size_type n_bucket = (size_type)
- bucket_type::get_bucket_num(local_it_, buckets[0], buckets[buckets_len]);
- do{
- if (++n_bucket == buckets_len){
- local_it_ = bucket_info_->buckets_->end();
- break;
- }
- local_it_ = bucket_type::bucket_to_slist(bucket_info_->buckets_[n_bucket]).begin();
- }
- while (local_it_ == bucket_type::bucket_to_slist(bucket_info_->buckets_[n_bucket]).end());
- }
- }
-
- Value& dereference() const
- { return *local_it_; }
-
- local_iterator local_it_;
- const_bucket_info_ptr bucket_info_;
+ bucket_ptr buckets_;
+ size_type buckets_len_;
};
-#else
-
-template<class T, class SlistImpl>
+template<class Container, bool IsConst>
class hashtable_iterator
- : public std::iterator<std::forward_iterator_tag, T>
+ : public std::iterator
+ < std::forward_iterator_tag
+ , typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>::type
+ >
{
- typedef typename SlistImpl::iterator local_iterator;
- typedef typename SlistImpl::const_iterator const_local_iterator;
- typedef typename SlistImpl::value_traits::node_ptr node_ptr;
- typedef typename SlistImpl::value_traits::const_node_ptr const_node_ptr;
-
- typedef bucket_type_impl<SlistImpl> bucket_type;
- typedef typename boost::pointer_to_other
- < typename SlistImpl::pointer, bucket_type>::type bucket_ptr;
- typedef typename boost::pointer_to_other
- < typename SlistImpl::pointer, const bucket_type>::type const_bucket_ptr;
- typedef detail::bucket_info_impl<SlistImpl> bucket_info_t;
- typedef typename boost::pointer_to_other
- <bucket_ptr, bucket_info_t>::type bucket_info_ptr;
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename Container::siterator siterator;
+ typedef typename Container::const_siterator const_siterator;
+ typedef typename Container::bucket_type bucket_type;
typedef typename boost::pointer_to_other
- <bucket_ptr, const bucket_info_t>::type const_bucket_info_ptr;
- typedef typename SlistImpl::size_type size_type;
- struct enabler {};
+ < typename Container::pointer, const Container>::type const_cont_ptr;
+ typedef typename Container::size_type size_type;
public:
- typedef T & reference;
- typedef T * pointer;
+ typedef typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>::type value_type;
hashtable_iterator ()
{}
- explicit hashtable_iterator(local_iterator ptr, const_bucket_info_ptr bucket_info)
- : local_it_ (ptr), bucket_info_ (bucket_info)
+ explicit hashtable_iterator(siterator ptr, const Container *cont)
+ : slist_it_ (ptr), cont_ (cont)
{}
-
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- hashtable_iterator(hashtable_iterator<OtherValue, SlistImpl> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : local_it_(other.local_it_), bucket_info_(other.bucket_info_)
- {}
- #else
- template <class OtherValue>
- hashtable_iterator(hashtable_iterator<OtherValue, SlistImpl> const& other,
- typename enable_if<is_convertible<OtherValue*, T*> >::type* = 0)
- : local_it_(other.local_it_), bucket_info_(other.bucket_info_)
+ hashtable_iterator(const hashtable_iterator<Container, false> &other)
+ : slist_it_(other.slist_it()), cont_(other.get_container())
{}
- #endif
-
- const local_iterator &local() const
- { return local_it_; }
-
- const_node_ptr pointed_node() const
- { return local_it_.pointed_node(); }
- const const_bucket_info_ptr &bucket_info() const
- { return bucket_info_; }
+ const siterator &slist_it() const
+ { return slist_it_; }
public:
hashtable_iterator& operator++()
- { increment(); return *this; }
+ { this->increment(); return *this; }
hashtable_iterator operator++(int)
{
hashtable_iterator result (*this);
- increment();
+ this->increment();
return result;
}
friend bool operator== (const hashtable_iterator& i, const hashtable_iterator& i2)
- { return i.pointed_node() == i2.pointed_node(); }
+ { return i.slist_it_ == i2.slist_it_; }
friend bool operator!= (const hashtable_iterator& i, const hashtable_iterator& i2)
{ return !(i == i2); }
- T& operator*() const
- { return *local_it_; }
+ value_type& operator*() const
+ { return *this->operator ->(); }
- pointer operator->() const
- { return &(*local_it_); }
+ value_type* operator->() const
+ { return detail::get_pointer(this->get_real_value_traits()->to_value_ptr(slist_it_.pointed_node())); }
+
+ const Container *get_container() const
+ { return detail::get_pointer(cont_); }
+
+ const real_value_traits *get_real_value_traits() const
+ { return &this->get_container()->get_real_value_traits(); }
private:
void increment()
{
- size_type buckets_len = bucket_info_->buckets_len_;
- const_bucket_ptr buckets = bucket_info_->buckets_;
- const_local_iterator first = bucket_type::bucket_to_slist(buckets[0]).cend();
- const_local_iterator last = bucket_type::bucket_to_slist(buckets[buckets_len]).cend();
-
- ++local_it_;
- if(first.pointed_node() <= local_it_.pointed_node() &&
- local_it_.pointed_node() <= last.pointed_node()){
+ const Container *cont = detail::get_pointer(cont_);
+ bucket_type* buckets = detail::get_pointer(cont->bucket_pointer());
+ size_type buckets_len = cont->bucket_count();
+ const_siterator first(buckets[0].cend());
+ const_siterator last (buckets[buckets_len].cend());
+
+ ++slist_it_;
+ if(first.pointed_node() <= slist_it_.pointed_node() &&
+ slist_it_.pointed_node()<= last.pointed_node() ){
size_type n_bucket = (size_type)
- bucket_type::get_bucket_num(local_it_, buckets[0], buckets[buckets_len]);
+ bucket_type::get_bucket_num(slist_it_, buckets[0], buckets[buckets_len]);
do{
if (++n_bucket == buckets_len){
- local_it_ = bucket_info_->buckets_->end();
+ slist_it_ = buckets->end();
break;
}
- local_it_ = bucket_type::bucket_to_slist(bucket_info_->buckets_[n_bucket]).begin();
+ slist_it_ = buckets[n_bucket].begin();
}
- while (local_it_ == bucket_type::bucket_to_slist(bucket_info_->buckets_[n_bucket]).end());
+ while (slist_it_ == buckets[n_bucket].end());
}
}
- local_iterator local_it_;
- const_bucket_info_ptr bucket_info_;
+ siterator slist_it_;
+ const_cont_ptr cont_;
};
-#endif
} //namespace detail {
} //namespace intrusive {
Modified: branches/bcbboost/boost/intrusive/detail/list_node.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/list_node.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/list_node.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -19,35 +19,31 @@
#include <boost/intrusive/detail/assert.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/circular_list_algorithms.hpp>
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-#include <boost/iterator/iterator_facade.hpp>
-#endif
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
-#include <boost/utility/enable_if.hpp>
-#include <boost/type_traits/is_convertible.hpp>
-#endif
namespace boost {
namespace intrusive {
-namespace detail {
// list_node_traits can be used with circular_list_algorithms and supplies
// a list_node holding the pointers needed for a double-linked list
// it is used by list_derived_node and list_member_node
+
+template<class VoidPointer>
+struct list_node
+{
+ typedef typename boost::pointer_to_other
+ <VoidPointer, list_node>::type node_ptr;
+ node_ptr prev_, next_;
+};
+
template<class VoidPointer>
struct list_node_traits
{
- struct node;
+ typedef list_node<VoidPointer> node;
typedef typename boost::pointer_to_other
<VoidPointer, node>::type node_ptr;
typedef typename boost::pointer_to_other
<VoidPointer, const node>::type const_node_ptr;
- struct node
- {
- node_ptr prev_, next_;
- };
-
static node_ptr get_previous(const_node_ptr n)
{ return n->prev_; }
@@ -61,178 +57,126 @@
{ n->next_ = next; }
};
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-
-// list_iterator provides some basic functions for a
-// node oriented forward iterator:
-template<class T, class ValueTraits>
-class list_iterator
- : public boost::iterator_facade
- < list_iterator<T, ValueTraits>
- , T
- , boost::bidirectional_traversal_tag
- , T&
- , typename std::iterator_traits<typename ValueTraits::node_ptr>::difference_type
- >
-{
- typedef typename ValueTraits::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
- typedef typename node_traits::const_node_ptr const_node_ptr;
- struct enabler{};
-
- public:
- typedef typename pointer_to_other<typename ValueTraits::node_ptr, T>::type pointer;
- typedef typename std::iterator_traits<node_ptr>::difference_type difference_type;
-
- list_iterator ()
- : node_ (0)
- {}
-
- explicit list_iterator(node_ptr node)
- : node_ (node)
- {}
-
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- list_iterator(list_iterator<OtherValue, ValueTraits> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : node_(other.pointed_node())
- {}
- #else
- template <class OtherValue>
- list_iterator(list_iterator<OtherValue, ValueTraits> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : node_(other.pointed_node())
- {}
- #endif
-
- const node_ptr &pointed_node() const
- { return node_; }
-
- private:
- friend class boost::iterator_core_access;
- template <class, class> friend class list_iterator;
-
- template <class OtherValue>
- bool equal(list_iterator<OtherValue, ValueTraits> const& other) const
- { return other.pointed_node() == node_; }
-
- void increment()
- { node_ = node_traits::get_next(node_); }
-
- void decrement()
- { node_ = node_traits::get_previous(node_); }
-
- T& dereference() const
- { return *ValueTraits::to_value_ptr(node_); }
-
- node_ptr node_;
-};
-
-#else //BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-
// list_iterator provides some basic functions for a
// node oriented bidirectional iterator:
-template<class T, class ValueTraits>
+template<class Container, bool IsConst>
class list_iterator
- : public std::iterator<std::bidirectional_iterator_tag, T>
+ : public std::iterator
+ < std::bidirectional_iterator_tag
+ , typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>::type
+ >
{
- struct enabler{};
protected:
- typedef typename ValueTraits::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
-
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef typename node_traits::node_ptr node_ptr;
+ typedef typename boost::pointer_to_other
+ <node_ptr, void>::type void_pointer;
+ static const bool store_container_ptr =
+ detail::store_cont_ptr_on_it<Container>::value;
+
public:
- typedef T & reference;
- typedef T * pointer;
+ typedef typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>
+ ::type value_type;
+ typedef value_type & reference;
+ typedef value_type * pointer;
list_iterator()
- : node_ (0)
+ : members_ (0, 0)
{}
- explicit list_iterator(node_ptr node)
- : node_ (node)
+ explicit list_iterator(node_ptr node, const Container *cont_ptr)
+ : members_ (node, cont_ptr)
{}
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- list_iterator(list_iterator<OtherValue, ValueTraits> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : node_(other.pointed_node())
- {}
- #else
- template <class OtherValue>
- list_iterator(list_iterator<OtherValue, ValueTraits> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : node_(other.pointed_node())
+
+ list_iterator(list_iterator<Container, false> const& other)
+ : members_(other.pointed_node(), other.get_container())
{}
- #endif
const node_ptr &pointed_node() const
- { return node_; }
+ { return members_.nodeptr_; }
list_iterator &operator=(const node_ptr &node)
- { node_ = node; return static_cast<list_iterator&>(*this); }
+ { members_.nodeptr_ = node; return static_cast<list_iterator&>(*this); }
public:
list_iterator& operator++()
{
- node_ = node_traits::get_next(node_);
+ members_.nodeptr_ = node_traits::get_next(members_.nodeptr_);
return static_cast<list_iterator&> (*this);
}
list_iterator operator++(int)
{
- list_iterator result (node_);
- node_ = node_traits::get_next(node_);
+ list_iterator result (*this);
+ members_.nodeptr_ = node_traits::get_next(members_.nodeptr_);
return result;
}
list_iterator& operator--()
{
- node_ = node_traits::get_previous(node_);
+ members_.nodeptr_ = node_traits::get_previous(members_.nodeptr_);
return static_cast<list_iterator&> (*this);
}
list_iterator operator--(int)
{
- list_iterator result (node_);
- node_ = node_traits::get_previous(node_);
+ list_iterator result (*this);
+ members_.nodeptr_ = node_traits::get_previous(members_.nodeptr_);
return result;
}
bool operator== (const list_iterator& i) const
- { return node_ == i.pointed_node(); }
+ { return members_.nodeptr_ == i.pointed_node(); }
bool operator!= (const list_iterator& i) const
- { return !operator== (i); }
+ { return !operator== (i); }
- T& operator*() const
- { return *ValueTraits::to_value_ptr(node_); }
+ value_type& operator*() const
+ { return *operator->(); }
pointer operator->() const
- { return detail::get_pointer(ValueTraits::to_value_ptr(node_)); }
+ { return detail::get_pointer(this->get_real_value_traits()->to_value_ptr(members_.nodeptr_)); }
+
+ const Container *get_container() const
+ {
+ if(store_container_ptr){
+ const Container* c = static_cast<const Container*>(members_.get_ptr());
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(c != 0);
+ return c;
+ }
+ else{
+ return 0;
+ }
+ }
+
+ const real_value_traits *get_real_value_traits() const
+ {
+ if(store_container_ptr)
+ return &this->get_container()->get_real_value_traits();
+ else
+ return 0;
+ }
private:
- node_ptr node_;
-};
+ struct members
+ : public detail::select_constptr
+ <void_pointer, store_container_ptr>::type
+ {
+ typedef typename detail::select_constptr
+ <void_pointer, store_container_ptr>::type Base;
+
+ members(const node_ptr &n_ptr, const void *cont)
+ : Base(cont), nodeptr_(n_ptr)
+ {}
-#endif
+ node_ptr nodeptr_;
+ } members_;
+};
-} //namespace detail
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/detail/mpl.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/mpl.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/mpl.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,6 +17,9 @@
namespace intrusive {
namespace detail {
+typedef char one;
+struct two {one _[2];};
+
template< bool C_ >
struct bool_
{
@@ -55,7 +58,61 @@
static false_t dispatch(...);
static T trigger();
public:
- enum { value = sizeof(dispatch(trigger())) == sizeof(true_t) };
+ static const bool value = sizeof(dispatch(trigger())) == sizeof(true_t);
+};
+
+template<
+ bool C
+ , typename T1
+ , typename T2
+ >
+struct if_c
+{
+ typedef T1 type;
+};
+
+template<
+ typename T1
+ , typename T2
+ >
+struct if_c<false,T1,T2>
+{
+ typedef T2 type;
+};
+
+template<
+ typename C
+ , typename T1
+ , typename T2
+ >
+struct if_
+{
+ typedef typename if_c<0 != C::value, T1, T2>::type type;
+};
+
+template<
+ bool C
+ , typename F1
+ , typename F2
+ >
+struct eval_if_c
+ : if_c<C,F1,F2>::type
+{};
+
+template<
+ typename C
+ , typename T1
+ , typename T2
+ >
+struct eval_if
+ : if_<C,T1,T2>::type
+{};
+
+// identity is an extension: it is not part of the standard.
+template <class T>
+struct identity
+{
+ typedef T type;
};
#if defined(BOOST_MSVC) || defined(__BORLANDC_)
@@ -130,18 +187,20 @@
template <typename T>
struct is_unary_or_binary_function_impl
{
- static T* t;
- enum{ value = sizeof(is_function_ptr_tester(t)) == sizeof(yes_type) };
+ static T* t;
+ static const bool value = sizeof(is_function_ptr_tester(t)) == sizeof(yes_type);
};
template <typename T>
struct is_unary_or_binary_function_impl<T&>
-{ enum {value = false }; };
+{
+ static const bool value = false;
+};
template<typename T>
struct is_unary_or_binary_function
{
- enum{ value = is_unary_or_binary_function_impl<T>::value };
+ static const bool value = is_unary_or_binary_function_impl<T>::value;
};
//boost::alignment_of yields to 10K lines of preprocessed code, so we
@@ -159,15 +218,68 @@
template <unsigned A, unsigned S>
struct alignment_logic
{
- enum{ value = A < S ? A : S };
+ static const std::size_t value = A < S ? A : S;
};
template< typename T >
struct alignment_of
{
- enum{ value = alignment_logic
+ static const std::size_t value = alignment_logic
< sizeof(alignment_of_hack<T>) - sizeof(T)
- , sizeof(T)>::value };
+ , sizeof(T)
+ >::value;
+};
+
+template <typename T, typename U>
+struct is_same
+{
+ typedef char yes_type;
+ struct no_type
+ {
+ char padding[8];
+ };
+
+ template <typename V>
+ static yes_type is_same_tester(V*, V*);
+ static no_type is_same_tester(...);
+
+ static T *t;
+ static U *u;
+
+ static const bool value = sizeof(yes_type) == sizeof(is_same_tester(t,u));
+};
+
+template<typename T>
+struct add_const
+{ typedef const T type; };
+
+template<class T>
+struct remove_reference
+{
+ typedef T type;
+};
+
+template<class T>
+struct remove_reference<T&>
+{
+ typedef T type;
+};
+
+template<class Class>
+class is_empty_class
+{
+ template <typename T>
+ struct empty_helper_t1 : public T
+ {
+ empty_helper_t1();
+ int i[256];
+ };
+
+ struct empty_helper_t2
+ { int i[256]; };
+
+ public:
+ static const bool value = sizeof(empty_helper_t1<Class>) == sizeof(empty_helper_t2);
};
} //namespace detail
Modified: branches/bcbboost/boost/intrusive/detail/parent_from_member.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/parent_from_member.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/parent_from_member.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,6 +13,7 @@
#define BOOST_INTRUSIVE_PARENT_FROM_MEMBER_HPP
#include <boost/intrusive/detail/config_begin.hpp>
+#include <boost/static_assert.hpp>
#include <cstddef>
namespace boost {
@@ -22,14 +23,18 @@
template<class Parent, class Member>
inline std::size_t offset_from_pointer_to_member(const Member Parent::* ptr_to_member)
{
+ //BOOST_STATIC_ASSERT(( sizeof(std::ptrdiff_t) == sizeof(ptr_to_member) ));
//The implementation of a pointer to member is compiler dependent.
- #if (defined(_MSC_VER) || defined(__GNUC__) || \
- defined(BOOST_INTEL) || defined(__HP_aCC))
- //This works with gcc, msvc, ac++
+ #if defined(BOOST_MSVC) || (defined (BOOST_WINDOWS) && defined(BOOST_INTEL))
+ //This works with gcc, msvc, ac++, ibmcpp
return *(const std::ptrdiff_t*)(void*)&ptr_to_member;
+ #elif defined(__GNUC__) || defined(__HP_aCC) || defined(BOOST_INTEL) || defined (__IBMCPP__)
+ const Parent * const parent = 0;
+ const char *const member = reinterpret_cast<const char*>(&(parent->*ptr_to_member));
+ return std::size_t(member - reinterpret_cast<const char*>(parent));
#else
//This is the traditional C-front approach: __MWERKS__, __DMC__, __SUNPRO_CC
- return *(const std::ptrdiff_t*)(void*)&ptr_to_member - 1;
+ return (*(const std::ptrdiff_t*)(void*)&ptr_to_member) - 1;
#endif
}
Modified: branches/bcbboost/boost/intrusive/detail/rbtree_node.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/rbtree_node.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/rbtree_node.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -18,19 +18,11 @@
#include <iterator>
#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/rbtree_algorithms.hpp>
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-#include <boost/iterator/iterator_facade.hpp>
-#endif
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
-#include <boost/utility/enable_if.hpp>
-#include <boost/type_traits/is_convertible.hpp>
-#endif
#include <boost/intrusive/pointer_plus_bit.hpp>
#include <boost/intrusive/detail/mpl.hpp>
namespace boost {
namespace intrusive {
-namespace detail {
/////////////////////////////////////////////////////////////////////////////
// //
@@ -164,14 +156,14 @@
: public compact_rbtree_node_traits_impl<VoidPointer>
{};
-//Inherit from the dispatcher depending on the embedding capabilities
+//Inherit from the detail::link_dispatch depending on the embedding capabilities
template<class VoidPointer>
struct rbtree_node_traits
: public rbtree_node_traits_dispatch
- <VoidPointer
- ,has_pointer_plus_bit
- <VoidPointer, detail::alignment_of<compact_rbtree_node<VoidPointer>
- >::value
+ < VoidPointer
+ , has_pointer_plus_bit
+ < VoidPointer
+ , detail::alignment_of<compact_rbtree_node<VoidPointer> >::value
>::value
>
{};
@@ -182,179 +174,124 @@
// //
/////////////////////////////////////////////////////////////////////////////
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-
-template<class T, class ValueTraits>
-class rbtree_iterator
- : public boost::iterator_facade
- < rbtree_iterator<T, ValueTraits>
- , T
- , boost::bidirectional_traversal_tag
- , T&
- , typename std::iterator_traits<typename ValueTraits::node_ptr>::difference_type
- >
-{
- typedef typename ValueTraits::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
- typedef typename node_traits::const_node_ptr const_node_ptr;
- typedef rbtree_algorithms<node_traits> node_algorithms;
- struct enabler{};
-
- public:
- typedef typename pointer_to_other<typename ValueTraits::node_ptr, T>::type pointer;
- typedef typename std::iterator_traits<node_ptr>::difference_type difference_type;
-
- rbtree_iterator ()
- : node_ (0)
- {}
-
- explicit rbtree_iterator(node_ptr node)
- : node_ (node)
- {}
-
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- rbtree_iterator(rbtree_iterator<OtherValue, ValueTraits> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : node_(other.pointed_node())
- {}
- #else
- template <class OtherValue>
- rbtree_iterator(rbtree_iterator<OtherValue, ValueTraits> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : node_(other.pointed_node())
- {}
- #endif
-
- const node_ptr &pointed_node() const
- { return node_; }
-
- private:
- friend class boost::iterator_core_access;
- template <class, class> friend class rbtree_iterator;
-
- template <class OtherValue>
- bool equal(rbtree_iterator<OtherValue, ValueTraits> const& other) const
- { return other.pointed_node() == node_; }
-
- void increment()
- { node_ = node_algorithms::next_node(node_); }
-
- void decrement()
- { node_ = node_algorithms::prev_node(node_); }
-
- T& dereference() const
- { return *ValueTraits::to_value_ptr(node_); }
-
- node_ptr node_;
-};
-
-#else
-
// rbtree_iterator provides some basic functions for a
// node oriented bidirectional iterator:
-template<class T, class ValueTraits>
+template<class Container, bool IsConst>
class rbtree_iterator
- : public std::iterator<std::bidirectional_iterator_tag, T>
+ : public std::iterator
+ < std::bidirectional_iterator_tag
+ , typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>::type
+ >
{
- struct enabler{};
protected:
- typedef typename ValueTraits::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
- typedef rbtree_algorithms<node_traits> node_algorithms;
-
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef typename node_traits::node_ptr node_ptr;
+ typedef rbtree_algorithms<node_traits> node_algorithms;
+ typedef typename boost::pointer_to_other
+ <node_ptr, void>::type void_pointer;
+ static const bool store_container_ptr =
+ detail::store_cont_ptr_on_it<Container>::value;
+
public:
- typedef T & reference;
- typedef T * pointer;
+ public:
+ typedef typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>
+ ::type value_type;
+ typedef value_type & reference;
+ typedef value_type * pointer;
rbtree_iterator()
- : node_ (0)
+ : members_ (0, 0)
{}
- explicit rbtree_iterator(node_ptr node)
- : node_ (node)
+ explicit rbtree_iterator(node_ptr node, const Container *cont_ptr)
+ : members_ (node, cont_ptr)
{}
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- rbtree_iterator(rbtree_iterator<OtherValue, ValueTraits> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : node_(other.pointed_node())
- {}
- #else
- template <class OtherValue>
- rbtree_iterator(rbtree_iterator<OtherValue, ValueTraits> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : node_(other.pointed_node())
+ rbtree_iterator(rbtree_iterator<Container, false> const& other)
+ : members_(other.pointed_node(), other.get_container())
{}
- #endif
const node_ptr &pointed_node() const
- { return node_; }
+ { return members_.nodeptr_; }
rbtree_iterator &operator=(const node_ptr &node)
- { node_ = node; return static_cast<rbtree_iterator&>(*this); }
+ { members_.nodeptr_ = node; return static_cast<rbtree_iterator&>(*this); }
public:
rbtree_iterator& operator++()
{
- node_ = node_algorithms::next_node(node_);
+ members_.nodeptr_ = node_algorithms::next_node(members_.nodeptr_);
return static_cast<rbtree_iterator&> (*this);
}
rbtree_iterator operator++(int)
{
- rbtree_iterator result (node_);
- node_ = node_algorithms::next_node(node_);
+ rbtree_iterator result (*this);
+ members_.nodeptr_ = node_algorithms::next_node(members_.nodeptr_);
return result;
}
rbtree_iterator& operator--()
{
- node_ = node_algorithms::prev_node(node_);
+ members_.nodeptr_ = node_algorithms::prev_node(members_.nodeptr_);
return static_cast<rbtree_iterator&> (*this);
}
rbtree_iterator operator--(int)
{
- rbtree_iterator result (node_);
- node_ = node_algorithms::prev_node(node_);
+ rbtree_iterator result (*this);
+ members_.nodeptr_ = node_algorithms::prev_node(members_.nodeptr_);
return result;
}
bool operator== (const rbtree_iterator& i) const
- { return node_ == i.pointed_node(); }
+ { return members_.nodeptr_ == i.pointed_node(); }
bool operator!= (const rbtree_iterator& i) const
{ return !operator== (i); }
- T& operator*() const
- { return *ValueTraits::to_value_ptr(node_); }
+ value_type& operator*() const
+ { return *operator->(); }
pointer operator->() const
- { return detail::get_pointer(ValueTraits::to_value_ptr(node_)); }
+ { return detail::get_pointer(this->get_real_value_traits()->to_value_ptr(members_.nodeptr_)); }
+
+ const Container *get_container() const
+ {
+ if(store_container_ptr)
+ return static_cast<const Container*>(members_.get_ptr());
+ else
+ return 0;
+ }
+
+ const real_value_traits *get_real_value_traits() const
+ {
+ if(store_container_ptr)
+ return &this->get_container()->get_real_value_traits();
+ else
+ return 0;
+ }
private:
- node_ptr node_;
-};
+ struct members
+ : public detail::select_constptr
+ <void_pointer, store_container_ptr>::type
+ {
+ typedef typename detail::select_constptr
+ <void_pointer, store_container_ptr>::type Base;
-#endif
+ members(const node_ptr &n_ptr, const void *cont)
+ : Base(cont), nodeptr_(n_ptr)
+ {}
+
+ node_ptr nodeptr_;
+ } members_;
+};
-} //namespace detail
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/detail/slist_node.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/slist_node.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/slist_node.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -19,17 +19,17 @@
#include <boost/intrusive/detail/assert.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/circular_slist_algorithms.hpp>
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-#include <boost/iterator/iterator_facade.hpp>
-#endif
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
-#include <boost/utility/enable_if.hpp>
-#include <boost/type_traits/is_convertible.hpp>
-#endif
namespace boost {
namespace intrusive {
-namespace detail {
+
+template<class VoidPointer>
+struct slist_node
+{
+ typedef typename boost::pointer_to_other
+ <VoidPointer, slist_node>::type node_ptr;
+ node_ptr next_;
+};
// slist_node_traits can be used with circular_slist_algorithms and supplies
// a slist_node holding the pointers needed for a singly-linked list
@@ -37,18 +37,12 @@
template<class VoidPointer>
struct slist_node_traits
{
- struct node;
-
+ typedef slist_node<VoidPointer> node;
typedef typename boost::pointer_to_other
<VoidPointer, node>::type node_ptr;
typedef typename boost::pointer_to_other
<VoidPointer, const node>::type const_node_ptr;
- struct node
- {
- node_ptr next_;
- };
-
static node_ptr get_next(const_node_ptr n)
{ return n->next_; }
@@ -56,163 +50,109 @@
{ n->next_ = next; }
};
-#ifdef BOOST_INTRUSIVE_USE_ITERATOR_FACADE
-
-// slist_iterator provides some basic functions for a
-// node oriented forward iterator:
-template<class T, class ValueTraits>
-class slist_iterator
- : public boost::iterator_facade
- < slist_iterator<T, ValueTraits>
- , T
- , boost::forward_traversal_tag
- , T&
- , typename std::iterator_traits<typename ValueTraits::node_ptr>::difference_type
- >
-{
- typedef typename ValueTraits::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
- typedef typename node_traits::const_node_ptr const_node_ptr;
- struct enabler{};
-
- public:
- typedef typename pointer_to_other<typename ValueTraits::node_ptr, T>::type pointer;
- typedef typename std::iterator_traits<node_ptr>::difference_type difference_type;
-
- slist_iterator ()
- : node_ (0)
- {}
-
- explicit slist_iterator(node_ptr node)
- : node_ (node)
- {}
-
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- slist_iterator(slist_iterator<OtherValue, ValueTraits> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : node_(other.pointed_node())
- {}
- #else
- template <class OtherValue>
- slist_iterator(slist_iterator<OtherValue, ValueTraits> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : node_(other.pointed_node())
- {}
- #endif
-
- const node_ptr &pointed_node() const
- { return node_; }
-
- private:
- friend class boost::iterator_core_access;
- template <class, class> friend class slist_iterator;
-
- template <class OtherValue>
- bool equal(slist_iterator<OtherValue, ValueTraits> const& other) const
- { return other.pointed_node() == node_; }
-
- void increment()
- { node_ = node_traits::get_next(node_); }
-
- T& dereference() const
- { return *ValueTraits::to_value_ptr(node_); }
-
- node_ptr node_;
-};
-
-#else
-
// slist_iterator provides some basic functions for a
// node oriented bidirectional iterator:
-template<class T, class ValueTraits>
+template<class Container, bool IsConst>
class slist_iterator
- : public std::iterator<std::forward_iterator_tag, T>
+ : public std::iterator
+ < std::forward_iterator_tag
+ , typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>::type
+ >
{
- struct enabler{};
protected:
- typedef typename ValueTraits::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
-
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef typename node_traits::node_ptr node_ptr;
+ typedef typename boost::pointer_to_other
+ <node_ptr, void>::type void_pointer;
+ static const bool store_container_ptr =
+ detail::store_cont_ptr_on_it<Container>::value;
+
public:
- typedef T & reference;
- typedef T * pointer;
+ typedef typename detail::add_const_if_c
+ <typename Container::value_type, IsConst>
+ ::type value_type;
+ typedef value_type & reference;
+ typedef value_type * pointer;
slist_iterator()
- : node_ (0)
+ : members_ (0, 0)
{}
- explicit slist_iterator(node_ptr node)
- : node_ (node)
+ explicit slist_iterator(node_ptr node, const Container *cont_ptr)
+ : members_ (node, cont_ptr)
{}
- #ifdef BOOST_INTRUSIVE_USE_ITERATOR_ENABLE_IF_CONVERTIBLE
- template <class OtherValue>
- slist_iterator(slist_iterator<OtherValue, ValueTraits> const& other
- ,typename boost::enable_if<
- boost::is_convertible<OtherValue*,T*>
- , enabler
- >::type = enabler()
- )
- : node_(other.pointed_node())
+ slist_iterator(slist_iterator<Container, false> const& other)
+ : members_(other.pointed_node(), other.get_container())
{}
- #else
- template <class OtherValue>
- slist_iterator(slist_iterator<OtherValue, ValueTraits> const& other,
- typename enable_if<
- is_convertible<OtherValue*,T*>
- >::type* = 0)
- : node_(other.pointed_node())
- {}
- #endif
const node_ptr &pointed_node() const
- { return node_; }
+ { return members_.nodeptr_; }
slist_iterator &operator=(const node_ptr &node)
- { node_ = node; return static_cast<slist_iterator&>(*this); }
+ { members_.nodeptr_ = node; return static_cast<slist_iterator&>(*this); }
public:
slist_iterator& operator++()
{
- node_ = node_traits::get_next(node_);
+ members_.nodeptr_ = node_traits::get_next(members_.nodeptr_);
return static_cast<slist_iterator&> (*this);
}
slist_iterator operator++(int)
{
- slist_iterator result (node_);
- node_ = node_traits::get_next(node_);
+ slist_iterator result (*this);
+ members_.nodeptr_ = node_traits::get_next(members_.nodeptr_);
return result;
}
bool operator== (const slist_iterator& i) const
- { return node_ == i.pointed_node(); }
+ { return members_.nodeptr_ == i.pointed_node(); }
bool operator!= (const slist_iterator& i) const
- { return !operator== (i); }
+ { return !operator== (i); }
- T& operator*() const
- { return *ValueTraits::to_value_ptr(node_); }
+ value_type& operator*() const
+ { return *operator->(); }
pointer operator->() const
- { return detail::get_pointer(ValueTraits::to_value_ptr(node_)); }
+ { return detail::get_pointer(this->get_real_value_traits()->to_value_ptr(members_.nodeptr_)); }
+
+ const Container *get_container() const
+ {
+ if(store_container_ptr)
+ return static_cast<const Container*>(members_.get_ptr());
+ else
+ return 0;
+ }
+
+ const real_value_traits *get_real_value_traits() const
+ {
+ if(store_container_ptr)
+ return &this->get_container()->get_real_value_traits();
+ else
+ return 0;
+ }
private:
- node_ptr node_;
-};
+ struct members
+ : public detail::select_constptr
+ <void_pointer, store_container_ptr>::type
+ {
+ typedef typename detail::select_constptr
+ <void_pointer, store_container_ptr>::type Base;
-#endif
+ members(const node_ptr &n_ptr, const void *cont)
+ : Base(cont), nodeptr_(n_ptr)
+ {}
+
+ node_ptr nodeptr_;
+ } members_;
+};
-} //namespace detail
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/detail/utilities.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/detail/utilities.hpp (original)
+++ branches/bcbboost/boost/intrusive/detail/utilities.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,7 +17,7 @@
#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/detail/parent_from_member.hpp>
#include <boost/intrusive/detail/ebo_functor_holder.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <boost/intrusive/detail/mpl.hpp>
#include <cstddef>
#include <iterator>
@@ -26,6 +26,64 @@
namespace intrusive {
namespace detail {
+template <class T>
+struct internal_member_value_traits
+{
+ template <class U> static detail::one test(...);
+ template <class U> static detail::two test(typename U::member_value_traits* = 0);
+ static const bool value = sizeof(test<T>(0)) == sizeof(detail::two);
+};
+
+template <class T>
+struct internal_base_hook_bool
+{
+ template<bool Add>
+ struct two_or_three {one _[2 + Add];};
+ template <class U> static one test(...);
+ template <class U> static two_or_three<U::boost_intrusive_tags::is_base_hook>
+ test (detail::bool_<U::boost_intrusive_tags::is_base_hook>* = 0);
+ static const int value = sizeof(test<T>(0));
+};
+
+template <class T>
+struct internal_base_hook_bool_is_true
+{
+ static const bool value = internal_base_hook_bool<T>::value == 3;
+};
+
+template <class T>
+struct external_value_traits_bool
+{
+ template<bool Add>
+ struct two_or_three {one _[2 + Add];};
+ template <class U> static one test(...);
+ template <class U> static two_or_three<U::external_value_traits>
+ test (detail::bool_<U::external_value_traits>* = 0);
+ static const int value = sizeof(test<T>(0));
+};
+
+template <class T>
+struct external_bucket_traits_bool
+{
+ template<bool Add>
+ struct two_or_three {one _[2 + Add];};
+ template <class U> static one test(...);
+ template <class U> static two_or_three<U::external_bucket_traits>
+ test (detail::bool_<U::external_bucket_traits>* = 0);
+ static const int value = sizeof(test<T>(0));
+};
+
+template <class T>
+struct external_value_traits_is_true
+{
+ static const bool value = external_value_traits_bool<T>::value == 3;
+};
+
+template<class Node, class Tag, link_mode_type LinkMode, int>
+struct node_holder
+ : public Node
+{};
+
template<class SmartPtr>
struct smart_ptr_type
{
@@ -49,7 +107,6 @@
inline typename smart_ptr_type<Ptr>::pointer
get_pointer(const Ptr &ptr)
{ return smart_ptr_type<Ptr>::get(ptr); }
-//{ using boost::get_pointer; return get_pointer(ptr); }
//This functor compares a stored value
//and the one passed as an argument
@@ -75,10 +132,20 @@
{}
};
+template<class NodeAlgorithms>
+class init_disposer
+{
+ typedef typename NodeAlgorithms::node_ptr node_ptr;
+
+ public:
+ void operator()(node_ptr p)
+ { NodeAlgorithms::init(p); }
+};
+
template<bool ConstantSize, class SizeType>
struct size_holder
{
- enum { constant_time_size = ConstantSize };
+ static const bool constant_time_size = ConstantSize;
typedef SizeType size_type;
SizeType get_size() const
@@ -99,7 +166,7 @@
template<class SizeType>
struct size_holder<false, SizeType>
{
- enum { constant_time_size = false };
+ static const bool constant_time_size = false;
typedef SizeType size_type;
size_type get_size() const
@@ -115,185 +182,297 @@
{}
};
-template<class T, class DerivationHookType, typename Tag>
-struct derivation_hook_value_traits
+template<class KeyValueCompare, class Container>
+struct key_nodeptr_comp
+ : private detail::ebo_functor_holder<KeyValueCompare>
{
- public:
- typedef typename DerivationHookType::node_traits node_traits;
- typedef T value_type;
- typedef typename node_traits::node_ptr node_ptr;
- typedef typename node_traits::const_node_ptr const_node_ptr;
- typedef typename boost::pointer_to_other<node_ptr, T>::type pointer;
- typedef typename boost::pointer_to_other<node_ptr, const T>::type const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- enum { linking_policy = DerivationHookType::linking_policy };
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename real_value_traits::node_ptr node_ptr;
+ typedef detail::ebo_functor_holder<KeyValueCompare> base_t;
+ key_nodeptr_comp(KeyValueCompare kcomp, const Container *cont)
+ : base_t(kcomp), cont_(cont)
+ {}
- static node_ptr to_node_ptr(reference value)
- { return static_cast<DerivationHookType &>(value).to_node_ptr(); }
+ template<class KeyType>
+ bool operator()(node_ptr node, const KeyType &key) const
+ { return base_t::get()(*cont_->get_real_value_traits().to_value_ptr(node), key); }
- static const_node_ptr to_node_ptr(const_reference value)
- { return static_cast<const DerivationHookType &>(value).to_node_ptr(); }
+ template<class KeyType>
+ bool operator()(const KeyType &key, node_ptr node) const
+ { return base_t::get()(key, *cont_->get_real_value_traits().to_value_ptr(node)); }
- static pointer to_value_ptr(node_ptr n)
- {
- return static_cast<T*>(detail::get_pointer(DerivationHookType::to_hook_ptr(n)));
+ bool operator()(node_ptr node1, node_ptr node2) const
+ {
+ return base_t::get()
+ ( *cont_->get_real_value_traits().to_value_ptr(node1)
+ , *cont_->get_real_value_traits().to_value_ptr(node2)
+ );
}
- static const_pointer to_value_ptr(const_node_ptr n)
- {
- return static_cast<const T*>(detail::get_pointer(DerivationHookType::to_hook_ptr(n)));
- }
+ const Container *cont_;
};
-
-template<class T, class MemberHookType, MemberHookType T::* P>
-struct member_hook_value_traits
+template<class F, class Container>
+struct node_cloner
+ : private detail::ebo_functor_holder<F>
{
- public:
- typedef typename MemberHookType::node_traits node_traits;
- typedef T value_type;
- typedef typename node_traits::node_ptr node_ptr;
- typedef typename node_traits::const_node_ptr const_node_ptr;
- typedef typename boost::pointer_to_other<node_ptr, T>::type pointer;
- typedef typename boost::pointer_to_other<node_ptr, const T>::type const_pointer;
- typedef value_type & reference;
- typedef const value_type & const_reference;
- enum { linking_policy = MemberHookType::linking_policy };
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename Container::node_algorithms node_algorithms;
+ typedef typename real_value_traits::value_type value_type;
+ typedef typename real_value_traits::pointer pointer;
+ typedef typename real_value_traits::node_traits::node node;
+ typedef typename real_value_traits::node_ptr node_ptr;
+ typedef typename real_value_traits::const_node_ptr const_node_ptr;
+ typedef detail::ebo_functor_holder<F> base_t;
+ enum { safemode_or_autounlink =
+ (int)real_value_traits::link_mode == (int)auto_unlink ||
+ (int)real_value_traits::link_mode == (int)safe_link };
- public:
- static node_ptr to_node_ptr(reference value)
+ node_cloner(F f, const Container *cont)
+ : base_t(f), cont_(cont)
+ {}
+
+ node_ptr operator()(node_ptr p)
{
- MemberHookType* result = &(value.*P);
- return result->to_node_ptr();
+ node_ptr n = cont_->get_real_value_traits().to_node_ptr
+ (*base_t::get()(*cont_->get_real_value_traits().to_value_ptr(p)));
+ //Cloned node must be in default mode if the linking mode requires it
+ if(safemode_or_autounlink)
+ BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(n));
+ return n;
}
- static const_node_ptr to_node_ptr(const_reference value)
+ node_ptr operator()(const node &to_clone)
{
- const MemberHookType* result = &(value.*P);
- return result->to_node_ptr();
+ const value_type &v =
+ *cont_->get_real_value_traits().to_value_ptr(const_node_ptr(&to_clone));
+ node_ptr n = cont_->get_real_value_traits().to_node_ptr(*base_t::get()(v));
+ //Cloned node must be in default mode if the linking mode requires it
+ if(safemode_or_autounlink)
+ BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(n));
+ return n;
}
- static pointer to_value_ptr(node_ptr n)
- {
- return pointer
- (
- parent_from_member<value_type, MemberHookType>
- (detail::get_pointer(MemberHookType::to_hook_ptr(n)), P)
- );
- }
+ const Container *cont_;
+};
- static const_pointer to_value_ptr(const_node_ptr n)
+template<class F, class Container>
+struct node_disposer
+ : private detail::ebo_functor_holder<F>
+{
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename real_value_traits::node_ptr node_ptr;
+ typedef detail::ebo_functor_holder<F> base_t;
+ typedef typename Container::node_algorithms node_algorithms;
+ enum { safemode_or_autounlink =
+ (int)real_value_traits::link_mode == (int)auto_unlink ||
+ (int)real_value_traits::link_mode == (int)safe_link };
+
+ node_disposer(F f, const Container *cont)
+ : base_t(f), cont_(cont)
+ {}
+
+ void operator()(node_ptr p)
{
- return const_pointer
- (
- parent_from_member<value_type, MemberHookType>
- (detail::get_pointer(MemberHookType::to_hook_ptr(n)), P)
- );
+ if(safemode_or_autounlink)
+ node_algorithms::init(p);
+ base_t::get()(cont_->get_real_value_traits().to_value_ptr(p));
}
+ const Container *cont_;
};
-template<class KeyValueCompare, class ValueTraits>
-struct key_node_ptr_compare
- : private detail::ebo_functor_holder<KeyValueCompare>
+struct dummy_constptr
{
- typedef typename ValueTraits::node_ptr node_ptr;
- typedef detail::ebo_functor_holder<KeyValueCompare> base_t;
- key_node_ptr_compare(KeyValueCompare kcomp)
- : base_t(kcomp)
+ dummy_constptr(const void *)
{}
- template<class KeyType>
- bool operator()(node_ptr node, const KeyType &key) const
- { return base_t::get()(*ValueTraits::to_value_ptr(node), key); }
-
- template<class KeyType>
- bool operator()(const KeyType &key, node_ptr node) const
- { return base_t::get()(key, *ValueTraits::to_value_ptr(node)); }
-
- bool operator()(node_ptr node1, node_ptr node2) const
- {
- return base_t::get()
- (*ValueTraits::to_value_ptr(node1), *ValueTraits::to_value_ptr(node2));
- }
+ const void *get_ptr() const
+ { return 0; }
};
-template<class F, class ValueTraits>
-struct value_to_node_cloner
- : private detail::ebo_functor_holder<F>
+template<class VoidPointer>
+struct constptr
{
- typedef typename ValueTraits::node_ptr node_ptr;
- typedef detail::ebo_functor_holder<F> base_t;
+ typedef typename boost::pointer_to_other
+ <VoidPointer, const void>::type ConstVoidPtr;
- value_to_node_cloner(F f)
- : base_t(f)
+ constptr(const void *ptr)
+ : const_void_ptr_(ptr)
{}
-
- node_ptr operator()(node_ptr p)
- { return ValueTraits::to_node_ptr(*base_t::get()(*ValueTraits::to_value_ptr(p))); }
+
+ const void *get_ptr() const
+ { return detail::get_pointer(const_void_ptr_); }
+
+ ConstVoidPtr const_void_ptr_;
};
-template<class F, class ValueTraits>
-struct value_to_node_disposer
- : private detail::ebo_functor_holder<F>
+template <class VoidPointer, bool store_ptr>
+struct select_constptr
{
- typedef typename ValueTraits::node_ptr node_ptr;
- typedef detail::ebo_functor_holder<F> base_t;
- value_to_node_disposer(F f)
- : base_t(f)
+ typedef typename detail::if_c
+ < store_ptr
+ , constptr<VoidPointer>
+ , dummy_constptr
+ >::type type;
+};
+
+template <class Container>
+struct store_cont_ptr_on_it
+{
+ typedef typename Container::value_traits value_traits;
+ static const bool value =
+ !detail::is_empty_class<value_traits>::value
+ || detail::external_value_traits_is_true<value_traits>::value
+ ;
+};
+
+template<class T, bool Add>
+struct add_const_if_c
+{
+ typedef typename detail::if_c
+ < Add
+ , typename detail::add_const<T>::type
+ , T
+ >::type type;
+};
+
+template<class Container, bool IsConst>
+struct node_to_value
+ : public detail::select_constptr
+ < typename boost::pointer_to_other
+ <typename Container::pointer, void>::type
+ , detail::store_cont_ptr_on_it<Container>::value
+ >::type
+{
+ static const bool store_container_ptr =
+ detail::store_cont_ptr_on_it<Container>::value;
+
+ typedef typename Container::real_value_traits real_value_traits;
+ typedef typename real_value_traits::value_type value_type;
+ typedef typename detail::select_constptr
+ < typename boost::pointer_to_other
+ <typename Container::pointer, void>::type
+ , store_container_ptr >::type Base;
+ typedef typename real_value_traits::node_traits::node node;
+ typedef typename detail::add_const_if_c
+ <value_type, IsConst>::type vtype;
+ typedef typename detail::add_const_if_c
+ <node, IsConst>::type ntype;
+ typedef typename boost::pointer_to_other
+ <typename Container::pointer, ntype>::type npointer;
+
+ node_to_value(const Container *cont)
+ : Base(cont)
{}
- void operator()(node_ptr p)
- { base_t::get()(ValueTraits::to_value_ptr(p)); }
+ typedef vtype & result_type;
+ typedef ntype & first_argument_type;
+
+ const Container *get_container() const
+ {
+ if(store_container_ptr)
+ return static_cast<const Container*>(Base::get_ptr());
+ else
+ return 0;
+ }
+
+ const real_value_traits *get_real_value_traits() const
+ {
+ if(store_container_ptr)
+ return &this->get_container()->get_real_value_traits();
+ else
+ return 0;
+ }
+
+ result_type operator()(first_argument_type arg) const
+ { return *(this->get_real_value_traits()->to_value_ptr(npointer(&arg))); }
};
-template <linking_policy Policy>
-struct dispatcher
+template <link_mode_type LinkMode>
+struct link_dispatch
{};
template<class Container>
-void destructor_impl(Container &cont, dispatcher<safe_link>)
+void destructor_impl(Container &cont, detail::link_dispatch<safe_link>)
{ (void)cont; BOOST_INTRUSIVE_SAFE_HOOK_DESTRUCTOR_ASSERT(!cont.is_linked()); }
template<class Container>
-void destructor_impl(Container &cont, dispatcher<auto_unlink>)
+void destructor_impl(Container &cont, detail::link_dispatch<auto_unlink>)
{ cont.unlink(); }
template<class Container>
-void destructor_impl(Container &, dispatcher<normal_link>)
+void destructor_impl(Container &, detail::link_dispatch<normal_link>)
{}
-template<class Node, class MaybeClass>
-struct node_plus_pred
- : public ebo_functor_holder<MaybeClass>
- , public Node
+template<class T, class NodeTraits, link_mode_type LinkMode, class Tag, int HookType>
+struct base_hook_traits
{
- node_plus_pred()
- {}
+ public:
+ typedef detail::node_holder
+ <typename NodeTraits::node, Tag, LinkMode, HookType> node_holder;
+ typedef NodeTraits node_traits;
+ typedef T value_type;
+ typedef typename node_traits::node_ptr node_ptr;
+ typedef typename node_traits::const_node_ptr const_node_ptr;
+ typedef typename boost::pointer_to_other<node_ptr, T>::type pointer;
+ typedef typename boost::pointer_to_other<node_ptr, const T>::type const_pointer;
+ typedef typename std::iterator_traits<pointer>::reference reference;
+ typedef typename std::iterator_traits<const_pointer>::reference const_reference;
+ static const link_mode_type link_mode = LinkMode;
- node_plus_pred(const Node &x, const MaybeClass &y)
- : Node(x), ebo_functor_holder<MaybeClass>(y) {}
+ static node_ptr to_node_ptr(reference value)
+ { return static_cast<node_holder*>(&value); }
+
+ static const_node_ptr to_node_ptr(const_reference value)
+ { return static_cast<const node_holder*>(&value); }
+
+ static pointer to_value_ptr(node_ptr n)
+ { return static_cast<T*>(static_cast<node_holder*>(&*n)); }
+
+ static const_pointer to_value_ptr(const_node_ptr n)
+ { return static_cast<const T*>(static_cast<const node_holder*>(&*n)); }
+};
+
+template<class T, class Hook, Hook T::* P>
+struct member_hook_traits
+{
+ public:
+ typedef Hook hook_type;
+ typedef typename hook_type::boost_intrusive_tags::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef T value_type;
+ typedef typename node_traits::node_ptr node_ptr;
+ typedef typename node_traits::const_node_ptr const_node_ptr;
+ typedef typename boost::pointer_to_other<node_ptr, T>::type pointer;
+ typedef typename boost::pointer_to_other<node_ptr, const T>::type const_pointer;
+ typedef typename std::iterator_traits<pointer>::reference reference;
+ typedef typename std::iterator_traits<const_pointer>::reference const_reference;
+ static const link_mode_type link_mode = Hook::boost_intrusive_tags::link_mode;
- node_plus_pred(const MaybeClass &y)
- : ebo_functor_holder<MaybeClass>(y) {}
+ static node_ptr to_node_ptr(reference value)
+ {
+ return reinterpret_cast<node*>(&(value.*P));
+ }
- Node &first()
- { return *this; }
- const Node &first() const
- { return *this; }
- MaybeClass &second()
- { return ebo_functor_holder<MaybeClass>::get(); }
- const MaybeClass &second() const
- { return ebo_functor_holder<MaybeClass>::get(); }
+ static const_node_ptr to_node_ptr(const_reference value)
+ {
+ return static_cast<const node*>(&(value.*P));
+ }
- static node_plus_pred *this_from_node(Node *n)
- { return static_cast<node_plus_pred*>(n); }
+ static pointer to_value_ptr(node_ptr n)
+ {
+ return detail::parent_from_member<T, Hook>
+ (static_cast<Hook*>(detail::get_pointer(n)), P);
+ }
- static node_plus_pred *this_from_node(const Node *n)
- { return static_cast<const node_plus_pred*>(n); }
+ static const_pointer to_value_ptr(const_node_ptr n)
+ {
+ return detail::parent_from_member<T, Hook>
+ (static_cast<const Hook*>(detail::get_pointer(n)), P);
+ }
};
-} //namespace detail
+} //namespace detail
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/hashtable.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/hashtable.hpp (original)
+++ branches/bcbboost/boost/intrusive/hashtable.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -22,156 +22,390 @@
#include <boost/intrusive/detail/assert.hpp>
#include <boost/static_assert.hpp>
#include <boost/functional/hash.hpp>
-#ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
-#include <boost/detail/no_exceptions_support.hpp>
-#endif
+#include <boost/intrusive/detail/no_exceptions_support.hpp>
//General intrusive utilities
#include <boost/intrusive/intrusive_fwd.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/detail/hashtable_node.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/detail/transform_iterator.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <boost/intrusive/detail/ebo_functor_holder.hpp>
//Implementation utilities
+#include <boost/intrusive/trivial_value_traits.hpp>
#include <boost/intrusive/unordered_set_hook.hpp>
#include <boost/intrusive/slist.hpp>
namespace boost {
namespace intrusive {
+/// @cond
+
+namespace detail{
+
+template<class Config>
+struct bucket_plus_size
+ : public detail::size_holder
+ < Config::constant_time_size
+ , typename Config::size_type>
+{
+ typedef detail::size_holder
+ < Config::constant_time_size
+ , typename Config::size_type> size_traits;
+ typedef typename Config::bucket_traits bucket_traits;
+
+ bucket_plus_size(const bucket_traits &b_traits)
+ : bucket_traits_(b_traits)
+ {}
+ bucket_traits bucket_traits_;
+};
+
+template<class Config>
+struct bucket_hash_t : public detail::ebo_functor_holder<typename Config::hash>
+{
+ typedef typename Config::hash hasher;
+ typedef detail::size_holder
+ < Config::constant_time_size
+ , typename Config::size_type> size_traits;
+ typedef typename Config::bucket_traits bucket_traits;
+
+ bucket_hash_t(const bucket_traits &b_traits, const hasher & h)
+ : detail::ebo_functor_holder<hasher>(h), bucket_plus_size_(b_traits)
+ {}
+
+ bucket_plus_size<Config> bucket_plus_size_;
+};
+
+template<class Config>
+struct bucket_hash_equal_t : public detail::ebo_functor_holder<typename Config::equal>
+{
+ typedef typename Config::equal equal;
+ typedef typename Config::hash hasher;
+ typedef typename Config::bucket_traits bucket_traits;
+
+ bucket_hash_equal_t(const bucket_traits &b_traits, const hasher & h, const equal &e)
+ : detail::ebo_functor_holder<typename Config::equal>(e), bucket_hash(b_traits, h)
+ {}
+ bucket_hash_t<Config> bucket_hash;
+};
+
+template<class Config>
+struct data_t : public Config::value_traits
+{
+ typedef typename Config::value_traits value_traits;
+ typedef typename Config::equal equal;
+ typedef typename Config::hash hasher;
+ typedef typename Config::bucket_traits bucket_traits;
+
+ data_t( const bucket_traits &b_traits, const hasher & h
+ , const equal &e, const value_traits &val_traits)
+ : Config::value_traits(val_traits), bucket_hash_equal_(b_traits, h, e)
+ {}
+ bucket_hash_equal_t<Config> bucket_hash_equal_;
+};
+
+} //namespace detail {
+
+template <class T>
+struct internal_default_uset_hook
+{
+ template <class U> static detail::one test(...);
+ template <class U> static detail::two test(typename U::default_uset_hook* = 0);
+ static const bool value = sizeof(test<T>(0)) == sizeof(detail::two);
+};
+
+template <class T>
+struct get_default_uset_hook
+{
+ typedef typename T::default_uset_hook type;
+};
+
+template < class ValueTraits
+ , class Hash
+ , class Equal
+ , class SizeType
+ , bool ConstantTimeSize
+ , class BucketTraits
+ , bool Power2Buckets
+ >
+struct usetopt
+{
+ typedef ValueTraits value_traits;
+ typedef Hash hash;
+ typedef Equal equal;
+ typedef SizeType size_type;
+ typedef BucketTraits bucket_traits;
+ static const bool constant_time_size = ConstantTimeSize;
+ static const bool power_2_buckets = Power2Buckets;
+};
+
+struct default_bucket_traits;
+
+template <class T>
+struct uset_defaults
+ : pack_options
+ < none
+ , base_hook
+ < typename detail::eval_if_c
+ < internal_default_uset_hook<T>::value
+ , get_default_uset_hook<T>
+ , detail::identity<none>
+ >::type
+ >
+ , constant_time_size<true>
+ , size_type<std::size_t>
+ , equal<std::equal_to<T> >
+ , hash<boost::hash<T> >
+ , bucket_traits<default_bucket_traits>
+ , power_2_buckets<false>
+ >::type
+{};
+
+template<class NodeTraits>
+struct get_slist_impl
+{
+ typedef trivial_value_traits<NodeTraits, normal_link> trivial_traits;
+
+ //Reducing symbol length
+ struct type : make_slist
+ < typename NodeTraits::node
+ , boost::intrusive::value_traits<trivial_traits>
+ , boost::intrusive::constant_time_size<false>
+ , boost::intrusive::size_type<std::size_t>
+ >::type
+ {};
+};
+
+/// @endcond
+
+template<class ValueTraitsOrHookOption>
+struct unordered_bucket
+{
+ /// @cond
+ typedef typename ValueTraitsOrHookOption::
+ template pack<none>::value_traits supposed_value_traits;
+
+ typedef typename detail::eval_if_c
+ < detail::external_value_traits_is_true
+ <supposed_value_traits>::value
+ , detail::eval_value_traits
+ <supposed_value_traits>
+ , detail::identity
+ <supposed_value_traits>
+ >::type real_value_traits;
+
+ typedef typename detail::get_node_traits
+ <real_value_traits>::type node_traits;
+ typedef typename get_slist_impl
+ <node_traits>::type slist_impl;
+ typedef detail::bucket_impl<slist_impl> implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+template<class ValueTraitsOrHookOption>
+struct unordered_bucket_ptr
+{
+ /// @cond
+ typedef typename ValueTraitsOrHookOption::
+ template pack<none>::value_traits supposed_value_traits;
+ typedef typename detail::eval_if_c
+ < detail::external_value_traits_is_true
+ <supposed_value_traits>::value
+ , detail::eval_value_traits
+ <supposed_value_traits>
+ , detail::identity
+ <supposed_value_traits>
+ >::type real_value_traits;
+ typedef typename detail::get_node_traits
+ <supposed_value_traits>::type::node_ptr node_ptr;
+ typedef typename unordered_bucket
+ <ValueTraitsOrHookOption>::type bucket_type;
+ typedef typename boost::pointer_to_other
+ <node_ptr, bucket_type>::type implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
//! The class template hashtable is an intrusive hash table container, that
//! is used to construct intrusive unordered_set and unordered_multiset containers. The
//! no-throw guarantee holds only, if the Equal object and Hasher don't throw.
-template< class ValueTraits
- , class Hash //= boost::hash<typename ValueTraits::value_type>
- , class Equal //= std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class hashtable
- : private detail::size_holder<ConstantTimeSize, SizeType>
+//!
+//! hashtable is a pseudo-intrusive container: each object to be stored in the
+//! container must contain a proper hook, but the container also needs
+//! additional auxiliary memory to work: hashtable needs a pointer to an array
+//! of type `bucket_type` to be passed in the constructor. This bucket array must
+//! have at least the same lifetime as the container. This makes the use of
+//! hashtable more complicated than purely intrusive containers.
+//! `bucket_type` is default-constructible, copyable and assignable
+//!
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
+//!
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<>, \c size_type<>, \c hash<> and \c equal<> .
+//!
+//! hashtable only provides forward iterators but it provides 4 iterator types:
+//! iterator and const_iterator to navigate through the whole container and
+//! local_iterator and const_local_iterator to navigate through the values
+//! stored in a single bucket. Local iterators are faster and smaller.
+//!
+//! It's not recommended to use non constant-time size hashtables because several
+//! key functions, like "empty()", become non-constant time functions. Non
+//! constant_time size hashtables are mainly provided to support auto-unlink hooks.
+//!
+//! hashtables, does not make automatic rehashings nor
+//! offers functions related to a load factor. Rehashing can be explicitly requested
+//! and the user must provide a new bucket array that will be used from that moment.
+//!
+//! Since no automatic rehashing is done, iterators are never invalidated when
+//! inserting or erasing elements. Iterators are only invalidated when rehashing.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class hashtable_impl
+ : private detail::data_t<Config>
{
+ public:
+ typedef typename Config::value_traits value_traits;
+
/// @cond
- private:
- typedef slist<ValueTraits, false, SizeType> slist_impl;
- typedef hashtable<ValueTraits, Hash, Equal
- ,ConstantTimeSize, SizeType> this_type;
- typedef typename ValueTraits::node_traits node_traits;
- typedef detail::size_holder<ConstantTimeSize, SizeType> size_traits;
- //noncopyable
- hashtable (const hashtable&);
- hashtable operator =(const hashtable&);
+ static const bool external_value_traits =
+ detail::external_value_traits_is_true<value_traits>::value;
+ typedef typename detail::eval_if_c
+ < external_value_traits
+ , detail::eval_value_traits<value_traits>
+ , detail::identity<value_traits>
+ >::type real_value_traits;
+ typedef typename Config::bucket_traits bucket_traits;
+ static const bool external_bucket_traits =
+ detail::external_bucket_traits_is_true<bucket_traits>::value;
+ typedef typename detail::eval_if_c
+ < external_bucket_traits
+ , detail::eval_bucket_traits<bucket_traits>
+ , detail::identity<bucket_traits>
+ >::type real_bucket_traits;
+ typedef typename get_slist_impl
+ <typename real_value_traits::node_traits>::type slist_impl;
/// @endcond
- public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef value_type key_type;
- typedef Hash hasher;
- typedef Equal key_equal;
- typedef detail::bucket_type_impl<slist_impl> bucket_type;
+ typedef typename real_value_traits::pointer pointer;
+ typedef typename real_value_traits::const_pointer const_pointer;
+ typedef typename std::iterator_traits<pointer>::value_type value_type;
+ typedef typename std::iterator_traits<pointer>::reference reference;
+ typedef typename std::iterator_traits<const_pointer>::reference const_reference;
+ typedef typename std::iterator_traits<pointer>::difference_type difference_type;
+ typedef typename Config::size_type size_type;
+ typedef value_type key_type;
+ typedef typename Config::equal key_equal;
+ typedef typename Config::hash hasher;
+ typedef detail::bucket_impl<slist_impl> bucket_type;
+ typedef typename boost::pointer_to_other
+ <pointer, bucket_type>::type bucket_ptr;
+ typedef typename slist_impl::iterator siterator;
+ typedef typename slist_impl::const_iterator const_siterator;
+ typedef detail::hashtable_iterator<hashtable_impl, false> iterator;
+ typedef detail::hashtable_iterator<hashtable_impl, true> const_iterator;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
typedef typename boost::pointer_to_other
- <pointer, bucket_type>::type bucket_ptr;
- typedef typename slist_impl::iterator local_iterator;
- typedef typename slist_impl::const_iterator const_local_iterator;
+ <pointer, node>::type node_ptr;
+ typedef typename boost::pointer_to_other
+ <node_ptr, const node>::type const_node_ptr;
+ typedef typename slist_impl::node_algorithms node_algorithms;
- typedef detail::hashtable_iterator<value_type, slist_impl> iterator;
- typedef detail::hashtable_iterator<value_type, slist_impl> const_iterator;
+ static const bool constant_time_size = Config::constant_time_size;
+ static const bool stateful_value_traits = detail::store_cont_ptr_on_it<hashtable_impl>::value;
/// @cond
private:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <pointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <node_ptr, const node>::type const_node_ptr;
+ typedef detail::size_holder<constant_time_size, size_type> size_traits;
+ typedef detail::data_t<Config> base_type;
+ typedef detail::transform_iterator
+ < typename slist_impl::iterator
+ , detail::node_to_value<hashtable_impl, false> > local_iterator_impl;
+ typedef detail::transform_iterator
+ < typename slist_impl::iterator
+ , detail::node_to_value<hashtable_impl, true> > const_local_iterator_impl;
+
+ //noncopyable
+ hashtable_impl (const hashtable_impl&);
+ hashtable_impl operator =(const hashtable_impl&);
enum { safemode_or_autounlink =
- (int)ValueTraits::linking_policy == (int)auto_unlink ||
- (int)ValueTraits::linking_policy == (int)safe_link };
+ (int)real_value_traits::link_mode == (int)auto_unlink ||
+ (int)real_value_traits::link_mode == (int)safe_link };
//Constant-time size is incompatible with auto-unlink hooks!
- BOOST_STATIC_ASSERT(!(ConstantTimeSize && ((int)ValueTraits::linking_policy == (int)auto_unlink)));
+ BOOST_STATIC_ASSERT(!(constant_time_size && ((int)real_value_traits::link_mode == (int)auto_unlink)));
- typedef detail::bucket_info_impl<slist_impl> bucket_info_t;
- typedef typename boost::pointer_to_other
- <pointer, bucket_info_t>::type bucket_info_ptr;
- typedef typename boost::pointer_to_other
- <pointer, const bucket_info_t>::type const_bucket_info_ptr;
+ static const bool power_2_buckets = Config::power_2_buckets;
- //User scattered boost::compressed pair to get EBO all compilers
-// boost::compressed_pair
-// <boost::compressed_pair<bucket_info_t, Hash>
-// ,Equal> members_;
- struct bucket_hash_t
- : public detail::ebo_functor_holder<Hash>
- {
- bucket_hash_t(const Hash & h)
- : detail::ebo_functor_holder<Hash>(h)
- {}
- bucket_info_t bucket_info;
- };
+ std::size_t from_hash_to_bucket(std::size_t hash_value) const
+ { return from_hash_to_bucket(hash_value, detail::bool_<power_2_buckets>()); }
- struct bucket_hash_equal_t
- : public detail::ebo_functor_holder<Equal>
- {
- bucket_hash_equal_t(const Hash & h, const Equal &e)
- : detail::ebo_functor_holder<Equal>(e), bucket_hash(h)
- {}
- bucket_hash_t bucket_hash;
- } bucket_hash_equal_;
+ std::size_t from_hash_to_bucket(std::size_t hash_value, detail::bool_<false>) const
+ { return hash_value % this->get_real_bucket_traits().bucket_count(); }
+
+ std::size_t from_hash_to_bucket(std::size_t hash_value, detail::bool_<true>) const
+ { return hash_value & (this->get_real_bucket_traits().bucket_count() - 1); }
+
+ const key_equal &priv_equal() const
+ { return static_cast<const key_equal&>(this->bucket_hash_equal_.get()); }
+
+ key_equal &priv_equal()
+ { return static_cast<key_equal&>(this->bucket_hash_equal_.get()); }
- const Equal &priv_equal() const
- { return static_cast<const Equal&>(bucket_hash_equal_.get()); }
+ const real_bucket_traits &get_real_bucket_traits(detail::bool_<false>) const
+ { return this->bucket_hash_equal_.bucket_hash.bucket_plus_size_.bucket_traits_; }
- Equal &priv_equal()
- { return static_cast<Equal&>(bucket_hash_equal_.get()); }
+ const real_bucket_traits &get_real_bucket_traits(detail::bool_<true>) const
+ { return this->bucket_hash_equal_.bucket_hash.bucket_plus_size_.bucket_traits_.get_bucket_traits(*this); }
- const bucket_info_t &priv_bucket_info() const
- { return bucket_hash_equal_.bucket_hash.bucket_info; }
+ real_bucket_traits &get_real_bucket_traits(detail::bool_<false>)
+ { return this->bucket_hash_equal_.bucket_hash.bucket_plus_size_.bucket_traits_; }
- bucket_info_t &priv_bucket_info()
- { return bucket_hash_equal_.bucket_hash.bucket_info; }
+ real_bucket_traits &get_real_bucket_traits(detail::bool_<true>)
+ { return this->bucket_hash_equal_.bucket_hash.bucket_plus_size_.bucket_traits_.get_bucket_traits(*this); }
- const Hash &priv_hasher() const
- { return static_cast<const Hash&>(bucket_hash_equal_.bucket_hash.get()); }
+ const real_bucket_traits &get_real_bucket_traits() const
+ { return this->get_real_bucket_traits(detail::bool_<external_bucket_traits>()); }
- Hash &priv_hasher()
- { return static_cast<Hash&>(bucket_hash_equal_.bucket_hash.get()); }
+ real_bucket_traits &get_real_bucket_traits()
+ { return this->get_real_bucket_traits(detail::bool_<external_bucket_traits>()); }
- const bucket_ptr &priv_buckets() const
- { return priv_bucket_info().buckets_; }
+ const hasher &priv_hasher() const
+ { return static_cast<const hasher&>(this->bucket_hash_equal_.bucket_hash.get()); }
- bucket_ptr &priv_buckets()
- { return priv_bucket_info().buckets_; }
+ hasher &priv_hasher()
+ { return static_cast<hasher&>(this->bucket_hash_equal_.bucket_hash.get()); }
- const size_type &priv_buckets_len() const
- { return priv_bucket_info().buckets_len_; }
+ bucket_ptr priv_buckets() const
+ { return this->get_real_bucket_traits().bucket_begin(); }
- size_type &priv_buckets_len()
- { return priv_bucket_info().buckets_len_; }
+ size_type priv_buckets_len() const
+ { return this->get_real_bucket_traits().bucket_count(); }
static node_ptr uncast(const_node_ptr ptr)
{
return node_ptr(const_cast<node*>(detail::get_pointer(ptr)));
}
-// static bucket_info_ptr uncast(const_bucket_info_ptr ptr)
-// {
-// return bucket_info_ptr(const_cast<bucket_info_t*>(detail::get_pointer(ptr)));
-// }
+ node &from_value_to_node(value_type &v)
+ { return *this->get_real_value_traits().to_node_ptr(v); }
- static slist_impl &bucket_to_slist(bucket_type &b)
- { return static_cast<slist_impl &>(b); }
+ const node &from_value_to_node(const value_type &v) const
+ { return *this->get_real_value_traits().to_node_ptr(v); }
- static const slist_impl &bucket_to_slist(const bucket_type &b)
- { return static_cast<const slist_impl &>(b); }
+ size_traits &priv_size_traits()
+ { return this->bucket_hash_equal_.bucket_hash.bucket_plus_size_; }
+
+ const size_traits &priv_size_traits() const
+ { return this->bucket_hash_equal_.bucket_hash.bucket_plus_size_; }
struct insert_commit_data_impl
{
@@ -180,33 +414,82 @@
/// @endcond
public:
+
+ class local_iterator
+ : public local_iterator_impl
+ {
+ public:
+ local_iterator()
+ {}
+
+ local_iterator(siterator sit, const hashtable_impl *cont)
+ : local_iterator_impl(sit, cont)
+ {}
+ };
+
+ class const_local_iterator
+ : public const_local_iterator_impl
+ {
+ public:
+ const_local_iterator()
+ {}
+
+ const_local_iterator(siterator sit, const hashtable_impl *cont)
+ : const_local_iterator_impl(sit, cont)
+ {}
+ };
+
typedef insert_commit_data_impl insert_commit_data;
+ /// @cond
+
+ const real_value_traits &get_real_value_traits(detail::bool_<false>) const
+ { return *this; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<true>) const
+ { return base_type::get_value_traits(*this); }
+
+ real_value_traits &get_real_value_traits(detail::bool_<false>)
+ { return *this; }
+
+ real_value_traits &get_real_value_traits(detail::bool_<true>)
+ { return base_type::get_value_traits(*this); }
+
+ /// @endcond
+
+ public:
+
+ const real_value_traits &get_real_value_traits() const
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
+ real_value_traits &get_real_value_traits()
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
//! <b>Requires</b>: buckets must not be being used by any other resource.
//!
//! <b>Effects</b>: Constructs an empty unordered_set, storing a reference
- //! to the bucket array and copies of the hasher and equal functors.
+ //! to the bucket array and copies of the key_hasher and equal_func functors.
//!
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor or invocation of Hash or Equal throws.
+ //! or the copy constructor or invocation of hash_func or equal_func throws.
//!
//! <b>Notes</b>: buckets array must be disposed only after
- //! *this is disposed.
- hashtable( bucket_ptr buckets
- , size_type buckets_len
- , const Hash & hasher = Hash()
- , const Equal &equal = Equal())
- : bucket_hash_equal_(hasher, equal)
+ //! *this is disposed.
+ hashtable_impl ( const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : base_type(b_traits, hash_func, equal_func, v_traits)
{
-
- BOOST_INTRUSIVE_INVARIANT_ASSERT(buckets_len != 0);
- priv_buckets() = buckets;
- priv_buckets_len() = buckets_len;
priv_clear_buckets();
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(this->priv_buckets_len() != 0);
+ //Check power of two bucket array if the option is activated
+ BOOST_INTRUSIVE_INVARIANT_ASSERT
+ (!power_2_buckets || (0 == (this->priv_buckets_len() & (this->priv_buckets_len()-1))));
}
//! <b>Effects</b>: Detaches all elements from this. The objects in the unordered_set
@@ -216,7 +499,7 @@
//! it's a safe-mode or auto-unlink value. Otherwise constant.
//!
//! <b>Throws</b>: Nothing.
- ~hashtable()
+ ~hashtable_impl()
{ this->clear(); }
//! <b>Effects</b>: Returns an iterator pointing to the beginning of the unordered_set.
@@ -228,8 +511,7 @@
iterator begin()
{
size_type bucket_num;
- local_iterator local_it = priv_begin(bucket_num);
- return iterator(local_it, const_bucket_info_ptr(&this->priv_bucket_info()));
+ return iterator(this->priv_begin(bucket_num), this);
}
//! <b>Effects</b>: Returns a const_iterator pointing to the beginning
@@ -240,7 +522,7 @@
//!
//! <b>Throws</b>: Nothing.
const_iterator begin() const
- { return cbegin(); }
+ { return this->cbegin(); }
//! <b>Effects</b>: Returns a const_iterator pointing to the beginning
//! of the unordered_set.
@@ -252,8 +534,7 @@
const_iterator cbegin() const
{
size_type bucket_num;
- local_iterator local_it = priv_begin(bucket_num);
- return const_iterator( local_it, const_bucket_info_ptr(&this->priv_bucket_info()));
+ return const_iterator(this->priv_begin(bucket_num), this);
}
//! <b>Effects</b>: Returns an iterator pointing to the end of the unordered_set.
@@ -262,7 +543,7 @@
//!
//! <b>Throws</b>: Nothing.
iterator end()
- { return iterator(invalid_local_it(this->priv_bucket_info()), 0); }
+ { return iterator(invalid_local_it(this->get_real_bucket_traits()), 0); }
//! <b>Effects</b>: Returns a const_iterator pointing to the end of the unordered_set.
//!
@@ -270,7 +551,7 @@
//!
//! <b>Throws</b>: Nothing.
const_iterator end() const
- { return cend(); }
+ { return this->cend(); }
//! <b>Effects</b>: Returns a const_iterator pointing to the end of the unordered_set.
//!
@@ -278,7 +559,7 @@
//!
//! <b>Throws</b>: Nothing.
const_iterator cend() const
- { return const_iterator(invalid_local_it(this->priv_bucket_info()), 0); }
+ { return const_iterator(invalid_local_it(this->get_real_bucket_traits()), 0); }
//! <b>Effects</b>: Returns the hasher object used by the unordered_set.
//!
@@ -298,15 +579,15 @@
//! <b>Effects</b>: Returns true is the container is empty.
//!
- //! <b>Complexity</b>: if ConstantTimeSize is false, average constant time
+ //! <b>Complexity</b>: if constant_time_size is false, average constant time
//! (worst case, with empty() == true): O(this->bucket_count()).
//! Otherwise constant.
//!
//! <b>Throws</b>: Nothing.
bool empty() const
{
- if(ConstantTimeSize){
- return !size();
+ if(constant_time_size){
+ return !this->size();
}
else{
size_type buckets_len = this->priv_buckets_len();
@@ -323,13 +604,13 @@
//! <b>Effects</b>: Returns the number of elements stored in the unordered_set.
//!
//! <b>Complexity</b>: Linear to elements contained in *this if
- //! ConstantTimeSize is false. Constant-time otherwise.
+ //! constant_time_size is false. Constant-time otherwise.
//!
//! <b>Throws</b>: Nothing.
size_type size() const
{
- if(ConstantTimeSize)
- return size_traits::get_size();
+ if(constant_time_size)
+ return this->priv_size_traits().get_size();
else{
size_type len = 0;
size_type buckets_len = this->priv_buckets_len();
@@ -351,19 +632,18 @@
//!
//! <b>Throws</b>: If the swap() call for the comparison or hash functors
//! found using ADL throw. Basic guarantee.
- void swap(hashtable& other)
+ void swap(hashtable_impl& other)
{
using std::swap;
//These can throw
swap(this->priv_equal(), other.priv_equal());
swap(this->priv_hasher(), other.priv_hasher());
//These can't throw
- swap(this->priv_buckets(), other.priv_buckets());
- swap(this->priv_buckets_len(), other.priv_buckets_len());
- if(ConstantTimeSize){
- size_type backup = size_traits::get_size();
- size_traits::set_size(other.get_size());
- other.set_size(backup);
+ swap(this->get_real_bucket_traits(), other.get_real_bucket_traits());
+ if(constant_time_size){
+ size_type backup = this->priv_size_traits().get_size();
+ this->priv_size_traits().set_size(other.priv_size_traits().get_size());
+ other.priv_size_traits().set_size(backup);
}
}
@@ -381,12 +661,17 @@
//!
//! <b>Throws</b>: If cloner throws. Basic guarantee.
template <class Cloner, class Disposer>
- void clone_from(const hashtable &src, Cloner cloner, Disposer disposer)
+ void clone_from(const hashtable_impl &src, Cloner cloner, Disposer disposer)
{
this->clear_and_dispose(disposer);
- if(!ConstantTimeSize || !src.empty()){
+ if(!constant_time_size || !src.empty()){
const size_type src_bucket_count = src.bucket_count();
const size_type dst_bucket_count = this->bucket_count();
+ //Check power of two bucket array if the option is activated
+ BOOST_INTRUSIVE_INVARIANT_ASSERT
+ (!power_2_buckets || (0 == (src_bucket_count & (src_bucket_count-1))));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT
+ (!power_2_buckets || (0 == (dst_bucket_count & (dst_bucket_count-1))));
//If src bucket count is bigger or equal, structural copy is possible
if(src_bucket_count >= dst_bucket_count){
@@ -394,72 +679,76 @@
const bucket_ptr src_buckets = src.priv_buckets();
const bucket_ptr dst_buckets = this->priv_buckets();
size_type constructed;
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- BOOST_TRY{
- #endif
+ BOOST_INTRUSIVE_TRY{
for( constructed = 0
; constructed < dst_bucket_count
; ++constructed){
- dst_buckets[constructed].clone_from(src_buckets[constructed], cloner, disposer);
+ dst_buckets[constructed].clone_from
+ ( src_buckets[constructed]
+ , detail::node_cloner<Cloner, hashtable_impl>(cloner, this)
+ , detail::node_disposer<Disposer, hashtable_impl>(disposer, this)
+ );
}
if(src_bucket_count != dst_bucket_count){
//Now insert the remaining ones using the modulo trick
for(//"constructed" comes from the previous loop
; constructed < src_bucket_count
; ++constructed){
- bucket_type &dst_b = dst_buckets[constructed % dst_bucket_count];
+ bucket_type &dst_b = (power_2_buckets)
+ ? dst_buckets[constructed & (dst_bucket_count-1)]
+ : dst_buckets[constructed % dst_bucket_count];
bucket_type &src_b = src_buckets[constructed];
- for( local_iterator b(src_b.begin()), e(src_b.end())
+ for( siterator b(src_b.begin()), e(src_b.end())
; b != e
; ++b){
- dst_b.push_front(*cloner(*b));
+ dst_b.push_front(*detail::node_cloner<Cloner, hashtable_impl>
+ (cloner, this)(b.pointed_node()));
}
}
}
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
}
- BOOST_CATCH(...){
+ BOOST_INTRUSIVE_CATCH(...){
while(constructed--){
- dst_buckets[constructed].clear_and_dispose(disposer);
+ dst_buckets[constructed].clear_and_dispose
+ (detail::node_disposer<Disposer, hashtable_impl>(disposer, this));
}
- BOOST_RETHROW;
+ BOOST_INTRUSIVE_RETHROW;
}
- BOOST_CATCH_END
- #endif
- size_traits::set_size(src.get_size());
+ BOOST_INTRUSIVE_CATCH_END
+ this->priv_size_traits().set_size(src.priv_size_traits().get_size());
}
else{
//Unlike previous cloning algorithm, this can throw
//if cloner, the hasher or comparison functor throw
const_iterator b(src.begin()), e(src.end());
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- BOOST_TRY{
- #endif
+ BOOST_INTRUSIVE_TRY{
for(; b != e; ++b){
this->insert_equal(*cloner(*b));
}
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
}
- BOOST_CATCH(...){
+ BOOST_INTRUSIVE_CATCH(...){
this->clear_and_dispose(disposer);
BOOST_RETHROW;
}
- BOOST_CATCH_END
- #endif
+ BOOST_INTRUSIVE_CATCH_END
}
}
}
iterator insert_equal(reference value)
{
- size_type bucket_num, hash;
- local_iterator it = priv_find(value, this->priv_hasher(), this->priv_equal(), bucket_num, hash);
+ size_type bucket_num, hash_func;
+ siterator it = this->priv_find
+ (value, this->priv_hasher(), this->priv_equal(), bucket_num, hash_func);
bucket_type &b = this->priv_buckets()[bucket_num];
- if(it == invalid_local_it(this->priv_bucket_info())){
+ if(it == invalid_local_it(this->get_real_bucket_traits())){
it = b.before_begin();
}
- size_traits::increment();
- return iterator(b.insert_after(it, value), const_bucket_info_ptr(&this->priv_bucket_info()));
+ node_ptr n = node_ptr(&from_value_to_node(value));
+ if(safemode_or_autounlink)
+ BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(n));
+ this->priv_size_traits().increment();
+ return iterator(b.insert_after(it, *n), this);
}
template<class Iterator>
@@ -488,10 +777,12 @@
std::pair<iterator, bool> insert_unique(reference value)
{
insert_commit_data commit_data;
- std::pair<iterator, bool> ret = insert_unique_check(value, this->priv_hasher(), this->priv_equal(), commit_data);
+ std::pair<iterator, bool> ret = this->insert_unique_check
+ (value, this->priv_hasher(), this->priv_equal(), commit_data);
if(!ret.second)
return ret;
- return std::pair<iterator, bool> (insert_unique_commit(value, commit_data), true);
+ return std::pair<iterator, bool>
+ (this->insert_unique_commit(value, commit_data), true);
}
//! <b>Requires</b>: Dereferencing iterator must yield an lvalue
@@ -513,13 +804,13 @@
this->insert_unique(*b);
}
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Checks if a value can be inserted in the unordered_set, using
//! a user provided key instead of the value itself.
@@ -532,7 +823,7 @@
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or key_value_equal throw. Strong guarantee.
+ //! <b>Throws</b>: If hash_func or equal_func throw. Strong guarantee.
//!
//! <b>Notes</b>: This function is used to improve performance when constructing
//! a value_type is expensive: if there is an equivalent value
@@ -551,20 +842,18 @@
template<class KeyType, class KeyHasher, class KeyValueEqual>
std::pair<iterator, bool> insert_unique_check
( const KeyType &key
- , KeyHasher hasher
- , KeyValueEqual key_value_eq
+ , KeyHasher hash_func
+ , KeyValueEqual equal_func
, insert_commit_data &commit_data)
{
size_type bucket_num;
- local_iterator prev_pos =
- priv_find(key, hasher, key_value_eq, bucket_num, commit_data.hash);
- bool success = prev_pos == invalid_local_it(this->priv_bucket_info());
+ siterator prev_pos =
+ this->priv_find(key, hash_func, equal_func, bucket_num, commit_data.hash);
+ bool success = prev_pos == invalid_local_it(this->get_real_bucket_traits());
if(success){
prev_pos = this->priv_buckets()[bucket_num].before_begin();
}
- return std::pair<iterator, bool>
- (iterator(prev_pos, const_bucket_info_ptr(&this->priv_bucket_info()))
- ,success);
+ return std::pair<iterator, bool>(iterator(prev_pos, this),success);
}
//! <b>Requires</b>: value must be an lvalue of type value_type. commit_data
@@ -588,11 +877,13 @@
//! After a successful rehashing insert_commit_data remains valid.
iterator insert_unique_commit(reference value, const insert_commit_data &commit_data)
{
- size_type bucket_num = commit_data.hash % this->priv_buckets_len();
+ size_type bucket_num = from_hash_to_bucket(commit_data.hash);
bucket_type &b = this->priv_buckets()[bucket_num];
- size_traits::increment();
- return iterator( b.insert_after(b.before_begin(), value)
- , const_bucket_info_ptr(&this->priv_bucket_info()));
+ this->priv_size_traits().increment();
+ node_ptr n = node_ptr(&from_value_to_node(value));
+ if(safemode_or_autounlink)
+ BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(n));
+ return iterator( b.insert_after(b.before_begin(), *n), this);
}
//! <b>Effects</b>: Erases the element pointed to by i.
@@ -604,7 +895,7 @@
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased element. No destructors are called.
void erase(const_iterator i)
- { erase_and_dispose(i, detail::null_disposer()); }
+ { this->erase_and_dispose(i, detail::null_disposer()); }
//! <b>Effects</b>: Erases the range pointed to by b end e.
//!
@@ -616,7 +907,7 @@
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
void erase(const_iterator b, const_iterator e)
- { erase_and_dispose(b, e, detail::null_disposer()); }
+ { this->erase_and_dispose(b, e, detail::null_disposer()); }
//! <b>Effects</b>: Erases all the elements with the given value.
//!
@@ -625,20 +916,21 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If the internal hasher or the equality functor throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal hasher or the equality functor throws.
+ //! Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
size_type erase(const_reference value)
{ return this->erase(value, this->priv_hasher(), this->priv_equal()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Erases all the elements that have the same hash and
//! compare equal with the given key.
@@ -648,13 +940,13 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw. Basic guarantee.
+ //! <b>Throws</b>: If hash_func or equal_func throw. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- size_type erase(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return erase_and_dispose(key, hasher, equal, detail::null_disposer()); }
+ size_type erase(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return this->erase_and_dispose(key, hash_func, equal_func, detail::null_disposer()); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
//!
@@ -670,11 +962,12 @@
template<class Disposer>
void erase_and_dispose(const_iterator i, Disposer disposer)
{
- local_iterator to_erase(i.local());
+ siterator to_erase(i.slist_it());
bucket_ptr f(priv_buckets()), l(f + priv_buckets_len());
bucket_type &b = this->priv_buckets()[bucket_type::get_bucket_num(to_erase, *f, *l)];
- b.erase_after_and_dispose(b.previous(to_erase), disposer);
- size_traits::decrement();
+ b.erase_after_and_dispose
+ (b.previous(to_erase), detail::node_disposer<Disposer, hashtable_impl>(disposer, this));
+ this->priv_size_traits().decrement();
}
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
@@ -696,12 +989,12 @@
//Get the bucket number and local iterator for both iterators
bucket_ptr f(priv_buckets()), l(f + priv_buckets_len());
- size_type first_bucket_num = bucket_type::get_bucket_num(b.local(), *f, *l);
+ size_type first_bucket_num = bucket_type::get_bucket_num(b.slist_it(), *f, *l);
- local_iterator before_first_local_it
- = priv_buckets()[first_bucket_num].previous(b.local());
+ siterator before_first_local_it
+ = priv_buckets()[first_bucket_num].previous(b.slist_it());
size_type last_bucket_num;
- local_iterator last_local_it;
+ siterator last_local_it;
//For the end iterator, we will assign the end iterator
//of the last bucket
@@ -710,7 +1003,7 @@
last_local_it = priv_buckets()[last_bucket_num].end();
}
else{
- last_local_it = e.local();
+ last_local_it = e.slist_it();
last_bucket_num = bucket_type::get_bucket_num(last_local_it, *f, *l);
}
@@ -718,11 +1011,13 @@
//First erase the nodes of the first bucket
{
bucket_type &first_b = buckets[first_bucket_num];
- local_iterator nxt(before_first_local_it); ++nxt;
- local_iterator end = first_b.end();
+ siterator nxt(before_first_local_it); ++nxt;
+ siterator end = first_b.end();
while(nxt != end){
- nxt = first_b.erase_after_and_dispose(before_first_local_it, disposer);
- size_traits::decrement();
+ nxt = first_b.erase_after_and_dispose
+ ( before_first_local_it
+ , detail::node_disposer<Disposer, hashtable_impl>(disposer, this));
+ this->priv_size_traits().decrement();
}
}
@@ -731,23 +1026,26 @@
bucket_type &b = buckets[i];
if(b.empty())
continue;
- local_iterator b_begin(b.before_begin());
- local_iterator nxt(b_begin); ++nxt;
- local_iterator end = b.end();
+ siterator b_begin(b.before_begin());
+ siterator nxt(b_begin); ++nxt;
+ siterator end = b.end();
while(nxt != end){
- nxt = b.erase_after_and_dispose(b_begin, disposer);
- size_traits::decrement();
+ nxt = b.erase_after_and_dispose
+ (b_begin, detail::node_disposer<Disposer, hashtable_impl>(disposer, this));
+ this->priv_size_traits().decrement();
}
}
//Now erase nodes from the last bucket
{
bucket_type &last_b = buckets[last_bucket_num];
- local_iterator b_begin(last_b.before_begin());
- local_iterator nxt(b_begin); ++nxt;
+ siterator b_begin(last_b.before_begin());
+ siterator nxt(b_begin); ++nxt;
while(nxt != last_local_it){
- nxt = last_b.erase_after_and_dispose(b_begin, disposer);
- size_traits::decrement();
+ nxt = last_b.erase_after_and_dispose
+ (b_begin, detail::node_disposer<Disposer, hashtable_impl>
+ (disposer, this));
+ this->priv_size_traits().decrement();
}
}
}
@@ -762,18 +1060,19 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If the internal hasher or the equality functor throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal hasher or the equality functor throws.
+ //! Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
template<class Disposer>
size_type erase_and_dispose(const_reference value, Disposer disposer)
- { return erase_and_dispose(value, priv_hasher(), priv_equal(), disposer); }
+ { return this->erase_and_dispose(value, priv_hasher(), priv_equal(), disposer); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
//!
//! <b>Effects</b>: Erases all the elements with the given key.
- //! according to the comparison functor "equal".
+ //! according to the comparison functor "equal_func".
//! Disposer::operator()(pointer) is called for the removed elements.
//!
//! <b>Returns</b>: The number of erased elements.
@@ -781,28 +1080,30 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or key_value_equal throw. Basic guarantee.
+ //! <b>Throws</b>: If hash_func or equal_func throw. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators
//! to the erased elements.
template<class KeyType, class KeyHasher, class KeyValueEqual, class Disposer>
- size_type erase_and_dispose(const KeyType& key, KeyHasher hasher
- ,KeyValueEqual equal, Disposer disposer)
+ size_type erase_and_dispose(const KeyType& key, KeyHasher hash_func
+ ,KeyValueEqual equal_func, Disposer disposer)
{
size_type count(0);
- if(ConstantTimeSize && this->empty()){
+ if(constant_time_size && this->empty()){
return 0;
}
- bucket_type &b = this->priv_buckets()[hasher(key) % this->priv_buckets_len()];
- local_iterator it = b.begin();
- local_iterator prev = b.before_begin();
+ bucket_type &b = this->priv_buckets()[from_hash_to_bucket(hash_func(key))];
+ siterator it = b.begin();
+ siterator prev = b.before_begin();
bool found = false;
//Find equal value
while(it != b.end()){
- if(equal(key, *it)){
+ const value_type &v =
+ *this->get_real_value_traits().to_value_ptr(it.pointed_node());
+ if(equal_func(key, v)){
found = true;
break;
}
@@ -814,9 +1115,12 @@
return 0;
//If found erase all equal values
- for(local_iterator end = b.end(); it != end && equal(key, *it); ++count){
- it = b.erase_after_and_dispose(prev, disposer);
- size_traits::decrement();
+ for(siterator end = b.end(); it != end &&
+ equal_func(key, *this->get_real_value_traits().to_value_ptr(it.pointed_node()))
+ ; ++count){
+ it = b.erase_after_and_dispose
+ (prev, detail::node_disposer<Disposer, hashtable_impl>(disposer, this));
+ this->priv_size_traits().decrement();
}
return count;
}
@@ -832,10 +1136,8 @@
//! to the erased elements. No destructors are called.
void clear()
{
- if(safemode_or_autounlink){
- priv_clear_buckets();
- }
- size_traits::set_size(size_type(0));
+ priv_clear_buckets();
+ this->priv_size_traits().set_size(size_type(0));
}
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
@@ -852,13 +1154,14 @@
template<class Disposer>
void clear_and_dispose(Disposer disposer)
{
- if(!ConstantTimeSize || !this->empty()){
+ if(!constant_time_size || !this->empty()){
size_type num_buckets = this->bucket_count();
bucket_ptr b = this->priv_buckets();
for(; num_buckets--; ++b){
- b->clear_and_dispose(disposer);
+ b->clear_and_dispose
+ (detail::node_disposer<Disposer, hashtable_impl>(disposer, this));
}
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
}
}
@@ -870,24 +1173,24 @@
size_type count(const_reference value) const
{ return this->count(value, this->priv_hasher(), this->priv_equal()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Returns the number of contained elements with the given key
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw.
+ //! <b>Throws</b>: If hash_func or equal throw.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- size_type count(const KeyType &key, const KeyHasher &hasher, const KeyValueEqual &equal) const
+ size_type count(const KeyType &key, const KeyHasher &hash_func, const KeyValueEqual &equal_func) const
{
size_type bucket_n1, bucket_n2, count;
- priv_equal_range(key, hasher, equal, bucket_n1, bucket_n2, count);
+ this->priv_equal_range(key, hash_func, equal_func, bucket_n1, bucket_n2, count);
return count;
}
@@ -898,34 +1201,33 @@
//!
//! <b>Throws</b>: If the internal hasher or the equality functor throws.
iterator find(const_reference value)
- { return find(value, this->priv_hasher(), this->priv_equal()); }
+ { return this->find(value, this->priv_hasher(), this->priv_equal()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Finds an iterator to the first element whose key is
- //! "key" according to the given hasher and equality functor or end() if
+ //! "key" according to the given hash and equality functor or end() if
//! that element does not exist.
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw.
+ //! <b>Throws</b>: If hash_func or equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- iterator find(const KeyType &key, KeyHasher hasher, KeyValueEqual equal)
+ iterator find(const KeyType &key, KeyHasher hash_func, KeyValueEqual equal_func)
{
size_type bucket_n, hash;
- local_iterator local_it = priv_find(key, hasher, equal, bucket_n, hash);
- return iterator( local_it
- , const_bucket_info_ptr(&this->priv_bucket_info()));
+ siterator local_it = this->priv_find(key, hash_func, equal_func, bucket_n, hash);
+ return iterator(local_it, this);
}
//! <b>Effects</b>: Finds a const_iterator to the first element whose key is
@@ -935,15 +1237,15 @@
//!
//! <b>Throws</b>: If the internal hasher or the equality functor throws.
const_iterator find(const_reference value) const
- { return find(value, this->priv_hasher(), this->priv_equal()); }
+ { return this->find(value, this->priv_hasher(), this->priv_equal()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Finds an iterator to the first element whose key is
//! "key" according to the given hasher and equality functor or end() if
@@ -951,19 +1253,18 @@
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw.
+ //! <b>Throws</b>: If hash_func or equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
const_iterator find
- (const KeyType &key, KeyHasher hasher, KeyValueEqual equal) const
+ (const KeyType &key, KeyHasher hash_func, KeyValueEqual equal_func) const
{
size_type bucket_n, hash;
- local_iterator local_it = priv_find(key, hasher, equal, bucket_n, hash);
- return const_iterator( local_it
- , const_bucket_info_ptr(&this->priv_bucket_info()));
+ siterator sit = this->priv_find(key, hash_func, equal_func, bucket_n, hash);
+ return const_iterator(sit, this);
}
//! <b>Effects</b>: Returns a range containing all elements with values equivalent
@@ -976,36 +1277,35 @@
std::pair<iterator,iterator> equal_range(const_reference value)
{ return this->equal_range(value, this->priv_hasher(), this->priv_equal()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Returns a range containing all elements with equivalent
//! keys. Returns std::make_pair(this->end(), this->end()) if no such
//! elements exist.
//!
- //! <b>Complexity</b>: Average case O(this->count(key, hasher, equal)). Worst case O(this->size()).
+ //! <b>Complexity</b>: Average case O(this->count(key, hash_func, equal_func)).
+ //! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or the equal throw.
+ //! <b>Throws</b>: If hash_func or the equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
std::pair<iterator,iterator> equal_range
- (const KeyType &key, KeyHasher hasher, KeyValueEqual equal)
+ (const KeyType &key, KeyHasher hash_func, KeyValueEqual equal_func)
{
size_type bucket_n1, bucket_n2, count;
- std::pair<local_iterator, local_iterator> ret
- = priv_equal_range(key, hasher, equal, bucket_n1, bucket_n2, count);
- const_bucket_info_ptr info_ptr (&this->priv_bucket_info());
+ std::pair<siterator, siterator> ret = this->priv_equal_range
+ (key, hash_func, equal_func, bucket_n1, bucket_n2, count);
return std::pair<iterator, iterator>
- ( iterator( ret.first, info_ptr)
- , iterator( ret.second, info_ptr) );
+ (iterator(ret.first, this), iterator(ret.second, this));
}
//! <b>Effects</b>: Returns a range containing all elements with values equivalent
@@ -1019,36 +1319,35 @@
equal_range(const_reference value) const
{ return this->equal_range(value, this->priv_hasher(), this->priv_equal()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Returns a range containing all elements with equivalent
//! keys. Returns std::make_pair(this->end(), this->end()) if no such
//! elements exist.
//!
- //! <b>Complexity</b>: Average case O(this->count(key, hasher, equal)). Worst case O(this->size()).
+ //! <b>Complexity</b>: Average case O(this->count(key, hash_func, equal_func)).
+ //! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If the hasher or equal throw.
+ //! <b>Throws</b>: If the hasher or equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
std::pair<const_iterator,const_iterator> equal_range
- (const KeyType &key, KeyHasher hasher, KeyValueEqual equal) const
+ (const KeyType &key, KeyHasher hash_func, KeyValueEqual equal_func) const
{
size_type bucket_n1, bucket_n2, count;
- std::pair<local_iterator, local_iterator> ret
- = priv_equal_range(key, hasher, equal, bucket_n1, bucket_n2, count);
- const_bucket_info_ptr info_ptr (&this->priv_bucket_info());
+ std::pair<siterator, siterator> ret =
+ this->priv_equal_range(key, hash_func, equal_func, bucket_n1, bucket_n2, count);
return std::pair<const_iterator, const_iterator>
- ( const_iterator( ret.first, info_ptr)
- , const_iterator( ret.second, info_ptr) );
+ (const_iterator(ret.first, this), const_iterator(ret.second, this));
}
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
@@ -1062,8 +1361,7 @@
//! <b>Throws</b>: If the internal hash function throws.
iterator iterator_to(reference value)
{
- return iterator( bucket_type::iterator_to(value)
- , const_bucket_info_ptr(&this->priv_bucket_info()));
+ return iterator(bucket_type::s_iterator_to(from_value_to_node(value)), this);
}
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
@@ -1077,10 +1375,12 @@
//! <b>Throws</b>: If the internal hash function throws.
const_iterator iterator_to(const_reference value) const
{
- return const_iterator( bucket_type::iterator_to(const_cast<reference>(value))
- , const_bucket_info_ptr(&this->priv_bucket_info()));
+ return const_iterator(bucket_type::s_iterator_to(from_value_to_node(const_cast<reference>(value))), this);
}
+
+
+
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
//! appropriate type. Otherwise the behavior is undefined.
//!
@@ -1090,8 +1390,15 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static local_iterator local_iterator_to(reference value)
- { return bucket_type::iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static local_iterator s_local_iterator_to(reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ siterator sit = bucket_type::s_iterator_to(((hashtable_impl*)0)->from_value_to_node(value));
+ return local_iterator(sit, (hashtable_impl*)0);
+ }
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
//! appropriate type. Otherwise the behavior is undefined.
@@ -1102,8 +1409,46 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static const_local_iterator local_iterator_to(const_reference value)
- { return bucket_type::iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_local_iterator s_local_iterator_to(const_reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ siterator sit = bucket_type::s_iterator_to(((hashtable_impl*)0)->from_value_to_node(const_cast<value_type&>(value)));
+ return const_local_iterator(sit, (hashtable_impl*)0);
+ }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid local_iterator belonging to the unordered_set
+ //! that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ local_iterator local_iterator_to(reference value)
+ {
+ siterator sit = bucket_type::s_iterator_to(this->from_value_to_node(value));
+ return local_iterator(sit, this);
+ }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid const_local_iterator belonging to
+ //! the unordered_set that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ const_local_iterator local_iterator_to(const_reference value) const
+ {
+ siterator sit = bucket_type::s_iterator_to
+ (const_cast<node &>(this->from_value_to_node(value)));
+ return const_local_iterator(sit, this);
+ }
//! <b>Effects</b>: Returns the number of buckets passed in the constructor
//! or the last rehash function.
@@ -1135,21 +1480,21 @@
size_type bucket(const key_type& k) const
{ return this->bucket(k, this->priv_hasher()); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! <b>Effects</b>: Returns the index of the bucket in which elements
//! with keys equivalent to k would be found, if any such element existed.
//!
//! <b>Complexity</b>: Constant.
//!
- //! <b>Throws</b>: If hasher throws.
+ //! <b>Throws</b>: If hash_func throws.
//!
//! <b>Note</b>: the return value is in the range [0, this->bucket_count()).
template<class KeyType, class KeyHasher>
- size_type bucket(const KeyType& k, const KeyHasher &hasher) const
- { return hasher(k) % this->priv_buckets_len(); }
+ size_type bucket(const KeyType& k, const KeyHasher &hash_func) const
+ { return from_hash_to_bucket(hash_func(k)); }
//! <b>Effects</b>: Returns the bucket array pointer passed in the constructor
//! or the last rehash function.
@@ -1172,7 +1517,7 @@
//! <b>Note</b>: [this->begin(n), this->end(n)) is a valid range
//! containing all of the elements in the nth bucket.
local_iterator begin(size_type n)
- { return this->priv_buckets()[n].begin(); }
+ { return local_iterator(this->priv_buckets()[n].begin(), this); }
//! <b>Requires</b>: n is in the range [0, this->bucket_count()).
//!
@@ -1200,7 +1545,10 @@
//! <b>Note</b>: [this->begin(n), this->end(n)) is a valid range
//! containing all of the elements in the nth bucket.
const_local_iterator cbegin(size_type n) const
- { return const_cast<const bucket_type&>(this->priv_buckets()[n]).begin(); }
+ {
+ siterator sit = const_cast<bucket_type&>(this->priv_buckets()[n]).begin();
+ return const_local_iterator(sit, this);
+ }
//! <b>Requires</b>: n is in the range [0, this->bucket_count()).
//!
@@ -1214,7 +1562,7 @@
//! <b>Note</b>: [this->begin(n), this->end(n)) is a valid range
//! containing all of the elements in the nth bucket.
local_iterator end(size_type n)
- { return this->priv_buckets()[n].end(); }
+ { return local_iterator(this->priv_buckets()[n].end(), this); }
//! <b>Requires</b>: n is in the range [0, this->bucket_count()).
//!
@@ -1242,7 +1590,7 @@
//! <b>Note</b>: [this->begin(n), this->end(n)) is a valid range
//! containing all of the elements in the nth bucket.
const_local_iterator cend(size_type n) const
- { return const_cast<const bucket_type&>(this->priv_buckets()[n]).end(); }
+ { return const_local_iterator(const_cast<bucket_type&>(this->priv_buckets()[n]).end(), this); }
//! <b>Requires</b>: new_buckets must be a pointer to a new bucket array
//! or the same as the old bucket array. new_size is the length of the
@@ -1255,19 +1603,23 @@
//! <b>Complexity</b>: Average case linear in this->size(), worst case quadratic.
//!
//! <b>Throws</b>: If the hasher functor throws. Basic guarantee.
- void rehash(bucket_ptr new_buckets, size_type new_buckets_len)
+ void rehash(const bucket_traits &new_bucket_traits)
{
+ bucket_ptr new_buckets = new_bucket_traits.bucket_begin();
+ size_type new_buckets_len = new_bucket_traits.bucket_count();
bucket_ptr old_buckets = this->priv_buckets();
size_type old_buckets_len = this->priv_buckets_len();
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- BOOST_TRY{
- #endif
+ //Check power of two bucket array if the option is activated
+ BOOST_INTRUSIVE_INVARIANT_ASSERT
+ (!power_2_buckets || (0 == (new_buckets_len & (new_buckets_len-1u))));
+
+ BOOST_INTRUSIVE_TRY{
size_type n = 0;
const bool same_buffer = old_buckets == new_buckets;
//If the new bucket length is a common factor
//of the old one we can avoid hash calculations.
const bool fast_shrink = (old_buckets_len > new_buckets_len) &&
- (old_buckets_len % new_buckets_len) == 0;
+ (power_2_buckets ||(old_buckets_len % new_buckets_len) == 0);
//If we are shrinking the same bucket array and it's
//is a fast shrink, just rehash the last nodes
if(same_buffer && fast_shrink){
@@ -1279,11 +1631,15 @@
bucket_type &old_bucket = old_buckets[n];
if(!fast_shrink){
- local_iterator before_i(old_bucket.before_begin());
- local_iterator end(old_bucket.end());
- local_iterator i(old_bucket.begin());
+ siterator before_i(old_bucket.before_begin());
+ siterator end(old_bucket.end());
+ siterator i(old_bucket.begin());
for(;i != end; ++i){
- const size_type new_n = (this->priv_hasher()(*i) % new_buckets_len);
+ const value_type &v = *this->get_real_value_traits().to_value_ptr(i.pointed_node());
+ const std::size_t hash_value = this->priv_hasher()(v);
+ const size_type new_n = (power_2_buckets)
+ ? ( hash_value & (new_buckets_len-1))
+ : ( hash_value % new_buckets_len);
//If this is a buffer expansion don't move if it's not necessary
if(same_buffer && new_n == n){
++before_i;
@@ -1296,26 +1652,33 @@
}
}
else{
- const size_type new_n = n % new_buckets_len;
+ const size_type new_n = (power_2_buckets)
+ ? (n & (new_buckets_len-1))
+ : (n % new_buckets_len);
bucket_type &new_b = new_buckets[new_n];
new_b.splice_after(new_b.before_begin(), old_bucket);
}
}
- this->priv_buckets() = new_buckets;
- this->priv_buckets_len() = new_buckets_len;
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
+ this->get_real_bucket_traits()= new_bucket_traits;
}
- BOOST_CATCH(...){
+ BOOST_INTRUSIVE_CATCH(...){
for(size_type n = 0; n < new_buckets_len; ++n){
- new_buckets[n].clear();
- old_buckets[n].clear();
+ if(safemode_or_autounlink){
+ new_buckets[n].clear_and_dispose
+ (detail::init_disposer<node_algorithms>());
+ old_buckets[n].clear_and_dispose
+ (detail::init_disposer<node_algorithms>());
+ }
+ else{
+ new_buckets[n].clear();
+ old_buckets[n].clear();
+ }
}
- size_traits::set_size(size_type(0));
- BOOST_RETHROW;
+ this->priv_size_traits().set_size(size_type(0));
+ BOOST_INTRUSIVE_RETHROW;
}
- BOOST_CATCH_END
- #endif
+ BOOST_INTRUSIVE_CATCH_END
}
//! <b>Effects</b>: Returns the nearest new bucket count optimized for
@@ -1360,10 +1723,10 @@
/// @cond
private:
- static local_iterator invalid_local_it(const bucket_info_t &b)
- { return b.buckets_->end(); }
+ static siterator invalid_local_it(const real_bucket_traits &b)
+ { return b.bucket_begin()->end(); }
- local_iterator priv_begin(size_type &bucket_num) const
+ siterator priv_begin(size_type &bucket_num) const
{
size_type buckets_len = this->priv_buckets_len();
for (bucket_num = 0; bucket_num < buckets_len; ++bucket_num){
@@ -1371,7 +1734,7 @@
if(!b.empty())
return b.begin();
}
- return invalid_local_it(this->priv_bucket_info());
+ return invalid_local_it(this->get_real_bucket_traits());
}
void priv_clear_buckets()
@@ -1380,41 +1743,46 @@
static void priv_clear_buckets(bucket_ptr buckets_ptr, size_type buckets_len)
{
for(; buckets_len--; ++buckets_ptr){
- buckets_ptr->clear();
+ if(safemode_or_autounlink){
+ buckets_ptr->clear_and_dispose(detail::init_disposer<node_algorithms>());
+ }
+ else{
+ buckets_ptr->clear();
+ }
}
}
template<class KeyType, class KeyHasher, class KeyValueEqual>
- local_iterator priv_find
- ( const KeyType &key, KeyHasher hasher
- , KeyValueEqual equal, size_type &bucket_number, size_type &h) const
- {
- size_type b_len(this->priv_buckets_len());
- h = hasher(key);
- bucket_number = h % b_len;
+ siterator priv_find
+ ( const KeyType &key, KeyHasher hash_func
+ , KeyValueEqual equal_func, size_type &bucket_number, size_type &h) const
+ {
+ bucket_number = from_hash_to_bucket((h = hash_func(key)));
- if(ConstantTimeSize && this->empty()){
- return invalid_local_it(this->priv_bucket_info());
+ if(constant_time_size && this->empty()){
+ return invalid_local_it(this->get_real_bucket_traits());
}
bucket_type &b = this->priv_buckets()[bucket_number];
- local_iterator it = b.begin();
+ siterator it = b.begin();
while(it != b.end()){
- if(equal(key, *it)){
+ const value_type &v =
+ *this->get_real_value_traits().to_value_ptr(it.pointed_node());
+ if(equal_func(key, v)){
return it;
}
++it;
}
- return invalid_local_it(this->priv_bucket_info());
+ return invalid_local_it(this->get_real_bucket_traits());
}
template<class KeyType, class KeyHasher, class KeyValueEqual>
- std::pair<local_iterator, local_iterator> priv_equal_range
+ std::pair<siterator, siterator> priv_equal_range
( const KeyType &key
- , KeyHasher hasher
- , KeyValueEqual equal
+ , KeyHasher hash_func
+ , KeyValueEqual equal_func
, size_type &bucket_number_first
, size_type &bucket_number_second
, size_type &count) const
@@ -1422,9 +1790,9 @@
size_type h;
count = 0;
//Let's see if the element is present
- std::pair<local_iterator, local_iterator> to_return
- ( priv_find(key, hasher, equal, bucket_number_first, h)
- , invalid_local_it(this->priv_bucket_info()));
+ std::pair<siterator, siterator> to_return
+ ( priv_find(key, hash_func, equal_func, bucket_number_first, h)
+ , invalid_local_it(this->get_real_bucket_traits()));
if(to_return.first == to_return.second){
bucket_number_second = bucket_number_first;
return to_return;
@@ -1433,11 +1801,13 @@
//If it's present, find the first that it's not equal in
//the same bucket
bucket_type &b = this->priv_buckets()[bucket_number_first];
- local_iterator it = to_return.first;
+ siterator it = to_return.first;
++it;
while(it != b.end()){
- if(!equal(key, *it)){
+ const value_type &v =
+ *this->get_real_value_traits().to_value_ptr(it.pointed_node());
+ if(!equal_func(key, v)){
to_return.second = it;
bucket_number_second = bucket_number_first;
return to_return;
@@ -1458,12 +1828,116 @@
}
//Otherwise, return the end node
- to_return.second = invalid_local_it(this->priv_bucket_info());
+ to_return.second = invalid_local_it(this->get_real_bucket_traits());
return to_return;
}
/// @endcond
};
+/// @cond
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none
+ , class O5 = none, class O6 = none
+ , class O7 = none
+ >
+struct make_hashtable_opt
+{
+ typedef typename pack_options
+ < uset_defaults<T>, O1, O2, O3, O4, O5, O6, O7>::type packed_options;
+
+ //Real value traits must be calculated from options
+ typedef typename detail::get_value_traits
+ <T, typename packed_options::value_traits>::type value_traits;
+ /// @cond
+ static const bool external_value_traits =
+ detail::external_value_traits_is_true<value_traits>::value;
+ typedef typename detail::eval_if_c
+ < external_value_traits
+ , detail::eval_value_traits<value_traits>
+ , detail::identity<value_traits>
+ >::type real_value_traits;
+ typedef typename packed_options::bucket_traits specified_bucket_traits;
+ /// @endcond
+ //Real bucket traits must be calculated from options and calculated valute_traits
+ typedef typename get_slist_impl
+ <typename real_value_traits::node_traits>::type slist_impl;
+ typedef typename
+ detail::if_c< detail::is_same
+ < specified_bucket_traits
+ , default_bucket_traits
+ >::value
+ , detail::bucket_traits_impl<slist_impl>
+ , specified_bucket_traits
+ >::type real_bucket_traits;
+
+ typedef usetopt
+ < value_traits
+ , typename packed_options::hash
+ , typename packed_options::equal
+ , typename packed_options::size_type
+ , packed_options::constant_time_size
+ , real_bucket_traits
+ , packed_options::power_2_buckets
+ > type;
+};
+/// @endcond
+
+//! Helper metafunction to define a \c hashtable that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none
+ , class O5 = none, class O6 = none
+ , class O7 = none
+ >
+#endif
+struct make_hashtable
+{
+ /// @cond
+ typedef hashtable_impl
+ < typename make_hashtable_opt
+ <T, O1, O2, O3, O4, O5, O6, O7>::type
+ > implementation_defined;
+
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3, class O4, class O5, class O6, class O7>
+class hashtable
+ : public make_hashtable<T, O1, O2, O3, O4, O5, O6, O7>::type
+{
+ typedef typename make_hashtable
+ <T, O1, O2, O3, O4, O5, O6, O7>::type Base;
+
+ public:
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::real_value_traits real_value_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+ typedef typename Base::bucket_ptr bucket_ptr;
+ typedef typename Base::size_type size_type;
+ typedef typename Base::hasher hasher;
+ typedef typename Base::bucket_traits bucket_traits;
+ typedef typename Base::key_equal key_equal;
+
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename real_value_traits::value_type, T>::value));
+
+ hashtable ( const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : Base(b_traits, hash_func, equal_func, v_traits)
+ {}
+};
+
+#endif
+
+
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/intrusive_fwd.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/intrusive_fwd.hpp (original)
+++ branches/bcbboost/boost/intrusive/intrusive_fwd.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -14,8 +14,9 @@
#define BOOST_INTRUSIVE_FWD_HPP
#include <cstddef>
-#include <boost/intrusive/tag.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
+
+/// @cond
//std predeclarations
namespace std{
@@ -36,6 +37,14 @@
namespace intrusive {
+struct none;
+
+} //namespace intrusive{
+} //namespace boost{
+
+namespace boost {
+namespace intrusive {
+
////////////////////////////
// Node algorithms
////////////////////////////
@@ -55,104 +64,148 @@
////////////////////////////
//slist
-template < class ValueTraits
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t>
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class slist;
-template< class Tag = tag
- , linking_policy Policy = safe_link
- , class VoidPointer = void *
- >
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class slist_base_hook;
-template< linking_policy Policy = safe_link
- , class VoidPointer = void *>
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class slist_member_hook;
//list
-template< class ValueTraits
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t>
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class list;
-template< class Tag = tag
- , linking_policy Policy = safe_link
- , class VoidPointer = void *
- >
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class list_base_hook;
-template< linking_policy Policy = safe_link
- , class VoidPointer = void *>
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class list_member_hook;
+//rbtree/set/multiset
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ , class O4 = none
+ >
+class rbtree;
+
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ , class O4 = none
+ >
+class set;
+
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ , class O4 = none
+ >
+class multiset;
+
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
+class set_base_hook;
+
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
+class set_member_hook;
+
//hash/unordered
-template< class ValueTraits
- , class Hash = boost::hash<typename ValueTraits::value_type>
- , class Equal = std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
+//rbtree/set/multiset
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ , class O4 = none
+ , class O5 = none
+ , class O6 = none
+ , class O7 = none
+ >
class hashtable;
-template< class ValueTraits
- , class Hash = boost::hash<typename ValueTraits::value_type>
- , class Equal = std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ , class O4 = none
+ , class O5 = none
+ , class O6 = none
+ , class O7 = none
+ >
class unordered_set;
-template< class ValueTraits
- , class Hash = boost::hash<typename ValueTraits::value_type>
- , class Equal = std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
+template
+ < class T
+ , class O1 = none
+ , class O2 = none
+ , class O3 = none
+ , class O4 = none
+ , class O5 = none
+ , class O6 = none
+ , class O7 = none
+ >
class unordered_multiset;
-template< class Tag = tag
- , linking_policy Policy = safe_link
- , class VoidPointer = void *
- >
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class unordered_set_base_hook;
-template< linking_policy Policy = safe_link
- , class VoidPointer = void *>
+template
+ < class O1 = none
+ , class O2 = none
+ , class O3 = none
+ >
class unordered_set_member_hook;
-
-//rbtree/set
-template < class ValueTraits
- , class Compare = std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
-class rbtree;
-
-template < class ValueTraits
- , class Compare = std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t>
-class set;
-
-template < class ValueTraits
- , class Compare = std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t>
-class multiset;
-
-template< class Tag = tag
- , linking_policy Policy = safe_link
- , class VoidPointer = void *
- >
-class set_base_hook;
-
-template< linking_policy Policy = safe_link
- , class VoidPointer = void *>
-class set_member_hook;
-
} //namespace intrusive {
} //namespace boost {
+/// @endcond
+
#endif //#ifndef BOOST_INTRUSIVE_FWD_HPP
Deleted: branches/bcbboost/boost/intrusive/linking_policy.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/linking_policy.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,46 +0,0 @@
-/////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2006-2007
-//
-// 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)
-//
-// See http://www.boost.org/libs/intrusive for documentation.
-//
-/////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTRUSIVE_VALUE_LINKING_POLICY_HPP
-#define BOOST_INTRUSIVE_VALUE_LINKING_POLICY_HPP
-
-namespace boost {
-namespace intrusive {
-
-//!This enumeration defines the type of value_traits that can be defined
-//!for Boost.Intrusive containers
-enum linking_policy{
- //!If this linking policy is specified in a value_traits class
- //!as the linking_policy, containers
- //!configured with such value_traits won't set the hooks
- //!of the erased values to a default state. Containers also won't
- //!check that the hooks of the new values are default initialized.
- normal_link,
-
- //!If this linking policy is specified in a value_traits class
- //!as the linking_policy, containers
- //!configured with such value_traits will set the hooks
- //!of the erased values to a default state. Containers also will
- //!check that the hooks of the new values are default initialized.
- safe_link,
-
- //!Same as "safe_link" but the user type is an auto-unlink
- //!type, so the containers with constant-time size features won't be
- //!compatible with value_traits configured with this policy.
- //!Containers also know that the a value can be silently erased from
- //!the container without using any function provided by the containers.
- auto_unlink
-};
-} //namespace intrusive
-} //namespace boost
-
-#endif //BOOST_INTRUSIVE_VALUE_LINKING_POLICY_HPP
Modified: branches/bcbboost/boost/intrusive/list.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/list.hpp (original)
+++ branches/bcbboost/boost/intrusive/list.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,79 +20,127 @@
#include <boost/intrusive/list_hook.hpp>
#include <boost/intrusive/circular_list_algorithms.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/detail/mpl.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <boost/static_assert.hpp>
-#ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
-#include <boost/detail/no_exceptions_support.hpp>
-#endif
+#include <boost/intrusive/options.hpp>
+#include <boost/intrusive/detail/no_exceptions_support.hpp>
#include <iterator>
#include <algorithm>
#include <functional>
#include <cstddef>
-#include <iterator>
namespace boost {
namespace intrusive {
+/// @cond
+
+template <class T>
+struct internal_default_list_hook
+{
+ template <class U> static detail::one test(...);
+ template <class U> static detail::two test(typename U::default_list_hook* = 0);
+ static const bool value = sizeof(test<T>(0)) == sizeof(detail::two);
+};
+
+template <class T>
+struct get_default_list_hook
+{
+ typedef typename T::default_list_hook type;
+};
+
+template <class ValueTraits, class SizeType, bool ConstantTimeSize>
+struct listopt
+{
+ typedef ValueTraits value_traits;
+ typedef SizeType size_type;
+ static const bool constant_time_size = ConstantTimeSize;
+};
+
+template <class T>
+struct list_defaults
+ : pack_options
+ < none
+ , base_hook
+ < typename detail::eval_if_c
+ < internal_default_list_hook<T>::value
+ , get_default_list_hook<T>
+ , detail::identity<none>
+ >::type
+ >
+ , constant_time_size<true>
+ , size_type<std::size_t>
+ >::type
+{};
+
+/// @endcond
+
//! The class template list is an intrusive container that mimics most of the
//! interface of std::list as described in the C++ standard.
//!
-//! The template parameter ValueTraits is called "value traits". It stores
-//! information and operations about the type to be stored in the container.
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
//!
-//! If the user specifies ConstantTimeSize as "true", a member of type SizeType
-//! will be embedded in the class, that will keep track of the number of stored objects.
-//! This will allow constant-time O(1) size() member, instead of default O(N) size.
-template< class ValueTraits
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class list
- : private detail::size_holder<ConstantTimeSize, SizeType>
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<> and \c size_type<>.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class list_impl
{
- /// @cond
- private:
- typename ValueTraits::node_traits::node root_;
- typedef list<ValueTraits, ConstantTimeSize, SizeType> this_type;
- typedef typename ValueTraits::node_traits node_traits;
- typedef detail::size_holder<ConstantTimeSize, SizeType> size_traits;
-
- //! This class is
- //! non-copyable
- list (const list&);
-
- //! This class is
- //! non-assignable
- list &operator =(const list&);
- /// @endcond
-
//Public typedefs
public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
+ typedef typename Config::value_traits value_traits;
+ /// @cond
+ static const bool external_value_traits =
+ detail::external_value_traits_is_true<value_traits>::value;
+ typedef typename detail::eval_if_c
+ < external_value_traits
+ , detail::eval_value_traits<value_traits>
+ , detail::identity<value_traits>
+ >::type real_value_traits;
+ /// @endcond
+ typedef typename real_value_traits::pointer pointer;
+ typedef typename real_value_traits::const_pointer const_pointer;
+ typedef typename std::iterator_traits<pointer>::value_type value_type;
typedef typename std::iterator_traits<pointer>::reference reference;
typedef typename std::iterator_traits<const_pointer>::reference const_reference;
typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef detail::list_iterator<value_type, ValueTraits> iterator;
- typedef detail::list_iterator<const value_type, ValueTraits> const_iterator;
+ typedef typename Config::size_type size_type;
+ typedef list_iterator<list_impl, false> iterator;
+ typedef list_iterator<list_impl, true> const_iterator;
typedef std::reverse_iterator<iterator> reverse_iterator;
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef typename node_traits::node_ptr node_ptr;
+ typedef typename node_traits::const_node_ptr const_node_ptr;
+ typedef circular_list_algorithms<node_traits> node_algorithms;
+
+ static const bool constant_time_size = Config::constant_time_size;
+ static const bool stateful_value_traits = detail::store_cont_ptr_on_it<list_impl>::value;
/// @cond
+
private:
- typedef typename node_traits::node node;
- typedef typename node_traits::node_ptr node_ptr;
- typedef typename node_traits::const_node_ptr const_node_ptr;
- typedef circular_list_algorithms<node_traits> node_algorithms;
+ typedef detail::size_holder<constant_time_size, size_type> size_traits;
+
+ //Non-copyable and non-moveable
+ list_impl (const list_impl&);
+ list_impl &operator =(const list_impl&);
+
enum { safemode_or_autounlink =
- (int)ValueTraits::linking_policy == (int)auto_unlink ||
- (int)ValueTraits::linking_policy == (int)safe_link };
+ (int)real_value_traits::link_mode == (int)auto_unlink ||
+ (int)real_value_traits::link_mode == (int)safe_link };
//Constant-time size is incompatible with auto-unlink hooks!
- BOOST_STATIC_ASSERT(!(ConstantTimeSize && ((int)ValueTraits::linking_policy == (int)auto_unlink)));
+ BOOST_STATIC_ASSERT(!(constant_time_size &&
+ ((int)real_value_traits::link_mode == (int)auto_unlink)
+ ));
//Const cast emulation for smart pointers
static node_ptr uncast(const_node_ptr ptr)
@@ -102,22 +150,64 @@
}
node_ptr get_root_node()
- { return node_ptr(&root_); }
+ { return node_ptr(&data_.root_plus_size_.root_); }
const_node_ptr get_root_node() const
- { return const_node_ptr(&root_); }
+ { return const_node_ptr(&data_.root_plus_size_.root_); }
+
+ struct root_plus_size : public size_traits
+ {
+ node root_;
+ };
+
+ struct data_t : public value_traits
+ {
+ typedef typename list_impl::value_traits value_traits;
+ data_t(const value_traits &val_traits)
+ : value_traits(val_traits)
+ {}
+
+ root_plus_size root_plus_size_;
+ } data_;
+
+ size_traits &priv_size_traits()
+ { return data_.root_plus_size_; }
+
+ const size_traits &priv_size_traits() const
+ { return data_.root_plus_size_; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<false>) const
+ { return data_; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<true>) const
+ { return data_.get_value_traits(*this); }
+
+ real_value_traits &get_real_value_traits(detail::bool_<false>)
+ { return data_; }
+
+ real_value_traits &get_real_value_traits(detail::bool_<true>)
+ { return data_.get_value_traits(*this); }
+
/// @endcond
public:
+
+ const real_value_traits &get_real_value_traits() const
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
+ real_value_traits &get_real_value_traits()
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
//! <b>Effects</b>: constructs an empty list.
//!
//! <b>Complexity</b>: Constant
//!
- //! <b>Throws</b>: If value_traits::node_traits::node
+ //! <b>Throws</b>: If real_value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks).
- list()
+ list_impl(const value_traits &v_traits = value_traits())
+ : data_(v_traits)
{
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
node_algorithms::init(this->get_root_node());
}
@@ -127,12 +217,13 @@
//!
//! <b>Complexity</b>: Linear in std::distance(b, e). No copy constructors are called.
//!
- //! <b>Throws</b>: If value_traits::node_traits::node
+ //! <b>Throws</b>: If real_value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks).
template<class Iterator>
- list(Iterator b, Iterator e)
+ list_impl(Iterator b, Iterator e, const value_traits &v_traits = value_traits())
+ : data_(v_traits)
{
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
node_algorithms::init(this->get_root_node());
this->insert(this->end(), b, e);
}
@@ -146,7 +237,7 @@
//!
//! <b>Complexity</b>: Linear to the number of elements in the list, if
//! it's a safe-mode or auto-unlink value . Otherwise constant.
- ~list()
+ ~list_impl()
{
if(safemode_or_autounlink){
this->clear();
@@ -165,11 +256,11 @@
//! <b>Note</b>: Does not affect the validity of iterators and references.
void push_back(reference value)
{
- node_ptr to_insert = ValueTraits::to_node_ptr(value);
+ node_ptr to_insert = get_real_value_traits().to_node_ptr(value);
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
node_algorithms::link_before(this->get_root_node(), to_insert);
- size_traits::increment();
+ this->priv_size_traits().increment();
}
//! <b>Requires</b>: value must be an lvalue.
@@ -184,11 +275,11 @@
//! <b>Note</b>: Does not affect the validity of iterators and references.
void push_front(reference value)
{
- node_ptr to_insert = ValueTraits::to_node_ptr(value);
+ node_ptr to_insert = get_real_value_traits().to_node_ptr(value);
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
node_algorithms::link_before(node_traits::get_next(this->get_root_node()), to_insert);
- size_traits::increment();
+ this->priv_size_traits().increment();
}
//! <b>Effects</b>: Erases the last element of the list.
@@ -203,7 +294,7 @@
{
node_ptr to_erase = node_traits::get_previous(this->get_root_node());
node_algorithms::unlink(to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
}
@@ -224,10 +315,10 @@
{
node_ptr to_erase = node_traits::get_previous(this->get_root_node());
node_algorithms::unlink(to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
- disposer(ValueTraits::to_value_ptr(to_erase));
+ disposer(get_real_value_traits().to_value_ptr(to_erase));
}
//! <b>Effects</b>: Erases the first element of the list.
@@ -242,7 +333,7 @@
{
node_ptr to_erase = node_traits::get_next(this->get_root_node());
node_algorithms::unlink(to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
}
@@ -263,10 +354,10 @@
{
node_ptr to_erase = node_traits::get_next(this->get_root_node());
node_algorithms::unlink(to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
- disposer(ValueTraits::to_value_ptr(to_erase));
+ disposer(get_real_value_traits().to_value_ptr(to_erase));
}
//! <b>Effects</b>: Returns a reference to the first element of the list.
@@ -275,7 +366,7 @@
//!
//! <b>Complexity</b>: Constant.
reference front()
- { return *ValueTraits::to_value_ptr(node_traits::get_next(this->get_root_node())); }
+ { return *get_real_value_traits().to_value_ptr(node_traits::get_next(this->get_root_node())); }
//! <b>Effects</b>: Returns a const_reference to the first element of the list.
//!
@@ -283,7 +374,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference front() const
- { return *ValueTraits::to_value_ptr(uncast(node_traits::get_next(this->get_root_node()))); }
+ { return *get_real_value_traits().to_value_ptr(uncast(node_traits::get_next(this->get_root_node()))); }
//! <b>Effects</b>: Returns a reference to the last element of the list.
//!
@@ -291,7 +382,7 @@
//!
//! <b>Complexity</b>: Constant.
reference back()
- { return *ValueTraits::to_value_ptr(node_traits::get_previous(this->get_root_node())); }
+ { return *get_real_value_traits().to_value_ptr(node_traits::get_previous(this->get_root_node())); }
//! <b>Effects</b>: Returns a const_reference to the last element of the list.
//!
@@ -299,7 +390,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference back() const
- { return *ValueTraits::to_value_ptr(uncast(node_traits::get_previous(this->get_root_node()))); }
+ { return *get_real_value_traits().to_value_ptr(uncast(node_traits::get_previous(this->get_root_node()))); }
//! <b>Effects</b>: Returns an iterator to the first element contained in the list.
//!
@@ -307,7 +398,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator begin()
- { return iterator(node_traits::get_next(this->get_root_node())); }
+ { return iterator(node_traits::get_next(this->get_root_node()), this); }
//! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
//!
@@ -323,7 +414,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator cbegin() const
- { return const_iterator(node_traits::get_next(this->get_root_node())); }
+ { return const_iterator(node_traits::get_next(this->get_root_node()), this); }
//! <b>Effects</b>: Returns an iterator to the end of the list.
//!
@@ -331,7 +422,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator end()
- { return iterator(this->get_root_node()); }
+ { return iterator(this->get_root_node(), this); }
//! <b>Effects</b>: Returns a const_iterator to the end of the list.
//!
@@ -347,7 +438,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator cend() const
- { return const_iterator(uncast(this->get_root_node())); }
+ { return const_iterator(uncast(this->get_root_node()), this); }
//! <b>Effects</b>: Returns a reverse_iterator pointing to the beginning
//! of the reversed list.
@@ -411,11 +502,8 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static list &container_from_end_iterator(iterator end_iterator)
- {
- return *detail::parent_from_member<list, node>
- ( detail::get_pointer(end_iterator.pointed_node()), &list::root_);
- }
+ static list_impl &container_from_end_iterator(iterator end_iterator)
+ { return priv_container_from_end_iterator(end_iterator); }
//! <b>Precondition</b>: end_iterator must be a valid end const_iterator
//! of list.
@@ -425,24 +513,21 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static const list &container_from_end_iterator(const_iterator end_iterator)
- {
- return *detail::parent_from_member<list, node>
- ( detail::get_pointer(end_iterator.pointed_node()), &list::root_);
- }
+ static const list_impl &container_from_end_iterator(const_iterator end_iterator)
+ { return priv_container_from_end_iterator(end_iterator); }
//! <b>Effects</b>: Returns the number of the elements contained in the list.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Linear to the number of elements contained in the list.
- //! if ConstantTimeSize is false. Constant time otherwise.
+ //! if constant-time size option is disabled. Constant time otherwise.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
size_type size() const
{
- if(ConstantTimeSize)
- return size_traits::get_size();
+ if(constant_time_size)
+ return this->priv_size_traits().get_size();
else
return node_algorithms::count(this->get_root_node()) - 1;
}
@@ -464,13 +549,13 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
- void swap(list& other)
+ void swap(list_impl& other)
{
node_algorithms::swap_nodes(this->get_root_node(), other.get_root_node());
- if(ConstantTimeSize){
- size_type backup = size_traits::get_size();
- size_traits::set_size(other.get_size());
- other.set_size(backup);
+ if(constant_time_size){
+ size_type backup = this->priv_size_traits().get_size();
+ this->priv_size_traits().set_size(other.priv_size_traits().get_size());
+ other.priv_size_traits().set_size(backup);
}
}
@@ -543,7 +628,7 @@
++i;
node_ptr to_erase = erase.pointed_node();
node_algorithms::unlink(to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
return i;
@@ -566,7 +651,7 @@
//! erased elements.
iterator erase(iterator b, iterator e)
{
- if(safemode_or_autounlink || ConstantTimeSize){
+ if(safemode_or_autounlink || constant_time_size){
while(b != e){
b = this->erase(b);
}
@@ -599,10 +684,10 @@
++i;
node_ptr to_erase = erase.pointed_node();
node_algorithms::unlink(to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
- disposer(ValueTraits::to_value_ptr(to_erase));
+ disposer(get_real_value_traits().to_value_ptr(to_erase));
return i;
}
@@ -645,7 +730,7 @@
}
else{
node_algorithms::init(this->get_root_node());
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
}
}
@@ -678,24 +763,20 @@
//!
//! <b>Throws</b>: If cloner throws. Basic guarantee.
template <class Cloner, class Disposer>
- void clone_from(const list &src, Cloner cloner, Disposer disposer)
+ void clone_from(const list_impl &src, Cloner cloner, Disposer disposer)
{
this->clear_and_dispose(disposer);
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- BOOST_TRY{
- #endif
+ BOOST_INTRUSIVE_TRY{
const_iterator b(src.begin()), e(src.end());
for(; b != e; ++b){
this->push_back(*cloner(*b));
}
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
}
- BOOST_CATCH(...){
- clear_and_dispose(disposer);
- BOOST_RETHROW;
+ BOOST_INTRUSIVE_CATCH(...){
+ this->clear_and_dispose(disposer);
+ BOOST_INTRUSIVE_RETHROW;
}
- BOOST_CATCH_END
- #endif
+ BOOST_INTRUSIVE_CATCH_END
}
//! <b>Requires</b>: value must be an lvalue and p must be a valid iterator of *this.
@@ -711,12 +792,12 @@
//! <b>Note</b>: Does not affect the validity of iterators and references.
iterator insert(iterator p, reference value)
{
- node_ptr to_insert = ValueTraits::to_node_ptr(value);
+ node_ptr to_insert = get_real_value_traits().to_node_ptr(value);
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
node_algorithms::link_before(p.pointed_node(), to_insert);
- size_traits::increment();
- return iterator(to_insert);
+ this->priv_size_traits().increment();
+ return iterator(to_insert, this);
}
//! <b>Requires</b>: Dereferencing iterator must yield
@@ -793,13 +874,15 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of
//! this list. Iterators of this list and all the references are not invalidated.
- void splice(iterator p, list& x)
+ void splice(iterator p, list_impl& x)
{
if(!x.empty()){
+ size_traits &thist = this->priv_size_traits();
+ size_traits &xt = x.priv_size_traits();
node_algorithms::transfer
(p.pointed_node(), x.begin().pointed_node(), x.end().pointed_node());
- size_traits::set_size(size_traits::get_size() + x.get_size());
- x.set_size(size_type(0));
+ thist.set_size(thist.get_size() + xt.get_size());
+ xt.set_size(size_type(0));
}
}
@@ -816,11 +899,11 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice(iterator p, list&x, iterator new_ele)
+ void splice(iterator p, list_impl&x, iterator new_ele)
{
node_algorithms::transfer(p.pointed_node(), new_ele.pointed_node());
- x.decrement();
- size_traits::increment();
+ x.priv_size_traits().decrement();
+ this->priv_size_traits().increment();
}
//! <b>Requires</b>: p must be a valid iterator of *this.
@@ -832,18 +915,20 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Linear to the number of elements transferred
- //! if ConstantTimeSize is true. Constant-time otherwise.
+ //! if constant-time size option is enabled. Constant-time otherwise.
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice(iterator p, list&x, iterator start, iterator end)
+ void splice(iterator p, list_impl&x, iterator start, iterator end)
{
if(start != end){
- if(ConstantTimeSize){
+ if(constant_time_size){
+ size_traits &thist = this->priv_size_traits();
+ size_traits &xt = x.priv_size_traits();
size_type increment = std::distance(start, end);
node_algorithms::transfer(p.pointed_node(), start.pointed_node(), end.pointed_node());
- size_traits::set_size(size_traits::get_size() + increment);
- x.set_size(x.get_size() - increment);
+ thist.set_size(thist.get_size() + increment);
+ xt.set_size(xt.get_size() - increment);
}
else{
node_algorithms::transfer(p.pointed_node(), start.pointed_node(), end.pointed_node());
@@ -864,14 +949,16 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice(iterator p, list&x, iterator start, iterator end, difference_type n)
+ void splice(iterator p, list_impl&x, iterator start, iterator end, difference_type n)
{
if(n){
- if(ConstantTimeSize){
+ if(constant_time_size){
+ size_traits &thist = this->priv_size_traits();
+ size_traits &xt = x.priv_size_traits();
BOOST_INTRUSIVE_INVARIANT_ASSERT(n == std::distance(start, end));
node_algorithms::transfer(p.pointed_node(), start.pointed_node(), end.pointed_node());
- size_traits::set_size(size_traits::get_size() + n);
- x.set_size(x.get_size() - n);
+ thist.set_size(thist.get_size() + n);
+ xt.set_size(xt.get_size() - n);
}
else{
node_algorithms::transfer(p.pointed_node(), start.pointed_node(), end.pointed_node());
@@ -882,7 +969,7 @@
//! <b>Effects</b>: This function sorts the list *this according to std::less<value_type>.
//! The sort is stable, that is, the relative order of equivalent elements is preserved.
//!
- //! <b>Throws</b>: If value_traits::node_traits::node
+ //! <b>Throws</b>: If real_value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
//! or std::less<value_type> throws. Basic guarantee.
//!
@@ -898,12 +985,12 @@
//! <b>Effects</b>: This function sorts the list *this according to p. The sort is
//! stable, that is, the relative order of equivalent elements is preserved.
//!
- //! <b>Throws</b>: If value_traits::node_traits::node
+ //! <b>Throws</b>: If real_value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
//! or the predicate throws. Basic guarantee.
//!
- //! <b>Notes</b>: This won't throw if list_base_hook<>::value_traits or
- //! list_member_hook::::value_traits are used as value traits.
+ //! <b>Notes</b>: This won't throw if list_base_hook<> or
+ //! list_member_hook are used.
//! Iterators and references are not invalidated.
//!
//! <b>Complexity</b>: The number of comparisons is approximately N log N, where N
@@ -913,8 +1000,8 @@
{
if(node_traits::get_next(this->get_root_node())
!= node_traits::get_previous(this->get_root_node())){
- list carry;
- list counter[64];
+ list_impl carry;
+ list_impl counter[64];
int fill = 0;
while(!this->empty()){
carry.splice(carry.begin(), *this, this->begin());
@@ -943,7 +1030,7 @@
//! size() + x.size() - 1 comparisons.
//!
//! <b>Note</b>: Iterators and references are not invalidated
- void merge(list& x)
+ void merge(list_impl& x)
{ merge(x, std::less<value_type>()); }
//! <b>Requires</b>: p must be a comparison function that induces a strict weak
@@ -961,7 +1048,7 @@
//!
//! <b>Note</b>: Iterators and references are not invalidated.
template<class Predicate>
- void merge(list& x, Predicate p)
+ void merge(list_impl& x, Predicate p)
{
iterator e = this->end();
iterator bx = x.begin();
@@ -1142,10 +1229,46 @@
//! <b>Complexity</b>: Constant time.
//!
//! <b>Note</b>: Iterators and references are not invalidated.
- static iterator iterator_to(reference value)
+ //! This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static iterator s_iterator_to(reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(!node_algorithms::unique(real_value_traits::to_node_ptr(value)));
+ return iterator(real_value_traits::to_node_ptr(value), 0);
+ }
+
+ //! <b>Requires</b>: value must be a const reference to a value inserted in a list.
+ //!
+ //! <b>Effects</b>: This function returns an iterator pointing to the element.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Complexity</b>: Constant time.
+ //!
+ //! <b>Note</b>: Iterators and references are not invalidated.
+ //! This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_iterator s_iterator_to(const_reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(!node_algorithms::unique(real_value_traits::to_node_ptr(const_cast<reference> (value))));
+ return const_iterator(real_value_traits::to_node_ptr(const_cast<reference> (value)), 0);
+ }
+
+ //! <b>Requires</b>: value must be a reference to a value inserted in a list.
+ //!
+ //! <b>Effects</b>: This function returns a const_iterator pointing to the element
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Complexity</b>: Constant time.
+ //!
+ //! <b>Note</b>: Iterators and references are not invalidated.
+ iterator iterator_to(reference value)
{
- BOOST_INTRUSIVE_INVARIANT_ASSERT(!node_algorithms::unique(ValueTraits::to_node_ptr(value)));
- return iterator(ValueTraits::to_node_ptr(value));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(!node_algorithms::unique(real_value_traits::to_node_ptr(value)));
+ return iterator(real_value_traits::to_node_ptr(value), this);
}
//! <b>Requires</b>: value must be a const reference to a value inserted in a list.
@@ -1157,20 +1280,58 @@
//! <b>Complexity</b>: Constant time.
//!
//! <b>Note</b>: Iterators and references are not invalidated.
- static const_iterator iterator_to(const_reference value)
+ const_iterator iterator_to(const_reference value) const
{
- BOOST_INTRUSIVE_INVARIANT_ASSERT(!node_algorithms::unique(ValueTraits::to_node_ptr(const_cast<reference> (value))));
- return const_iterator(ValueTraits::to_node_ptr(const_cast<reference> (value)));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(!node_algorithms::unique(real_value_traits::to_node_ptr(const_cast<reference> (value))));
+ return const_iterator(real_value_traits::to_node_ptr(const_cast<reference> (value)), this);
}
+
+ /// @cond
+
+ private:
+ static list_impl &priv_container_from_end_iterator(const const_iterator &end_iterator)
+ {
+ root_plus_size *r = detail::parent_from_member<root_plus_size, node>
+ ( detail::get_pointer(end_iterator.pointed_node()), &root_plus_size::root_);
+ data_t *d = detail::parent_from_member<data_t, root_plus_size>
+ ( r, &data_t::root_plus_size_);
+ list_impl *s = detail::parent_from_member<list_impl, data_t>(d, &list_impl::data_);
+ return *s;
+ }
+ /// @endcond
};
-template <class V, bool C, class S>
-inline bool operator==(const list<V, C, S>& x, const list<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const list_impl<T, Options...> &x, const list_impl<T, Options...> &y)
+#else
+(const list_impl<Config> &x, const list_impl<Config> &y)
+#endif
+{ return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+bool operator==
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const list_impl<T, Options...> &x, const list_impl<T, Options...> &y)
+#else
+(const list_impl<Config> &x, const list_impl<Config> &y)
+#endif
{
+ typedef list_impl<Config> list_type;
+ typedef typename list_type::const_iterator const_iterator;
+ const bool C = list_type::constant_time_size;
if(C && x.size() != y.size()){
return false;
}
- typedef typename list<V, C, S>::const_iterator const_iterator;
const_iterator end1 = x.end();
const_iterator i1 = x.begin();
@@ -1192,31 +1353,132 @@
}
}
-template <class V, bool C, class S>
-inline bool operator<(const list<V, C, S>& x,
- const list<V, C, S>& y)
-{ return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); }
-
-template <class V, bool C, class S>
-inline bool operator!=(const list<V, C, S>& x, const list<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator!=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const list_impl<T, Options...> &x, const list_impl<T, Options...> &y)
+#else
+(const list_impl<Config> &x, const list_impl<Config> &y)
+#endif
{ return !(x == y); }
-template <class V, bool C, class S>
-inline bool operator>(const list<V, C, S>& x, const list<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const list_impl<T, Options...> &x, const list_impl<T, Options...> &y)
+#else
+(const list_impl<Config> &x, const list_impl<Config> &y)
+#endif
{ return y < x; }
-template <class V, bool C, class S>
-inline bool operator<=(const list<V, C, S>& x, const list<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const list_impl<T, Options...> &x, const list_impl<T, Options...> &y)
+#else
+(const list_impl<Config> &x, const list_impl<Config> &y)
+#endif
{ return !(y < x); }
-template <class V, bool C, class S>
-inline bool operator>=(const list<V, C, S>& x, const list<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const list_impl<T, Options...> &x, const list_impl<T, Options...> &y)
+#else
+(const list_impl<Config> &x, const list_impl<Config> &y)
+#endif
{ return !(x < y); }
-template <class V, bool C, class S>
-inline void swap(list<V, C, S>& x, list<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline void swap
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(list_impl<T, Options...> &x, list_impl<T, Options...> &y)
+#else
+(list_impl<Config> &x, list_impl<Config> &y)
+#endif
{ x.swap(y); }
+//! Helper metafunction to define a \c list that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_list
+{
+ /// @cond
+ typedef typename pack_options
+ < list_defaults<T>, O1, O2, O3>::type packed_options;
+ typedef typename detail::get_value_traits
+ <T, typename packed_options::value_traits>::type value_traits;
+
+ typedef list_impl
+ <
+ listopt
+ < value_traits
+ , typename packed_options::size_type
+ , packed_options::constant_time_size
+ >
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3>
+class list
+ : public make_list<T, O1, O2, O3>::type
+{
+ typedef typename make_list
+ <T, O1, O2, O3>::type Base;
+ typedef typename Base::real_value_traits real_value_traits;
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename real_value_traits::value_type, T>::value));
+ public:
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+
+ list(const value_traits &v_traits = value_traits())
+ : Base(v_traits)
+ {}
+
+ template<class Iterator>
+ list(Iterator b, Iterator e, const value_traits &v_traits = value_traits())
+ : Base(b, e, v_traits)
+ {}
+
+ static list &container_from_end_iterator(iterator end_iterator)
+ { return static_cast<list &>(Base::container_from_end_iterator(end_iterator)); }
+
+ static const list &container_from_end_iterator(const_iterator end_iterator)
+ { return static_cast<const list &>(Base::container_from_end_iterator(end_iterator)); }
+};
+
+#endif
+
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/list_hook.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/list_hook.hpp (original)
+++ branches/bcbboost/boost/intrusive/list_hook.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,116 +17,104 @@
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
#include <boost/intrusive/detail/utilities.hpp>
-#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/detail/list_node.hpp>
#include <boost/intrusive/circular_list_algorithms.hpp>
-#include <boost/intrusive/linking_policy.hpp>
-#include <boost/intrusive/tag.hpp>
-#include <boost/static_assert.hpp>
+#include <boost/intrusive/options.hpp>
+#include <boost/intrusive/detail/generic_hook.hpp>
namespace boost {
namespace intrusive {
-//! Derive a class from list_base_hook in order to store objects in
-//! in an list. list_base_hook holds the data necessary to maintain the
-//! list and provides an appropriate value_traits class for list.
+/// @cond
+template<class VoidPointer>
+struct get_list_node_algo
+{
+ typedef circular_list_algorithms<list_node_traits<VoidPointer> > type;
+};
+/// @endcond
+
+//! Helper metafunction to define a \c \c list_base_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_list_base_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
+
+ typedef detail::generic_hook
+ < get_list_node_algo<typename packed_options::void_pointer>
+ , typename packed_options::tag
+ , packed_options::link_mode
+ , detail::ListBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+//! Derive a class from this hook in order to store objects of that class
+//! in an list.
//!
-//! The first integer template argument defines a tag to identify the node.
+//! The hook admits the following options: \c tag<>, \c void_pointer<> and
+//! \c link_mode<>.
+//!
+//! \c tag<> defines a tag to identify the node.
//! The same tag value can be used in different classes, but if a class is
-//! derived from more than one list_base_hook, then each list_base_hook needs its
+//! derived from more than one \c list_base_hook, then each \c list_base_hook needs its
//! unique tag.
//!
-//! The second boolean template parameter will specify the linking mode of the hook.
+//! \c link_mode<> will specify the linking mode of the hook (\c normal_link,
+//! \c auto_unlink or \c safe_link).
//!
-//! The third argument is the pointer type that will be used internally in the hook
-//! and the list configured from this hook.
-template< class Tag //= tag
- , linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+//! \c void_pointer<> is the pointer type that will be used internally in the hook
+//! and the the container configured to use this hook.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class list_base_hook
- : private detail::list_node_traits<VoidPointer>::node
+ : public make_list_base_hook<O1, O2, O3>::type
{
- public:
- typedef detail::list_node_traits<VoidPointer> node_traits;
- enum { linking_policy = Policy };
-
- /// @cond
- private:
- typedef circular_list_algorithms<node_traits> node_algorithms;
-
- public:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef list_base_hook
- <Tag, Policy, VoidPointer> this_type;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type>::type this_type_ptr;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type>::type const_this_type_ptr;
-
- private:
- node_ptr this_as_node()
- { return node_ptr(static_cast<node *const>(this)); }
-
- const_node_ptr this_as_node() const
- { return const_node_ptr(static_cast<const node *const>(this)); }
- /// @endcond
-
- public:
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
//! <b>Throws</b>: Nothing.
- list_base_hook()
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ list_base_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using list_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- list_base_hook(const list_base_hook& )
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ list_base_hook(const list_base_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using list_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- list_base_hook& operator=(const list_base_hook& )
- { return *this; }
+ list_base_hook& operator=(const list_base_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an list an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
//!
//! <b>Throws</b>: Nothing.
- ~list_base_hook()
- { detail::destructor_impl(*this, detail::dispatcher<Policy>()); }
+ ~list_base_hook();
//! <b>Effects</b>: Swapping two nodes swaps the position of the elements
//! related to those nodes in one or two containers. That is, if the node
@@ -140,170 +128,102 @@
//! <b>Complexity</b>: Constant
//!
//! <b>Throws</b>: Nothing.
- void swap_nodes(list_base_hook &other)
- { node_algorithms::swap_nodes(this_as_node(), other.this_as_node()); }
+ void swap_nodes(list_base_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
//! <b>Returns</b>: true, if the node belongs to a container, false
- //! otherwise. This function can be used to test whether list::iterator_to
+ //! otherwise. This function can be used to test whether \c list::iterator_to
//! will return a valid iterator.
//!
//! <b>Complexity</b>: Constant
- bool is_linked() const
- {
- //is_linked() can be only used in safe-mode or auto-unlink
- BOOST_STATIC_ASSERT((Policy == safe_link || Policy == auto_unlink));
- return !node_algorithms::unique(this_as_node());
- }
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
- //!
- //! <b>Throws</b>: Nothing.
- void unlink()
- {
- BOOST_STATIC_ASSERT((Policy == auto_unlink));
- node_algorithms::unlink(this_as_node());
- node_algorithms::init(this_as_node());
- }
-
- //! The value_traits class is used as the first template argument for list.
- //! The template argument T defines the class type stored in list. Objects
- //! of type T and of types derived from T can be stored. T doesn't need to be
- //! copy-constructible or assignable.
- template<class T>
- struct value_traits
- : detail::derivation_hook_value_traits<T, this_type, Tag>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr(static_cast<list_base_hook*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr(static_cast<const list_base_hook*> (detail::get_pointer(p)));
- }
+ void unlink();
+ #endif
+};
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return this_as_node(); }
+//! Helper metafunction to define a \c \c list_member_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_list_member_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return this_as_node(); }
+ typedef detail::generic_hook
+ < get_list_node_algo<typename packed_options::void_pointer>
+ , member_tag
+ , packed_options::link_mode
+ , detail::NoBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
};
-//! Put a public data member list_member_hook in order to store objects of this class in
-//! an list. list_member_hook holds the data necessary for maintaining the list and
-//! provides an appropriate value_traits class for list.
+//! Store this hook in a class to be inserted
+//! in an list.
//!
-//! The first boolean template parameter will specify the linking mode of the hook.
+//! The hook admits the following options: \c void_pointer<> and
+//! \c link_mode<>.
+//!
+//! \c link_mode<> will specify the linking mode of the hook (\c normal_link,
+//! \c auto_unlink or \c safe_link).
//!
-//! The second argument is the pointer type that will be used internally in the hook
-//! and the list configured from this hook.
-template< linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+//! \c void_pointer<> is the pointer type that will be used internally in the hook
+//! and the the container configured to use this hook.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class list_member_hook
- : private detail::list_node_traits<VoidPointer>::node
+ : public make_list_member_hook<O1, O2, O3>::type
{
- public:
- typedef detail::list_node_traits<VoidPointer> node_traits;
- enum { linking_policy = Policy };
-
- /// @cond
- private:
- typedef circular_list_algorithms<node_traits> node_algorithms;
- /// @endcond
-
- public:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef list_member_hook
- <Policy, VoidPointer> this_type;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type >::type this_type_ptr;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type >::type const_this_type_ptr;
-
- /// @cond
- private:
- node_ptr this_as_node()
- { return node_ptr(static_cast<node *const>(this)); }
-
- const_node_ptr this_as_node() const
- { return const_node_ptr(static_cast<const node *const>(this)); }
- /// @endcond
-
- public:
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
//! <b>Throws</b>: Nothing.
- list_member_hook()
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ list_member_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using list_member_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- list_member_hook(const list_member_hook& )
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ list_member_hook(const list_member_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using list_member_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- list_member_hook& operator=(const list_member_hook& )
- { return *this; }
+ list_member_hook& operator=(const list_member_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an list an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
//!
//! <b>Throws</b>: Nothing.
- ~list_member_hook()
- { detail::destructor_impl(*this, detail::dispatcher<Policy>()); }
+ ~list_member_hook();
//! <b>Effects</b>: Swapping two nodes swaps the position of the elements
//! related to those nodes in one or two containers. That is, if the node
@@ -316,73 +236,24 @@
//!
//! <b>Complexity</b>: Constant
//!
- //! <b>Throws</b>: Nothing.
- void swap_nodes(list_member_hook& other)
- { node_algorithms::swap_nodes(this_as_node(), other.this_as_node()); }
+ //! <b>Throws</b>: Nothing.
+ void swap_nodes(list_member_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
//! <b>Returns</b>: true, if the node belongs to a container, false
- //! otherwise. This function can be used to test whether list::iterator_to
+ //! otherwise. This function can be used to test whether \c list::iterator_to
//! will return a valid iterator.
//!
- //! <b>Complexity</b>: Constant
- bool is_linked() const
- {
- //is_linked() can be only used in safe-mode or auto-unlink
- BOOST_STATIC_ASSERT((Policy == safe_link || Policy == auto_unlink));
- return !node_algorithms::unique(this_as_node());
- }
+ //! <b>Complexity</b>: Constant
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
- //!
- //! <b>Throws</b>: Nothing.
- void unlink()
- {
- BOOST_STATIC_ASSERT((Policy == auto_unlink));
- node_algorithms::unlink(this_as_node());
- node_algorithms::init(this_as_node());
- }
-
- //! The value_traits class is used as the first template argument for list.
- //! The template argument is a pointer to member pointing to the node in
- //! the class. Objects of type T and of types derived from T can be stored.
- //! T doesn't need to be copy-constructible or assignable.
- template<class T, this_type T::* M>
- struct value_traits
- : detail::member_hook_value_traits<T, this_type, M>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr(static_cast<this_type*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr(static_cast<const this_type*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return this_as_node(); }
-
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return this_as_node(); }
+ void unlink();
+ #endif
};
} //namespace intrusive
Modified: branches/bcbboost/boost/intrusive/member_value_traits.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/member_value_traits.hpp (original)
+++ branches/bcbboost/boost/intrusive/member_value_traits.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,7 +13,7 @@
#ifndef BOOST_INTRUSIVE_MEMBER_VALUE_TRAITS_HPP
#define BOOST_INTRUSIVE_MEMBER_VALUE_TRAITS_HPP
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <iterator>
#include <boost/intrusive/detail/parent_from_member.hpp>
@@ -25,7 +25,7 @@
//!store a node_traits::node
template< class T, class NodeTraits
, typename NodeTraits::node T::* PtrToMember
- , linking_policy Policy>
+ , link_mode_type LinkMode = safe_link>
struct member_value_traits
{
public:
@@ -38,8 +38,7 @@
typedef typename boost::pointer_to_other<node_ptr, const T>::type const_pointer;
typedef typename std::iterator_traits<pointer>::reference reference;
typedef typename std::iterator_traits<const_pointer>::reference const_reference;
-
- enum { linking_policy = Policy };
+ static const link_mode_type link_mode = LinkMode;
static node_ptr to_node_ptr(reference value)
{ return node_ptr(&(value.*PtrToMember)); }
Modified: branches/bcbboost/boost/intrusive/pointer_plus_bit.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/pointer_plus_bit.hpp (original)
+++ branches/bcbboost/boost/intrusive/pointer_plus_bit.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,7 +23,7 @@
template<class VoidPointer, std::size_t Alignment>
struct has_pointer_plus_bit
{
- enum { value = false };
+ static const bool value = false;
};
//!This is an specialization for raw pointers.
@@ -32,7 +32,7 @@
template<std::size_t N>
struct has_pointer_plus_bit<void*, N>
{
- enum { value = N % 2u == 0 };
+ static const bool value = (N % 2u == 0);
};
//!This is class that is supposed to have static methods
Modified: branches/bcbboost/boost/intrusive/rbtree.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/rbtree.hpp (original)
+++ branches/bcbboost/boost/intrusive/rbtree.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -23,123 +23,228 @@
#include <boost/intrusive/set_hook.hpp>
#include <boost/intrusive/detail/rbtree_node.hpp>
#include <boost/intrusive/detail/ebo_functor_holder.hpp>
+#include <boost/intrusive/options.hpp>
#include <boost/intrusive/rbtree_algorithms.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <cstddef>
#include <iterator>
namespace boost {
namespace intrusive {
+/// @cond
+
+template <class T>
+struct internal_default_set_hook
+{
+ template <class U> static detail::one test(...);
+ template <class U> static detail::two test(typename U::default_set_hook* = 0);
+ static const bool value = sizeof(test<T>(0)) == sizeof(detail::two);
+};
+
+template <class T>
+struct get_default_set_hook
+{
+ typedef typename T::default_set_hook type;
+};
+
+template <class ValueTraits, class Compare, class SizeType, bool ConstantTimeSize>
+struct setopt
+{
+ typedef ValueTraits value_traits;
+ typedef Compare compare;
+ typedef SizeType size_type;
+ static const bool constant_time_size = ConstantTimeSize;
+};
+
+template <class T>
+struct set_defaults
+ : pack_options
+ < none
+ , base_hook
+ < typename detail::eval_if_c
+ < internal_default_set_hook<T>::value
+ , get_default_set_hook<T>
+ , detail::identity<none>
+ >::type
+ >
+ , constant_time_size<true>
+ , size_type<std::size_t>
+ , compare<std::less<T> >
+ >::type
+{};
+
+/// @endcond
+
//! The class template rbtree is an intrusive red-black tree container, that
//! is used to construct intrusive set and tree containers. The no-throw
-//! guarantee holds only, if the Compare object
+//! guarantee holds only, if the value_compare object
//! doesn't throw.
-template < class ValueTraits
- , class Compare //= std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class rbtree
- : private detail::size_holder<ConstantTimeSize, SizeType>
+//!
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
+//!
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<>, \c size_type<> and
+//! \c compare<>.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class rbtree_impl
{
+ public:
+ typedef typename Config::value_traits value_traits;
/// @cond
- private:
- typename ValueTraits::node_traits::node root_;
- typedef rbtree<ValueTraits, Compare
- ,ConstantTimeSize, SizeType> this_type;
- typedef typename ValueTraits::node_traits node_traits;
- typedef detail::size_holder<ConstantTimeSize, SizeType> size_traits;
-
- //noncopyable
- rbtree (const rbtree&);
- rbtree operator =(const rbtree&);
+ static const bool external_value_traits =
+ detail::external_value_traits_is_true<value_traits>::value;
+ typedef typename detail::eval_if_c
+ < external_value_traits
+ , detail::eval_value_traits<value_traits>
+ , detail::identity<value_traits>
+ >::type real_value_traits;
/// @endcond
+ typedef typename real_value_traits::pointer pointer;
+ typedef typename real_value_traits::const_pointer const_pointer;
+ typedef typename std::iterator_traits<pointer>::value_type value_type;
+ typedef value_type key_type;
+ typedef typename std::iterator_traits<pointer>::reference reference;
+ typedef typename std::iterator_traits<const_pointer>::reference const_reference;
+ typedef typename std::iterator_traits<pointer>::difference_type difference_type;
+ typedef typename Config::size_type size_type;
+ typedef typename Config::compare value_compare;
+ typedef value_compare key_compare;
+ typedef rbtree_iterator<rbtree_impl, false> iterator;
+ typedef rbtree_iterator<rbtree_impl, true> const_iterator;
+ typedef std::reverse_iterator<iterator> reverse_iterator;
+ typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef typename boost::pointer_to_other
+ <pointer, node>::type node_ptr;
+ typedef typename boost::pointer_to_other
+ <node_ptr, const node>::type const_node_ptr;
+ typedef rbtree_algorithms<node_traits> node_algorithms;
- public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef value_type key_type;
- typedef Compare value_compare;
- typedef detail::rbtree_iterator<value_type, ValueTraits> iterator;
- typedef detail::rbtree_iterator<const value_type, ValueTraits> const_iterator;
- typedef std::reverse_iterator<iterator> reverse_iterator;
- typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
+ static const bool constant_time_size = Config::constant_time_size;
+ static const bool stateful_value_traits = detail::store_cont_ptr_on_it<rbtree_impl>::value;
/// @cond
private:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <pointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <node_ptr, const node>::type const_node_ptr;
- typedef rbtree_algorithms<node_traits> node_algorithms;
+ typedef detail::size_holder<constant_time_size, size_type> size_traits;
+
+ //noncopyable
+ rbtree_impl (const rbtree_impl&);
+ rbtree_impl operator =(const rbtree_impl&);
+
enum { safemode_or_autounlink =
- (int)ValueTraits::linking_policy == (int)auto_unlink ||
- (int)ValueTraits::linking_policy == (int)safe_link };
+ (int)real_value_traits::link_mode == (int)auto_unlink ||
+ (int)real_value_traits::link_mode == (int)safe_link };
//Constant-time size is incompatible with auto-unlink hooks!
- BOOST_STATIC_ASSERT(!(ConstantTimeSize && ((int)ValueTraits::linking_policy == (int)auto_unlink)));
+ BOOST_STATIC_ASSERT(!(constant_time_size && ((int)real_value_traits::link_mode == (int)auto_unlink)));
- //Use EBO if possible
- typedef detail::node_plus_pred<node, Compare> members_t;
- members_t members_;
-
- const Compare &priv_comp() const
- { return members_.second(); }
+ struct header_plus_size : public size_traits
+ { node header_; };
- Compare &priv_comp()
- { return members_.second(); }
+ struct node_plus_pred_t : public detail::ebo_functor_holder<value_compare>
+ {
+ node_plus_pred_t(const value_compare &comp)
+ : detail::ebo_functor_holder<value_compare>(comp)
+ {}
+ header_plus_size header_plus_size_;
+ };
+
+ struct data_t : public rbtree_impl::value_traits
+ {
+ typedef typename rbtree_impl::value_traits value_traits;
+ data_t(const value_compare & comp, const value_traits &val_traits)
+ : value_traits(val_traits), node_plus_pred_(comp)
+ {}
+ node_plus_pred_t node_plus_pred_;
+ } data_;
+
+ const value_compare &priv_comp() const
+ { return data_.node_plus_pred_.get(); }
+
+ value_compare &priv_comp()
+ { return data_.node_plus_pred_.get(); }
const node &priv_header() const
- { return members_.first(); }
+ { return data_.node_plus_pred_.header_plus_size_.header_; }
node &priv_header()
- { return members_.first(); }
+ { return data_.node_plus_pred_.header_plus_size_.header_; }
static node_ptr uncast(const_node_ptr ptr)
{
return node_ptr(const_cast<node*>(detail::get_pointer(ptr)));
}
+
+ size_traits &priv_size_traits()
+ { return data_.node_plus_pred_.header_plus_size_; }
+
+ const size_traits &priv_size_traits() const
+ { return data_.node_plus_pred_.header_plus_size_; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<false>) const
+ { return data_; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<true>) const
+ { return data_.get_value_traits(*this); }
+
+ real_value_traits &get_real_value_traits(detail::bool_<false>)
+ { return data_; }
+
+ real_value_traits &get_real_value_traits(detail::bool_<true>)
+ { return data_.get_value_traits(*this); }
+
/// @endcond
public:
+
+ const real_value_traits &get_real_value_traits() const
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
+ real_value_traits &get_real_value_traits()
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
typedef typename node_algorithms::insert_commit_data insert_commit_data;
//! <b>Effects</b>: Constructs an empty tree.
//!
//! <b>Complexity</b>: Constant.
//!
- //! <b>Throws</b>: Nothing unless the copy constructor of the Compare object throws.
- rbtree(Compare cmp = Compare())
- : members_(cmp)
+ //! <b>Throws</b>: Nothing unless the copy constructor of the value_compare object throws.
+ rbtree_impl( value_compare cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : data_(cmp, v_traits)
{
node_algorithms::init_header(&priv_header());
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
}
- //! <b>Requires</b>: Dereferencing iterator must yield an lvalue of type value_type.
+ //! <b>Requires</b>: Dereferencing iterator must yield an lvalue of type value_type.
//! cmp must be a comparison function that induces a strict weak ordering.
- //!
- //! <b>Effects</b>: Constructs an empty tree and inserts elements from
+ //!
+ //! <b>Effects</b>: Constructs an empty tree and inserts elements from
//! [b, e).
- //!
- //! <b>Complexity</b>: Linear in N if [b, e) is already sorted using
+ //!
+ //! <b>Complexity</b>: Linear in N if [b, e) is already sorted using
//! comp and otherwise N * log N, where N is last first.
//!
- //! <b>Throws</b>: Nothing unless the copy constructor of the Compare object throws.
+ //! <b>Throws</b>: Nothing unless the copy constructor of the value_compare object throws.
template<class Iterator>
- rbtree(bool unique, Iterator b, Iterator e, Compare cmp = Compare())
- : members_(cmp)
+ rbtree_impl( bool unique, Iterator b, Iterator e
+ , value_compare cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : data_(cmp, v_traits)
{
node_algorithms::init_header(&priv_header());
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
if(unique)
this->insert_unique(b, e);
else
@@ -148,12 +253,12 @@
//! <b>Effects</b>: Detaches all elements from this. The objects in the set
//! are not deleted (i.e. no destructors are called), but the nodes according to
- //! the ValueTraits template parameter are reinitialized and thus can be reused.
+ //! the value_traits template parameter are reinitialized and thus can be reused.
//!
//! <b>Complexity</b>: Linear to elements contained in *this.
//!
//! <b>Throws</b>: Nothing.
- ~rbtree()
+ ~rbtree_impl()
{ this->clear(); }
//! <b>Effects</b>: Returns an iterator pointing to the beginning of the tree.
@@ -162,7 +267,7 @@
//!
//! <b>Throws</b>: Nothing.
iterator begin()
- { return iterator (node_traits::get_left(node_ptr(&priv_header()))); }
+ { return iterator (node_traits::get_left(node_ptr(&priv_header())), this); }
//! <b>Effects</b>: Returns a const_iterator pointing to the beginning of the tree.
//!
@@ -178,7 +283,7 @@
//!
//! <b>Throws</b>: Nothing.
const_iterator cbegin() const
- { return const_iterator (node_traits::get_left(const_node_ptr(&priv_header()))); }
+ { return const_iterator (node_traits::get_left(const_node_ptr(&priv_header())), this); }
//! <b>Effects</b>: Returns an iterator pointing to the end of the tree.
//!
@@ -186,10 +291,10 @@
//!
//! <b>Throws</b>: Nothing.
iterator end()
- { return iterator (node_ptr(&priv_header())); }
+ { return iterator (node_ptr(&priv_header()), this); }
//! <b>Effects</b>: Returns a const_iterator pointing to the end of the tree.
- //!
+ //!
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
@@ -202,7 +307,7 @@
//!
//! <b>Throws</b>: Nothing.
const_iterator cend() const
- { return const_iterator (uncast(const_node_ptr(&priv_header()))); }
+ { return const_iterator (uncast(const_node_ptr(&priv_header())), this); }
//! <b>Effects</b>: Returns a reverse_iterator pointing to the beginning of the
//! reversed tree.
@@ -266,12 +371,8 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static rbtree &container_from_end_iterator(iterator end_iterator)
- {
- return *detail::parent_from_member<rbtree, members_t>
- ( members_t::this_from_node(detail::get_pointer(end_iterator.pointed_node()))
- , &rbtree::members_);
- }
+ static rbtree_impl &container_from_end_iterator(iterator end_iterator)
+ { return priv_container_from_end_iterator(end_iterator); }
//! <b>Precondition</b>: end_iterator must be a valid end const_iterator
//! of rbtree.
@@ -281,12 +382,8 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static const rbtree &container_from_end_iterator(const_iterator end_iterator)
- {
- return *detail::parent_from_member<rbtree, members_t>
- ( members_t::this_from_node(detail::get_pointer(end_iterator.pointed_node()))
- , &rbtree::members_);
- }
+ static const rbtree_impl &container_from_end_iterator(const_iterator end_iterator)
+ { return priv_container_from_end_iterator(end_iterator); }
//! <b>Effects</b>: Returns the value_compare object used by the tree.
//!
@@ -311,8 +408,8 @@
//! <b>Throws</b>: Nothing.
size_type size() const
{
- if(ConstantTimeSize)
- return size_traits::get_size();
+ if(constant_time_size)
+ return this->priv_size_traits().get_size();
else
return empty() ? 0 : node_algorithms::count(node_traits::get_parent(const_node_ptr(&priv_header())));
}
@@ -321,18 +418,18 @@
//!
//! <b>Complexity</b>: Constant.
//!
- //! <b>Throws</b>: If the comparison functor's unspecified swap call throws.
- void swap(rbtree& other)
+ //! <b>Throws</b>: If the comparison functor's none swap call throws.
+ void swap(rbtree_impl& other)
{
//This can throw
using std::swap;
swap(priv_comp(), priv_comp());
//These can't throw
node_algorithms::swap_tree(node_ptr(&priv_header()), node_ptr(&other.priv_header()));
- if(ConstantTimeSize){
- size_type backup = size_traits::get_size();
- size_traits::set_size(other.get_size());
- other.set_size(backup);
+ if(constant_time_size){
+ size_type backup = this->priv_size_traits().get_size();
+ this->priv_size_traits().set_size(other.priv_size_traits().get_size());
+ other.priv_size_traits().set_size(backup);
}
}
@@ -349,13 +446,14 @@
//! No copy-constructors are called.
iterator insert_equal_upper_bound(reference value)
{
- detail::key_node_ptr_compare<value_compare, ValueTraits> key_node_comp(priv_comp());
- node_ptr to_insert(ValueTraits::to_node_ptr(value));
+ detail::key_nodeptr_comp<value_compare, rbtree_impl>
+ key_node_comp(priv_comp(), this);
+ node_ptr to_insert(get_real_value_traits().to_node_ptr(value));
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
- size_traits::increment();
+ this->priv_size_traits().increment();
return iterator(node_algorithms::insert_equal_upper_bound
- (node_ptr(&priv_header()), to_insert, key_node_comp));
+ (node_ptr(&priv_header()), to_insert, key_node_comp), this);
}
//! <b>Requires</b>: value must be an lvalue
@@ -371,13 +469,14 @@
//! No copy-constructors are called.
iterator insert_equal_lower_bound(reference value)
{
- detail::key_node_ptr_compare<value_compare, ValueTraits> key_node_comp(priv_comp());
- node_ptr to_insert(ValueTraits::to_node_ptr(value));
+ detail::key_nodeptr_comp<value_compare, rbtree_impl>
+ key_node_comp(priv_comp(), this);
+ node_ptr to_insert(get_real_value_traits().to_node_ptr(value));
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
- size_traits::increment();
+ this->priv_size_traits().increment();
return iterator(node_algorithms::insert_equal_lower_bound
- (node_ptr(&priv_header()), to_insert, key_node_comp));
+ (node_ptr(&priv_header()), to_insert, key_node_comp), this);
}
//! <b>Requires</b>: value must be an lvalue, and "hint" must be
@@ -396,13 +495,14 @@
//! No copy-constructors are called.
iterator insert_equal(const_iterator hint, reference value)
{
- detail::key_node_ptr_compare<value_compare, ValueTraits> key_node_comp(priv_comp());
- node_ptr to_insert(ValueTraits::to_node_ptr(value));
+ detail::key_nodeptr_comp<value_compare, rbtree_impl>
+ key_node_comp(priv_comp(), this);
+ node_ptr to_insert(get_real_value_traits().to_node_ptr(value));
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
- size_traits::increment();
+ this->priv_size_traits().increment();
return iterator(node_algorithms::insert_equal
- (node_ptr(&priv_header()), hint.pointed_node(), to_insert, key_node_comp));
+ (node_ptr(&priv_header()), hint.pointed_node(), to_insert, key_node_comp), this);
}
//! <b>Requires</b>: Dereferencing iterator must yield an lvalue
@@ -411,8 +511,8 @@
//! <b>Effects</b>: Inserts a each element of a range into the tree
//! before the upper bound of the key of each element.
//!
- //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
- //! size of the range. However, it is linear in N if the range is already sorted
+ //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
+ //! size of the range. However, it is linear in N if the range is already sorted
//! by value_comp().
//!
//! <b>Throws</b>: Nothing.
@@ -512,11 +612,12 @@
std::pair<iterator, bool> insert_unique_check
(const KeyType &key, KeyValueCompare key_value_comp, insert_commit_data &commit_data)
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> comp(key_value_comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ comp(key_value_comp, this);
std::pair<node_ptr, bool> ret =
(node_algorithms::insert_unique_check
(node_ptr(&priv_header()), key, comp, commit_data));
- return std::pair<iterator, bool>(iterator(ret.first), ret.second);
+ return std::pair<iterator, bool>(iterator(ret.first, this), ret.second);
}
std::pair<iterator, bool> insert_unique_check
@@ -528,22 +629,23 @@
(const_iterator hint, const KeyType &key
,KeyValueCompare key_value_comp, insert_commit_data &commit_data)
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> comp(key_value_comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ comp(key_value_comp, this);
std::pair<node_ptr, bool> ret =
(node_algorithms::insert_unique_check
(node_ptr(&priv_header()), hint.pointed_node(), key, comp, commit_data));
- return std::pair<iterator, bool>(iterator(ret.first), ret.second);
+ return std::pair<iterator, bool>(iterator(ret.first, this), ret.second);
}
iterator insert_unique_commit(reference value, const insert_commit_data &commit_data)
{
- node_ptr to_insert(ValueTraits::to_node_ptr(value));
+ node_ptr to_insert(get_real_value_traits().to_node_ptr(value));
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
- size_traits::increment();
+ this->priv_size_traits().increment();
node_algorithms::insert_unique_commit
(node_ptr(&priv_header()), to_insert, commit_data);
- return iterator(to_insert);
+ return iterator(to_insert, this);
}
//! <b>Effects</b>: Erases the element pointed to by pos.
@@ -562,7 +664,7 @@
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(!node_algorithms::unique(to_erase));
node_algorithms::erase(&priv_header(), to_erase);
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
return ret;
@@ -629,7 +731,7 @@
{
node_ptr to_erase(i.pointed_node());
iterator ret(this->erase(i));
- disposer(ValueTraits::to_value_ptr(to_erase));
+ disposer(get_real_value_traits().to_value_ptr(to_erase));
return ret;
}
@@ -706,20 +808,11 @@
void clear()
{
if(safemode_or_autounlink){
- while(1){
- node_ptr leftmost
- (node_algorithms::unlink_leftmost_without_rebalance
- (node_ptr(&priv_header())));
- if(!leftmost)
- break;
- size_traits::decrement();
- if(safemode_or_autounlink)
- node_algorithms::init(leftmost);
- }
+ this->clear_and_dispose(detail::null_disposer());
}
else{
node_algorithms::init_header(&priv_header());
- size_traits::set_size(0);
+ this->priv_size_traits().set_size(0);
}
}
@@ -735,17 +828,10 @@
template<class Disposer>
void clear_and_dispose(Disposer disposer)
{
- while(1){
- node_ptr leftmost
- (node_algorithms::unlink_leftmost_without_rebalance
- (node_ptr(&priv_header())));
- if(!leftmost)
- break;
- size_traits::decrement();
- if(safemode_or_autounlink)
- node_algorithms::init(leftmost);
- disposer(ValueTraits::to_value_ptr(leftmost));
- }
+ node_algorithms::clear_and_dispose(node_ptr(&priv_header())
+ , detail::node_disposer<Disposer, rbtree_impl>(disposer, this));
+ node_algorithms::init_header(&priv_header());
+ this->priv_size_traits().set_size(0);
}
//! <b>Effects</b>: Returns the number of contained elements with the given value
@@ -797,9 +883,10 @@
template<class KeyType, class KeyValueCompare>
iterator lower_bound(const KeyType &key, KeyValueCompare comp)
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
return iterator(node_algorithms::lower_bound
- (const_node_ptr(&priv_header()), key, key_node_comp));
+ (const_node_ptr(&priv_header()), key, key_node_comp), this);
}
//! <b>Effects</b>: Returns a const iterator to the first element whose
@@ -811,9 +898,10 @@
template<class KeyType, class KeyValueCompare>
const_iterator lower_bound(const KeyType &key, KeyValueCompare comp) const
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
return const_iterator(node_algorithms::lower_bound
- (const_node_ptr(&priv_header()), key, key_node_comp));
+ (const_node_ptr(&priv_header()), key, key_node_comp), this);
}
//! <b>Effects</b>: Returns an iterator to the first element whose
@@ -835,9 +923,10 @@
template<class KeyType, class KeyValueCompare>
iterator upper_bound(const KeyType &key, KeyValueCompare comp)
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
return iterator(node_algorithms::upper_bound
- (const_node_ptr(&priv_header()), key, key_node_comp));
+ (const_node_ptr(&priv_header()), key, key_node_comp), this);
}
//! <b>Effects</b>: Returns an iterator to the first element whose
@@ -859,9 +948,10 @@
template<class KeyType, class KeyValueCompare>
const_iterator upper_bound(const KeyType &key, KeyValueCompare comp) const
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
return const_iterator(node_algorithms::upper_bound
- (const_node_ptr(&priv_header()), key, key_node_comp));
+ (const_node_ptr(&priv_header()), key, key_node_comp), this);
}
//! <b>Effects</b>: Finds an iterator to the first element whose key is
@@ -882,9 +972,10 @@
template<class KeyType, class KeyValueCompare>
iterator find(const KeyType &key, KeyValueCompare comp)
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
return iterator
- (node_algorithms::find(const_node_ptr(&priv_header()), key, key_node_comp));
+ (node_algorithms::find(const_node_ptr(&priv_header()), key, key_node_comp), this);
}
//! <b>Effects</b>: Finds a const_iterator to the first element whose key is
@@ -905,9 +996,10 @@
template<class KeyType, class KeyValueCompare>
const_iterator find(const KeyType &key, KeyValueCompare comp) const
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
return const_iterator
- (node_algorithms::find(const_node_ptr(&priv_header()), key, key_node_comp));
+ (node_algorithms::find(const_node_ptr(&priv_header()), key, key_node_comp), this);
}
//! <b>Effects</b>: Finds a range containing all elements whose key is k or
@@ -930,10 +1022,11 @@
template<class KeyType, class KeyValueCompare>
std::pair<iterator,iterator> equal_range(const KeyType &key, KeyValueCompare comp)
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
std::pair<node_ptr, node_ptr> ret
(node_algorithms::equal_range(const_node_ptr(&priv_header()), key, key_node_comp));
- return std::pair<iterator, iterator>(iterator(ret.first), iterator(ret.second));
+ return std::pair<iterator, iterator>(iterator(ret.first, this), iterator(ret.second, this));
}
//! <b>Effects</b>: Finds a range containing all elements whose key is k or
@@ -958,23 +1051,24 @@
std::pair<const_iterator, const_iterator>
equal_range(const KeyType &key, KeyValueCompare comp) const
{
- detail::key_node_ptr_compare<KeyValueCompare, ValueTraits> key_node_comp(comp);
+ detail::key_nodeptr_comp<KeyValueCompare, rbtree_impl>
+ key_node_comp(comp, this);
std::pair<node_ptr, node_ptr> ret
(node_algorithms::equal_range(const_node_ptr(&priv_header()), key, key_node_comp));
- return std::pair<const_iterator, const_iterator>(const_iterator(ret.first), const_iterator(ret.second));
+ return std::pair<const_iterator, const_iterator>(const_iterator(ret.first, this), const_iterator(ret.second, this));
}
template <class Cloner, class Disposer>
- void clone_from(const rbtree &src, Cloner cloner, Disposer disposer)
+ void clone_from(const rbtree_impl &src, Cloner cloner, Disposer disposer)
{
this->clear_and_dispose(disposer);
if(!src.empty()){
- node_algorithms::clone_tree
+ node_algorithms::clone
(const_node_ptr(&src.priv_header())
,node_ptr(&this->priv_header())
- ,detail::value_to_node_cloner<Cloner, ValueTraits>(cloner)
- ,detail::value_to_node_disposer<Disposer, ValueTraits>(disposer));
- size_traits::set_size(src.get_size());
+ ,detail::node_cloner<Cloner, rbtree_impl>(cloner, this)
+ ,detail::node_disposer<Disposer, rbtree_impl>(disposer, this));
+ this->priv_size_traits().set_size(src.priv_size_traits().get_size());
}
}
@@ -984,10 +1078,31 @@
(node_ptr(&priv_header())));
if(!to_be_disposed)
return 0;
- size_traits::decrement();
- if(safemode_or_autounlink)
+ this->priv_size_traits().decrement();
+ if(safemode_or_autounlink)//If this is commented does not work with normal_link
node_algorithms::init(to_be_disposed);
- return ValueTraits::to_value_ptr(to_be_disposed);
+ return get_real_value_traits().to_value_ptr(to_be_disposed);
+ }
+
+ //! <b>Requires</b>: replace_this must be a valid iterator of *this
+ //! and with_this must not be inserted in any tree.
+ //!
+ //! <b>Effects</b>: Replaces replace_this in its position in the
+ //! tree with with_this. The tree does not need to be rebalanced.
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! with_this is not equivalent to *replace_this according to the
+ //! ordering rules. This function is faster than erasing and inserting
+ //! the node, since no rebalancing or comparison is needed.
+ void replace_node(iterator replace_this, reference with_this)
+ {
+ node_algorithms::replace_node( get_real_value_traits().to_node_ptr(*replace_this)
+ , node_ptr(&priv_header())
+ , get_real_value_traits().to_node_ptr(with_this));
}
//! <b>Requires</b>: value must be an lvalue and shall be in a set of
@@ -999,8 +1114,14 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static iterator iterator_to(reference value)
- { return iterator (ValueTraits::to_node_ptr(value)); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static iterator s_iterator_to(reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ return iterator (value_traits::to_node_ptr(value), 0);
+ }
//! <b>Requires</b>: value must be an lvalue and shall be in a set of
//! appropriate type. Otherwise the behavior is undefined.
@@ -1010,26 +1131,55 @@
//!
//! <b>Complexity</b>: Constant.
//!
+ //! <b>Throws</b>: Nothing.ç
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_iterator s_iterator_to(const_reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ return const_iterator (value_traits::to_node_ptr(const_cast<reference> (value)), 0);
+ }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid iterator i belonging to the set
+ //! that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
//! <b>Throws</b>: Nothing.
- static const_iterator iterator_to(const_reference value)
- { return const_iterator (ValueTraits::to_node_ptr(const_cast<reference> (value))); }
-/*
- //! <b>Requires</b>: value shall not be in a tree of the appropriate type.
+ iterator iterator_to(reference value)
+ { return iterator (value_traits::to_node_ptr(value), this); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a set of
+ //! appropriate type. Otherwise the behavior is undefined.
//!
- //! <b>Effects</b>: init_node post-constructs the node data in x used by multisets of
- //! the appropriate type. For the accessors multiset_derived_node and multiset_member_node
- //! init_node has no effect, since the constructors of multiset_node_d and multiset_node_m
- //! have already initialized the node data.
+ //! <b>Effects</b>: Returns: a valid const_iterator i belonging to the
+ //! set that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ const_iterator iterator_to(const_reference value) const
+ { return const_iterator (value_traits::to_node_ptr(const_cast<reference> (value)), this); }
+
+ //! <b>Requires</b>: value shall not be in a tree.
+ //!
+ //! <b>Effects</b>: init_node puts the hook of a value in a well-known default
+ //! state.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant time.
//!
- //! <b>Note</b>: This function is meant to be used mainly with the member value_traits,
- //! where no implicit node initialization during construction occurs.
+ //! <b>Note</b>: This function puts the hook in the well-known default state
+ //! used by auto_unlink and safe hooks.
static void init_node(reference value)
- { node_algorithms::init(node_ptr(&*ValueTraits::to_node_ptr(value))); }
+ { node_algorithms::init(value_traits::to_node_ptr(value)); }
+/*
//! <b>Effects</b>: removes x from a tree of the appropriate type. It has no effect,
//! if x is not in such a tree.
//!
@@ -1047,15 +1197,16 @@
{
//This function is only usable for safe mode hooks and non-constant
//time lists.
- //BOOST_STATIC_ASSERT((!(safemode_or_autounlink && ConstantTimeSize)));
- BOOST_STATIC_ASSERT((!ConstantTimeSize));
+ //BOOST_STATIC_ASSERT((!(safemode_or_autounlink && constant_time_size)));
+ BOOST_STATIC_ASSERT((!constant_time_size));
BOOST_STATIC_ASSERT((boost::is_convertible<T, value_type>::value));
- node_ptr to_remove(ValueTraits::to_node_ptr(value));
+ node_ptr to_remove(value_traits::to_node_ptr(value));
node_algorithms::unlink_and_rebalance(to_remove);
if(safemode_or_autounlink)
node_algorithms::init(to_remove);
}
*/
+
/// @cond
private:
template<class Disposer>
@@ -1073,20 +1224,55 @@
return b;
}
/// @endcond
+
+ private:
+ static rbtree_impl &priv_container_from_end_iterator(const const_iterator &end_iterator)
+ {
+ header_plus_size *r = detail::parent_from_member<header_plus_size, node>
+ ( detail::get_pointer(end_iterator.pointed_node()), &header_plus_size::header_);
+ node_plus_pred_t *n = detail::parent_from_member
+ <node_plus_pred_t, header_plus_size>(r, &node_plus_pred_t::header_plus_size_);
+ data_t *d = detail::parent_from_member<data_t, node_plus_pred_t>(n, &data_t::node_plus_pred_);
+ rbtree_impl *rb = detail::parent_from_member<rbtree_impl, data_t>(d, &rbtree_impl::data_);
+ return *rb;
+ }
};
-template <class V, class P, bool C, class S>
-inline bool operator==(const rbtree<V, P, C, S>& x, const rbtree<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const rbtree_impl<T, Options...> &x, const rbtree_impl<T, Options...> &y)
+#else
+(const rbtree_impl<Config> &x, const rbtree_impl<Config> &y)
+#endif
+{ return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+bool operator==
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const rbtree_impl<T, Options...> &x, const rbtree_impl<T, Options...> &y)
+#else
+(const rbtree_impl<Config> &x, const rbtree_impl<Config> &y)
+#endif
{
- if(C && x.size() != y.size()){
+ typedef rbtree_impl<Config> tree_type;
+ typedef typename tree_type::const_iterator const_iterator;
+ const bool CS = tree_type::constant_time_size;
+ if(CS && x.size() != y.size()){
return false;
}
- typedef typename rbtree<V, P, C, S>::const_iterator const_iterator;
const_iterator end1 = x.end();
-
const_iterator i1 = x.begin();
const_iterator i2 = y.begin();
- if(C){
+ if(CS){
while (i1 != end1 && *i1 == *i2) {
++i1;
++i2;
@@ -1103,31 +1289,151 @@
}
}
-template <class V, class P, bool C, class S>
-inline bool operator<(const rbtree<V, P, C, S>& x,
- const rbtree<V, P, C, S>& y)
-{ return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); }
-
-template <class V, class P, bool C, class S>
-inline bool operator!=(const rbtree<V, P, C, S>& x, const rbtree<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator!=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const rbtree_impl<T, Options...> &x, const rbtree_impl<T, Options...> &y)
+#else
+(const rbtree_impl<Config> &x, const rbtree_impl<Config> &y)
+#endif
{ return !(x == y); }
-template <class V, class P, bool C, class S>
-inline bool operator>(const rbtree<V, P, C, S>& x, const rbtree<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const rbtree_impl<T, Options...> &x, const rbtree_impl<T, Options...> &y)
+#else
+(const rbtree_impl<Config> &x, const rbtree_impl<Config> &y)
+#endif
{ return y < x; }
-template <class V, class P, bool C, class S>
-inline bool operator<=(const rbtree<V, P, C, S>& x, const rbtree<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const rbtree_impl<T, Options...> &x, const rbtree_impl<T, Options...> &y)
+#else
+(const rbtree_impl<Config> &x, const rbtree_impl<Config> &y)
+#endif
{ return !(y < x); }
-template <class V, class P, bool C, class S>
-inline bool operator>=(const rbtree<V, P, C, S>& x, const rbtree<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const rbtree_impl<T, Options...> &x, const rbtree_impl<T, Options...> &y)
+#else
+(const rbtree_impl<Config> &x, const rbtree_impl<Config> &y)
+#endif
{ return !(x < y); }
-template <class V, class P, bool C, class S>
-inline void swap(rbtree<V, P, C, S>& x, rbtree<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline void swap
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(rbtree_impl<T, Options...> &x, rbtree_impl<T, Options...> &y)
+#else
+(rbtree_impl<Config> &x, rbtree_impl<Config> &y)
+#endif
{ x.swap(y); }
+/// @cond
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none
+ , class O5 = none, class O6 = none
+ , class O7 = none
+ >
+struct make_rbtree_opt
+{
+ typedef typename pack_options
+ < set_defaults<T>, O1, O2, O3, O4>::type packed_options;
+ typedef typename detail::get_value_traits
+ <T, typename packed_options::value_traits>::type value_traits;
+
+ typedef setopt
+ < value_traits
+ , typename packed_options::compare
+ , typename packed_options::size_type
+ , packed_options::constant_time_size
+ > type;
+};
+/// @endcond
+
+//! Helper metafunction to define a \c rbtree that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none>
+#endif
+struct make_rbtree
+{
+ /// @cond
+ typedef rbtree_impl
+ < typename make_rbtree_opt<T, O1, O2, O3, O4>::type
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3, class O4>
+class rbtree
+ : public make_rbtree<T, O1, O2, O3, O4>::type
+{
+ typedef typename make_rbtree
+ <T, O1, O2, O3, O4>::type Base;
+
+ public:
+ typedef typename Base::value_compare value_compare;
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::real_value_traits real_value_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename real_value_traits::value_type, T>::value));
+
+ rbtree( const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : Base(cmp, v_traits)
+ {}
+
+ template<class Iterator>
+ rbtree( bool unique, Iterator b, Iterator e
+ , const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : Base(unique, b, e, cmp, v_traits)
+ {}
+
+ static rbtree &container_from_end_iterator(iterator end_iterator)
+ { return static_cast<rbtree &>(Base::container_from_end_iterator(end_iterator)); }
+
+ static const rbtree &container_from_end_iterator(const_iterator end_iterator)
+ { return static_cast<const rbtree &>(Base::container_from_end_iterator(end_iterator)); }
+};
+
+#endif
+
+
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/rbtree_algorithms.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/rbtree_algorithms.hpp (original)
+++ branches/bcbboost/boost/intrusive/rbtree_algorithms.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -35,6 +35,15 @@
// in supporting documentation. Hewlett-Packard Company makes no
// representations about the suitability of this software for any
// purpose. It is provided "as is" without express or implied warranty.
+//
+// The tree destruction algorithm is based on Julienne Walker and The EC Team code:
+//
+// This code is in the public domain. Anyone may use it or change it in any way that
+// they see fit. The author assumes no responsibility for damages incurred through
+// use of the original code or any variations thereof.
+//
+// It is requested, but not required, that due credit is given to the original author
+// and anyone who has modified the code through a header comment, such as this one.
#ifndef BOOST_INTRUSIVE_RBTREE_ALGORITHMS_HPP
#define BOOST_INTRUSIVE_RBTREE_ALGORITHMS_HPP
@@ -43,9 +52,7 @@
#include <boost/intrusive/detail/assert.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
#include <cstddef>
-#ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
-#include <boost/detail/no_exceptions_support.hpp>
-#endif
+#include <boost/intrusive/detail/no_exceptions_support.hpp>
#include <boost/intrusive/detail/utilities.hpp>
@@ -67,7 +74,7 @@
//! relinked into its place, rather than copied, so that the only
//! pointers invalidated are those referring to the deleted node.
//!
-//! rbtree_algorithms is configured with a NodeTraits class, which capsulates the
+//! rbtree_algorithms is configured with a NodeTraits class, which encapsulates the
//! information about the node to be manipulated. NodeTraits must support the
//! following interface:
//!
@@ -111,6 +118,7 @@
/// @endcond
public:
+ typedef NodeTraits node_traits;
typedef typename NodeTraits::node_ptr node_ptr;
typedef typename NodeTraits::const_node_ptr const_node_ptr;
typedef typename NodeTraits::color color;
@@ -121,6 +129,27 @@
{
return node_ptr(const_cast<node*>(::boost::intrusive::detail::get_pointer(ptr)));
}
+
+ static void swap_left(node_ptr this_node, node_ptr other_node)
+ {
+ node_ptr temp(NodeTraits::get_left(this_node));
+ NodeTraits::set_left(this_node, NodeTraits::get_left(other_node));
+ NodeTraits::set_left(other_node, temp);
+ }
+
+ static void swap_right(node_ptr this_node, node_ptr other_node)
+ {
+ node_ptr temp(NodeTraits::get_right(this_node));
+ NodeTraits::set_right(this_node, NodeTraits::get_right(other_node));
+ NodeTraits::set_right(other_node, temp);
+ }
+
+ static void swap_parent(node_ptr this_node, node_ptr other_node)
+ {
+ node_ptr temp(NodeTraits::get_parent(this_node));
+ NodeTraits::set_parent(this_node, NodeTraits::get_parent(other_node));
+ NodeTraits::set_parent(other_node, temp);
+ }
/// @endcond
public:
@@ -146,7 +175,14 @@
//!
//! <b>Throws</b>: Nothing.
static void swap_tree(node_ptr header1, node_ptr header2)
- {
+ {/*
+ if(NodeTraits::get_parent(header1)){
+ NodeTraits::node n1;
+ node_ptr n2(NodeTraits::get_parent(header1));
+ init(&n1);
+ swap_nodes(&n1, n2);
+ swap_nodes(&n1, n2);
+ }*/
if(header1 == header2)
return;
@@ -185,6 +221,276 @@
}
}
+ static node_ptr get_header(const_node_ptr node)
+ {
+ node_ptr h = uncast(node);
+ if(NodeTraits::get_parent(node)){
+ h = NodeTraits::get_parent(node);
+ while(!is_header(h))
+ h = NodeTraits::get_parent(h);
+ }
+ return h;
+ }
+
+ //! <b>Requires</b>: node1 and node2 can't be header nodes
+ //! of two trees.
+ //!
+ //! <b>Effects</b>: Swaps two nodes. After the function node1 will be inserted
+ //! in the position node2 before the function. node2 will be inserted in the
+ //! position node1 had before the function.
+ //!
+ //! <b>Complexity</b>: Logarithmic.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! node1 and node2 are not equivalent according to the ordering rules.
+ //!
+ //!Experimental function
+ static void swap_nodes(node_ptr node1, node_ptr node2)
+ {
+ if(node1 == node2)
+ return;
+
+ node_ptr header1(get_header(node1)), header2(get_header(node2));
+ swap_nodes(node1, header1, node2, header2);
+ }
+
+ //! <b>Requires</b>: node1 and node2 can't be header nodes
+ //! of two trees with header header1 and header2.
+ //!
+ //! <b>Effects</b>: Swaps two nodes. After the function node1 will be inserted
+ //! in the position node2 before the function. node2 will be inserted in the
+ //! position node1 had before the function.
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! node1 and node2 are not equivalent according to the ordering rules.
+ //!
+ //!Experimental function
+ static void swap_nodes(node_ptr node1, node_ptr header1, node_ptr node2, node_ptr header2)
+ {
+ if(node1 == node2)
+ return;
+
+ //node1 and node2 must not be header nodes
+ //BOOST_INTRUSIVE_INVARIANT_ASSERT((header1 != node1 && header2 != node2));
+ if(header1 != header2){
+ //Update header1 if necessary
+ if(node1 == NodeTraits::get_left(header1)){
+ NodeTraits::set_left(header1, node2);
+ }
+
+ if(node1 == NodeTraits::get_right(header1)){
+ NodeTraits::set_right(header1, node2);
+ }
+
+ if(node1 == NodeTraits::get_parent(header1)){
+ NodeTraits::set_parent(header1, node2);
+ }
+
+ //Update header2 if necessary
+ if(node2 == NodeTraits::get_left(header2)){
+ NodeTraits::set_left(header2, node1);
+ }
+
+ if(node2 == NodeTraits::get_right(header2)){
+ NodeTraits::set_right(header2, node1);
+ }
+
+ if(node2 == NodeTraits::get_parent(header2)){
+ NodeTraits::set_parent(header2, node1);
+ }
+ }
+ else{
+ //If both nodes are from the same tree
+ //Update header if necessary
+ if(node1 == NodeTraits::get_left(header1)){
+ NodeTraits::set_left(header1, node2);
+ }
+ else if(node2 == NodeTraits::get_left(header2)){
+ NodeTraits::set_left(header2, node1);
+ }
+
+ if(node1 == NodeTraits::get_right(header1)){
+ NodeTraits::set_right(header1, node2);
+ }
+ else if(node2 == NodeTraits::get_right(header2)){
+ NodeTraits::set_right(header2, node1);
+ }
+
+ if(node1 == NodeTraits::get_parent(header1)){
+ NodeTraits::set_parent(header1, node2);
+ }
+ else if(node2 == NodeTraits::get_parent(header2)){
+ NodeTraits::set_parent(header2, node1);
+ }
+
+ //Adjust data in nodes to be swapped
+ //so that final link swap works as expected
+ if(node1 == NodeTraits::get_parent(node2)){
+ NodeTraits::set_parent(node2, node2);
+
+ if(node2 == NodeTraits::get_right(node1)){
+ NodeTraits::set_right(node1, node1);
+ }
+ else{
+ NodeTraits::set_left(node1, node1);
+ }
+ }
+ else if(node2 == NodeTraits::get_parent(node1)){
+ NodeTraits::set_parent(node1, node1);
+
+ if(node1 == NodeTraits::get_right(node2)){
+ NodeTraits::set_right(node2, node2);
+ }
+ else{
+ NodeTraits::set_left(node2, node2);
+ }
+ }
+ }
+
+ //Now swap all the links
+ node_ptr temp;
+ //swap left link
+ temp = NodeTraits::get_left(node1);
+ NodeTraits::set_left(node1, NodeTraits::get_left(node2));
+ NodeTraits::set_left(node2, temp);
+ //swap right link
+ temp = NodeTraits::get_right(node1);
+ NodeTraits::set_right(node1, NodeTraits::get_right(node2));
+ NodeTraits::set_right(node2, temp);
+ //swap parent link
+ temp = NodeTraits::get_parent(node1);
+ NodeTraits::set_parent(node1, NodeTraits::get_parent(node2));
+ NodeTraits::set_parent(node2, temp);
+ //Swap color
+ color c = NodeTraits::get_color(node1);
+ NodeTraits::set_color(node1, NodeTraits::get_color(node2));
+ NodeTraits::set_color(node2, c);
+
+ //Now adjust adjacent nodes for newly inserted node 1
+ if((temp = NodeTraits::get_left(node1))){
+ NodeTraits::set_parent(temp, node1);
+ }
+ if((temp = NodeTraits::get_right(node1))){
+ NodeTraits::set_parent(temp, node1);
+ }
+ if((temp = NodeTraits::get_parent(node1)) &&
+ //The header has been already updated so avoid it
+ temp != header2){
+ if(NodeTraits::get_left(temp) == node2){
+ NodeTraits::set_left(temp, node1);
+ }
+ if(NodeTraits::get_right(temp) == node2){
+ NodeTraits::set_right(temp, node1);
+ }
+ }
+ //Now adjust adjacent nodes for newly inserted node 2
+ if((temp = NodeTraits::get_left(node2))){
+ NodeTraits::set_parent(temp, node2);
+ }
+ if((temp = NodeTraits::get_right(node2))){
+ NodeTraits::set_parent(temp, node2);
+ }
+ if((temp = NodeTraits::get_parent(node2)) &&
+ //The header has been already updated so avoid it
+ temp != header1){
+ if(NodeTraits::get_left(temp) == node1){
+ NodeTraits::set_left(temp, node2);
+ }
+ if(NodeTraits::get_right(temp) == node1){
+ NodeTraits::set_right(temp, node2);
+ }
+ }
+ }
+
+ //! <b>Requires</b>: node_to_be_replaced must be inserted in a tree
+ //! and new_node must not be inserted in a tree.
+ //!
+ //! <b>Effects</b>: Replaces node_to_be_replaced in its position in the
+ //! tree with new_node. The tree does not need to be rebalanced
+ //!
+ //! <b>Complexity</b>: Logarithmic.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! new_node is not equivalent to node_to_be_replaced according to the
+ //! ordering rules. This function is faster than erasing and inserting
+ //! the node, since no rebalancing and comparison is needed.
+ //!
+ //!Experimental function
+ static void replace_node(node_ptr node_to_be_replaced, node_ptr new_node)
+ {
+ if(node_to_be_replaced == new_node)
+ return;
+ replace_node(node_to_be_replaced, get_header(node_to_be_replaced), new_node);
+ }
+
+ //! <b>Requires</b>: node_to_be_replaced must be inserted in a tree
+ //! with header "header" and new_node must not be inserted in a tree.
+ //!
+ //! <b>Effects</b>: Replaces node_to_be_replaced in its position in the
+ //! tree with new_node. The tree does not need to be rebalanced
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! new_node is not equivalent to node_to_be_replaced according to the
+ //! ordering rules. This function is faster than erasing and inserting
+ //! the node, since no rebalancing or comparison is needed.
+ //!
+ //!Experimental function
+ static void replace_node(node_ptr node_to_be_replaced, node_ptr header, node_ptr new_node)
+ {
+ if(node_to_be_replaced == new_node)
+ return;
+
+ //Update header if necessary
+ if(node_to_be_replaced == NodeTraits::get_left(header)){
+ NodeTraits::set_left(header, new_node);
+ }
+
+ if(node_to_be_replaced == NodeTraits::get_right(header)){
+ NodeTraits::set_right(header, new_node);
+ }
+
+ if(node_to_be_replaced == NodeTraits::get_parent(header)){
+ NodeTraits::set_parent(header, new_node);
+ }
+
+ //Now set data from the original node
+ node_ptr temp;
+ NodeTraits::set_left(new_node, NodeTraits::get_left(node_to_be_replaced));
+ NodeTraits::set_right(new_node, NodeTraits::get_right(node_to_be_replaced));
+ NodeTraits::set_parent(new_node, NodeTraits::get_parent(node_to_be_replaced));
+ NodeTraits::set_color(new_node, NodeTraits::get_color(node_to_be_replaced));
+
+ //Now adjust adjacent nodes for newly inserted node
+ if((temp = NodeTraits::get_left(new_node))){
+ NodeTraits::set_parent(temp, new_node);
+ }
+ if((temp = NodeTraits::get_right(new_node))){
+ NodeTraits::set_parent(temp, new_node);
+ }
+ if((temp = NodeTraits::get_parent(new_node)) &&
+ //The header has been already updated so avoid it
+ temp != header){
+ if(NodeTraits::get_left(temp) == node_to_be_replaced){
+ NodeTraits::set_left(temp, new_node);
+ }
+ if(NodeTraits::get_right(temp) == node_to_be_replaced){
+ NodeTraits::set_right(temp, new_node);
+ }
+ }
+ }
+
//! <b>Requires</b>: node is a tree node but not the header.
//!
//! <b>Effects</b>: Unlinks the node and rebalances the tree.
@@ -202,6 +508,10 @@
}
}
+ static void unlink(node_ptr node)
+ { unlink_and_rebalance(node); }
+
+
//! <b>Requires</b>: header is the header of a tree.
//!
//! <b>Effects</b>: Unlinks the leftmost node from the tree, and
@@ -508,25 +818,42 @@
//!
//! <b>Throws</b>: If cloner functor throws. If this happens target nodes are disposed.
template <class Cloner, class Disposer>
- static void clone_tree
+ static void clone
(const_node_ptr source_header, node_ptr target_header, Cloner cloner, Disposer disposer)
{
if(!unique(target_header)){
- node_ptr p;
- while((p = unlink_leftmost_without_rebalance(target_header))){
- disposer(p);
- }
+ clear_and_dispose(target_header, disposer);
}
- node_ptr source_root = NodeTraits::get_parent(source_header);
+ node_ptr leftmost, rightmost;
+ node_ptr new_root = clone_subtree
+ (source_header, target_header, cloner, disposer, leftmost, rightmost);
+
+ //Now update header node
+ NodeTraits::set_parent(target_header, new_root);
+ NodeTraits::set_left (target_header, leftmost);
+ NodeTraits::set_right (target_header, rightmost);
+ }
+
+ //! <b>Requires</b>: "disposer" must be an object function
+ //! taking a node_ptr parameter and shouldn't throw.
+ //!
+ //! <b>Effects</b>: Empties the target tree calling
+ //! <tt>void disposer::operator()(node_ptr)</tt> for every node of the tree
+ //! except the header.
+ //!
+ //! <b>Complexity</b>: Linear to the number of element of the source tree plus the.
+ //! number of elements of tree target tree when calling this function.
+ //!
+ //! <b>Throws</b>: If cloner functor throws. If this happens target nodes are disposed.
+ template<class Disposer>
+ static void clear_and_dispose(node_ptr header, Disposer disposer)
+ {
+ node_ptr source_root = NodeTraits::get_parent(header);
if(!source_root)
return;
-
- NodeTraits::set_parent
- ( target_header
- , deep_clone_node(source_root, target_header, cloner, disposer));
- NodeTraits::set_left(target_header, minimum(NodeTraits::get_parent(target_header)));
- NodeTraits::set_right(target_header, maximum(NodeTraits::get_parent(target_header)));
+ dispose_subtree(source_root, disposer);
+ init_header(header);
}
//! <b>Requires</b>: "header" must be the header node of a tree.
@@ -694,6 +1021,17 @@
bool link_left = (y == h) ||
comp(new_node, y);
link_and_balance(new_node, y, link_left, h);
+/*
+ //erase me
+ NodeTraits::node n;
+ init(&n);
+ if(y!=h)
+ x = x;
+ node_ptr n1(y!=h ? y : &n);
+ node_ptr n2(new_node);
+ swap_nodes(n2, n1);
+ swap_nodes(n2, n1);
+*/
return new_node;
}
@@ -725,6 +1063,17 @@
bool link_left = (y == h) ||
!comp(y, new_node);
link_and_balance(new_node, y, link_left, h);
+/*
+ //erase me
+ NodeTraits::node n;
+ init(&n);
+ if(y!=h)
+ x = x;
+ node_ptr n1(y!=h ? y : &n);
+ node_ptr n2(new_node);
+ swap_nodes(n2, n1);
+ swap_nodes(n2, n1);
+*/
return new_node;
}
@@ -752,6 +1101,14 @@
!comp(new_node, (prev = prev_node(hint)))){
bool link_left = unique(header) || !NodeTraits::get_left(hint);
link_and_balance(new_node, link_left ? hint : prev, link_left, header);
+/*
+ //erase me
+ NodeTraits::node n1;
+ node_ptr n2(new_node);
+ init(&n1);
+ swap_nodes(n2, &n1);
+ swap_nodes(&n1, n2);
+*/
return new_node;
}
else{
@@ -922,6 +1279,109 @@
/// @cond
+ template <class Cloner, class Disposer>
+ static node_ptr clone_subtree
+ ( const_node_ptr source_parent, node_ptr target_parent
+ , Cloner cloner, Disposer disposer
+ , node_ptr &leftmost_out, node_ptr &rightmost_out
+ )
+ {
+ node_ptr target_sub_root = target_parent;
+ node_ptr source_root = NodeTraits::get_parent(source_parent);
+ if(!source_root){
+ leftmost_out = rightmost_out = source_root;
+ }
+ else{
+ //We'll calculate leftmost and rightmost nodes while iterating
+ node_ptr current = source_root;
+ node_ptr insertion_point = target_sub_root = cloner(current);
+
+ //We'll calculate leftmost and rightmost nodes while iterating
+ node_ptr leftmost = target_sub_root;
+ node_ptr rightmost = target_sub_root;
+
+ //First set the subroot
+ NodeTraits::set_left(target_sub_root, 0);
+ NodeTraits::set_right(target_sub_root, 0);
+ NodeTraits::set_parent(target_sub_root, target_parent);
+ NodeTraits::set_color(target_sub_root, NodeTraits::get_color(current));
+
+ try {
+ while(true) {
+ //First clone left nodes
+ if( NodeTraits::get_left(current) &&
+ !NodeTraits::get_left(insertion_point)) {
+ current = NodeTraits::get_left(current);
+ node_ptr temp = insertion_point;
+ //Clone and mark as leaf
+ insertion_point = cloner(current);
+ NodeTraits::set_left (insertion_point, 0);
+ NodeTraits::set_right (insertion_point, 0);
+ NodeTraits::set_color (insertion_point, NodeTraits::get_color(current));
+ //Insert left
+ NodeTraits::set_parent(insertion_point, temp);
+ NodeTraits::set_left (temp, insertion_point);
+ //Update leftmost
+ if(rightmost == target_sub_root)
+ leftmost = insertion_point;
+ }
+ //Then clone right nodes
+ else if( NodeTraits::get_right(current) &&
+ !NodeTraits::get_right(insertion_point)){
+ current = NodeTraits::get_right(current);
+ node_ptr temp = insertion_point;
+ //Clone and mark as leaf
+ insertion_point = cloner(current);
+ NodeTraits::set_left (insertion_point, 0);
+ NodeTraits::set_right (insertion_point, 0);
+ NodeTraits::set_color (insertion_point, NodeTraits::get_color(current));
+ //Insert right
+ NodeTraits::set_parent(insertion_point, temp);
+ NodeTraits::set_right (temp, insertion_point);
+ //Update rightmost
+ rightmost = insertion_point;
+ }
+ //If not, go up
+ else if(current == source_root){
+ break;
+ }
+ else{
+ //Branch completed, go up searching more nodes to clone
+ current = NodeTraits::get_parent(current);
+ insertion_point = NodeTraits::get_parent(insertion_point);
+ }
+ }
+ }
+ catch(...) {
+ dispose_subtree(target_sub_root, disposer);
+ throw;
+ }
+ leftmost_out = leftmost;
+ rightmost_out = rightmost;
+ }
+ return target_sub_root;
+ }
+
+ template<class Disposer>
+ static void dispose_subtree(node_ptr x, Disposer disposer)
+ {
+ node_ptr save;
+ while (x){
+ save = NodeTraits::get_left(x);
+ if (save) {
+ // Right rotation
+ NodeTraits::set_left(x, NodeTraits::get_right(save));
+ NodeTraits::set_right(save, x);
+ }
+ else {
+ save = NodeTraits::get_right(x);
+ init(x);
+ disposer(x);
+ }
+ x = save;
+ }
+ }
+
//! <b>Requires</b>: z is the node to be inserted, par is its parent,
//! left, indicates if z should be a left node of par and header is the header
//! of the tree.
@@ -1106,59 +1566,6 @@
}
NodeTraits::set_color(NodeTraits::get_parent(header), NodeTraits::black());
}
-
- template <class Cloner, class Disposer>
- static node_ptr deep_clone_node
- (node_ptr source_root, node_ptr new_parent, Cloner cloner, Disposer disposer)
- {
- // structural copy. source_root and new_parent must be non-null.
- node_ptr top = cloner(source_root);
- NodeTraits::set_parent(top, new_parent);
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- BOOST_TRY {
- #endif
- if(NodeTraits::get_right(source_root)){
- NodeTraits::set_right
- (top, deep_clone_node(NodeTraits::get_right(source_root), top
- ,cloner, disposer));
- }
- new_parent = top;
- source_root = NodeTraits::get_left(source_root);
-
- while(source_root){
- node_ptr y = cloner(source_root);
- NodeTraits::set_left(new_parent, y);
- NodeTraits::set_parent(y, new_parent);
-
- if(NodeTraits::get_right(source_root)){
- NodeTraits::set_right(y, deep_clone_node(NodeTraits::get_right(source_root), y
- ,cloner, disposer));
- }
- new_parent = y;
- source_root = NodeTraits::get_left(source_root);
- }
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- }
- BOOST_CATCH(...){
- deep_dispose_node(top, disposer);
- BOOST_RETHROW;
- }
- BOOST_CATCH_END
- #endif
- return top;
- }
-
- template<class Disposer>
- static void deep_dispose_node(node_ptr x, Disposer disposer)
- {
- // erase without rebalancing
- while(x){
- deep_dispose_node(NodeTraits::get_right(x), disposer);
- node_ptr y = NodeTraits::get_left(x);
- disposer(x);
- x = y;
- }
- }
/// @endcond
};
Modified: branches/bcbboost/boost/intrusive/set.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/set.hpp (original)
+++ branches/bcbboost/boost/intrusive/set.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,63 +24,59 @@
//! The class template set is an intrusive container, that mimics most of
//! the interface of std::set as described in the C++ standard.
//!
-//! The template parameter ValueTraits is called "value traits". It stores
-//! information and operations about the type to be stored in the container.
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
//!
-//! The template parameter Compare, provides a function object that can compare two
-//! element values as sort keys to determine their relative order in the set.
-//!
-//! If the user specifies ConstantTimeSize as "true", a member of type SizeType
-//! will be embedded in the class, that will keep track of the number of stored objects.
-//! This will allow constant-time O(1) size() member, instead of default O(N) size.
-template < class ValueTraits
- , class Compare //= std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class set
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<>, \c size_type<> and
+//! \c compare<>.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class set_impl
{
/// @cond
- typedef rbtree<ValueTraits, Compare, ConstantTimeSize, SizeType> tree_type;
-
+ typedef rbtree_impl<Config> tree_type;
//! This class is
//! non-copyable
- set (const set&);
+ set_impl (const set_impl&);
//! This class is
//! non-assignable
- set &operator =(const set&);
+ set_impl &operator =(const set_impl&);
typedef tree_type implementation_defined;
/// @endcond
public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef value_type key_type;
- typedef Compare value_compare;
- typedef value_compare key_compare;
+ typedef typename implementation_defined::value_type value_type;
+ typedef typename implementation_defined::value_traits value_traits;
+ typedef typename implementation_defined::pointer pointer;
+ typedef typename implementation_defined::const_pointer const_pointer;
+ typedef typename implementation_defined::reference reference;
+ typedef typename implementation_defined::const_reference const_reference;
+ typedef typename implementation_defined::difference_type difference_type;
+ typedef typename implementation_defined::size_type size_type;
+ typedef typename implementation_defined::value_compare value_compare;
+ typedef typename implementation_defined::key_compare key_compare;
typedef typename implementation_defined::iterator iterator;
typedef typename implementation_defined::const_iterator const_iterator;
typedef typename implementation_defined::reverse_iterator reverse_iterator;
typedef typename implementation_defined::const_reverse_iterator const_reverse_iterator;
typedef typename implementation_defined::insert_commit_data insert_commit_data;
+ typedef typename implementation_defined::node_traits node_traits;
+ typedef typename implementation_defined::node node;
+ typedef typename implementation_defined::node_ptr node_ptr;
+ typedef typename implementation_defined::const_node_ptr const_node_ptr;
+ typedef typename implementation_defined::node_algorithms node_algorithms;
/// @cond
private:
tree_type tree_;
-
- template <class V1, class P1, bool C1, class S1>
- friend bool operator==(const set<V1, P1, C1, S1>& x, const set<V1, P1, C1, S1>& y);
-
- template <class V1, class P1, bool C1, class S1>
- friend bool operator<(const set<V1, P1, C1, S1>& x, const set<V1, P1, C1, S1>& y);
/// @endcond
public:
@@ -90,9 +86,10 @@
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor of the Compare object throws.
- set(const Compare &cmp = Compare())
- : tree_(cmp)
+ //! or the copy constructor of the value_compare object throws.
+ set_impl( const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : tree_(cmp, v_traits)
{}
//! <b>Requires</b>: Dereferencing iterator must yield an lvalue of type value_type.
@@ -106,10 +103,12 @@
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor/operator() of the Compare object throws.
+ //! or the copy constructor/operator() of the value_compare object throws.
template<class Iterator>
- set(Iterator b, Iterator e, const Compare &cmp = Compare())
- : tree_(true, b, e, cmp)
+ set_impl( Iterator b, Iterator e
+ , const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : tree_(true, b, e, cmp, v_traits)
{ insert(b, e); }
//! <b>Effects</b>: Detaches all elements from this. The objects in the set
@@ -119,7 +118,7 @@
//! value. Otherwise constant.
//!
//! <b>Throws</b>: Nothing.
- ~set()
+ ~set_impl()
{}
//! <b>Effects</b>: Returns an iterator pointing to the beginning of the set.
@@ -232,11 +231,11 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static set &container_from_end_iterator(iterator end_iterator)
+ static set_impl &container_from_end_iterator(iterator end_iterator)
{
- return *detail::parent_from_member<set, tree_type>
+ return *detail::parent_from_member<set_impl, tree_type>
( &tree_type::container_from_end_iterator(end_iterator)
- , &set::tree_);
+ , &set_impl::tree_);
}
//! <b>Precondition</b>: end_iterator must be a valid end const_iterator
@@ -247,11 +246,11 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static const set &container_from_end_iterator(const_iterator end_iterator)
+ static const set_impl &container_from_end_iterator(const_iterator end_iterator)
{
- return *detail::parent_from_member<set, tree_type>
+ return *detail::parent_from_member<set_impl, tree_type>
( &tree_type::container_from_end_iterator(end_iterator)
- , &set::tree_);
+ , &set_impl::tree_);
}
//! <b>Effects</b>: Returns the key_compare object used by the set.
@@ -281,7 +280,7 @@
//! <b>Effects</b>: Returns the number of elements stored in the set.
//!
//! <b>Complexity</b>: Linear to elements contained in *this if,
- //! ConstantTimeSize is false. Constant-time otherwise.
+ //! constant-time size option is enabled. Constant-time otherwise.
//!
//! <b>Throws</b>: Nothing.
size_type size() const
@@ -293,7 +292,7 @@
//!
//! <b>Throws</b>: If the swap() call for the comparison functor
//! found using ADL throws. Strong guarantee.
- void swap(set& other)
+ void swap(set_impl& other)
{ tree_.swap(other.tree_); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
@@ -310,7 +309,7 @@
//!
//! <b>Throws</b>: If cloner throws.
template <class Cloner, class Disposer>
- void clone_from(const set &src, Cloner cloner, Disposer disposer)
+ void clone_from(const set_impl &src, Cloner cloner, Disposer disposer)
{ tree_.clone_from(src.tree_, cloner, disposer); }
//! <b>Requires</b>: value must be an lvalue
@@ -326,7 +325,7 @@
//! <b>Complexity</b>: Average complexity for insert element is at
//! most logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Strong guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Strong guarantee.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
//! No copy-constructors are called.
@@ -344,7 +343,7 @@
//! <b>Complexity</b>: Logarithmic in general, but it's amortized
//! constant time if t is inserted immediately before hint.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Strong guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Strong guarantee.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
//! No copy-constructors are called.
@@ -449,11 +448,11 @@
//!
//! <b>Effects</b>: Inserts a range into the set.
//!
- //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
- //! size of the range. However, it is linear in N if the range is already sorted
+ //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
+ //! size of the range. However, it is linear in N if the range is already sorted
//! by value_comp().
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Basic guarantee.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
//! No copy-constructors are called.
@@ -494,7 +493,7 @@
//!
//! <b>Complexity</b>: O(log(size()) + this->count(value)).
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
@@ -556,7 +555,7 @@
//! <b>Effects</b>: Erases all the elements with the given value.
//! Disposer::operator()(pointer) is called for the removed elements.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
//!
//! <b>Complexity</b>: O(log(size() + this->count(value)). Basic guarantee.
//!
@@ -618,7 +617,7 @@
//! <b>Complexity</b>: Logarithmic to the number of elements contained plus lineal
//! to number of objects with the given key.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
size_type count(const_reference value) const
{ return tree_.find(value) != end(); }
@@ -638,7 +637,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
iterator lower_bound(const_reference value)
{ return tree_.lower_bound(value); }
@@ -666,7 +665,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
const_iterator lower_bound(const_reference value) const
{ return tree_.lower_bound(value); }
@@ -694,7 +693,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
iterator upper_bound(const_reference value)
{ return tree_.upper_bound(value); }
@@ -722,7 +721,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
const_iterator upper_bound(const_reference value) const
{ return tree_.upper_bound(value); }
@@ -750,7 +749,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
iterator find(const_reference value)
{ return tree_.find(value); }
@@ -778,7 +777,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
const_iterator find(const_reference value) const
{ return tree_.find(value); }
@@ -807,7 +806,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
std::pair<iterator,iterator> equal_range(const_reference value)
{ return tree_.equal_range(value); }
@@ -837,7 +836,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
std::pair<const_iterator, const_iterator>
equal_range(const_reference value) const
{ return tree_.equal_range(value); }
@@ -872,8 +871,11 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static iterator iterator_to(reference value)
- { return tree_type::iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static iterator s_iterator_to(reference value)
+ { return tree_type::s_iterator_to(value); }
//! <b>Requires</b>: value must be an lvalue and shall be in a set of
//! appropriate type. Otherwise the behavior is undefined.
@@ -884,91 +886,245 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static const_iterator iterator_to(const_reference value)
- { return tree_type::iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_iterator s_iterator_to(const_reference value)
+ { return tree_type::s_iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid iterator i belonging to the set
+ //! that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ iterator iterator_to(reference value)
+ { return tree_.iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid const_iterator i belonging to the
+ //! set that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ const_iterator iterator_to(const_reference value) const
+ { return tree_.iterator_to(value); }
+
+ //! <b>Requires</b>: value shall not be in a set/multiset.
+ //!
+ //! <b>Effects</b>: init_node puts the hook of a value in a well-known default
+ //! state.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Complexity</b>: Constant time.
+ //!
+ //! <b>Note</b>: This function puts the hook in the well-known default state
+ //! used by auto_unlink and safe hooks.
+ static void init_node(reference value)
+ { tree_type::init_node(value); }
+
+ //! <b>Requires</b>: replace_this must be a valid iterator of *this
+ //! and with_this must not be inserted in any tree.
+ //!
+ //! <b>Effects</b>: Replaces replace_this in its position in the
+ //! tree with with_this. The tree does not need to be rebalanced.
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! with_this is not equivalent to *replace_this according to the
+ //! ordering rules. This function is faster than erasing and inserting
+ //! the node, since no rebalancing or comparison is needed.
+ void replace_node(iterator replace_this, reference with_this)
+ { tree_.replace_node(replace_this, with_this); }
/// @cond
- friend bool operator==(const set &x, const set &y)
+ friend bool operator==(const set_impl &x, const set_impl &y)
{ return x.tree_ == y.tree_; }
- friend bool operator<(const set &x, const set &y)
+ friend bool operator<(const set_impl &x, const set_impl &y)
{ return x.tree_ < y.tree_; }
/// @endcond
};
-template <class V, class P, bool C, class S>
-inline bool operator!=(const set<V, P, C, S>& x, const set<V, P, C, S>& y)
-{ return !(x==y); }
-
-template <class V, class P, bool C, class S>
-inline bool operator>(const set<V, P, C, S>& x, const set<V, P, C, S>& y)
-{ return y < x; }
-
-template <class V, class P, bool C, class S>
-inline bool operator<=(const set<V, P, C, S>& x, const set<V, P, C, S>& y)
-{ return !(y > x); }
-
-template <class V, class P, bool C, class S>
-inline bool operator>=(const set<V, P, C, S>& x, const set<V, P, C, S>& y)
-{ return !(x < y); }
-
-template <class V, class P, bool C, class S>
-inline void swap(set<V, P, C, S>& x, set<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator!=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const set_impl<T, Options...> &x, const set_impl<T, Options...> &y)
+#else
+(const set_impl<Config> &x, const set_impl<Config> &y)
+#endif
+{ return !(x == y); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const set_impl<T, Options...> &x, const set_impl<T, Options...> &y)
+#else
+(const set_impl<Config> &x, const set_impl<Config> &y)
+#endif
+{ return y < x; }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const set_impl<T, Options...> &x, const set_impl<T, Options...> &y)
+#else
+(const set_impl<Config> &x, const set_impl<Config> &y)
+#endif
+{ return !(y < x); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const set_impl<T, Options...> &x, const set_impl<T, Options...> &y)
+#else
+(const set_impl<Config> &x, const set_impl<Config> &y)
+#endif
+{ return !(x < y); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline void swap
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(set_impl<T, Options...> &x, set_impl<T, Options...> &y)
+#else
+(set_impl<Config> &x, set_impl<Config> &y)
+#endif
{ x.swap(y); }
+//! Helper metafunction to define a \c set that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none>
+#endif
+struct make_set
+{
+ /// @cond
+ typedef set_impl
+ < typename make_rbtree_opt<T, O1, O2, O3, O4>::type
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3, class O4>
+class set
+ : public make_set<T, O1, O2, O3, O4>::type
+{
+ typedef typename make_set
+ <T, O1, O2, O3, O4>::type Base;
+
+ public:
+ typedef typename Base::value_compare value_compare;
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename value_traits::value_type, T>::value));
+
+ set( const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : Base(cmp, v_traits)
+ {}
+
+ template<class Iterator>
+ set( Iterator b, Iterator e
+ , const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : Base(b, e, cmp, v_traits)
+ {}
+
+ static set &container_from_end_iterator(iterator end_iterator)
+ { return static_cast<set &>(Base::container_from_end_iterator(end_iterator)); }
+
+ static const set &container_from_end_iterator(const_iterator end_iterator)
+ { return static_cast<const set &>(Base::container_from_end_iterator(end_iterator)); }
+};
+
+#endif
+
//! The class template multiset is an intrusive container, that mimics most of
//! the interface of std::multiset as described in the C++ standard.
//!
-//! The template parameter ValueTraits is called "value traits". It stores
-//! information and operations about the type to be stored
-//! in list and what type of hook has been chosen to include it in the list.
-//! The value_traits class is supplied by the appropriate hook as a template subtype
-//! called "value_traits".
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
//!
-//! The template parameter Compare, provides a function object that can compare two
-//! element values as sort keys to determine their relative order in the set.
-//!
-//! If the user specifies ConstantTimeSize as "true", a member of type SizeType
-//! will be embedded in the class, that will keep track of the number of stored objects.
-//! This will allow constant-time O(1) size() member, instead of default O(N) size.
-template < class ValueTraits
- , class Compare //= std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class multiset
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<>, \c size_type<> and
+//! \c compare<>.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class multiset_impl
{
/// @cond
- typedef rbtree<ValueTraits, Compare, ConstantTimeSize, SizeType> tree_type;
-
- //! This class is
- //! non-copyable
- multiset (const multiset&);
-
- //! This class is
- //! non-asignable
- multiset &operator =(const multiset&);
+ typedef rbtree_impl<Config> tree_type;
+ //Non-copyable and non-assignable
+ multiset_impl (const multiset_impl&);
+ multiset_impl &operator =(const multiset_impl&);
typedef tree_type implementation_defined;
/// @endcond
public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef value_type key_type;
- typedef Compare value_compare;
- typedef value_compare key_compare;
+ typedef typename implementation_defined::value_type value_type;
+ typedef typename implementation_defined::value_traits value_traits;
+ typedef typename implementation_defined::pointer pointer;
+ typedef typename implementation_defined::const_pointer const_pointer;
+ typedef typename implementation_defined::reference reference;
+ typedef typename implementation_defined::const_reference const_reference;
+ typedef typename implementation_defined::difference_type difference_type;
+ typedef typename implementation_defined::size_type size_type;
+ typedef typename implementation_defined::value_compare value_compare;
+ typedef typename implementation_defined::key_compare key_compare;
typedef typename implementation_defined::iterator iterator;
typedef typename implementation_defined::const_iterator const_iterator;
typedef typename implementation_defined::reverse_iterator reverse_iterator;
typedef typename implementation_defined::const_reverse_iterator const_reverse_iterator;
typedef typename implementation_defined::insert_commit_data insert_commit_data;
+ typedef typename implementation_defined::node_traits node_traits;
+ typedef typename implementation_defined::node node;
+ typedef typename implementation_defined::node_ptr node_ptr;
+ typedef typename implementation_defined::const_node_ptr const_node_ptr;
+ typedef typename implementation_defined::node_algorithms node_algorithms;
/// @cond
private:
@@ -982,9 +1138,10 @@
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor/operator() of the Compare object throws.
- multiset(const Compare &cmp = Compare())
- : tree_(cmp)
+ //! or the copy constructor/operator() of the value_compare object throws.
+ multiset_impl( const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : tree_(cmp, v_traits)
{}
//! <b>Requires</b>: Dereferencing iterator must yield an lvalue of type value_type.
@@ -993,15 +1150,17 @@
//! <b>Effects</b>: Constructs an empty multiset and inserts elements from
//! [b, e).
//!
- //! <b>Complexity</b>: Linear in N if [b, e) is already sorted using
+ //! <b>Complexity</b>: Linear in N if [b, e) is already sorted using
//! comp and otherwise N * log N, where N is last first.
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor/operator() of the Compare object throws.
+ //! or the copy constructor/operator() of the value_compare object throws.
template<class Iterator>
- multiset(Iterator b, Iterator e, const Compare &cmp = Compare())
- : tree_(false, b, e, cmp)
+ multiset_impl( Iterator b, Iterator e
+ , const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : tree_(false, b, e, cmp, v_traits)
{}
//! <b>Effects</b>: Detaches all elements from this. The objects in the set
@@ -1011,7 +1170,7 @@
//! auto-unlink value. Otherwise constant.
//!
//! <b>Throws</b>: Nothing.
- ~multiset()
+ ~multiset_impl()
{}
//! <b>Effects</b>: Returns an iterator pointing to the beginning of the multiset.
@@ -1124,11 +1283,11 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static multiset &container_from_end_iterator(iterator end_iterator)
+ static multiset_impl &container_from_end_iterator(iterator end_iterator)
{
- return *detail::parent_from_member<multiset, tree_type>
+ return *detail::parent_from_member<multiset_impl, tree_type>
( &tree_type::container_from_end_iterator(end_iterator)
- , &multiset::tree_);
+ , &multiset_impl::tree_);
}
//! <b>Precondition</b>: end_iterator must be a valid end const_iterator
@@ -1139,11 +1298,11 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static const multiset &container_from_end_iterator(const_iterator end_iterator)
+ static const multiset_impl &container_from_end_iterator(const_iterator end_iterator)
{
- return *detail::parent_from_member<multiset, tree_type>
+ return *detail::parent_from_member<multiset_impl, tree_type>
( &tree_type::container_from_end_iterator(end_iterator)
- , &multiset::tree_);
+ , &multiset_impl::tree_);
}
//! <b>Effects</b>: Returns the key_compare object used by the multiset.
@@ -1173,7 +1332,7 @@
//! <b>Effects</b>: Returns the number of elements stored in the multiset.
//!
//! <b>Complexity</b>: Linear to elements contained in *this if,
- //! ConstantTimeSize is false. Constant-time otherwise.
+ //! constant-time size option is enabled. Constant-time otherwise.
//!
//! <b>Throws</b>: Nothing.
size_type size() const
@@ -1185,7 +1344,7 @@
//!
//! <b>Throws</b>: If the swap() call for the comparison functor
//! found using ADL throws. Strong guarantee.
- void swap(multiset& other)
+ void swap(multiset_impl& other)
{ tree_.swap(other.tree_); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
@@ -1202,7 +1361,7 @@
//!
//! <b>Throws</b>: If cloner throws. Basic guarantee.
template <class Cloner, class Disposer>
- void clone_from(const multiset &src, Cloner cloner, Disposer disposer)
+ void clone_from(const multiset_impl &src, Cloner cloner, Disposer disposer)
{ tree_.clone_from(src.tree_, cloner, disposer); }
//! <b>Requires</b>: value must be an lvalue
@@ -1215,7 +1374,7 @@
//! <b>Complexity</b>: Average complexity for insert element is at
//! most logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Strong guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Strong guarantee.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
//! No copy-constructors are called.
@@ -1233,7 +1392,7 @@
//! <b>Complexity</b>: Logarithmic in general, but it is amortized
//! constant time if t is inserted immediately before hint.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Strong guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Strong guarantee.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
//! No copy-constructors are called.
@@ -1248,11 +1407,11 @@
//! <b>Returns</b>: An iterator that points to the position where the new
//! element was inserted.
//!
- //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
- //! size of the range. However, it is linear in N if the range is already sorted
+ //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
+ //! size of the range. However, it is linear in N if the range is already sorted
//! by value_comp().
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Basic guarantee.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
//! No copy-constructors are called.
@@ -1293,7 +1452,7 @@
//!
//! <b>Complexity</b>: O(log(size() + this->count(value)).
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
@@ -1359,7 +1518,7 @@
//!
//! <b>Complexity</b>: O(log(size() + this->count(value)).
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws. Basic guarantee.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
@@ -1417,7 +1576,7 @@
//! <b>Complexity</b>: Logarithmic to the number of elements contained plus lineal
//! to number of objects with the given key.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
size_type count(const_reference value) const
{ return tree_.count(value); }
@@ -1437,7 +1596,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
iterator lower_bound(const_reference value)
{ return tree_.lower_bound(value); }
@@ -1465,7 +1624,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
const_iterator lower_bound(const_reference value) const
{ return tree_.lower_bound(value); }
@@ -1493,7 +1652,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
iterator upper_bound(const_reference value)
{ return tree_.upper_bound(value); }
@@ -1521,7 +1680,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
const_iterator upper_bound(const_reference value) const
{ return tree_.upper_bound(value); }
@@ -1549,7 +1708,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
iterator find(const_reference value)
{ return tree_.find(value); }
@@ -1577,7 +1736,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
const_iterator find(const_reference value) const
{ return tree_.find(value); }
@@ -1606,7 +1765,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
std::pair<iterator,iterator> equal_range(const_reference value)
{ return tree_.equal_range(value); }
@@ -1636,7 +1795,7 @@
//!
//! <b>Complexity</b>: Logarithmic.
//!
- //! <b>Throws</b>: If the internal Compare ordering function throws.
+ //! <b>Throws</b>: If the internal value_compare ordering function throws.
std::pair<const_iterator, const_iterator>
equal_range(const_reference value) const
{ return tree_.equal_range(value); }
@@ -1671,8 +1830,11 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static iterator iterator_to(reference value)
- { return tree_type::iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static iterator s_iterator_to(reference value)
+ { return tree_type::s_iterator_to(value); }
//! <b>Requires</b>: value must be an lvalue and shall be in a set of
//! appropriate type. Otherwise the behavior is undefined.
@@ -1683,38 +1845,197 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static const_iterator iterator_to(const_reference value)
- { return tree_type::iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_iterator s_iterator_to(const_reference value)
+ { return tree_type::s_iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid iterator i belonging to the set
+ //! that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ iterator iterator_to(reference value)
+ { return tree_.iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid const_iterator i belonging to the
+ //! set that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ const_iterator iterator_to(const_reference value) const
+ { return tree_.iterator_to(value); }
+
+ //! <b>Requires</b>: value shall not be in a set/multiset.
+ //!
+ //! <b>Effects</b>: init_node puts the hook of a value in a well-known default
+ //! state.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Complexity</b>: Constant time.
+ //!
+ //! <b>Note</b>: This function puts the hook in the well-known default state
+ //! used by auto_unlink and safe hooks.
+ static void init_node(reference value)
+ { tree_type::init_node(value); }
+
+ //! <b>Requires</b>: replace_this must be a valid iterator of *this
+ //! and with_this must not be inserted in any tree.
+ //!
+ //! <b>Effects</b>: Replaces replace_this in its position in the
+ //! tree with with_this. The tree does not need to be rebalanced.
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Note</b>: This function will break container ordering invariants if
+ //! with_this is not equivalent to *replace_this according to the
+ //! ordering rules. This function is faster than erasing and inserting
+ //! the node, since no rebalancing or comparison is needed.
+ void replace_node(iterator replace_this, reference with_this)
+ { tree_.replace_node(replace_this, with_this); }
/// @cond
- friend bool operator==(const multiset &x, const multiset &y)
+ friend bool operator==(const multiset_impl &x, const multiset_impl &y)
{ return x.tree_ == y.tree_; }
- friend bool operator<(const multiset &x, const multiset &y)
+ friend bool operator<(const multiset_impl &x, const multiset_impl &y)
{ return x.tree_ < y.tree_; }
/// @endcond
};
-template <class V, class P, bool C, class S>
-inline bool operator!=(const multiset<V, P, C, S>& x, const multiset<V, P, C, S>& y)
-{ return !(x==y); }
-
-template <class V, class P, bool C, class S>
-inline bool operator>(const multiset<V, P, C, S>& x, const multiset<V, P, C, S>& y)
-{ return y < x; }
-
-template <class V, class P, bool C, class S>
-inline bool operator<=(const multiset<V, P, C, S>& x, const multiset<V, P, C, S>& y)
-{ return !(y > x); }
-
-template <class V, class P, bool C, class S>
-inline bool operator>=(const multiset<V, P, C, S>& x, const multiset<V, P, C, S>& y)
-{ return !(x < y); }
-
-template <class V, class P, bool C, class S>
-inline void swap(multiset<V, P, C, S>& x, multiset<V, P, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator!=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const multiset_impl<T, Options...> &x, const multiset_impl<T, Options...> &y)
+#else
+(const multiset_impl<Config> &x, const multiset_impl<Config> &y)
+#endif
+{ return !(x == y); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const multiset_impl<T, Options...> &x, const multiset_impl<T, Options...> &y)
+#else
+(const multiset_impl<Config> &x, const multiset_impl<Config> &y)
+#endif
+{ return y < x; }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const multiset_impl<T, Options...> &x, const multiset_impl<T, Options...> &y)
+#else
+(const multiset_impl<Config> &x, const multiset_impl<Config> &y)
+#endif
+{ return !(y < x); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const multiset_impl<T, Options...> &x, const multiset_impl<T, Options...> &y)
+#else
+(const multiset_impl<Config> &x, const multiset_impl<Config> &y)
+#endif
+{ return !(x < y); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline void swap
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(multiset_impl<T, Options...> &x, multiset_impl<T, Options...> &y)
+#else
+(multiset_impl<Config> &x, multiset_impl<Config> &y)
+#endif
{ x.swap(y); }
+//! Helper metafunction to define a \c multiset that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none>
+#endif
+struct make_multiset
+{
+ /// @cond
+ typedef multiset_impl
+ < typename make_rbtree_opt<T, O1, O2, O3, O4>::type
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3, class O4>
+class multiset
+ : public make_multiset<T, O1, O2, O3, O4>::type
+{
+ typedef typename make_multiset
+ <T, O1, O2, O3, O4>::type Base;
+
+ public:
+ typedef typename Base::value_compare value_compare;
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename value_traits::value_type, T>::value));
+
+ multiset( const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : Base(cmp, v_traits)
+ {}
+
+ template<class Iterator>
+ multiset( Iterator b, Iterator e
+ , const value_compare &cmp = value_compare()
+ , const value_traits &v_traits = value_traits())
+ : Base(b, e, cmp, v_traits)
+ {}
+
+ static multiset &container_from_end_iterator(iterator end_iterator)
+ { return static_cast<multiset &>(Base::container_from_end_iterator(end_iterator)); }
+
+ static const multiset &container_from_end_iterator(const_iterator end_iterator)
+ { return static_cast<const multiset &>(Base::container_from_end_iterator(end_iterator)); }
+};
+
+#endif
+
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/set_hook.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/set_hook.hpp (original)
+++ branches/bcbboost/boost/intrusive/set_hook.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,16 +17,45 @@
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
#include <boost/intrusive/detail/utilities.hpp>
-#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/detail/rbtree_node.hpp>
#include <boost/intrusive/rbtree_algorithms.hpp>
-#include <boost/intrusive/linking_policy.hpp>
-#include <boost/intrusive/tag.hpp>
-#include <boost/static_assert.hpp>
+#include <boost/intrusive/options.hpp>
+#include <boost/intrusive/detail/generic_hook.hpp>
namespace boost {
namespace intrusive {
+/// @cond
+template<class VoidPointer>
+struct get_set_node_algo
+{
+ typedef rbtree_algorithms<rbtree_node_traits<VoidPointer> > type;
+};
+/// @endcond
+
+//! Helper metafunction to define a \c set_base_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_set_base_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
+
+ typedef detail::generic_hook
+ < get_set_node_algo<typename packed_options::void_pointer>
+ , typename packed_options::tag
+ , packed_options::link_mode
+ , detail::SetBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
//! Derive a class from set_base_hook in order to store objects in
//! in an set/multiset. set_base_hook holds the data necessary to maintain
//! the set/multiset and provides an appropriate value_traits class for set/multiset.
@@ -40,160 +69,102 @@
//!
//! The third argument is the pointer type that will be used internally in the hook
//! and the set/multiset configured from this hook.
-template< class Tag //= tag
- , linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class set_base_hook
- : private detail::rbtree_node_traits<VoidPointer>::node
+ : public make_set_base_hook<O1, O2, O3>::type
{
- public:
- typedef detail::rbtree_node_traits<VoidPointer> node_traits;
- enum { linking_policy = Policy };
-
- /// @cond
- private:
- typedef rbtree_algorithms<node_traits> node_algorithms;
- /// @endcond
-
- public:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef set_base_hook
- <Tag, Policy, VoidPointer> this_type;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type>::type this_type_ptr;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type>::type const_this_type_ptr;
-
- /// @cond
- private:
-
- node_ptr this_as_node()
- { return node_ptr(static_cast<node *const>(this)); }
-
- const_node_ptr this_as_node() const
- { return const_node_ptr(static_cast<const node *const>(this)); }
- /// @endcond
-
- public:
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
- //! <b>Throws</b>: Nothing.
- set_base_hook()
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ //! <b>Throws</b>: Nothing.
+ set_base_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using set_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- set_base_hook(const set_base_hook& )
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ set_base_hook(const set_base_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using set_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- set_base_hook& operator=(const set_base_hook& )
- { return *this; }
+ set_base_hook& operator=(const set_base_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
- //!
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an set an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
+ //!
+ //! <b>Throws</b>: Nothing.
+ ~set_base_hook();
+
+ //! <b>Effects</b>: Swapping two nodes swaps the position of the elements
+ //! related to those nodes in one or two containers. That is, if the node
+ //! this is part of the element e1, the node x is part of the element e2
+ //! and both elements are included in the containers s1 and s2, then after
+ //! the swap-operation e1 is in s2 at the position of e2 and e2 is in s1
+ //! at the position of e1. If one element is not in a container, then
+ //! after the swap-operation the other element is not in a container.
+ //! Iterators to e1 and e2 related to those nodes are invalidated.
+ //!
+ //! <b>Complexity</b>: Constant
+ //!
//! <b>Throws</b>: Nothing.
- ~set_base_hook()
- { detail::destructor_impl(*this, detail::dispatcher<Policy>()); }
+ void swap_nodes(set_base_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
//! <b>Returns</b>: true, if the node belongs to a container, false
- //! otherwise. This function can be used to test whether set::iterator_to
+ //! otherwise. This function can be used to test whether \c set::iterator_to
//! will return a valid iterator.
//!
//! <b>Complexity</b>: Constant
- bool is_linked() const
- {
- //is_linked() can be only used in safe-mode or auto-unlink
- BOOST_STATIC_ASSERT((Policy == safe_link || Policy == auto_unlink));
- return !node_algorithms::unique(this_as_node());
- }
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- void unlink()
- {
- BOOST_STATIC_ASSERT((Policy == auto_unlink));
- node_algorithms::unlink_and_rebalance(this_as_node());
- node_algorithms::init(this_as_node());
- }
-
- //! The value_traits class is used as the first template argument for multiset.
- //! The template argument T defines the class type stored in multiset. Objects
- //! of type T and of types derived from T can be stored. T don't need to be
- //! copy-constructible or assignable.
- template<class T>
- struct value_traits
- : detail::derivation_hook_value_traits<T, this_type, Tag>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr(static_cast<set_base_hook*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr(static_cast<const set_base_hook*> (detail::get_pointer(p)));
- }
+ void unlink();
+ #endif
+};
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return this_as_node(); }
+//! Helper metafunction to define a \c set_member_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_set_member_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return this_as_node(); }
+ typedef detail::generic_hook
+ < get_set_node_algo<typename packed_options::void_pointer>
+ , member_tag
+ , packed_options::link_mode
+ , detail::NoBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
};
//! Put a public data member set_member_hook in order to store objects of this class in
@@ -204,152 +175,79 @@
//!
//! The second argument is the pointer type that will be used internally in the hook
//! and the set/multiset configured from this hook.
-template< linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class set_member_hook
- : private detail::rbtree_node_traits<VoidPointer>::node
+ : public make_set_member_hook<O1, O2, O3>::type
{
- public:
- typedef detail::rbtree_node_traits<VoidPointer> node_traits;
- enum { linking_policy = Policy };
-
- /// @cond
- private:
- typedef rbtree_algorithms<node_traits> node_algorithms;
- /// @endcond
-
- public:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef set_member_hook
- <Policy, VoidPointer> this_type;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type >::type this_type_ptr;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type >::type const_this_type_ptr;
-
- /// @cond
- private:
- node_ptr this_as_node()
- { return node_ptr(static_cast<node *const>(this)); }
-
- const_node_ptr this_as_node() const
- { return const_node_ptr(static_cast<const node *const>(this)); }
- /// @endcond
-
- public:
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
//! <b>Throws</b>: Nothing.
- set_member_hook()
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ set_member_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using set_member_hook STL-compliant without forcing the
- //! user to do some additional work.
- set_member_hook(const set_member_hook& )
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
+ //! move-semantics.
+ set_member_hook(const set_member_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using set_member_hook STL-compliant without forcing the
- //! user to do some additional work.
- set_member_hook& operator=(const set_member_hook& )
- { return *this; }
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
+ //! move-semantics.
+ set_member_hook& operator=(const set_member_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
- //!
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an set an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
+ //!
+ //! <b>Throws</b>: Nothing.
+ ~set_member_hook();
+
+ //! <b>Effects</b>: Swapping two nodes swaps the position of the elements
+ //! related to those nodes in one or two containers. That is, if the node
+ //! this is part of the element e1, the node x is part of the element e2
+ //! and both elements are included in the containers s1 and s2, then after
+ //! the swap-operation e1 is in s2 at the position of e2 and e2 is in s1
+ //! at the position of e1. If one element is not in a container, then
+ //! after the swap-operation the other element is not in a container.
+ //! Iterators to e1 and e2 related to those nodes are invalidated.
+ //!
+ //! <b>Complexity</b>: Constant
+ //!
//! <b>Throws</b>: Nothing.
- ~set_member_hook()
- { detail::destructor_impl(*this, detail::dispatcher<Policy>()); }
+ void swap_nodes(set_member_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
- //! <b>Complexity</b>: Constant
- bool is_linked() const
- {
- //is_linked() can be only used in safe-mode or auto-unlink
- BOOST_STATIC_ASSERT((Policy == safe_link || Policy == auto_unlink));
- return !node_algorithms::unique(this_as_node());
- }
+ //! <b>Returns</b>: true, if the node belongs to a container, false
+ //! otherwise. This function can be used to test whether \c set::iterator_to
+ //! will return a valid iterator.
+ //!
+ //! <b>Complexity</b>: Constant
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
- //!
- //! <b>Throws</b>: Nothing.
- void unlink()
- {
- BOOST_STATIC_ASSERT((Policy == auto_unlink));
- node_algorithms::unlink_and_rebalance(this_as_node());
- node_algorithms::init(this_as_node());
- }
-
- //! The value_traits class is used as the first template argument for multiset.
- //! The template argument is a pointer to member pointing to the node in
- //! the class. Objects of type T and of types derived from T can be stored.
- //! T don't need to be copy-constructible or assignable.
- template<class T, this_type T::* P>
- struct value_traits
- : detail::member_hook_value_traits<T, this_type, P>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr(static_cast<this_type*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr(static_cast<const this_type*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return this_as_node(); }
-
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return this_as_node(); }
+ void unlink();
+ #endif
};
} //namespace intrusive
Modified: branches/bcbboost/boost/intrusive/slist.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/slist.hpp (original)
+++ branches/bcbboost/boost/intrusive/slist.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -16,21 +16,60 @@
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/static_assert.hpp>
-#ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
-#include <boost/detail/no_exceptions_support.hpp>
-#endif
+#include <boost/intrusive/detail/no_exceptions_support.hpp>
#include <boost/intrusive/detail/assert.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
#include <boost/intrusive/slist_hook.hpp>
#include <boost/intrusive/circular_slist_algorithms.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
+#include <boost/intrusive/options.hpp>
#include <functional>
#include <cstddef>
namespace boost {
namespace intrusive {
+/// @cond
+
+template <class T>
+struct internal_default_slist_hook
+{
+ template <class U> static detail::one test(...);
+ template <class U> static detail::two test(typename U::default_slist_hook* = 0);
+ static const bool value = sizeof(test<T>(0)) == sizeof(detail::two);
+};
+
+template <class T>
+struct get_default_slist_hook
+{ typedef typename T::default_slist_hook type; };
+
+template <class ValueTraits, class SizeType, bool ConstantTimeSize>
+struct slistopt
+{
+ typedef ValueTraits value_traits;
+ typedef SizeType size_type;
+ static const bool constant_time_size = ConstantTimeSize;
+};
+
+template <class T>
+struct slist_defaults
+ : pack_options
+ < none
+ , base_hook
+ < typename detail::eval_if_c
+ < internal_default_slist_hook<T>::value
+ , get_default_slist_hook<T>
+ , detail::identity<none>
+ >::type
+ >
+ , constant_time_size<true>
+ , size_type<std::size_t>
+ >::type
+{};
+
+/// @endcond
+
//! The class template slist is an intrusive container, that encapsulates
//! a singly-linked list. You can use such a list to squeeze the last bit
//! of performance from your application. Unfortunately, the little gains
@@ -39,12 +78,13 @@
//! this limitation some other member functions with rather unusual semantics
//! have to be introduced.
//!
-//! The template parameter ValueTraits is called "value traits". It stores
-//! information and operations about the type to be stored in the container.
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
//!
-//! If the user specifies ConstantTimeSize as "true", a member of type SizeType
-//! will be embedded in the class, that will keep track of the number of stored objects.
-//! This will allow constant-time O(1) size() member, instead of default O(N) size.
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<> and \c size_type<>.
//!
//! The iterators of slist are forward iterators. slist provides a static
//! function called "previous" to compute the previous iterator of a given iterator.
@@ -53,92 +93,131 @@
//! are defined. In addition, whenever you have an end iterator, 'after this
//! iterator' means 'at the beginning of the list'. To improve the self-documentation
//! a "before_begin()" function is defined, returning the end() iterator.
-template < class ValueTraits
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class slist
- : private detail::size_holder<ConstantTimeSize, SizeType>
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class slist_impl
{
+ //Public typedefs
+ public:
+ typedef typename Config::value_traits value_traits;
/// @cond
- private:
- typename ValueTraits::node_traits::node root_;
+ static const bool external_value_traits =
+ detail::external_value_traits_is_true<value_traits>::value;
+ typedef typename detail::eval_if_c
+ < external_value_traits
+ , detail::eval_value_traits<value_traits>
+ , detail::identity<value_traits>
+ >::type real_value_traits;
+ /// @endcond
+ typedef typename real_value_traits::pointer pointer;
+ typedef typename real_value_traits::const_pointer const_pointer;
+ typedef typename std::iterator_traits<pointer>::value_type value_type;
+ typedef typename std::iterator_traits<pointer>::reference reference;
+ typedef typename std::iterator_traits<const_pointer>::reference const_reference;
+ typedef typename std::iterator_traits<pointer>::difference_type difference_type;
+ typedef typename Config::size_type size_type;
+ typedef slist_iterator<slist_impl, false> iterator;
+ typedef slist_iterator<slist_impl, true> const_iterator;
+ typedef typename real_value_traits::node_traits node_traits;
+ typedef typename node_traits::node node;
+ typedef typename boost::pointer_to_other
+ <pointer, node>::type node_ptr;
+ typedef typename boost::pointer_to_other
+ <pointer, const node>::type const_node_ptr;
+ typedef circular_slist_algorithms<node_traits> node_algorithms;
- typedef slist<ValueTraits, ConstantTimeSize, SizeType> this_type;
- typedef typename ValueTraits::node_traits node_traits;
- typedef detail::size_holder<ConstantTimeSize, SizeType> size_traits;
+ static const bool constant_time_size = Config::constant_time_size;
+ static const bool stateful_value_traits = detail::store_cont_ptr_on_it<slist_impl>::value;
+
+ /// @cond
+ private:
+ typedef detail::size_holder<constant_time_size, size_type> size_traits;
//! This class is
//! non-copyable
- slist (const slist&);
+ slist_impl (const slist_impl&);
//! This class is
//! non-asignable
- slist &operator =(const slist&);
- /// @endcond
+ slist_impl &operator =(const slist_impl&);
- //Public typedefs
- public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef detail::slist_iterator<value_type, ValueTraits> iterator;
- typedef detail::slist_iterator<const value_type, ValueTraits> const_iterator;
-
- /// @cond
- private:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <pointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <pointer, const node>::type const_node_ptr;
- typedef circular_slist_algorithms<node_traits> node_algorithms;
enum { safemode_or_autounlink =
- (int)ValueTraits::linking_policy == (int)auto_unlink ||
- (int)ValueTraits::linking_policy == (int)safe_link };
+ (int)real_value_traits::link_mode == (int)auto_unlink ||
+ (int)real_value_traits::link_mode == (int)safe_link };
//Constant-time size is incompatible with auto-unlink hooks!
- BOOST_STATIC_ASSERT(!(ConstantTimeSize && ((int)ValueTraits::linking_policy == (int)auto_unlink)));
+ BOOST_STATIC_ASSERT(!(constant_time_size && ((int)real_value_traits::link_mode == (int)auto_unlink)));
node_ptr get_root_node()
- { return node_ptr(&root_); }
+ { return node_ptr(&data_.root_plus_size_.root_); }
const_node_ptr get_root_node() const
- { return const_node_ptr(&root_); }
+ { return const_node_ptr(&data_.root_plus_size_.root_); }
static node_ptr uncast(const_node_ptr ptr)
{
return node_ptr(const_cast<node*>(detail::get_pointer(ptr)));
}
- static iterator previous_node(iterator beg, iterator i)
+ struct root_plus_size
+ : public size_traits
{
- return iterator
- (node_algorithms::get_previous_node(beg.pointed_node(), i.pointed_node()));
- }
+ node root_;
+ };
- static const_iterator previous_node(const_iterator beg, const_iterator i)
+ struct data_t
+ : public slist_impl::value_traits
{
- return const_iterator
- (node_algorithms::get_previous_node(beg.pointed_node(), i.pointed_node()));
- }
+ typedef typename slist_impl::value_traits value_traits;
+ data_t(const value_traits &val_traits)
+ : value_traits(val_traits)
+ {}
+
+ root_plus_size root_plus_size_;
+ } data_;
+
+ size_traits &priv_size_traits()
+ { return data_.root_plus_size_; }
+
+ const size_traits &priv_size_traits() const
+ { return data_.root_plus_size_; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<false>) const
+ { return data_; }
+
+ const real_value_traits &get_real_value_traits(detail::bool_<true>) const
+ { return data_.get_value_traits(*this); }
+
+ real_value_traits &get_real_value_traits(detail::bool_<false>)
+ { return data_; }
+
+ real_value_traits &get_real_value_traits(detail::bool_<true>)
+ { return data_.get_value_traits(*this); }
+
/// @endcond
public:
+
+ const real_value_traits &get_real_value_traits() const
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
+ real_value_traits &get_real_value_traits()
+ { return this->get_real_value_traits(detail::bool_<external_value_traits>()); }
+
+ public:
//! <b>Effects</b>: constructs an empty list.
//!
//! <b>Complexity</b>: Constant
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks).
- slist()
+ slist_impl(const value_traits &v_traits = value_traits())
+ : data_(v_traits)
{
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
node_algorithms::init(this->get_root_node());
}
@@ -151,9 +230,10 @@
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks).
template<class Iterator>
- slist(Iterator b, Iterator e)
+ slist_impl(Iterator b, Iterator e, const value_traits &v_traits = value_traits())
+ : data_(v_traits)
{
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
node_algorithms::init(this->get_root_node());
insert_after(before_begin(), b, e);
}
@@ -162,12 +242,12 @@
//! or auto-unlink value, the destructor does nothing
//! (ie. no code is generated). Otherwise it detaches all elements from this.
//! In this case the objects in the list are not deleted (i.e. no destructors
- //! are called), but the hooks according to the ValueTraits template parameter
+ //! are called), but the hooks according to the value_traits template parameter
//! are set to their default value.
//!
//! <b>Complexity</b>: Linear to the number of elements in the list, if
//! it's a safe-mode or auto-unlink value. Otherwise constant.
- ~slist()
+ ~slist_impl()
{ this->clear(); }
//! <b>Effects</b>: Erases all the elements of the container.
@@ -185,7 +265,7 @@
}
else{
node_algorithms::init(this->get_root_node());
- size_traits::set_size(size_type(0));
+ this->priv_size_traits().set_size(size_type(0));
}
}
@@ -215,11 +295,11 @@
//! <b>Note</b>: Does not affect the validity of iterators and references.
void push_front(reference value)
{
- node_ptr to_insert = ValueTraits::to_node_ptr(value);
+ node_ptr to_insert = get_real_value_traits().to_node_ptr(value);
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(to_insert));
node_algorithms::link_after(this->get_root_node(), to_insert);
- size_traits::increment();
+ this->priv_size_traits().increment();
}
//! <b>Effects</b>: Erases the first element of the list.
@@ -234,7 +314,7 @@
{
node_ptr to_erase = node_traits::get_next(this->get_root_node());
node_algorithms::unlink_after(this->get_root_node());
- size_traits::decrement();
+ this->priv_size_traits().decrement();
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
}
@@ -254,7 +334,7 @@
{
node_ptr to_erase = node_traits::get_next(this->get_root_node());
this->pop_front();
- disposer(ValueTraits::to_value_ptr(to_erase));
+ disposer(get_real_value_traits().to_value_ptr(to_erase));
}
//! <b>Effects</b>: Returns a reference to the first element of the list.
@@ -263,7 +343,7 @@
//!
//! <b>Complexity</b>: Constant.
reference front()
- { return *ValueTraits::to_value_ptr(node_traits::get_next(this->get_root_node())); }
+ { return *get_real_value_traits().to_value_ptr(node_traits::get_next(this->get_root_node())); }
//! <b>Effects</b>: Returns a const_reference to the first element of the list.
//!
@@ -271,7 +351,7 @@
//!
//! <b>Complexity</b>: Constant.
const_reference front() const
- { return *ValueTraits::to_value_ptr(uncast(node_traits::get_next(this->get_root_node()))); }
+ { return *get_real_value_traits().to_value_ptr(uncast(node_traits::get_next(this->get_root_node()))); }
//! <b>Effects</b>: Returns an iterator to the first element contained in the list.
//!
@@ -279,7 +359,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator begin()
- { return iterator (node_traits::get_next(this->get_root_node())); }
+ { return iterator (node_traits::get_next(this->get_root_node()), this); }
//! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
//!
@@ -287,7 +367,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator begin() const
- { return const_iterator (node_traits::get_next(this->get_root_node())); }
+ { return const_iterator (node_traits::get_next(this->get_root_node()), this); }
//! <b>Effects</b>: Returns a const_iterator to the first element contained in the list.
//!
@@ -295,7 +375,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator cbegin() const
- { return const_iterator (node_traits::get_next(this->get_root_node())); }
+ { return const_iterator (node_traits::get_next(this->get_root_node()), this); }
//! <b>Effects</b>: Returns an iterator to the end of the list.
//!
@@ -303,7 +383,7 @@
//!
//! <b>Complexity</b>: Constant.
iterator end()
- { return iterator (this->get_root_node()); }
+ { return iterator (this->get_root_node(), this); }
//! <b>Effects</b>: Returns a const_iterator to the end of the list.
//!
@@ -311,7 +391,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator end() const
- { return const_iterator (uncast(this->get_root_node())); }
+ { return const_iterator (uncast(this->get_root_node()), this); }
//! <b>Effects</b>: Returns a const_iterator to the end of the list.
//!
@@ -319,7 +399,7 @@
//!
//! <b>Complexity</b>: Constant.
const_iterator cend() const
- { return const_iterator (uncast(this->get_root_node())); }
+ { return const_iterator (uncast(this->get_root_node()), this); }
//! <b>Effects</b>: Returns an iterator that points to a position
//! before the first element. Equivalent to "end()"
@@ -356,11 +436,8 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static slist &container_from_end_iterator(iterator end_iterator)
- {
- return *detail::parent_from_member<slist, node>
- ( detail::get_pointer(end_iterator.pointed_node()), &slist::root_);
- }
+ static slist_impl &container_from_end_iterator(iterator end_iterator)
+ { return priv_container_from_end_iterator(end_iterator); }
//! <b>Precondition</b>: end_iterator must be a valid end const_iterator
//! of slist.
@@ -370,24 +447,21 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Constant.
- static const slist &container_from_end_iterator(const_iterator end_iterator)
- {
- return *detail::parent_from_member<slist, node>
- ( detail::get_pointer(end_iterator.pointed_node()), &slist::root_);
- }
+ static const slist_impl &container_from_end_iterator(const_iterator end_iterator)
+ { return priv_container_from_end_iterator(end_iterator); }
//! <b>Effects</b>: Returns the number of the elements contained in the list.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Linear to the number of elements contained in the list.
- //! if ConstantTimeSize is false. Constant time otherwise.
+ //! if constant_time_size is false. Constant time otherwise.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
size_type size() const
{
- if(ConstantTimeSize)
- return size_traits::get_size();
+ if(constant_time_size)
+ return this->priv_size_traits().get_size();
else
return node_algorithms::count(this->get_root_node()) - 1;
}
@@ -409,13 +483,13 @@
//! <b>Complexity</b>: Linear to the number of elements of both lists.
//!
//! <b>Note</b>: Does not affect the validity of iterators and references.
- void swap(slist& other)
+ void swap(slist_impl& other)
{
node_algorithms::swap_nodes(this->get_root_node(), other.get_root_node());
- if(ConstantTimeSize){
- size_type backup = size_traits::get_size();
- size_traits::set_size(other.get_size());
- other.set_size(backup);
+ if(constant_time_size){
+ size_type backup = this->priv_size_traits().get_size();
+ this->priv_size_traits().set_size(other.priv_size_traits().get_size());
+ other.priv_size_traits().set_size(backup);
}
}
@@ -533,25 +607,21 @@
//!
//! <b>Throws</b>: If cloner throws.
template <class Cloner, class Disposer>
- void clone_from(const slist &src, Cloner cloner, Disposer disposer)
+ void clone_from(const slist_impl &src, Cloner cloner, Disposer disposer)
{
this->clear_and_dispose(disposer);
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
- BOOST_TRY{
- #endif
+ BOOST_INTRUSIVE_TRY{
iterator prev = this->before_begin();
const_iterator b(src.begin()), e(src.end());
for(; b != e; ++b, ++prev){
this->insert_after(prev, *cloner(*b));
}
- #ifndef BOOST_INTRUSIVE_DISABLE_EXCEPTION_HANDLING
}
- BOOST_CATCH(...){
+ BOOST_INTRUSIVE_CATCH(...){
this->clear_and_dispose(disposer);
BOOST_RETHROW;
}
- BOOST_CATCH_END
- #endif
+ BOOST_INTRUSIVE_CATCH_END
}
//! <b>Requires</b>: value must be an lvalue and prev_p must point to an element
@@ -569,12 +639,12 @@
//! <b>Note</b>: Does not affect the validity of iterators and references.
iterator insert_after(iterator prev_p, reference value)
{
- node_ptr n = ValueTraits::to_node_ptr(value);
+ node_ptr n = get_real_value_traits().to_node_ptr(value);
if(safemode_or_autounlink)
BOOST_INTRUSIVE_SAFE_HOOK_DEFAULT_ASSERT(node_algorithms::unique(n));
node_algorithms::link_after(prev_p.pointed_node(), n);
- size_traits::increment();
- return iterator (n);
+ this->priv_size_traits().increment();
+ return iterator (n, this);
}
//! <b>Requires</b>: Dereferencing iterator must yield
@@ -644,7 +714,7 @@
iterator it(prev); ++it;
node_ptr to_erase(it.pointed_node());
node_algorithms::unlink_after(prev.pointed_node());
- size_traits::decrement();
+ this->priv_size_traits().decrement();
iterator ret(++prev);
if(safemode_or_autounlink)
node_algorithms::init(to_erase);
@@ -725,7 +795,7 @@
iterator it(prev); ++it;
node_ptr to_erase(it.pointed_node());
iterator ret(this->erase_after(prev));
- disposer(ValueTraits::to_value_ptr(to_erase));
+ disposer(get_real_value_traits().to_value_ptr(to_erase));
return ret;
}
@@ -853,7 +923,7 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- iterator splice_after(iterator prev, slist &x)
+ iterator splice_after(iterator prev, slist_impl &x)
{
if (!x.empty()){
iterator last_x(x.previous(x.end()));
@@ -861,8 +931,8 @@
( prev.pointed_node()
, x.end().pointed_node()
, last_x.pointed_node());
- size_traits::set_size(size_traits::get_size() + x.get_size());
- x.set_size(size_type(0));
+ this->priv_size_traits().set_size(this->priv_size_traits().get_size() + x.priv_size_traits().get_size());
+ x.priv_size_traits().set_size(size_type(0));
return last_x;
}
else{
@@ -883,15 +953,15 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice_after(iterator prev, slist &x, iterator prev_ele)
+ void splice_after(iterator prev, slist_impl &x, iterator prev_ele)
{
iterator nxt = prev_ele;
++nxt;
if (nxt != prev && prev_ele != prev){
node_algorithms::transfer_after
(prev.pointed_node(), prev_ele.pointed_node(), nxt.pointed_node());
- size_traits::increment();
- x.decrement();
+ this->priv_size_traits().increment();
+ x.priv_size_traits().decrement();
}
}
@@ -906,19 +976,19 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Linear to the number of elements transferred
- //! if ConstantTimeSize is true. Constant-time otherwise.
+ //! if constant_time_size is true. Constant-time otherwise.
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice_after(iterator prev_pos, slist &x, iterator before_first, iterator before_last)
+ void splice_after(iterator prev_pos, slist_impl &x, iterator before_first, iterator before_last)
{
if (before_first != before_last){
- if(ConstantTimeSize){
+ if(constant_time_size){
size_type increment = std::distance(before_first, before_last);
node_algorithms::transfer_after
(prev_pos.pointed_node(), before_first.pointed_node(), before_last.pointed_node());
- size_traits::set_size(size_traits::get_size() + increment);
- x.set_size(x.get_size() - increment);
+ this->priv_size_traits().set_size(this->priv_size_traits().get_size() + increment);
+ x.priv_size_traits().set_size(x.priv_size_traits().get_size() - increment);
}
else{
node_algorithms::transfer_after
@@ -941,15 +1011,15 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice_after(iterator prev_pos, slist &x, iterator before_first, iterator before_last, difference_type n)
+ void splice_after(iterator prev_pos, slist_impl &x, iterator before_first, iterator before_last, difference_type n)
{
if(n){
- if(ConstantTimeSize){
+ if(constant_time_size){
BOOST_INTRUSIVE_INVARIANT_ASSERT(std::distance(before_first, before_last) == n);
node_algorithms::transfer_after
(prev_pos.pointed_node(), before_first.pointed_node(), before_last.pointed_node());
- size_traits::set_size(size_traits::get_size() + n);
- x.set_size(x.get_size() - n);
+ this->priv_size_traits().set_size(this->priv_size_traits().get_size() + n);
+ x.priv_size_traits().set_size(x.priv_size_traits().get_size() - n);
}
else{
node_algorithms::transfer_after
@@ -975,7 +1045,7 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- iterator splice(iterator it, slist &x)
+ iterator splice(iterator it, slist_impl &x)
{ return splice_after(this->previous(it), x); }
//! <b>Requires</b>: it p must be a valid iterator of *this.
@@ -991,7 +1061,7 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice(iterator pos, slist &x, iterator elem)
+ void splice(iterator pos, slist_impl &x, iterator elem)
{ return splice_after(this->previous(pos), x, this->previous(elem)); }
//! <b>Requires</b>: pos must be a dereferenceable iterator in *this
@@ -1004,11 +1074,11 @@
//! <b>Throws</b>: Nothing.
//!
//! <b>Complexity</b>: Linear to the sum of elements before pos, first, and last.
- //! Plus linear to the number of elements transferred if ConstantTimeSize is true.
+ //! Plus linear to the number of elements transferred if constant_time_size is true.
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice(iterator pos, slist &x, iterator first, iterator last)
+ void splice(iterator pos, slist_impl &x, iterator first, iterator last)
{ return splice_after(this->previous(pos), x, this->previous(first), this->previous(last)); }
//! <b>Requires</b>: pos must be a dereferenceable iterator in *this
@@ -1025,7 +1095,7 @@
//!
//! <b>Note</b>: Iterators of values obtained from list x now point to elements of this
//! list. Iterators of this list and all the references are not invalidated.
- void splice(iterator pos, slist &x, iterator first, iterator last, difference_type n)
+ void splice(iterator pos, slist_impl &x, iterator first, iterator last, difference_type n)
{ return splice_after(this->previous(pos), x, this->previous(first), this->previous(last), n); }
//! <b>Effects</b>: This function sorts the list *this according to std::less<value_type>.
@@ -1044,8 +1114,8 @@
{
if (node_traits::get_next(node_traits::get_next(this->get_root_node()))
!= this->get_root_node()) {
- slist carry;
- slist counter[64];
+ slist_impl carry;
+ slist_impl counter[64];
int fill = 0;
iterator last_inserted;
while(!this->empty()){
@@ -1057,8 +1127,10 @@
}
BOOST_INTRUSIVE_INVARIANT_ASSERT(counter[i].empty());
- iterator last_element(previous_node(last_inserted, carry.end()));
- if(ConstantTimeSize){
+ node_ptr p = node_algorithms::get_previous_node
+ (last_inserted.pointed_node(), carry.end().pointed_node());
+ iterator last_element(p, this);
+ if(constant_time_size){
counter[i].splice_after( counter[i].end(), carry
, carry.before_begin(), last_element
, carry.size());
@@ -1067,19 +1139,18 @@
counter[i].splice_after( counter[i].end(), carry
, carry.before_begin(), last_element);
}
- //counter[i].splice_after(counter[i].end(), carry, carry.end(), previous_node(last_inserted, carry.end()));
- //carry.swap(counter[i]);
if(i == fill)
++fill;
}
for (int i = 1; i < fill; ++i)
last_inserted = counter[i].merge(counter[i-1], p);
- //this->swap(counter[fill-1]);
BOOST_INTRUSIVE_INVARIANT_ASSERT(this->empty());
- iterator last_element(previous_node(last_inserted, counter[--fill].end()));
- if(ConstantTimeSize){
+ node_ptr p = node_algorithms::get_previous_node
+ (last_inserted.pointed_node(), counter[--fill].end().pointed_node());
+ iterator last_element(p, this);
+ if(constant_time_size){
this->splice_after( end(), counter[fill], counter[fill].before_begin()
, last_element, counter[fill].size());
}
@@ -1126,7 +1197,7 @@
//!
//! <b>Note</b>: Iterators and references are not invalidated.
template<class Predicate>
- iterator merge(slist& x, Predicate p)
+ iterator merge(slist_impl& x, Predicate p)
{
iterator a(before_begin()), e(end()), ax(x.before_begin());
iterator last_inserted(e);
@@ -1161,7 +1232,7 @@
//! size() + x.size() - 1 comparisons.
//!
//! <b>Note</b>: Iterators and references are not invalidated
- void merge(slist& x)
+ void merge(slist_impl& x)
{ this->merge(x, std::less<value_type>()); }
//! <b>Effects</b>: Reverses the order of elements in the list.
@@ -1328,10 +1399,46 @@
//! <b>Complexity</b>: Constant time.
//!
//! <b>Note</b>: Iterators and references are not invalidated.
- static iterator iterator_to(reference value)
+ //! This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static iterator s_iterator_to(reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT (!node_algorithms::unique(value_traits::to_node_ptr(value)));
+ return iterator (value_traits::to_node_ptr(value), 0);
+ }
+
+ //! <b>Requires</b>: value must be a const reference to a value inserted in a list.
+ //!
+ //! <b>Effects</b>: This function returns an iterator pointing to the element.
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Complexity</b>: Constant time.
+ //!
+ //! <b>Note</b>: Iterators and references are not invalidated.
+ //! This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_iterator s_iterator_to(const_reference value)
+ {
+ BOOST_STATIC_ASSERT((!stateful_value_traits));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT (!node_algorithms::unique(value_traits::to_node_ptr(const_cast<reference> (value))));
+ return const_iterator (value_traits::to_node_ptr(const_cast<reference> (value)), 0);
+ }
+
+ //! <b>Requires</b>: value must be a reference to a value inserted in a list.
+ //!
+ //! <b>Effects</b>: This function returns a const_iterator pointing to the element
+ //!
+ //! <b>Throws</b>: Nothing.
+ //!
+ //! <b>Complexity</b>: Constant time.
+ //!
+ //! <b>Note</b>: Iterators and references are not invalidated.
+ iterator iterator_to(reference value)
{
- BOOST_INTRUSIVE_INVARIANT_ASSERT (!node_algorithms::unique(ValueTraits::to_node_ptr(value)));
- return iterator (ValueTraits::to_node_ptr(value));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT (!node_algorithms::unique(value_traits::to_node_ptr(value)));
+ return iterator (value_traits::to_node_ptr(value), this);
}
//! <b>Requires</b>: value must be a const reference to a value inserted in a list.
@@ -1343,10 +1450,10 @@
//! <b>Complexity</b>: Constant time.
//!
//! <b>Note</b>: Iterators and references are not invalidated.
- static const_iterator iterator_to(const_reference value)
+ const_iterator iterator_to(const_reference value) const
{
- BOOST_INTRUSIVE_INVARIANT_ASSERT (!node_algorithms::unique(ValueTraits::to_node_ptr(const_cast<reference> (value))));
- return const_iterator (ValueTraits::to_node_ptr(const_cast<reference> (value)));
+ BOOST_INTRUSIVE_INVARIANT_ASSERT (!node_algorithms::unique(value_traits::to_node_ptr(const_cast<reference> (value))));
+ return const_iterator (value_traits::to_node_ptr(const_cast<reference> (value)), this);
}
//! <b>Returns</b>: The iterator to the element before i in the list.
@@ -1360,7 +1467,7 @@
{
return iterator
(node_algorithms::get_previous_node
- (before_begin().pointed_node(), i.pointed_node()));
+ (before_begin().pointed_node(), i.pointed_node()), 0);
}
//! <b>Returns</b>: The const_iterator to the element before i in the list.
@@ -1374,17 +1481,52 @@
{
return const_iterator
(node_algorithms::get_previous_node
- (before_begin().pointed_node(), i.pointed_node()));
+ (before_begin().pointed_node(), i.pointed_node()), 0);
+ }
+
+ private:
+ static slist_impl &priv_container_from_end_iterator(const const_iterator &end_iterator)
+ {
+ root_plus_size *r = detail::parent_from_member<root_plus_size, node>
+ ( detail::get_pointer(end_iterator.pointed_node()), &root_plus_size::root_);
+ data_t *d = detail::parent_from_member<data_t, root_plus_size>
+ ( r, &data_t::root_plus_size_);
+ slist_impl *s = detail::parent_from_member<slist_impl, data_t>(d, &slist_impl::data_);
+ return *s;
}
};
-template <class V, bool C, class S>
-inline bool operator==(const slist<V, C, S>& x, const slist<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const slist_impl<T, Options...> &x, const slist_impl<T, Options...> &y)
+#else
+(const slist_impl<Config> &x, const slist_impl<Config> &y)
+#endif
+{ return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); }
+
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+bool operator==
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const slist_impl<T, Options...> &x, const slist_impl<T, Options...> &y)
+#else
+(const slist_impl<Config> &x, const slist_impl<Config> &y)
+#endif
{
+ typedef slist_impl<Config> slist_type;
+ typedef typename slist_type::const_iterator const_iterator;
+ const bool C = slist_type::constant_time_size;
if(C && x.size() != y.size()){
return false;
}
- typedef typename slist<V, C, S>::const_iterator const_iterator;
const_iterator end1 = x.end();
const_iterator i1 = x.begin();
@@ -1406,31 +1548,131 @@
}
}
-template <class V, bool C, class S>
-inline bool operator<(const slist<V, C, S>& x,
- const slist<V, C, S>& y)
-{ return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end()); }
-
-template <class V, bool C, class S>
-inline bool operator!=(const slist<V, C, S>& x, const slist<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator!=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const slist_impl<T, Options...> &x, const slist_impl<T, Options...> &y)
+#else
+(const slist_impl<Config> &x, const slist_impl<Config> &y)
+#endif
{ return !(x == y); }
-template <class V, bool C, class S>
-inline bool operator>(const slist<V, C, S>& x, const slist<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const slist_impl<T, Options...> &x, const slist_impl<T, Options...> &y)
+#else
+(const slist_impl<Config> &x, const slist_impl<Config> &y)
+#endif
{ return y < x; }
-template <class V, bool C, class S>
-inline bool operator<=(const slist<V, C, S>& x, const slist<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator<=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const slist_impl<T, Options...> &x, const slist_impl<T, Options...> &y)
+#else
+(const slist_impl<Config> &x, const slist_impl<Config> &y)
+#endif
{ return !(y < x); }
-template <class V, bool C, class S>
-inline bool operator>=(const slist<V, C, S>& x, const slist<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline bool operator>=
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(const slist_impl<T, Options...> &x, const slist_impl<T, Options...> &y)
+#else
+(const slist_impl<Config> &x, const slist_impl<Config> &y)
+#endif
{ return !(x < y); }
-template <class V, bool C, class S>
-inline void swap(slist<V, C, S>& x, slist<V, C, S>& y)
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+inline void swap
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+(slist_impl<T, Options...> &x, slist_impl<T, Options...> &y)
+#else
+(slist_impl<Config> &x, slist_impl<Config> &y)
+#endif
{ x.swap(y); }
+//! Helper metafunction to define a \c slist that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_slist
+{
+ /// @cond
+ typedef typename pack_options
+ < slist_defaults<T>, O1, O2, O3>::type packed_options;
+ typedef typename detail::get_value_traits
+ <T, typename packed_options::value_traits>::type value_traits;
+ typedef slist_impl
+ <
+ slistopt
+ < value_traits
+ , typename packed_options::size_type
+ , packed_options::constant_time_size
+ >
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3>
+class slist
+ : public make_slist<T, O1, O2, O3>::type
+{
+ typedef typename make_slist
+ <T, O1, O2, O3>::type Base;
+ typedef typename Base::real_value_traits real_value_traits;
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename real_value_traits::value_type, T>::value));
+ public:
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+
+ slist(const value_traits &v_traits = value_traits())
+ : Base(v_traits)
+ {}
+
+ template<class Iterator>
+ slist(Iterator b, Iterator e, const value_traits &v_traits = value_traits())
+ : Base(b, e, v_traits)
+ {}
+
+ static slist &container_from_end_iterator(iterator end_iterator)
+ { return static_cast<slist &>(Base::container_from_end_iterator(end_iterator)); }
+
+ static const slist &container_from_end_iterator(const_iterator end_iterator)
+ { return static_cast<const slist &>(Base::container_from_end_iterator(end_iterator)); }
+};
+
+#endif
+
} //namespace intrusive
} //namespace boost
Modified: branches/bcbboost/boost/intrusive/slist_hook.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/slist_hook.hpp (original)
+++ branches/bcbboost/boost/intrusive/slist_hook.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,19 +17,48 @@
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
#include <boost/intrusive/detail/utilities.hpp>
-#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/detail/slist_node.hpp>
#include <boost/intrusive/circular_slist_algorithms.hpp>
-#include <boost/intrusive/linking_policy.hpp>
-#include <boost/intrusive/tag.hpp>
-#include <boost/static_assert.hpp>
+#include <boost/intrusive/options.hpp>
+#include <boost/intrusive/detail/generic_hook.hpp>
namespace boost {
namespace intrusive {
+/// @cond
+template<class VoidPointer>
+struct get_slist_node_algo
+{
+ typedef circular_slist_algorithms<slist_node_traits<VoidPointer> > type;
+};
+/// @endcond
+
+//! Helper metafunction to define a \c slist_base_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_slist_base_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
+
+ typedef detail::generic_hook
+ < get_slist_node_algo<typename packed_options::void_pointer>
+ , typename packed_options::tag
+ , packed_options::link_mode
+ , detail::SlistBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
//! Derive a class from slist_base_hook in order to store objects in
-//! in an slist. slist_base_hook holds the data necessary to maintain the
-//! list and provides an appropriate value_traits class for slist.
+//! in an list. slist_base_hook holds the data necessary to maintain the
+//! list and provides an appropriate value_traits class for list.
//!
//! The first integer template argument defines a tag to identify the node.
//! The same tag value can be used in different classes, but if a class is
@@ -39,97 +68,50 @@
//! The second boolean template parameter will specify the linking mode of the hook.
//!
//! The third argument is the pointer type that will be used internally in the hook
-//! and the slist configured from this hook.
-template< class Tag //= tag
- , linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+//! and the list configured from this hook.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class slist_base_hook
- : private detail::slist_node_traits<VoidPointer>::node
+ : public make_slist_base_hook<O1, O2, O3>::type
{
- public:
- typedef detail::slist_node_traits<VoidPointer> node_traits;
- enum { linking_policy = Policy };
-
- /// @cond
- private:
- typedef circular_slist_algorithms<node_traits> node_algorithms;
- /// @endcond
-
- public:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef slist_base_hook
- <Tag, Policy, VoidPointer> this_type;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type>::type this_type_ptr;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type>::type const_this_type_ptr;
-
- /// @cond
- private:
- node_ptr this_as_node()
- { return node_ptr(static_cast<node *const>(this)); }
-
- const_node_ptr this_as_node() const
- { return const_node_ptr(static_cast<const node *const>(this)); }
- /// @endcond
-
- public:
-
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
//! <b>Throws</b>: Nothing.
- slist_base_hook()
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ slist_base_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using slist_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- slist_base_hook(const slist_base_hook& )
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ slist_base_hook(const slist_base_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using slist_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- slist_base_hook& operator=(const slist_base_hook& )
- { return *this; }
+ slist_base_hook& operator=(const slist_base_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an slist an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
//!
//! <b>Throws</b>: Nothing.
- ~slist_base_hook()
- { detail::destructor_impl(*this, detail::dispatcher<Policy>()); }
+ ~slist_base_hook();
//! <b>Effects</b>: Swapping two nodes swaps the position of the elements
//! related to those nodes in one or two containers. That is, if the node
@@ -143,174 +125,99 @@
//! <b>Complexity</b>: Constant
//!
//! <b>Throws</b>: Nothing.
- void swap_nodes(slist_base_hook &other)
- { node_algorithms::swap_nodes(this_as_node(), other.this_as_node()); }
+ void swap_nodes(slist_base_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
//! <b>Returns</b>: true, if the node belongs to a container, false
- //! otherwise. This function can be used to test whether list::iterator_to
+ //! otherwise. This function can be used to test whether \c slist::iterator_to
//! will return a valid iterator.
//!
//! <b>Complexity</b>: Constant
- bool is_linked() const
- {
- //is_linked() can be only used in safe-mode or auto-unlink
- BOOST_STATIC_ASSERT((Policy == safe_link || Policy == auto_unlink));
- return !node_algorithms::unique(this_as_node());
- }
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
- //!
- //! <b>Throws</b>: Nothing.
- void unlink()
- {
- BOOST_STATIC_ASSERT((Policy == auto_unlink));
- node_algorithms::unlink(this_as_node());
- node_algorithms::init(this_as_node());
- }
-
- //! The value_traits class is used as the first template argument for list.
- //! The template argument T defines the class type stored in list. Objects
- //! of type T and of types derived from T can be stored. T doesn't need to be
- //! copy-constructible or assignable.
- template<class T>
- struct value_traits
- : detail::derivation_hook_value_traits<T, this_type, Tag>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr(static_cast<slist_base_hook*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr(static_cast<const slist_base_hook*> (detail::get_pointer(p)));
- }
+ void unlink();
+ #endif
+};
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return this_as_node(); }
+//! Helper metafunction to define a \c slist_member_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_slist_member_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return this_as_node(); }
+ typedef detail::generic_hook
+ < get_slist_node_algo<typename packed_options::void_pointer>
+ , member_tag
+ , packed_options::link_mode
+ , detail::NoBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
};
//! Put a public data member slist_member_hook in order to store objects of this class in
-//! an slist. slist_member_hook holds the data necessary for maintaining the list and
-//! provides an appropriate value_traits class for slist.
-//!
-//! The template argument T defines the class type stored in slist. Objects of type
-//! T and of types derived from T can be stored. T doesn't need to be
-//! copy-constructible or assignable.
+//! an list. slist_member_hook holds the data necessary for maintaining the list and
+//! provides an appropriate value_traits class for list.
//!
-//! The second boolean template parameter will specify the linking mode of the hook.
+//! The first boolean template parameter will specify the linking mode of the hook.
//!
-//! The third argument is the pointer type that will be used internally in the hook
-//! and the slist configured from this hook.
-template< linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
-class slist_member_hook
- : private detail::slist_node_traits<VoidPointer>::node
+//! The second argument is the pointer type that will be used internally in the hook
+//! and the list configured from this hook.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
+class slist_member_hook
+ : public make_slist_member_hook<O1, O2, O3>::type
{
- public:
- typedef detail::slist_node_traits<VoidPointer> node_traits;
- enum { linking_policy = Policy };
-
- /// @cond
- private:
- typedef circular_slist_algorithms<node_traits> node_algorithms;
- /// @endcond
-
- public:
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef slist_member_hook
- <Policy, VoidPointer> this_type;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type >::type this_type_ptr;
-
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type >::type const_this_type_ptr;
-
- /// @cond
- private:
- node_ptr this_as_node()
- { return node_ptr(static_cast<node *const>(this)); }
-
- const_node_ptr this_as_node() const
- { return const_node_ptr(static_cast<const node *const>(this)); }
- /// @endcond
-
- public:
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
//! <b>Throws</b>: Nothing.
- slist_member_hook()
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ slist_member_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using slist_member_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- slist_member_hook(const slist_member_hook& )
- : node()
- {
- if(Policy == safe_link || Policy == auto_unlink){
- node_algorithms::init(this_as_node());
- }
- }
+ slist_member_hook(const slist_member_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using slist_member_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- slist_member_hook& operator=(const slist_member_hook& )
- { return *this; }
+ slist_member_hook& operator=(const slist_member_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an slist an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
//!
//! <b>Throws</b>: Nothing.
- ~slist_member_hook()
- { detail::destructor_impl(*this, detail::dispatcher<Policy>()); }
+ ~slist_member_hook();
//! <b>Effects</b>: Swapping two nodes swaps the position of the elements
//! related to those nodes in one or two containers. That is, if the node
@@ -323,78 +230,29 @@
//!
//! <b>Complexity</b>: Constant
//!
- //! <b>Throws</b>: Nothing.
- void swap_nodes(slist_member_hook& other)
- { node_algorithms::swap_nodes(this_as_node(), other.this_as_node()); }
+ //! <b>Throws</b>: Nothing.
+ void swap_nodes(slist_member_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
//! <b>Returns</b>: true, if the node belongs to a container, false
- //! otherwise. This function can be used to test whether list::iterator_to
+ //! otherwise. This function can be used to test whether \c slist::iterator_to
//! will return a valid iterator.
//!
- //! <b>Complexity</b>: Constant
- bool is_linked() const
- {
- //is_linked() can be only used in safe-mode or auto-unlink
- BOOST_STATIC_ASSERT((Policy == safe_link || Policy == auto_unlink));
- return !node_algorithms::unique(this_as_node());
- }
+ //! <b>Complexity</b>: Constant
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
- //!
- //! <b>Throws</b>: Nothing.
- void unlink()
- {
- BOOST_STATIC_ASSERT((Policy == auto_unlink));
- node_algorithms::unlink(this_as_node());
- node_algorithms::init(this_as_node());
- }
-
- //! The value_traits class is used as the first template argument for list.
- //! The template argument is a pointer to member pointing to the node in
- //! the class. Objects of type T and of types derived from T can be stored.
- //! T doesn't need to be copy-constructible or assignable.
- template<class T, this_type T::* M>
- struct value_traits
- : detail::member_hook_value_traits<T, this_type, M>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr(static_cast<this_type*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr(static_cast<const this_type*> (detail::get_pointer(p)));
- }
-
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return this_as_node(); }
-
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return this_as_node(); }
+ void unlink();
+ #endif
};
} //namespace intrusive
} //namespace boost
-#include<boost/intrusive/detail/config_end.hpp>
+#include <boost/intrusive/detail/config_end.hpp>
#endif //BOOST_INTRUSIVE_SLIST_HOOK_HPP
Deleted: branches/bcbboost/boost/intrusive/tag.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/tag.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,26 +0,0 @@
-/////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2006-2007
-//
-// 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)
-//
-// See http://www.boost.org/libs/intrusive for documentation.
-//
-/////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTRUSIVE_DEFAULT_TAG_HPP
-#define BOOST_INTRUSIVE_DEFAULT_TAG_HPP
-
-namespace boost {
-namespace intrusive {
-
-//!This is the declaration of the default
-//!hook used by base hooks
-class tag;
-
-} //namespace intrusive
-} //namespace boost
-
-#endif //BOOST_INTRUSIVE_DEFAULT_TAG_HPP
Modified: branches/bcbboost/boost/intrusive/trivial_value_traits.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/trivial_value_traits.hpp (original)
+++ branches/bcbboost/boost/intrusive/trivial_value_traits.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -13,7 +13,7 @@
#ifndef BOOST_INTRUSIVE_TRIVIAL_VALUE_TRAITS_HPP
#define BOOST_INTRUSIVE_TRIVIAL_VALUE_TRAITS_HPP
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
namespace boost {
namespace intrusive {
@@ -21,7 +21,7 @@
//!This value traits template is used to create value traits
//!from user defined node traits where value_traits::value_type and
//!node_traits::node should be equal
-template<class NodeTraits, linking_policy LinkingPolicy = safe_link>
+template<class NodeTraits, link_mode_type LinkMode = normal_link>
struct trivial_value_traits
{
typedef NodeTraits node_traits;
@@ -30,11 +30,11 @@
typedef typename node_traits::node value_type;
typedef node_ptr pointer;
typedef const_node_ptr const_pointer;
- enum { linking_policy = LinkingPolicy };
- static node_ptr to_node_ptr (value_type &value) { return node_ptr(&value); }
+ static const link_mode_type link_mode = LinkMode;
+ static node_ptr to_node_ptr (value_type &value) { return node_ptr(&value); }
static const_node_ptr to_node_ptr (const value_type &value) { return const_node_ptr(&value); }
- static pointer to_value_ptr(node_ptr n) { return pointer(n); }
- static const_pointer to_value_ptr(const_node_ptr n) { return const_pointer(n); }
+ static pointer to_value_ptr(node_ptr n) { return pointer(n); }
+ static const_pointer to_value_ptr(const_node_ptr n) { return const_pointer(n); }
};
} //namespace intrusive
Modified: branches/bcbboost/boost/intrusive/unordered_set.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/unordered_set.hpp (original)
+++ branches/bcbboost/boost/intrusive/unordered_set.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,8 +10,8 @@
// See http://www.boost.org/libs/intrusive for documentation.
//
/////////////////////////////////////////////////////////////////////////////
-#ifndef BOOST_INTRUSIVE_HASHSET_HPP
-#define BOOST_INTRUSIVE_HASHSET_HPP
+#ifndef BOOST_INTRUSIVE_UNORDERED_SET_HPP
+#define BOOST_INTRUSIVE_UNORDERED_SET_HPP
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
@@ -32,27 +32,22 @@
//! unordered_set more complicated than purely intrusive containers.
//! `bucket_type` is default-constructible, copyable and assignable
//!
-//! The template parameter ValueTraits is called "value traits". It stores
-//! information and operations about the type to be stored in the container.
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
//!
-//! The template parameter Hash is a unary function object that take an argument
-//! of type ValueTraits::value_type and returns a value of type std::size_t.
-//!
-//! The template parameter Equal is a binary predicate that takes two arguments of
-//! type ValueTraits::value_type. Equal is an equivalence relation.
-//!
-//! If the user specifies ConstantTimeSize as "true", a member of type SizeType
-//! will be embedded in the class, that will keep track of the number of stored objects.
-//! This will allow constant-time O(1) size() member, instead of default O(N) size.
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<>, \c size_type<>, \c hash<> and \c equal<> .
//!
//! unordered_set only provides forward iterators but it provides 4 iterator types:
//! iterator and const_iterator to navigate through the whole container and
//! local_iterator and const_local_iterator to navigate through the values
//! stored in a single bucket. Local iterators are faster and smaller.
//!
-//! It's not recommended to use non ConstantTimeSize unordered_sets because several
+//! It's not recommended to use non constant-time size unordered_sets because several
//! key functions, like "empty()", become non-constant time functions. Non
-//! ConstantTimeSize unordered_sets are mainly provided to support auto-unlink hooks.
+//! constant-time size unordered_sets are mainly provided to support auto-unlink hooks.
//!
//! unordered_set, unlike std::unordered_set, does not make automatic rehashings nor
//! offers functions related to a load factor. Rehashing can be explicitly requested
@@ -60,48 +55,53 @@
//!
//! Since no automatic rehashing is done, iterators are never invalidated when
//! inserting or erasing elements. Iterators are only invalidated when rehasing.
-template< class ValueTraits
- , class Hash //= boost::hash<typename ValueTraits::value_type>
- , class Equal //= std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class unordered_set
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class unordered_set_impl
{
/// @cond
private:
- typedef hashtable<ValueTraits, Hash, Equal, ConstantTimeSize, SizeType> table_type;
+ typedef hashtable_impl<Config> table_type;
//! This class is
//! non-copyable
- unordered_set (const unordered_set&);
+ unordered_set_impl (const unordered_set_impl&);
//! This class is
//! non-assignable
- unordered_set &operator =(const unordered_set&);
+ unordered_set_impl &operator =(const unordered_set_impl&);
typedef table_type implementation_defined;
/// @endcond
public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef value_type key_type;
- typedef Equal key_equal;
- typedef Hash hasher;
+ typedef typename implementation_defined::value_type value_type;
+ typedef typename implementation_defined::value_traits value_traits;
+ typedef typename implementation_defined::bucket_traits bucket_traits;
+ typedef typename implementation_defined::pointer pointer;
+ typedef typename implementation_defined::const_pointer const_pointer;
+ typedef typename implementation_defined::reference reference;
+ typedef typename implementation_defined::const_reference const_reference;
+ typedef typename implementation_defined::difference_type difference_type;
+ typedef typename implementation_defined::size_type size_type;
+ typedef typename implementation_defined::key_type key_type;
+ typedef typename implementation_defined::key_equal key_equal;
+ typedef typename implementation_defined::hasher hasher;
typedef typename implementation_defined::bucket_type bucket_type;
- typedef typename boost::pointer_to_other<pointer, bucket_type>::type bucket_ptr;
+ typedef typename implementation_defined::bucket_ptr bucket_ptr;
typedef typename implementation_defined::iterator iterator;
typedef typename implementation_defined::const_iterator const_iterator;
typedef typename implementation_defined::insert_commit_data insert_commit_data;
typedef typename implementation_defined::local_iterator local_iterator;
typedef typename implementation_defined::const_local_iterator const_local_iterator;
+ typedef typename implementation_defined::node_traits node_traits;
+ typedef typename implementation_defined::node node;
+ typedef typename implementation_defined::node_ptr node_ptr;
+ typedef typename implementation_defined::const_node_ptr const_node_ptr;
+ typedef typename implementation_defined::node_algorithms node_algorithms;
/// @cond
private:
@@ -112,7 +112,7 @@
//! <b>Requires</b>: buckets must not be being used by any other resource.
//!
- //! <b>Effects</b>: Constructs an empty unordered_set, storing a reference
+ //! <b>Effects</b>: Constructs an empty unordered_set_impl, storing a reference
//! to the bucket array and copies of the hasher and equal functors.
//!
//! <b>Complexity</b>: Constant.
@@ -123,11 +123,11 @@
//!
//! <b>Notes</b>: buckets array must be disposed only after
//! *this is disposed.
- unordered_set( bucket_ptr buckets
- , size_type buckets_len
- , const Hash & hasher = Hash()
- , const Equal &equal = Equal())
- : table_(buckets, buckets_len, hasher, equal)
+ unordered_set_impl( const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : table_(b_traits, hash_func, equal_func, v_traits)
{}
//! <b>Requires</b>: buckets must not be being used by any other resource
@@ -141,18 +141,18 @@
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor or invocation of Hash or Equal throws.
+ //! or the copy constructor or invocation of hasher or key_equal throws.
//!
//! <b>Notes</b>: buckets array must be disposed only after
//! *this is disposed.
template<class Iterator>
- unordered_set( bucket_ptr buckets
- , size_type buckets_len
- , Iterator b
- , Iterator e
- , const Hash & hasher = Hash()
- , const Equal &equal = Equal())
- : table_(buckets, buckets_len, hasher, equal)
+ unordered_set_impl( Iterator b
+ , Iterator e
+ , const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : table_(b_traits, hash_func, equal_func, v_traits)
{ table_.insert_unique(b, e); }
//! <b>Effects</b>: Detaches all elements from this. The objects in the unordered_set
@@ -162,7 +162,7 @@
//! it's a safe-mode or auto-unlink value. Otherwise constant.
//!
//! <b>Throws</b>: Nothing.
- ~unordered_set()
+ ~unordered_set_impl()
{}
//! <b>Effects</b>: Returns an iterator pointing to the beginning of the unordered_set.
@@ -236,7 +236,7 @@
//! <b>Effects</b>: Returns true is the container is empty.
//!
- //! <b>Complexity</b>: if ConstantTimeSize is false, average constant time
+ //! <b>Complexity</b>: if constant-time size option is disabled, average constant time
//! (worst case, with empty() == true): O(this->bucket_count()).
//! Otherwise constant.
//!
@@ -247,7 +247,7 @@
//! <b>Effects</b>: Returns the number of elements stored in the unordered_set.
//!
//! <b>Complexity</b>: Linear to elements contained in *this if
- //! ConstantTimeSize is false. Constant-time otherwise.
+ //! constant-time size option is enabled. Constant-time otherwise.
//!
//! <b>Throws</b>: Nothing.
size_type size() const
@@ -263,7 +263,7 @@
//!
//! <b>Throws</b>: If the swap() call for the comparison or hash functors
//! found using ADL throw. Basic guarantee.
- void swap(unordered_set& other)
+ void swap(unordered_set_impl& other)
{ table_.swap(other.table_); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
@@ -280,7 +280,7 @@
//!
//! <b>Throws</b>: If cloner throws. Basic guarantee.
template <class Cloner, class Disposer>
- void clone_from(const unordered_set &src, Cloner cloner, Disposer disposer)
+ void clone_from(const unordered_set_impl &src, Cloner cloner, Disposer disposer)
{ table_.clone_from(src.table_, cloner, disposer); }
//! <b>Requires</b>: value must be an lvalue
@@ -433,13 +433,13 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw. Basic guarantee.
+ //! <b>Throws</b>: If hash_func or equal_func throw. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- size_type erase(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return table_.erase(key, hasher, equal); }
+ size_type erase(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return table_.erase(key, hash_func, equal_func); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
//!
@@ -493,7 +493,7 @@
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
//!
//! <b>Effects</b>: Erases all the elements with the given key.
- //! according to the comparison functor "equal".
+ //! according to the comparison functor "equal_func".
//! Disposer::operator()(pointer) is called for the removed elements.
//!
//! <b>Returns</b>: The number of erased elements.
@@ -501,13 +501,13 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or key_value_equal throw. Basic guarantee.
+ //! <b>Throws</b>: If hash_func or equal_func throw. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators
//! to the erased elements.
template<class KeyType, class KeyHasher, class KeyValueEqual, class Disposer>
- size_type erase_and_dispose(const KeyType& key, KeyHasher hasher, KeyValueEqual equal, Disposer disposer)
- { return table_.erase_and_dispose(key, hasher, equal, disposer); }
+ size_type erase_and_dispose(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func, Disposer disposer)
+ { return table_.erase_and_dispose(key, hash_func, equal_func, disposer); }
//! <b>Effects</b>: Erases all of the elements.
//!
@@ -544,22 +544,22 @@
size_type count(const_reference value) const
{ return table_.find(value) != end(); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Returns the number of contained elements with the given key
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw.
+ //! <b>Throws</b>: If hash_func or equal_func throw.
template<class KeyType, class KeyHasher, class KeyValueEqual, class Disposer>
- size_type count(const KeyType& key, KeyHasher hasher, KeyValueEqual equal) const
- { return table_.find(key, hasher, equal) != end(); }
+ size_type count(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func) const
+ { return table_.find(key, hash_func, equal_func) != end(); }
//! <b>Effects</b>: Finds an iterator to the first element is equal to
//! "value" or end() if that element does not exist.
@@ -570,13 +570,13 @@
iterator find(const_reference value)
{ return table_.find(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Finds an iterator to the first element whose key is
//! "key" according to the given hasher and equality functor or end() if
@@ -584,14 +584,14 @@
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw.
+ //! <b>Throws</b>: If hash_func or equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- iterator find(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return table_.find(key, hasher, equal); }
+ iterator find(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return table_.find(key, hash_func, equal_func); }
//! <b>Effects</b>: Finds a const_iterator to the first element whose key is
//! "key" or end() if that element does not exist.
@@ -602,13 +602,13 @@
const_iterator find(const_reference value) const
{ return table_.find(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Finds an iterator to the first element whose key is
//! "key" according to the given hasher and equality functor or end() if
@@ -616,14 +616,14 @@
//!
//! <b>Complexity</b>: Average case O(1), worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw.
+ //! <b>Throws</b>: If hash_func or equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- const_iterator find(const KeyType& key, KeyHasher hasher, KeyValueEqual equal) const
- { return table_.find(key, equal); }
+ const_iterator find(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func) const
+ { return table_.find(key, hash_func, equal_func); }
//! <b>Effects</b>: Returns a range containing all elements with values equivalent
//! to value. Returns std::make_pair(this->end(), this->end()) if no such
@@ -635,28 +635,29 @@
std::pair<iterator,iterator> equal_range(const_reference value)
{ return table_.equal_range(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Returns a range containing all elements with equivalent
//! keys. Returns std::make_pair(this->end(), this->end()) if no such
//! elements exist.
//!
- //! <b>Complexity</b>: Average case O(this->count(key, hasher, equal)). Worst case O(this->size()).
+ //! <b>Complexity</b>: Average case O(this->count(key, hash_func, hash_func)).
+ //! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or the equal throw.
+ //! <b>Throws</b>: If hash_func or the equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- std::pair<iterator,iterator> equal_range(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return table_.equal_range(key, hasher, equal); }
+ std::pair<iterator,iterator> equal_range(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return table_.equal_range(key, hash_func, equal_func); }
//! <b>Effects</b>: Returns a range containing all elements with values equivalent
//! to value. Returns std::make_pair(this->end(), this->end()) if no such
@@ -669,29 +670,30 @@
equal_range(const_reference value) const
{ return table_.equal_range(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
- //! "key_value_equal" must be a equality function that induces
+ //! "equal_func" must be a equality function that induces
//! the same equality as key_equal. The difference is that
- //! "key_value_equal" compares an arbitrary key with the contained values.
+ //! "equal_func" compares an arbitrary key with the contained values.
//!
//! <b>Effects</b>: Returns a range containing all elements with equivalent
//! keys. Returns std::make_pair(this->end(), this->end()) if no such
//! elements exist.
//!
- //! <b>Complexity</b>: Average case O(this->count(key, hasher, equal)). Worst case O(this->size()).
+ //! <b>Complexity</b>: Average case O(this->count(key, hash_func, equal_func)).
+ //! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If the hasher or equal throw.
+ //! <b>Throws</b>: If the hash_func or equal_func throw.
//!
//! <b>Note</b>: This function is used when constructing a value_type
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
std::pair<const_iterator, const_iterator>
- equal_range(const KeyType& key, KeyHasher hasher, KeyValueEqual equal) const
- { return table_.equal_range(key, equal); }
+ equal_range(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func) const
+ { return table_.equal_range(key, hash_func, equal_func); }
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
//! appropriate type. Otherwise the behavior is undefined.
@@ -726,8 +728,11 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static local_iterator local_iterator_to(reference value)
- { return table_type::local_iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static local_iterator s_local_iterator_to(reference value)
+ { return table_type::s_local_iterator_to(value); }
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
//! appropriate type. Otherwise the behavior is undefined.
@@ -738,8 +743,35 @@
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static const_local_iterator local_iterator_to(const_reference value)
- { return table_type::local_iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_local_iterator s_local_iterator_to(const_reference value)
+ { return table_type::s_local_iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid local_iterator belonging to the unordered_set
+ //! that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ local_iterator local_iterator_to(reference value)
+ { return table_.local_iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid const_local_iterator belonging to
+ //! the unordered_set that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ const_local_iterator local_iterator_to(const_reference value) const
+ { return table_.local_iterator_to(value); }
//! <b>Effects</b>: Returns the number of buckets passed in the constructor
//! or the last rehash function.
@@ -771,21 +803,21 @@
size_type bucket(const value_type& k) const
{ return table_.bucket(k); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! <b>Effects</b>: Returns the index of the bucket in which elements
//! with keys equivalent to k would be found, if any such element existed.
//!
//! <b>Complexity</b>: Constant.
//!
- //! <b>Throws</b>: If hasher throws.
+ //! <b>Throws</b>: If hash_func throws.
//!
//! <b>Note</b>: the return value is in the range [0, this->bucket_count()).
template<class KeyType, class KeyHasher>
- size_type bucket(const KeyType& k, KeyHasher hasher) const
- { return table_.bucket(k, hasher); }
+ size_type bucket(const KeyType& k, KeyHasher hash_func) const
+ { return table_.bucket(k, hash_func); }
//! <b>Effects</b>: Returns the bucket array pointer passed in the constructor
//! or the last rehash function.
@@ -891,8 +923,8 @@
//! <b>Complexity</b>: Average case linear in this->size(), worst case quadratic.
//!
//! <b>Throws</b>: If the hasher functor throws. Basic guarantee.
- void rehash(bucket_ptr new_buckets, size_type new_size)
- { table_.rehash(new_buckets, new_size); }
+ void rehash(const bucket_traits &new_bucket_traits)
+ { table_.rehash(new_bucket_traits); }
//! <b>Effects</b>: Returns the nearest new bucket count optimized for
//! the container that is bigger than n. This suggestion can be used
@@ -919,6 +951,70 @@
{ return table_type::suggested_lower_bucket_count(n); }
};
+//! Helper metafunction to define an \c unordered_set that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none
+ , class O5 = none, class O6 = none
+ , class O7 = none
+ >
+#endif
+struct make_unordered_set
+{
+ /// @cond
+ typedef unordered_set_impl
+ < typename make_hashtable_opt
+ <T, O1, O2, O3, O4, O5, O6, O7>::type
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3, class O4, class O5, class O6, class O7>
+class unordered_set
+ : public make_unordered_set<T, O1, O2, O3, O4, O5, O6, O7>::type
+{
+ typedef typename make_unordered_set
+ <T, O1, O2, O3, O4, O5, O6, O7>::type Base;
+
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename Base::value_traits::value_type, T>::value));
+
+ public:
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::bucket_traits bucket_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+ typedef typename Base::bucket_ptr bucket_ptr;
+ typedef typename Base::size_type size_type;
+ typedef typename Base::hasher hasher;
+ typedef typename Base::key_equal key_equal;
+
+ unordered_set ( const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : Base(b_traits, hash_func, equal_func, v_traits)
+ {}
+
+ template<class Iterator>
+ unordered_set ( Iterator b
+ , Iterator e
+ , const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : Base(b, e, b_traits, hash_func, equal_func, v_traits)
+ {}
+};
+
+#endif
+
+
//! The class template unordered_multiset is an intrusive container, that mimics most of
//! the interface of std::tr1::unordered_multiset as described in the C++ TR1.
//!
@@ -930,27 +1026,22 @@
//! unordered_multiset more complicated than purely intrusive containers.
//! `bucket_type` is default-constructible, copyable and assignable
//!
-//! The template parameter ValueTraits is called "value traits". It stores
-//! information and operations about the type to be stored in the container.
-//!
-//! The template parameter Hash is a unary function object that take an argument
-//! of type ValueTraits::value_type and returns a value of type std::size_t.
+//! The template parameter \c T is the type to be managed by the container.
+//! The user can specify additional options and if no options are provided
+//! default options are used.
//!
-//! The template parameter Equal is a binary predicate that takes two arguments of
-//! type ValueTraits::value_type. Equal is an equivalence relation.
-//!
-//! If the user specifies ConstantTimeSize as "true", a member of type SizeType
-//! will be embedded in the class, that will keep track of the number of stored objects.
-//! This will allow constant-time O(1) size() member, instead of default O(N) size.
+//! The container supports the following options:
+//! \c base_hook<>/member_hook<>/value_traits<>,
+//! \c constant_time_size<>, \c size_type<>, \c hash<> and \c equal<> .
//!
//! unordered_multiset only provides forward iterators but it provides 4 iterator types:
//! iterator and const_iterator to navigate through the whole container and
//! local_iterator and const_local_iterator to navigate through the values
//! stored in a single bucket. Local iterators are faster and smaller.
//!
-//! It's not recommended to use non ConstantTimeSize unordered_multisets because several
+//! It's not recommended to use non constant-time size unordered_multisets because several
//! key functions, like "empty()", become non-constant time functions. Non
-//! ConstantTimeSize unordered_multisets are mainly provided to support auto-unlink hooks.
+//! constant-time size unordered_multisets are mainly provided to support auto-unlink hooks.
//!
//! unordered_multiset, unlike std::unordered_set, does not make automatic rehashings nor
//! offers functions related to a load factor. Rehashing can be explicitly requested
@@ -958,48 +1049,53 @@
//!
//! Since no automatic rehashing is done, iterators are never invalidated when
//! inserting or erasing elements. Iterators are only invalidated when rehasing.
-template< class ValueTraits
- , class Hash //= boost::hash<typename ValueTraits::value_type>
- , class Equal //= std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize //= true
- , class SizeType //= std::size_t
- >
-class unordered_multiset
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class Config>
+#endif
+class unordered_multiset_impl
{
/// @cond
private:
- typedef hashtable<ValueTraits, Hash, Equal, ConstantTimeSize, SizeType> table_type;
+ typedef hashtable_impl<Config> table_type;
/// @endcond
//! This class is
//! non-copyable
- unordered_multiset (const unordered_multiset&);
+ unordered_multiset_impl (const unordered_multiset_impl&);
//! This class is
//! non-assignable
- unordered_multiset &operator =(const unordered_multiset&);
+ unordered_multiset_impl &operator =(const unordered_multiset_impl&);
typedef table_type implementation_defined;
public:
- typedef ValueTraits value_traits;
- typedef typename ValueTraits::value_type value_type;
- typedef typename ValueTraits::pointer pointer;
- typedef typename ValueTraits::const_pointer const_pointer;
- typedef typename std::iterator_traits<pointer>::reference reference;
- typedef typename std::iterator_traits<const_pointer>::reference const_reference;
- typedef typename std::iterator_traits<pointer>::difference_type difference_type;
- typedef SizeType size_type;
- typedef value_type key_type;
- typedef Equal key_equal;
- typedef Hash hasher;
+ typedef typename implementation_defined::value_type value_type;
+ typedef typename implementation_defined::value_traits value_traits;
+ typedef typename implementation_defined::bucket_traits bucket_traits;
+ typedef typename implementation_defined::pointer pointer;
+ typedef typename implementation_defined::const_pointer const_pointer;
+ typedef typename implementation_defined::reference reference;
+ typedef typename implementation_defined::const_reference const_reference;
+ typedef typename implementation_defined::difference_type difference_type;
+ typedef typename implementation_defined::size_type size_type;
+ typedef typename implementation_defined::key_type key_type;
+ typedef typename implementation_defined::key_equal key_equal;
+ typedef typename implementation_defined::hasher hasher;
typedef typename implementation_defined::bucket_type bucket_type;
- typedef typename boost::pointer_to_other<pointer, bucket_type>::type bucket_ptr;
+ typedef typename implementation_defined::bucket_ptr bucket_ptr;
typedef typename implementation_defined::iterator iterator;
typedef typename implementation_defined::const_iterator const_iterator;
typedef typename implementation_defined::insert_commit_data insert_commit_data;
typedef typename implementation_defined::local_iterator local_iterator;
typedef typename implementation_defined::const_local_iterator const_local_iterator;
+ typedef typename implementation_defined::node_traits node_traits;
+ typedef typename implementation_defined::node node;
+ typedef typename implementation_defined::node_ptr node_ptr;
+ typedef typename implementation_defined::const_node_ptr const_node_ptr;
+ typedef typename implementation_defined::node_algorithms node_algorithms;
/// @cond
private:
@@ -1021,11 +1117,11 @@
//!
//! <b>Notes</b>: buckets array must be disposed only after
//! *this is disposed.
- unordered_multiset ( bucket_ptr buckets
- , size_type buckets_len
- , const Hash & hasher = Hash()
- , const Equal &equal = Equal())
- : table_(buckets, buckets_len, hasher, equal)
+ unordered_multiset_impl ( const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : table_(b_traits, hash_func, equal_func, v_traits)
{}
//! <b>Requires</b>: buckets must not be being used by any other resource
@@ -1039,18 +1135,18 @@
//!
//! <b>Throws</b>: If value_traits::node_traits::node
//! constructor throws (this does not happen with predefined Boost.Intrusive hooks)
- //! or the copy constructor or invocation of Hash or Equal throws.
+ //! or the copy constructor or invocation of hasher or key_equal throws.
//!
//! <b>Notes</b>: buckets array must be disposed only after
//! *this is disposed.
template<class Iterator>
- unordered_multiset ( bucket_ptr buckets
- , size_type buckets_len
- , Iterator b
- , Iterator e
- , const Hash & hasher = Hash()
- , const Equal &equal = Equal())
- : table_(buckets, buckets_len, hasher, equal)
+ unordered_multiset_impl ( Iterator b
+ , Iterator e
+ , const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : table_(b_traits, hash_func, equal_func, v_traits)
{ table_.insert_equal(b, e); }
//! <b>Effects</b>: Detaches all elements from this. The objects in the unordered_multiset
@@ -1060,7 +1156,7 @@
//! it's a safe-mode or auto-unlink value. Otherwise constant.
//!
//! <b>Throws</b>: Nothing.
- ~unordered_multiset()
+ ~unordered_multiset_impl()
{}
//! <b>Effects</b>: Returns an iterator pointing to the beginning of the unordered_multiset.
@@ -1134,7 +1230,7 @@
//! <b>Effects</b>: Returns true is the container is empty.
//!
- //! <b>Complexity</b>: if ConstantTimeSize is false, average constant time
+ //! <b>Complexity</b>: if constant-time size option is disabled, average constant time
//! (worst case, with empty() == true): O(this->bucket_count()).
//! Otherwise constant.
//!
@@ -1145,7 +1241,7 @@
//! <b>Effects</b>: Returns the number of elements stored in the unordered_multiset.
//!
//! <b>Complexity</b>: Linear to elements contained in *this if
- //! ConstantTimeSize is false. Constant-time otherwise.
+ //! constant-time size option is enabled. Constant-time otherwise.
//!
//! <b>Throws</b>: Nothing.
size_type size() const
@@ -1162,7 +1258,7 @@
//!
//! <b>Throws</b>: If the swap() call for the comparison or hash functors
//! found using ADL throw. Basic guarantee.
- void swap(unordered_multiset& other)
+ void swap(unordered_multiset_impl& other)
{ table_.swap(other.table_); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
@@ -1179,7 +1275,7 @@
//!
//! <b>Throws</b>: If cloner throws.
template <class Cloner, class Disposer>
- void clone_from(const unordered_multiset &src, Cloner cloner, Disposer disposer)
+ void clone_from(const unordered_multiset_impl &src, Cloner cloner, Disposer disposer)
{ table_.clone_from(src.table_, cloner, disposer); }
//! <b>Requires</b>: value must be an lvalue
@@ -1202,8 +1298,8 @@
//!
//! <b>Effects</b>: Equivalent to this->insert(t) for each element in [b, e).
//!
- //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
- //! size of the range. However, it is linear in N if the range is already sorted
+ //! <b>Complexity</b>: Insert range is in general O(N * log(N)), where N is the
+ //! size of the range. However, it is linear in N if the range is already sorted
//! by value_comp().
//!
//! <b>Throws</b>: If the internal hasher or the equality functor throws. Basic guarantee.
@@ -1251,9 +1347,9 @@
size_type erase(const_reference value)
{ return table_.erase(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! "key_value_equal" must be a equality function that induces
//! the same equality as key_equal. The difference is that
@@ -1267,13 +1363,14 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If the hasher or the equal functors throws. Basic guarantee.
+ //! <b>Throws</b>: If the hash_func or the equal_func functors throws.
+ //! Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators (but not the references)
//! to the erased elements. No destructors are called.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- size_type erase(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return table_.erase(key, hasher, equal); }
+ size_type erase(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return table_.erase(key, hash_func, equal_func); }
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
//!
@@ -1327,7 +1424,7 @@
//! <b>Requires</b>: Disposer::operator()(pointer) shouldn't throw.
//!
//! <b>Effects</b>: Erases all the elements with the given key.
- //! according to the comparison functor "equal".
+ //! according to the comparison functor "equal_func".
//! Disposer::operator()(pointer) is called for the removed elements.
//!
//! <b>Returns</b>: The number of erased elements.
@@ -1335,13 +1432,13 @@
//! <b>Complexity</b>: Average case O(this->count(value)).
//! Worst case O(this->size()).
//!
- //! <b>Throws</b>: If hasher or equal throw. Basic guarantee.
+ //! <b>Throws</b>: If hash_func or equal_func throw. Basic guarantee.
//!
//! <b>Note</b>: Invalidates the iterators
//! to the erased elements.
template<class KeyType, class KeyHasher, class KeyValueEqual, class Disposer>
- size_type erase_and_dispose(const KeyType& key, KeyHasher hasher, KeyValueEqual equal, Disposer disposer)
- { return table_.erase_and_dispose(key, hasher, equal, disposer); }
+ size_type erase_and_dispose(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func, Disposer disposer)
+ { return table_.erase_and_dispose(key, hash_func, equal_func, disposer); }
//! <b>Effects</b>: Erases all the elements of the container.
//!
@@ -1378,9 +1475,9 @@
size_type count(const_reference value) const
{ return table_.count(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! "key_value_equal" must be a equality function that induces
//! the same equality as key_equal. The difference is that
@@ -1392,8 +1489,8 @@
//!
//! <b>Throws</b>: If the internal hasher or the equality functor throws.
template<class KeyType, class KeyHasher, class KeyValueEqual, class Disposer>
- size_type count(const KeyType& key, KeyHasher hasher, KeyValueEqual equal) const
- { return table_.count(key, hasher, equal); }
+ size_type count(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func) const
+ { return table_.count(key, hash_func, equal_func); }
//! <b>Effects</b>: Finds an iterator to the first element whose value is
//! "value" or end() if that element does not exist.
@@ -1404,9 +1501,9 @@
iterator find(const_reference value)
{ return table_.find(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! "key_value_equal" must be a equality function that induces
//! the same equality as key_equal. The difference is that
@@ -1424,8 +1521,8 @@
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- iterator find(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return table_.find(key, hasher, equal); }
+ iterator find(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return table_.find(key, hash_func, equal_func); }
//! <b>Effects</b>: Finds a const_iterator to the first element whose key is
//! "key" or end() if that element does not exist.
@@ -1436,9 +1533,9 @@
const_iterator find(const_reference value) const
{ return table_.find(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! "key_value_equal" must be a equality function that induces
//! the same equality as key_equal. The difference is that
@@ -1456,8 +1553,8 @@
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- const_iterator find(const KeyType& key, KeyHasher hasher, KeyValueEqual equal) const
- { return table_.find(key, equal); }
+ const_iterator find(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func) const
+ { return table_.find(key, hash_func, equal_func); }
//! <b>Effects</b>: Returns a range containing all elements with values equivalent
//! to value. Returns std::make_pair(this->end(), this->end()) if no such
@@ -1469,9 +1566,9 @@
std::pair<iterator,iterator> equal_range(const_reference value)
{ return table_.equal_range(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! "key_value_equal" must be a equality function that induces
//! the same equality as key_equal. The difference is that
@@ -1481,7 +1578,8 @@
//! keys. Returns std::make_pair(this->end(), this->end()) if no such
//! elements exist.
//!
- //! <b>Complexity</b>: Average case O(this->count(key, hasher, equal)). Worst case O(this->size()).
+ //! <b>Complexity</b>: Average case O(this->count(key, hash_func, equal_func)).
+ //! Worst case O(this->size()).
//!
//! <b>Throws</b>: If the internal hasher or the equality functor throws.
//!
@@ -1489,8 +1587,9 @@
//! is expensive and the value_type can be compared with a cheaper
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
- std::pair<iterator,iterator> equal_range(const KeyType& key, KeyHasher hasher, KeyValueEqual equal)
- { return table_.equal_range(key, hasher, equal); }
+ std::pair<iterator,iterator> equal_range
+ (const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func)
+ { return table_.equal_range(key, hash_func, equal_func); }
//! <b>Effects</b>: Returns a range containing all elements with values equivalent
//! to value. Returns std::make_pair(this->end(), this->end()) if no such
@@ -1503,9 +1602,9 @@
equal_range(const_reference value) const
{ return table_.equal_range(value); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! "key_value_equal" must be a equality function that induces
//! the same equality as key_equal. The difference is that
@@ -1515,7 +1614,8 @@
//! keys. Returns std::make_pair(this->end(), this->end()) if no such
//! elements exist.
//!
- //! <b>Complexity</b>: Average case O(this->count(key, hasher, equal)). Worst case O(this->size()).
+ //! <b>Complexity</b>: Average case O(this->count(key, hash_func, equal_func)).
+ //! Worst case O(this->size()).
//!
//! <b>Throws</b>: If the internal hasher or the equality functor throws.
//!
@@ -1524,8 +1624,8 @@
//! key type. Usually this key is part of the value_type.
template<class KeyType, class KeyHasher, class KeyValueEqual>
std::pair<const_iterator, const_iterator>
- equal_range(const KeyType& key, KeyHasher hasher, KeyValueEqual equal) const
- { return table_.equal_range(key, equal); }
+ equal_range(const KeyType& key, KeyHasher hash_func, KeyValueEqual equal_func) const
+ { return table_.equal_range(key, hash_func, equal_func); }
//! <b>Requires</b>: value must be an lvalue and shall be in a unordered_multiset of
//! appropriate type. Otherwise the behavior is undefined.
@@ -1551,29 +1651,59 @@
const_iterator iterator_to(const_reference value) const
{ return table_.iterator_to(value); }
- //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_multiset of
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
//! appropriate type. Otherwise the behavior is undefined.
//!
- //! <b>Effects</b>: Returns: a valid local_iterator belonging to the unordered_multiset
+ //! <b>Effects</b>: Returns: a valid local_iterator belonging to the unordered_set
//! that points to the value
//!
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static local_iterator local_iterator_to(reference value)
- { return table_type::local_iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static local_iterator s_local_iterator_to(reference value)
+ { return table_type::s_local_iterator_to(value); }
- //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_multiset of
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
//! appropriate type. Otherwise the behavior is undefined.
//!
//! <b>Effects</b>: Returns: a valid const_local_iterator belonging to
- //! the unordered_multiset that points to the value
+ //! the unordered_set that points to the value
//!
//! <b>Complexity</b>: Constant.
//!
//! <b>Throws</b>: Nothing.
- static const_local_iterator local_iterator_to(const_reference value)
- { return table_type::local_iterator_to(value); }
+ //!
+ //! <b>Note</b>: This static function is available only if the <i>value traits</i>
+ //! is stateless.
+ static const_local_iterator s_local_iterator_to(const_reference value)
+ { return table_type::s_local_iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid local_iterator belonging to the unordered_set
+ //! that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ local_iterator local_iterator_to(reference value)
+ { return table_.local_iterator_to(value); }
+
+ //! <b>Requires</b>: value must be an lvalue and shall be in a unordered_set of
+ //! appropriate type. Otherwise the behavior is undefined.
+ //!
+ //! <b>Effects</b>: Returns: a valid const_local_iterator belonging to
+ //! the unordered_set that points to the value
+ //!
+ //! <b>Complexity</b>: Constant.
+ //!
+ //! <b>Throws</b>: Nothing.
+ const_local_iterator local_iterator_to(const_reference value) const
+ { return table_.local_iterator_to(value); }
//! <b>Effects</b>: Returns the number of buckets passed in the constructor
//! or the last rehash function.
@@ -1605,9 +1735,9 @@
size_type bucket(const value_type& k) const
{ return table_.bucket(k); }
- //! <b>Requires</b>: "hasher" must be a hash function that induces
+ //! <b>Requires</b>: "hash_func" must be a hash function that induces
//! the same hash values as the stored hasher. The difference is that
- //! "hasher" hashes the given key instead of the value_type.
+ //! "hash_func" hashes the given key instead of the value_type.
//!
//! <b>Effects</b>: Returns the index of the bucket in which elements
//! with keys equivalent to k would be found, if any such element existed.
@@ -1618,8 +1748,8 @@
//!
//! <b>Note</b>: the return value is in the range [0, this->bucket_count()).
template<class KeyType, class KeyHasher>
- size_type bucket(const KeyType& k, const KeyHasher &hasher) const
- { return table_.bucket(k, hasher); }
+ size_type bucket(const KeyType& k, const KeyHasher &hash_func) const
+ { return table_.bucket(k, hash_func); }
//! <b>Effects</b>: Returns the bucket array pointer passed in the constructor
//! or the last rehash function.
@@ -1725,8 +1855,8 @@
//! <b>Complexity</b>: Average case linear in this->size(), worst case quadratic.
//!
//! <b>Throws</b>: If the hasher functor throws.
- void rehash(bucket_ptr new_buckets, size_type new_size)
- { table_.rehash(new_buckets, new_size); }
+ void rehash(const bucket_traits &new_bucket_traits)
+ { table_.rehash(new_bucket_traits); }
//! <b>Effects</b>: Returns the nearest new bucket count optimized for
//! the container that is bigger than n. This suggestion can be used
@@ -1753,9 +1883,71 @@
{ return table_type::suggested_lower_bucket_count(n); }
};
+//! Helper metafunction to define an \c unordered_multiset that yields to the same type when the
+//! same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class ...Options>
+#else
+template<class T, class O1 = none, class O2 = none
+ , class O3 = none, class O4 = none
+ , class O5 = none, class O6 = none
+ , class O7 = none
+ >
+#endif
+struct make_unordered_multiset
+{
+ /// @cond
+ typedef unordered_multiset_impl
+ < typename make_hashtable_opt
+ <T, O1, O2, O3, O4, O5, O6, O7>::type
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
+#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class T, class O1, class O2, class O3, class O4, class O5, class O6, class O7>
+class unordered_multiset
+ : public make_unordered_multiset<T, O1, O2, O3, O4, O5, O6, O7>::type
+{
+ typedef typename make_unordered_multiset
+ <T, O1, O2, O3, O4, O5, O6, O7>::type Base;
+ //Assert if passed value traits are compatible with the type
+ BOOST_STATIC_ASSERT((detail::is_same<typename Base::value_traits::value_type, T>::value));
+
+ public:
+ typedef typename Base::value_traits value_traits;
+ typedef typename Base::bucket_traits bucket_traits;
+ typedef typename Base::iterator iterator;
+ typedef typename Base::const_iterator const_iterator;
+ typedef typename Base::bucket_ptr bucket_ptr;
+ typedef typename Base::size_type size_type;
+ typedef typename Base::hasher hasher;
+ typedef typename Base::key_equal key_equal;
+
+ unordered_multiset( const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : Base(b_traits, hash_func, equal_func, v_traits)
+ {}
+
+ template<class Iterator>
+ unordered_multiset( Iterator b
+ , Iterator e
+ , const bucket_traits &b_traits
+ , const hasher & hash_func = hasher()
+ , const key_equal &equal_func = key_equal()
+ , const value_traits &v_traits = value_traits())
+ : Base(b, e, b_traits, hash_func, equal_func, v_traits)
+ {}
+};
+
+#endif
+
} //namespace intrusive
} //namespace boost
#include <boost/intrusive/detail/config_end.hpp>
-#endif //BOOST_INTRUSIVE_HASHSET_HPP
+#endif //BOOST_INTRUSIVE_UNORDERED_SET_HPP
Modified: branches/bcbboost/boost/intrusive/unordered_set_hook.hpp
==============================================================================
--- branches/bcbboost/boost/intrusive/unordered_set_hook.hpp (original)
+++ branches/bcbboost/boost/intrusive/unordered_set_hook.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -11,19 +11,50 @@
//
/////////////////////////////////////////////////////////////////////////////
-#ifndef BOOST_INTRUSIVE_HASHSET_HOOK_HPP
-#define BOOST_INTRUSIVE_HASHSET_HOOK_HPP
+#ifndef BOOST_INTRUSIVE_UNORDERED_SET_HOOK_HPP
+#define BOOST_INTRUSIVE_UNORDERED_SET_HOOK_HPP
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/intrusive_fwd.hpp>
#include <boost/intrusive/detail/utilities.hpp>
-#include <boost/intrusive/detail/pointer_to_other.hpp>
#include <boost/intrusive/slist_hook.hpp>
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/options.hpp>
+#include <boost/intrusive/detail/generic_hook.hpp>
namespace boost {
namespace intrusive {
+/// @cond
+template<class VoidPointer>
+struct get_uset_node_algo
+{
+ typedef circular_slist_algorithms<slist_node_traits<VoidPointer> > type;
+};
+/// @endcond
+
+//! Helper metafunction to define a \c unordered_set_base_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_unordered_set_base_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
+
+ typedef detail::generic_hook
+ < get_slist_node_algo<typename packed_options::void_pointer>
+ , typename packed_options::tag
+ , packed_options::link_mode
+ , detail::UsetBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
+};
+
//! Derive a class from unordered_set_base_hook in order to store objects in
//! in an unordered_set/unordered_multi_set. unordered_set_base_hook holds the data necessary to maintain
//! the unordered_set/unordered_multi_set and provides an appropriate value_traits class for unordered_set/unordered_multi_set.
@@ -37,122 +68,103 @@
//!
//! The third argument is the pointer type that will be used internally in the hook
//! and the unordered_set/unordered_multi_set configured from this hook.
-template< class Tag //= tag
- , linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class unordered_set_base_hook
+ : public make_unordered_set_base_hook<O1, O2, O3>::type
{
- /// @cond
- typedef slist_base_hook<Tag, Policy, VoidPointer> IsListHook;
- IsListHook m_slisthook;
- typedef IsListHook implementation_defined;
- /// @endcond
-
- public:
- enum { linking_policy = Policy };
- typedef typename implementation_defined::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef unordered_set_base_hook
- <Tag, Policy, VoidPointer> this_type;
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type>::type this_type_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type>::type const_this_type_ptr;
-
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
- //! <b>Throws</b>: Nothing.
- unordered_set_base_hook()
- : m_slisthook()
- {}
+ //! <b>Throws</b>: Nothing.
+ unordered_set_base_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
- //! <b>Throws</b>: Nothing.
+ //! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using unordered_set_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- unordered_set_base_hook(const unordered_set_base_hook &other)
- : m_slisthook(other.m_slisthook)
- {}
+ unordered_set_base_hook(const unordered_set_base_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
- //! <b>Throws</b>: Nothing.
+ //! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using unordered_set_base_hook STL-compliant without forcing the
- //! user to do some additional work. "swap" can be used to emulate
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
//! move-semantics.
- unordered_set_base_hook& operator=(const unordered_set_base_hook &other)
- { return *this; }
+ unordered_set_base_hook& operator=(const unordered_set_base_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
- //!
- //! <b>Throws</b>: Nothing.
- ~unordered_set_base_hook()
- {} //m_slisthook's destructor does the job
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an unordered_set an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
+ //!
+ //! <b>Throws</b>: Nothing.
+ ~unordered_set_base_hook();
+
+ //! <b>Effects</b>: Swapping two nodes swaps the position of the elements
+ //! related to those nodes in one or two containers. That is, if the node
+ //! this is part of the element e1, the node x is part of the element e2
+ //! and both elements are included in the containers s1 and s2, then after
+ //! the swap-operation e1 is in s2 at the position of e2 and e2 is in s1
+ //! at the position of e1. If one element is not in a container, then
+ //! after the swap-operation the other element is not in a container.
+ //! Iterators to e1 and e2 related to those nodes are invalidated.
+ //!
+ //! <b>Complexity</b>: Constant
+ //!
+ //! <b>Throws</b>: Nothing.
+ void swap_nodes(unordered_set_base_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
//!
//! <b>Returns</b>: true, if the node belongs to a container, false
- //! otherwise. This function can be used to test whether unordered_set/unordered_multiset::iterator_to
+ //! otherwise. This function can be used to test whether \c unordered_set::iterator_to
//! will return a valid iterator.
//!
- //! <b>Complexity</b>: Constant
- bool is_linked() const
- { return m_slisthook.is_linked(); }
-
- //! The value_traits class is used as the first template argument for unordered_set/unordered_multiset.
- //! The template argument T defines the class type stored in unordered_set/unordered_multiset. Objects
- //! of type T and of types derived from T can be stored. T doesn't need to be
- //! copy-constructible or assignable.
- template<class T>
- struct value_traits
- : detail::derivation_hook_value_traits<T, this_type, Tag>
- {};
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr((this_type*)detail::get_pointer(IsListHook::to_hook_ptr(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr((const this_type*)detail::get_pointer(IsListHook::to_hook_ptr(p)));
- }
-
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return m_slisthook.to_node_ptr(); }
-
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return m_slisthook.to_node_ptr(); }
+ //! <b>Complexity</b>: Constant
+ bool is_linked() const;
+
+ //! <b>Effects</b>: Removes the node if it's inserted in a container.
+ //! This function is only allowed if link_mode is \c auto_unlink.
+ //!
+ //! <b>Throws</b>: Nothing.
+ void unlink();
+ #endif
+};
+
+
+//! Helper metafunction to define a \c unordered_set_member_hook that yields to the same
+//! type when the same options (either explicitly or implicitly) are used.
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1 = none, class O2 = none, class O3 = none>
+#endif
+struct make_unordered_set_member_hook
+{
+ /// @cond
+ typedef typename pack_options
+ < hook_defaults, O1, O2, O3>::type packed_options;
+
+ typedef detail::generic_hook
+ < get_uset_node_algo<typename packed_options::void_pointer>
+ , member_tag
+ , packed_options::link_mode
+ , detail::NoBaseHook
+ > implementation_defined;
+ /// @endcond
+ typedef implementation_defined type;
};
//! Put a public data member unordered_set_member_hook in order to store objects of this class in
@@ -163,123 +175,79 @@
//!
//! The second argument is the pointer type that will be used internally in the hook
//! and the unordered_set/unordered_multi_set configured from this hook.
-template< linking_policy Policy //= safe_link
- , class VoidPointer //= void *
- >
+#ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+template<class ...Options>
+#else
+template<class O1, class O2, class O3>
+#endif
class unordered_set_member_hook
+ : public make_unordered_set_member_hook<O1, O2, O3>::type
{
- /// @cond
- typedef slist_member_hook<Policy, VoidPointer> IsListHook;
- IsListHook m_slisthook;
- typedef IsListHook implementation_defined;
- /// @endcond
-
- public:
- enum { linking_policy = Policy };
- typedef typename implementation_defined::node_traits node_traits;
- typedef typename node_traits::node node;
- typedef typename boost::pointer_to_other
- <VoidPointer, node>::type node_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const node>::type const_node_ptr;
- typedef unordered_set_member_hook
- <Policy, VoidPointer> this_type;
- typedef typename boost::pointer_to_other
- <VoidPointer, this_type>::type this_type_ptr;
- typedef typename boost::pointer_to_other
- <VoidPointer, const this_type>::type const_this_type_ptr;
-
- public:
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ #ifdef BOOST_INTRUSIVE_DOXYGEN_INVOKED
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state.
//!
//! <b>Throws</b>: Nothing.
- unordered_set_member_hook()
- : m_slisthook()
- {}
+ unordered_set_member_hook();
- //! <b>Effects</b>: If Policy is auto_unlink or safe_mode_linnk
+ //! <b>Effects</b>: If link_mode is \c auto_unlink or \c safe_link
//! initializes the node to an unlinked state. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing a copy-constructor
- //! makes classes using unordered_set_member_hook STL-compliant without forcing the
- //! user to do some additional work.
- unordered_set_member_hook(const unordered_set_member_hook &other)
- : m_slisthook(other.m_slisthook)
- {}
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
+ //! move-semantics.
+ unordered_set_member_hook(const unordered_set_member_hook& );
//! <b>Effects</b>: Empty function. The argument is ignored.
//!
//! <b>Throws</b>: Nothing.
//!
//! <b>Rationale</b>: Providing an assignment operator
- //! makes classes using unordered_set_member_hook STL-compliant without forcing the
- //! user to do some additional work.
- unordered_set_member_hook& operator=(const unordered_set_member_hook &other)
- { return *this; }
+ //! makes classes using the hook STL-compliant without forcing the
+ //! user to do some additional work. \c swap can be used to emulate
+ //! move-semantics.
+ unordered_set_member_hook& operator=(const unordered_set_member_hook& );
- //! <b>Effects</b>: If Policy is normal_link, the destructor does
- //! nothing (ie. no code is generated). If Policy is safe_link and the
- //! object is stored in an list an assertion is raised. If Policy is
- //! auto_unlink and "is_linked()" is true, the node is unlinked.
- //!
+ //! <b>Effects</b>: If link_mode is \c normal_link, the destructor does
+ //! nothing (ie. no code is generated). If link_mode is \c safe_link and the
+ //! object is stored in an unordered_set an assertion is raised. If link_mode is
+ //! \c auto_unlink and \c is_linked() is true, the node is unlinked.
+ //!
+ //! <b>Throws</b>: Nothing.
+ ~unordered_set_member_hook();
+
+ //! <b>Effects</b>: Swapping two nodes swaps the position of the elements
+ //! related to those nodes in one or two containers. That is, if the node
+ //! this is part of the element e1, the node x is part of the element e2
+ //! and both elements are included in the containers s1 and s2, then after
+ //! the swap-operation e1 is in s2 at the position of e2 and e2 is in s1
+ //! at the position of e1. If one element is not in a container, then
+ //! after the swap-operation the other element is not in a container.
+ //! Iterators to e1 and e2 related to those nodes are invalidated.
+ //!
+ //! <b>Complexity</b>: Constant
+ //!
//! <b>Throws</b>: Nothing.
- ~unordered_set_member_hook()
- {} //m_slisthook's destructor does the job
+ void swap_nodes(unordered_set_member_hook &other);
- //! <b>Precondition</b>: Policy must be safe_link or auto_unlink.
+ //! <b>Precondition</b>: link_mode must be \c safe_link or \c auto_unlink.
+ //!
+ //! <b>Returns</b>: true, if the node belongs to a container, false
+ //! otherwise. This function can be used to test whether \c unordered_set::iterator_to
+ //! will return a valid iterator.
//!
//! <b>Complexity</b>: Constant
- bool is_linked() const
- { return m_slisthook.is_linked(); }
-
- //! The value_traits class is used as the first template argument for unordered_set/unordered_multiset.
- //! The template argument is a pointer to member pointing to the node in
- //! the class. Objects of type T and of types derived from T can be stored.
- //! T doesn't need to be copy-constructible or assignable.
- template<class T, this_type T::* M>
- struct value_traits
- : detail::member_hook_value_traits<T, this_type, M>
- {};
+ bool is_linked() const;
//! <b>Effects</b>: Removes the node if it's inserted in a container.
- //! This function is only allowed if Policy is auto_unlink.
- //!
- //! <b>Throws</b>: Nothing.
- void unlink()
- { m_slisthook.unlink(); }
-
- //! <b>Effects</b>: Converts a pointer to a node into
- //! a pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static this_type_ptr to_hook_ptr(node_ptr p)
- {
- return this_type_ptr((this_type*)detail::get_pointer(IsListHook::to_hook_ptr(p)));
- }
-
- //! <b>Effects</b>: Converts a const pointer to a node stored in a container into
- //! a const pointer to the hook that holds that node.
- //!
- //! <b>Throws</b>: Nothing.
- static const_this_type_ptr to_hook_ptr(const_node_ptr p)
- {
- return const_this_type_ptr((const this_type*)detail::get_pointer(IsListHook::to_hook_ptr(p)));
- }
-
- //! <b>Effects</b>: Returns a pointer to the node that this hook holds.
- //!
- //! <b>Throws</b>: Nothing.
- node_ptr to_node_ptr()
- { return m_slisthook.to_node_ptr(); }
-
- //! <b>Effects</b>: Returns a const pointer to the node that this hook holds.
+ //! This function is only allowed if link_mode is \c auto_unlink.
//!
//! <b>Throws</b>: Nothing.
- const_node_ptr to_node_ptr() const
- { return m_slisthook.to_node_ptr(); }
+ void unlink();
+ #endif
};
} //namespace intrusive
@@ -287,4 +255,4 @@
#include <boost/intrusive/detail/config_end.hpp>
-#endif //BOOST_INTRUSIVE_HASHSET_HOOK_HPP
+#endif //BOOST_INTRUSIVE_UNORDERED_SET_HOOK_HPP
Modified: branches/bcbboost/boost/system/error_code.hpp
==============================================================================
--- branches/bcbboost/boost/system/error_code.hpp (original)
+++ branches/bcbboost/boost/system/error_code.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -172,10 +172,6 @@
static const error_category & errno_ecat = get_posix_category();
static const error_category & native_ecat = get_system_category();
- // EDG with --dep_name requires make_error_condition be defined before use
-
- template <class T> error_condition make_error_condition(T);
-
// class error_condition -----------------------------------------------//
// error_conditions are portable, error_codes are system or lib specific
@@ -259,10 +255,6 @@
};
- // EDG with --dep_name requires make_error_code be defined before use
-
- template <class T> error_code make_error_code(T);
-
// class error_code ----------------------------------------------------//
// We want error_code to be a value type that can be copied without slicing
@@ -408,13 +400,16 @@
// make_* functions for posix::posix_errno -----------------------------//
- // explicit conversion:
- template<> inline error_code make_error_code( posix::posix_errno e )
- { return error_code( e, posix_category ); }
-
- // implicit conversion:
- template<> inline error_condition make_error_condition( posix::posix_errno e )
- { return error_condition( e, posix_category ); }
+ namespace posix
+ {
+ // explicit conversion:
+ inline error_code make_error_code( posix_errno e )
+ { return error_code( e, posix_category ); }
+
+ // implicit conversion:
+ inline error_condition make_error_condition( posix_errno e )
+ { return error_condition( e, posix_category ); }
+ }
// error_category default implementation -------------------------------//
@@ -496,8 +491,11 @@
template<> struct is_error_code_enum<cygwin::cygwin_errno>
{ static const bool value = true; };
- template<> inline error_code make_error_code(cygwin::cygwin_errno e)
- { return error_code( e, system_category ); }
+ namespace cygwin
+ {
+ inline error_code make_error_code( cygwin_errno e )
+ { return error_code( e, system_category ); }
+ }
# elif defined(linux) || defined(__linux) || defined(__linux__)
@@ -563,8 +561,11 @@
template<> struct is_error_code_enum<Linux::linux_error>
{ static const bool value = true; };
- template<> inline error_code make_error_code(Linux::linux_error e)
- { return error_code( e, system_category ); }
+ namespace Linux
+ {
+ inline error_code make_error_code( linux_error e )
+ { return error_code( e, system_category ); }
+ }
# endif
@@ -642,13 +643,17 @@
// TODO: add more Windows errors
};
+
} // namespace windows
template<> struct is_error_code_enum<windows::windows_error>
{ static const bool value = true; };
- template<> inline error_code make_error_code(windows::windows_error e)
- { return error_code( e, system_category ); }
+ namespace windows
+ {
+ inline error_code make_error_code( windows_error e )
+ { return error_code( e, system_category ); }
+ }
#else
# error BOOST_POSIX_API or BOOST_WINDOWS_API must be defined
Modified: branches/bcbboost/libs/filesystem/src/operations.cpp
==============================================================================
--- branches/bcbboost/libs/filesystem/src/operations.cpp (original)
+++ branches/bcbboost/libs/filesystem/src/operations.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -192,7 +192,8 @@
|| (ec.value() == ERROR_PATH_NOT_FOUND)
|| (ec.value() == ERROR_INVALID_NAME) // "tools/jam/src/:sys:stat.h", "//foo"
|| (ec.value() == ERROR_INVALID_PARAMETER) // ":sys:stat.h"
- || (ec.value() == ERROR_BAD_NETPATH))
+ || (ec.value() == ERROR_BAD_PATHNAME) // "//nosuch" on Win64
+ || (ec.value() == ERROR_BAD_NETPATH)) // "//nosuch" on Win32
{
ec = error_code(); // these are not considered errors
return fs::file_status( fs::file_not_found );
Modified: branches/bcbboost/libs/filesystem/src/path.cpp
==============================================================================
--- branches/bcbboost/libs/filesystem/src/path.cpp (original)
+++ branches/bcbboost/libs/filesystem/src/path.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -69,7 +69,7 @@
if ( locked ) boost::throw_exception(
wfilesystem_error(
"boost::filesystem::wpath_traits::imbue() after lockdown",
- system::make_error_code( system::posix::not_supported ) ) );
+ make_error_code( system::posix::not_supported ) ) );
imbue( new_loc, std::nothrow );
}
Modified: branches/bcbboost/libs/interprocess/doc/Jamfile.v2
==============================================================================
--- branches/bcbboost/libs/interprocess/doc/Jamfile.v2 (original)
+++ branches/bcbboost/libs/interprocess/doc/Jamfile.v2 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -26,6 +26,8 @@
<doxygen:param>HIDE_UNDOC_MEMBERS=YES
<doxygen:param>EXTRACT_PRIVATE=NO
<doxygen:param>EXPAND_ONLY_PREDEF=YES
+ <xsl:param>"boost.doxygen.reftitle=\"Boost.Interprocess Reference\""
+ <xsl:param>"boost.doxygen.refid=\"reference\""
;
xml interprocess : interprocess.qbk ;
@@ -36,7 +38,9 @@
:
<xsl:param>boost.root=../../../..
<xsl:param>boost.libraries=../../../../libs/libraries.htm
- <xsl:param>generate.section.toc.level=3
+ <xsl:param>toc.max.depth=1
+ <xsl:param>toc.section.depth=2
<xsl:param>chunk.first.sections=1
+ <xsl:param>chunk.section.depth=2
<dependency>autodoc
;
Modified: branches/bcbboost/libs/interprocess/doc/interprocess.qbk
==============================================================================
--- branches/bcbboost/libs/interprocess/doc/interprocess.qbk (original)
+++ branches/bcbboost/libs/interprocess/doc/interprocess.qbk 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -48,10 +48,16 @@
[section:introduction_building_interprocess Building Boost.Interprocess]
-There is no need to compile anything to use [*Boost.Interprocess], since it's
+There is no need to compile [*Boost.Interprocess], since it's
a header only library. Just include your Boost header directory in your
compiler include path.
+[*Boost.Interprocess] depends on
+[@http://www.boost.org/libs/date_time/ [*Boost.DateTime]], which needs
+separate compilation. However, the subset used by [*Boost.Interprocess] does
+not need any separate compilation so the user can define `BOOST_DATE_TIME_NO_LIB`
+to avoid Boost from trying to automatically link the [*Boost.DateTime].
+
[endsect]
[section:tested_compilers Tested compilers]
@@ -225,6 +231,7 @@
[[Message queue] [Kernel or Filesystem]]
[[Named mutex] [Kernel or Filesystem]]
[[Named semaphore] [Kernel or Filesystem]]
+ [[Named condition] [Kernel or Filesystem]]
]
As you can see, [*Boost.Interprocess] defines some mechanisms with "Kernel or Filesystem"
@@ -256,8 +263,54 @@
[endsect]
+
+[section:constructors_destructors_and_resource_lifetime
+ Constructors, destructors and lifetime of Interprocess named resources]
+
+Named [*Boost.Interprocess] resources (shared memory, memory mapped files,
+named mutexes/conditions/semaphores) have kernel or filesystem persistency.
+This means that even if all processes that have opened those resources
+end, the resource will still be accesible to be opened again and the resource
+can only be destructed via an explicit to their static member `remove` function.
+This behavior can be easily understood, since it's the same mechanism used
+by functions controlling file opening/creation/erasure:
+
+[table Boost.Interprocess-Filesystem Analogy
+ [[Named Interprocess resource] [Corresponding std file] [Corresponding POSIX operation]]
+ [[Constructor] [std::fstream constructor][open]]
+ [[Destructor] [std::fstream destructor] [close]]
+ [[Member `remove`] [None. `std::remove`] [unlink]]
+]
+
+Now the correspondence between POSIX and Boost.Interprocess
+regarding shared memory and named semaphores:
+
+[table Boost.Interprocess-POSIX shared memory
+ [[`shared_memory_object` operation] [POSIX operation]]
+ [[Constructor] [shm_open]]
+ [[Destructor] [close]]
+ [[Member `remove`] [shm_unlink]]
+]
+
+[table Boost.Interprocess-POSIX named semaphore
+ [[`named_semaphore` operation] [POSIX operation]]
+ [[Constructor] [sem_open]]
+ [[Destructor] [close]]
+ [[Member `remove`] [sem_unlink]]
+]
+
+The most important property is that [*destructors of named resources
+don't remove the resource from the system], they only liberate resources
+allocated by the system for use by the process for the named resource.
+[*To remove the resource from the system the programmer must use
+`remove`].
+
+[endsect]
+
[endsect]
+[section:sharedmemorybetweenprocesses Sharing memory between processes]
+
[section:sharedmemory Shared memory]
[section:shared_memory_what_is What is shared memory?]
@@ -446,6 +499,59 @@
[endsect]
+[section:emulation Emulation for systems without shared memory objects]
+
+[*Boost.Interprocess] provides portable shared memory in terms of POSIX
+semantics. Some operating systems don't support shared memory as defined by
+POSIX:
+
+* Windows operating systems provide shared memory using memory backed by the
+ paging file but the lifetime semantics are different from the ones
+ defined by POSIX (see [link interprocess.sharedmemorybetweenprocesses.sharedmemory.windows_shared_memory
+ Native windows shared memory] section for more information).
+
+* Some UNIX systems don't support shared memory objects at all. MacOS is
+ one of these operating systems.
+
+In those platforms, shared memory is emulated with mapped files created
+in the temporary files directory. Because of this emulation, shared memory
+has filesystem lifetime in those systems.
+
+[endsect]
+
+[section:removing Removing shared memory]
+
+[classref boost::interprocess::shared_memory_object shared_memory_object]
+provides an static `remove` function to remove a shared memory objects.
+
+This function [*can] fail if the shared memory objects does not exist or
+it's opened by another process. Note that this function is similar to the
+standard C `int remove(const char *path)` function. In UNIX systems,
+`shared_memory_object::remove` calls `shm_unlink`:
+
+* The function will remove the name of the shared memory object
+named by the string pointed to by name.
+
+* If one or more references to the shared memory object exist when
+is unlinked, the name will be removed before the function returns, but the
+removal of the memory object contents will be postponed until all open and
+map references to the shared memory object have been removed.
+
+* Even if the object continues to exist after the last function call, reuse of
+the name will subsequently cause the creation of a
+[classref boost::interprocess::shared_memory_object] instance to behave as if no
+shared memory object of this name exists (that is, trying to open an object
+with that name will fail and an object of the same name can be created again).
+
+In Windows operating systems, the function fails if the object is being used,
+so a programmer can't consider the UNIX behavior as the portable behavior:
+
+`shared_memory_object::remove` [*can] fail if the shared memory is still in use,
+but this does not mean that it [*will] fail if it's in use. Just the same
+behavior as the standard C (stdio.h) `int remove(const char *path)` function.
+
+[endsect]
+
[section:windows_shared_memory Native windows shared memory]
Windows operating system also offers shared memory, but the lifetime of this
@@ -459,8 +565,8 @@
and Windows operating systems.
However, accessing native windows shared memory is a common request of
-[*Boost.Interprocess] users because they want to access using modern C++
-mechanisms to shared memory created with other process that don't use
+[*Boost.Interprocess] users because they want to access
+to shared memory created with other process that don't use
[*Boost.Interprocess]. In order to manage the native windows shared memory
[*Boost.Interprocess] offers the
[classref boost::interprocess::windows_shared_memory windows_shared_memory] class.
@@ -927,7 +1033,141 @@
[endsect]
-[section:synchronization_mechanisms Synchronization mechanisms overview]
+[endsect]
+
+[section:offset_ptr Mapping Address Independent Pointer: offset_ptr]
+
+When creating shared memory and memory mapped files to communicate two
+processes the memory segment can be mapped in a different address in each process:
+
+[c++]
+
+ #include<boost/interprocess/shared_memory_object.hpp>
+
+ // ...
+
+ using boost::interprocess;
+
+ //Open a shared memory segment
+ shared_memory_object shm_obj
+ (open_only //open or create
+ ,"shared_memory" //name
+ ,read_only //read-only mode
+ );
+
+ //Map the whole shared memory
+ mapped_region region
+ ( shm //Memory-mappable object
+ , read_write //Access mode
+ );
+
+ //This address can be different in each process
+ void *addr = region.get_address();
+
+This difficults the creation of complex objects in mapped regions: a C++
+class instance placed in a mapped region might have a pointer pointing to
+another object also placed in the mapped region. Since the pointer stores an
+absolute address, that address is only valid for the process that placed
+the object there unless all processes map the mapped region in the same
+address.
+
+To be able to simulate pointers in mapped regions, users must use [*offsets]
+(distance between objets) instead of absolute addresses. The offset between
+two objects in a mapped region is the same for any process that maps the
+mapped region, even if that region is placed in different base addreses.
+To facilitate the use of offsets, [*Boost.Interprocess] offers
+[classref boost::interprocess::offset_ptr offset_ptr].
+
+[classref boost::interprocess::offset_ptr offset_ptr]
+wraps all the background operations
+needed to offer a pointer-like interface. The class interface is
+inspired in Boost Smart Pointers and this smart pointer
+stores the offset (distance in bytes)
+between the pointee's address and it's own `this` pointer.
+Imagine an structure in a common
+32 bit processor:
+
+[c++]
+
+ struct structure
+ {
+ int integer1; //The compiler places this at offset 0 in the structure
+ offset_ptr<int> ptr; //The compiler places this at offset 4 in the structure
+ int integer2; //The compiler places this at offset 8 in the structure
+ };
+
+ //...
+
+ structure s;
+
+ //Assign the address of "integer1" to "ptr".
+ //"ptr" will store internally "-4":
+ // (char*)&s.integer1 - (char*)&s.ptr;
+ s.ptr = &s.integer1;
+
+ //Assign the address of "integer2" to "ptr".
+ //"ptr" will store internally "4":
+ // (char*)&s.integer2 - (char*)&s.ptr;
+ s.ptr = &s.integer2;
+
+
+One of the big problems of
+`offset_ptr` is the representation of the null pointer. The null pointer
+can't be safely represented like an offset, since the absolute address 0
+is always outside of the mapped region. Due to the fact that the segment can be mapped
+in a different base address in each process the distance between the address 0
+and `offset_ptr` is different for every process.
+
+Some implementations choose the offset 0 (that is, an `offset_ptr`
+pointing to itself) as the null pointer pointer representation
+but this is not valid for many use cases
+since many times structures like linked lists or nodes from STL containers
+point to themselves (the
+end node in an empty container, for example) and 0 offset value
+is needed. An alternative is to store, in addition to the offset, a boolean
+to indicate if the pointer is null. However, this increments the size of the
+pointer and hurts performance.
+
+In consequence,
+[classref boost::interprocess::offset_ptr offset_ptr] defines offset 1
+as the null pointer, meaning that this class [*can't] point to the byte
+after its own ['this] pointer:
+
+[c++]
+
+ using namespace boost::interprocess;
+
+ offset_ptr<char> ptr;
+
+ //Pointing to the next byte of it's own address
+ //marks the smart pointer as null.
+ ptr = (char*)&ptr + 1;
+
+ //ptr is equal to null
+ assert(!ptr);
+
+ //This is the same as assigning the null value...
+ ptr = 0;
+
+ //ptr is also equal to null
+ assert(!ptr);
+
+
+In practice, this limitation is not important, since a user almost never
+wants to point to this address.
+
+[classref boost::interprocess::offset_ptr offset_ptr]
+offers all pointer-like operations and
+random_access_iterator typedefs, so it can be used in STL
+algorithms requiring random access iterators and detected via traits.
+For more information about the members and operations of the class, see
+[classref boost::interprocess::offset_ptr offset_ptr reference].
+
+[endsect]
+
+[section:synchronization_mechanisms Synchronization mechanisms]
+
+[section:synchronization_mechanisms_overview Synchronization mechanisms overview]
As mentioned before, the ability to shared memory between processes through memory
mapped files or shared memory objects is not very useful if the access to that
@@ -1111,14 +1351,14 @@
#include <boost/interprocess/sync/named_mutex.hpp>
-* [classref boost::interprocess::interprocess_mutex named_mutex]: A non-recursive,
+* [classref boost::interprocess::named_mutex named_mutex]: A non-recursive,
named mutex.
[c++]
#include <boost/interprocess/sync/named_recursive_mutex.hpp>
-* [classref boost::interprocess::interprocess_mutex named_recursive_mutex]: A recursive,
+* [classref boost::interprocess::named_recursive_mutex named_recursive_mutex]: A recursive,
named mutex.
[endsect]
@@ -1657,7 +1897,6 @@
[endsect]
[section:upgradable_mutexes_operations_promotions Promotions]
-
[blurb ['[*void unlock_upgradable_and_lock()]]]
[*Precondition:] The thread must have upgradable ownership of the mutex.
@@ -1665,9 +1904,7 @@
[*Effects:] The thread atomically releases upgradable ownership and acquires exclusive
ownership. This operation will block until all threads with sharable ownership releas it.
-[*Throws:] An exception derived from *interprocess_exception* on error.
-
-[blurb ['[*bool try_unlock_upgradable_and_lock()]]]
+[*Throws:] An exception derived from *interprocess_exception* on error.[blurb ['[*bool try_unlock_upgradable_and_lock()]]]
[*Precondition:] The thread must have upgradable ownership of the mutex.
@@ -1678,9 +1915,7 @@
[*Returns:] If acquires exclusive ownership, returns true. Otherwise
returns false.
-[*Throws:] An exception derived from *interprocess_exception* on error.
-
-[blurb ['[*bool timed_unlock_upgradable_and_lock(const boost::posix_time::ptime &abs_time)]]]
+[*Throws:] An exception derived from *interprocess_exception* on error.[blurb ['[*bool timed_unlock_upgradable_and_lock(const boost::posix_time::ptime &abs_time)]]]
[*Precondition:] The thread must have upgradable ownership of the mutex.
@@ -1692,9 +1927,7 @@
[*Returns:] If acquires exclusive ownership, returns true. Otherwise
returns false.
-[*Throws:] An exception derived from *interprocess_exception* on error.
-
-[blurb ['[*bool try_unlock_sharable_and_lock()]]]
+[*Throws:] An exception derived from *interprocess_exception* on error.[blurb ['[*bool try_unlock_sharable_and_lock()]]]
[*Precondition:] The thread must have sharable ownership of the mutex.
@@ -1705,9 +1938,7 @@
[*Returns:] If acquires exclusive ownership, returns true. Otherwise
returns false.
-[*Throws:] An exception derived from *interprocess_exception* on error.
-
-[blurb ['[*bool try_unlock_sharable_and_lock_upgradable()]]]
+[*Throws:] An exception derived from *interprocess_exception* on error.[blurb ['[*bool try_unlock_sharable_and_lock_upgradable()]]]
[*Precondition:] The thread must have sharable ownership of the mutex.
@@ -1718,11 +1949,7 @@
[*Returns:] If acquires upgradable ownership, returns true. Otherwise
returns false.
-[*Throws:] An exception derived from *interprocess_exception* on error.
-
-[endsect]
-
-[endsect]
+[*Throws:] An exception derived from *interprocess_exception* on error.[endsect][endsect]
[section:upgradable_mutexes_mutex_interprocess_mutexes Boost.Interprocess Upgradable Mutex Types And Headers]
@@ -2200,166 +2427,53 @@
[endsect]
-[section:message_queue Message Queue]
+[section:file_lock File Locks]
-[section:message_queue_whats_a_mq What's A Message Queue?]
+[section:file_lock_whats_a_file_lock What's A File Lock?]
-A message queue is similar to a list of messages. Threads can put messages
-in the queue and they can also remove messages from the queue. Each message
-can have also a [*priority] so that higher priority messages are read before
-lower priority messages. Each message has some attributes:
+A file lock is an interprocess synchronization mechanism to protect concurrent
+writes and reads to files using a mutex ['embedded] in the file. This ['embedded mutex]
+has sharable and exclusive locking capabilities.
+With a file lock, an existing file can be used as a mutex without the need
+of creating additional synchronization objects to control concurrent file
+reads or writes.
-* A priority.
-* The length of the message.
-* The data (if length is bigger than 0).
+Generally speaking, we can have two file locking capabilities:
-A thread can send a message to or receive a message from the message
-queue using 3 methods:
+* [*Advisory locking:] The operating system kernel maintains a list of files that
+ have been locked. But does not prevent writing to those files even if a process
+ has acquired a sharable lock or does not prevent reading from the file when a process
+ has acquired the exclusive lock. Any process can ignore an advisory lock.
+ This means that advisory locks are for [*cooperating] processes,
+ processes that can trust each other. This is similar to a mutex protecting data
+ in a shared memory segment: any process connected to that memory can overwrite the
+ data but [*cooperative] processes use mutexes to protect the data first acquiring
+ the mutex lock.
-* [*Blocking]: If the message queue is full when sending or the message queue
- is empty when receiving, the thread is blocked until there
- is room for a new message or there is a new message.
-* [*Try]: If the message queue is full when sending or the message queue is empty
- when receiving, the thread returns immediately with an error.
-* [*Timed]: If the message queue is full when sending or the message queue is empty
- when receiving, the thread retries the operation until succeeds (returning
- successful state) or a timeout is reached (returning a failure).
+* [*Mandatory locking:] The OS kernel checks every read and write request to verify
+ that the operation can be performed according to the acquired lock. Reads and writes
+ block until the lock is released.
-A message queue [*just copies raw bytes between processes] and does not send
-objects. This means that if we want to send an object using a message queue
-[*the object must be binary serializable]. For example, we can send integers
-between processes but [*not] a `std::string`. You should use [*Boost.Serialization]
-or use advanced [*Boost.Interprocess] mechanisms to send complex data between
-processes.
+[*Boost.Interprocess] implements [*advisory blocking] because of portability reasons.
+This means that every process accessing to a file concurrently, must cooperate using
+file locks to synchronize the access.
-The [*Boost.Interprocess] message queue is a named interprocess communication: the
-message queue is created with a name and it's opened with a name, just like a file.
-When creating a message queue, the user must specify the maximum message size and
-the maximum message number that the message queue can store. These parameters will
-define the resources (for example the size of the shared memory used to implement
-the message queue if shared memory is used).
+In some systems file locking can be even further refined, leading to [*record locking],
+where a user can specify a [*byte range] within the file where the lock is applied.
+This allows concurrent write access by several processes if they need to access a
+different byte range in the file. [*Boost.Interprocess] does [*not] offer record
+locking for the moment, but might offer it in the future. To use a file lock just
+include:
[c++]
- using boost::interprocess;
- //Create a message_queue. If the queue
- //exists throws an exception
- message_queue mq
- (create_only //only create
- ,"message_queue" //name
- ,100 //max message number
- ,100 //max message size
- );
-
-[c++]
+ #include <boost/interprocess/sync/file_lock.hpp>
- using boost::interprocess;
- //Creates or opens a message_queue. If the queue
- //does not exist creates it, otherwise opens it.
- //Message number and size are ignored if the queue
- //is opened
- message_queue mq
- (open_or_create //open or create
- ,"message_queue" //name
- ,100 //max message number
- ,100 //max message size
- );
-
-[c++]
-
- using boost::interprocess;
- //Opens a message_queue. If the queue
- //does not exist throws an exception.
- message_queue mq
- (open_only //only open
- ,"message_queue" //name
- );
-
-The message queue is explicitly removed calling the static `remove` function:
-
-[c++]
-
- using boost::interprocess;
- message_queue::remove("message_queue");
-
-The funtion can fail if the message queue is still being used by any process.
-
-[endsect]
-
-[section:message_queue_example Using a message queue]
-
-To use a message queue you must include the following header:
-
-[c++]
-
- #include <boost/interprocess/ipc/message_queue.hpp>
-
-In the following example, the first process creates the message queue, and writes
-an array of integers on it. The other process just reads the array and checks that
-the sequence number is correct. This is the first process:
-
-[import ../example/doc_message_queueA.cpp]
-[doc_message_queueA]
-
-This is the second process:
-
-[import ../example/doc_message_queueB.cpp]
-[doc_message_queueB]
-
-To know more about this class and all its operations, please see the
-[classref boost::interprocess::message_queue] class reference.
-
-[endsect]
-
-[endsect]
-
-[section:file_lock File Locks]
-
-[section:file_lock_whats_a_file_lock What's A File Lock?]
-
-A file lock is an interprocess synchronization mechanism to protect concurrent
-writes and reads to files using a mutex ['embedded] in the file. This ['embedded mutex]
-has sharable and exclusive locking capabilities.
-With a file lock, an existing file can be used as a mutex without the need
-of creating additional synchronization objects to control concurrent file
-reads or writes.
-
-Generally speaking, we can have two file locking capabilities:
-
-* [*Advisory locking:] The operating system kernel maintains a list of files that
- have been locked. But does not prevent writing to those files even if a process
- has acquired a sharable lock or does not prevent reading from the file when a process
- has acquired the exclusive lock. Any process can ignore an advisory lock.
- This means that advisory locks are for [*cooperating] processes,
- processes that can trust each other. This is similar to a mutex protecting data
- in a shared memory segment: any process connected to that memory can overwrite the
- data but [*cooperative] processes use mutexes to protect the data first acquiring
- the mutex lock.
-
-* [*Mandatory locking:] The OS kernel checks every read and write request to verify
- that the operation can be performed according to the acquired lock. Reads and writes
- block until the lock is released.
-
-[*Boost.Interprocess] implements [*advisory blocking] because of portability reasons.
-This means that every process accessing to a file concurrently, must cooperate using
-file locks to synchronize the access.
-
-In some systems file locking can be even further refined, leading to [*record locking],
-where a user can specify a [*byte range] within the file where the lock is applied.
-This allows concurrent write access by several processes if they need to access a
-different byte range in the file. [*Boost.Interprocess] does [*not] offer record
-locking for the moment, but might offer it in the future. To use a file lock just
-include:
-
-[c++]
-
- #include <boost/interprocess/sync/file_lock.hpp>
-
-A file locking is a class that has [*process lifetime]. This means that if a process
-holding a file lock ends or crashes, the operating system will automatically unlock
-it. This feature is very useful in some situations where we want to assure
-automatic unlocking even when the process crashes and avoid leaving blocked resources
-in the system. A file lock is constructed using the name of the file as an argument:
+A file locking is a class that has [*process lifetime]. This means that if a process
+holding a file lock ends or crashes, the operating system will automatically unlock
+it. This feature is very useful in some situations where we want to assure
+automatic unlocking even when the process crashes and avoid leaving blocked resources
+in the system. A file lock is constructed using the name of the file as an argument:
[c++]
@@ -2615,136 +2729,124 @@
[endsect]
-[section:offset_ptr Mapping Address Independent Pointer: offset_ptr]
+[section:message_queue Message Queue]
-When creating shared memory and memory mapped files to communicate two
-processes. The memory segment can be mapped in different address in each process:
+[section:message_queue_whats_a_mq What's A Message Queue?]
-[c++]
+A message queue is similar to a list of messages. Threads can put messages
+in the queue and they can also remove messages from the queue. Each message
+can have also a [*priority] so that higher priority messages are read before
+lower priority messages. Each message has some attributes:
- #include<boost/interprocess/shared_memory_object.hpp>
+* A priority.
+* The length of the message.
+* The data (if length is bigger than 0).
- // ...
+A thread can send a message to or receive a message from the message
+queue using 3 methods:
- using boost::interprocess;
+* [*Blocking]: If the message queue is full when sending or the message queue
+ is empty when receiving, the thread is blocked until there
+ is room for a new message or there is a new message.
+* [*Try]: If the message queue is full when sending or the message queue is empty
+ when receiving, the thread returns immediately with an error.
+* [*Timed]: If the message queue is full when sending or the message queue is empty
+ when receiving, the thread retries the operation until succeeds (returning
+ successful state) or a timeout is reached (returning a failure).
- //Open a shared memory segment
- shared_memory_object shm_obj
- (open_only //open or create
- ,"shared_memory" //name
- ,read_only //read-only mode
- );
+A message queue [*just copies raw bytes between processes] and does not send
+objects. This means that if we want to send an object using a message queue
+[*the object must be binary serializable]. For example, we can send integers
+between processes but [*not] a `std::string`. You should use [*Boost.Serialization]
+or use advanced [*Boost.Interprocess] mechanisms to send complex data between
+processes.
- //Map the whole shared memory
- mapped_region region
- ( shm //Memory-mappable object
- , read_write //Access mode
- );
+The [*Boost.Interprocess] message queue is a named interprocess communication: the
+message queue is created with a name and it's opened with a name, just like a file.
+When creating a message queue, the user must specify the maximum message size and
+the maximum message number that the message queue can store. These parameters will
+define the resources (for example the size of the shared memory used to implement
+the message queue if shared memory is used).
- //This address can be different in each process
- void *addr = region.get_address();
+[c++]
-This difficults the creation of complex objects in mapped regions: a C++
-class instance placed in a mapped region might have a pointer pointing to
-another object also placed in the mapped region. Since the pointer stores an
-absolute address, that address is only valid for the process that placed
-the object there, unless all processes map the mapped region in the same
-address.
+ using boost::interprocess;
+ //Create a message_queue. If the queue
+ //exists throws an exception
+ message_queue mq
+ (create_only //only create
+ ,"message_queue" //name
+ ,100 //max message number
+ ,100 //max message size
+ );
-To be able to simulate pointers in mapped regions, users must use [*offsets]
-(distance between objets) instead of absolute address. The offset between
-two objects in a mapped region is the same for any process that maps the
-mapped region, even if that region is placed in different base addreses.
-To facilitate the use of offsets, [*Boost.Interprocess] offers
-[classref boost::interprocess::offset_ptr offset_ptr].
+[c++]
-[classref boost::interprocess::offset_ptr offset_ptr]
-wraps all the background operations
-needed to offer a pointer-like interface. The class interface is
-inspired in Boost Smart Pointers and stores the offset (distance in bytes)
-between the pointee's address and the
-[classref boost::interprocess::offset_ptr offset_ptr]'s "this" pointer
-(the address of the offset_ptr itself). Imagine an structure in a common
-32 bit processor:
+ using boost::interprocess;
+ //Creates or opens a message_queue. If the queue
+ //does not exist creates it, otherwise opens it.
+ //Message number and size are ignored if the queue
+ //is opened
+ message_queue mq
+ (open_or_create //open or create
+ ,"message_queue" //name
+ ,100 //max message number
+ ,100 //max message size
+ );
[c++]
- struct structure
- {
- int integer1; //This is placed at offset 0 in the structure
- offset_ptr<int> ptr; //This is placed at offset 4 in the structure
- int integer2; //This is placed at offset 8 in the structure
- };
+ using boost::interprocess;
+ //Opens a message_queue. If the queue
+ //does not exist throws an exception.
+ message_queue mq
+ (open_only //only open
+ ,"message_queue" //name
+ );
- //...
+The message queue is explicitly removed calling the static `remove` function:
- structure s;
-
- //Assign the address of "integer1" to "ptr".
- //"ptr" will store internally "-4":
- // (char*)&s.integer1 - (char*)&s.ptr;
- s.ptr = &s.integer1;
+[c++]
- //Assign the address of "integer2" to "ptr".
- //"ptr" will store internally "4":
- // (char*)&s.integer2 - (char*)&s.ptr;
- s.ptr = &s.integer2;
+ using boost::interprocess;
+ message_queue::remove("message_queue");
+The funtion can fail if the message queue is still being used by any process.
-One of the big problems of
-`offset_ptr` is the representation of the null pointer. The null pointer
-can't be safely represented like an offset, since the 0 absolute address
-is always out of the mapped region and the segment can be mapped
-in a different base address in each process, the distance between the address 0
-and `offset_ptr` is different for every process.
+[endsect]
-Some implementations choose
-0 offset as a null pointer but this is not valid for many uses,
-since many times structures like linked lists or nodes from STL containers
-point to themselves (the
-end node in an empty container, for example), and 0 offset value
-is needed. An alternative is to store, in addition to the offset, a boolean
-to indicate if the pointer is null. However, this increments the size of the
-pointer and hurts performance.
+[section:message_queue_example Using a message queue]
-In consequence,
-[classref boost::interprocess::offset_ptr offset_ptr] defines offset 1
-as the null pointer, meaning that this class [*can't] point to the byte
-after its own ['this] pointer:
+To use a message queue you must include the following header:
[c++]
- using namespace boost::interprocess;
+ #include <boost/interprocess/ipc/message_queue.hpp>
- offset_ptr<char> ptr;
-
- //Pointing to the next byte of it's own address
- //marks the smart pointer as null.
- ptr = (char*)&ptr + 1;
+In the following example, the first process creates the message queue, and writes
+an array of integers on it. The other process just reads the array and checks that
+the sequence number is correct. This is the first process:
- //ptr is equal to null
- assert(!ptr);
+[import ../example/doc_message_queueA.cpp]
+[doc_message_queueA]
- //This is the same as assigning the null value...
- ptr = 0;
+This is the second process:
- //ptr is also equal to null
- assert(!ptr);
+[import ../example/doc_message_queueB.cpp]
+[doc_message_queueB]
+To know more about this class and all its operations, please see the
+[classref boost::interprocess::message_queue] class reference.
-In practice, this limitation is not important, since a user almost never
-wants to point to this address.
+[endsect]
-[classref boost::interprocess::offset_ptr offset_ptr]
-offers all pointer-like operations and
-random_access_iterator typedefs, so it can be used in STL
-algorithms requiring random access and detected via traits.
-For more information about the members and operations of the class, see
-[classref boost::interprocess::offset_ptr offset_ptr reference].
+[endsect]
[endsect]
-[section:managed_memory_segments Managed Memory Segments: Making Interprocess Data Communication Easy]
+[section:managed_memory_segments Managed Memory Segments]
+
+[section:making_ipc_easy Making Interprocess Data Communication Easy]
[section:managed_memory_segments_intro Introduction]
@@ -2850,24 +2952,24 @@
[c++]
- /*!Defines a managed shared memory with c-strings as keys for named objects,
- the default memory algorithm (with process-shared mutexes,
- and offset_ptr as internal pointers) as memory allocation algorithm
- and the default index type as the index.
- This class allows the shared memory to be mapped in different base
- in different processes*/
+ //!Defines a managed shared memory with c-strings as keys for named objects,
+ //!the default memory algorithm (with process-shared mutexes,
+ //!and offset_ptr as internal pointers) as memory allocation algorithm
+ //!and the default index type as the index.
+ //!This class allows the shared memory to be mapped in different base
+ //!in different processes
typedef
basic_managed_shared_memory<char
,/*Default memory algorithm defining offset_ptr<void> as void_pointer*/
,/*Default index type*/>
managed_shared_memory;
- /*!Defines a managed shared memory with wide strings as keys for named objects,
- the default memory algorithm (with process-shared mutexes,
- and offset_ptr as internal pointers) as memory allocation algorithm
- and the default index type as the index.
- This class allows the shared memory to be mapped in different base
- in different processes*/
+ //!Defines a managed shared memory with wide strings as keys for named objects,
+ //!the default memory algorithm (with process-shared mutexes,
+ //!and offset_ptr as internal pointers) as memory allocation algorithm
+ //!and the default index type as the index.
+ //!This class allows the shared memory to be mapped in different base
+ //!in different processes
typedef
basic_managed_shared_memory<wchar_t
,/*Default memory algorithm defining offset_ptr<void> as void_pointer*/
@@ -2885,24 +2987,24 @@
[c++]
- /*!Defines a managed shared memory with c-strings as keys for named objects,
- the default memory algorithm (with process-shared mutexes,
- and offset_ptr as internal pointers) as memory allocation algorithm
- and the default index type as the index.
- This class allows the shared memory to be mapped in different base
- in different processes*/
+ //!Defines a managed shared memory with c-strings as keys for named objects,
+ //!the default memory algorithm (with process-shared mutexes,
+ //!and offset_ptr as internal pointers) as memory allocation algorithm
+ //!and the default index type as the index.
+ //!This class allows the shared memory to be mapped in different base
+ //!in different processes*/
typedef basic_managed_shared_memory
<char
,/*Default memory algorithm defining void * as void_pointer*/
,/*Default index type*/>
fixed_managed_shared_memory;
- /*!Defines a managed shared memory with wide strings as keys for named objects,
- the default memory algorithm (with process-shared mutexes,
- and offset_ptr as internal pointers) as memory allocation algorithm
- and the default index type as the index.
- This class allows the shared memory to be mapped in different base
- in different processes*/
+ //!Defines a managed shared memory with wide strings as keys for named objects,
+ //!the default memory algorithm (with process-shared mutexes,
+ //!and offset_ptr as internal pointers) as memory allocation algorithm
+ //!and the default index type as the index.
+ //!This class allows the shared memory to be mapped in different base
+ //!in different processes
typedef basic_managed_shared_memory
<wchar_t
,/*Default memory algorithm defining void * as void_pointer*/
@@ -2945,11 +3047,7 @@
// to implement managed features.
//!! If anything fails, throws interprocess_exception
//
- managed_shared_memory segment
- (create_only,
- "MySharedMemory", //Shared memory object name
- 65536); //Shared memory object size in bytes
-
+ managed_shared_memory segment (create_only, "MySharedMemory", //Shared memory object name 65536); //Shared memory object size in bytes
[c++]
//1. Opens a shared memory object
@@ -2960,22 +3058,14 @@
// to implement managed features.
//!! If anything fails, throws interprocess_exception
//
- managed_shared_memory segment
- (open_only,
- "MySharedMemory");//Shared memory object name
-
-[c++]
+ managed_shared_memory segment (open_only, "MySharedMemory");//Shared memory object name[c++]
//1. If the segment was previously created
// equivalent to "open_only".
//2. Otherwise, equivalent to "open_only" (size is ignored)
//!! If anything fails, throws interprocess_exception
//
- managed_shared_memory segment
- (open_or_create,
- "MySharedMemory", //Shared memory object name
- 65536); //Shared memory object size in bytes
-
+ managed_shared_memory segment (open_or_create, "MySharedMemory", //Shared memory object name 65536); //Shared memory object size in bytes
When the a `managed_shared_memory` object is destroyed, the shared memory
object is automatically unmapped, and all the resources are freed. To remove
the shared memory object from the system you must use the `shared_memory_object::remove`
@@ -2988,9 +3078,7 @@
[c++]
- fixed_managed_shared_memory segment
- (open_only
- ,"MyFixedAddressSharedMemory" //Shared memory object name
+ fixed_managed_shared_memory segment (open_only ,"MyFixedAddressSharedMemory" //Shared memory object name
,(void*)0x30000000 //Mapping address
[endsect]
@@ -3094,11 +3182,7 @@
// file to implement managed features.
//!! If anything fails, throws interprocess_exception
//
- managed_mapped_file mfile
- (create_only,
- "MyMappedFile", //Mapped file name
- 65536); //Mapped file size
-
+ managed_mapped_file mfile (create_only, "MyMappedFile", //Mapped file name 65536); //Mapped file size
[c++]
//1. Opens a file
@@ -3109,11 +3193,7 @@
// to implement managed features.
//!! If anything fails, throws interprocess_exception
//
- managed_mapped_file mfile
- (open_only,
- "MyMappedFile"); //Mapped file name
-
-[c++]
+ managed_mapped_file mfile (open_only, "MyMappedFile"); //Mapped file name[c++]
//1. If the file was previously created
// equivalent to "open_only".
@@ -3121,11 +3201,7 @@
//
//!! If anything fails, throws interprocess_exception
//
- managed_mapped_file mfile
- (open_or_create,
- "MyMappedFile", //Mapped file name
- 65536); //Mapped file size
-
+ managed_mapped_file mfile (open_or_create, "MyMappedFile", //Mapped file name 65536); //Mapped file size
When the a `managed_mapped_file` object is destroyed, the file is
automatically unmapped, and all the resources are freed. To remove
the file from the filesystem you can use standard C `std::remove`
@@ -3194,39 +3270,39 @@
[c++]
- /*!Allocates and constructs an object of type MyType (throwing version) */
+ //!Allocates and constructs an object of type MyType (throwing version)
MyType *ptr = managed_memory_segment.construct<MyType>("Name") (par1, par2...);
- /*!Allocates and constructs an array of objects of type MyType (throwing version)
- Each object receives the same parameters (par1, par2, ...)*/
+ //!Allocates and constructs an array of objects of type MyType (throwing version)
+ //!Each object receives the same parameters (par1, par2, ...)
MyType *ptr = managed_memory_segment.construct<MyType>("Name")[count](par1, par2...);
- /*!Tries to find a previously created object. If not present, allocates
- and constructs an object of type MyType (throwing version) */
+ //!Tries to find a previously created object. If not present, allocates
+ //!and constructs an object of type MyType (throwing version)
MyType *ptr = managed_memory_segment.find_or_construct<MyType>("Name") (par1, par2...);
- /*!Tries to find a previously created object. If not present, allocates and
- constructs an array of objects of type MyType (throwing version). Each object
- receives the same parameters (par1, par2, ...)*/
+ //!Tries to find a previously created object. If not present, allocates and
+ //!constructs an array of objects of type MyType (throwing version). Each object
+ //!receives the same parameters (par1, par2, ...)
MyType *ptr = managed_memory_segment.find_or_construct<MyType>("Name")[count](par1, par2...);
- /*!Allocates and constructs an array of objects of type MyType (throwing version)
- Each object receives parameters returned with the expression (*it1++, *it2++,... )*/
+ //!Allocates and constructs an array of objects of type MyType (throwing version)
+ //!Each object receives parameters returned with the expression (*it1++, *it2++,... )
MyType *ptr = managed_memory_segment.construct_it<MyType>("Name")[count](it1, it2...);
- /*!Tries to find a previously created object. If not present, allocates and constructs
- an array of objects of type MyType (throwing version). Each object receives
- parameters returned with the expression (*it1++, *it2++,... ) */
+ //!Tries to find a previously created object. If not present, allocates and constructs
+ //!an array of objects of type MyType (throwing version). Each object receives
+ //!parameters returned with the expression (*it1++, *it2++,... )
MyType *ptr = managed_memory_segment.find_or_construct_it<MyType>("Name")[count](it1, it2...);
- /*!Tries to find a previously created object. Returns a pointer to the object and the
- count (if it is not an array, returns 1). If not present, the returned pointer is 0*/
+ //!Tries to find a previously created object. Returns a pointer to the object and the
+ //!count (if it is not an array, returns 1). If not present, the returned pointer is 0
std::pair<MyType *,std::size_t> ret = managed_memory_segment.find<MyType>("Name");
- /*!Destroys the created object, returns false if not present*/
+ //!Destroys the created object, returns false if not present
bool destroyed = managed_memory_segment.destroy<MyType>("Name");
- /*!Destroys the created object via pointer*/
+ //!Destroys the created object via pointer
managed_memory_segment.destroy_ptr(ptr);
All these functions have a non-throwing version, that
@@ -3235,7 +3311,7 @@
[c++]
- /*!Allocates and constructs an object of type MyType (no throwing version) */
+ //!Allocates and constructs an object of type MyType (no throwing version)
MyType *ptr = managed_memory_segment.construct<MyType>("Name", std::nothrow) (par1, par2...);
[endsect]
@@ -3646,27 +3722,7 @@
/[import ../example/doc_managed_multiple_allocation.cpp]
/[doc_managed_multiple_allocation]
/
-/Allocating N buffers of the same size improves the performance of pools
-/and node containers (for example STL-like lists):
-/when inserting a range of forward iterators in a STL-like
-/list, the insertion function can detect the number of needed elements
-/and allocate in a single call. The nodes still can be deallocated.
-/
-/Allocating N buffers of different sizes can be used to speed up allocation in
-/cases where several objects must always be allocated at the same time but
-/deallocated at different times. For example, a class might perform several initial
-/allocations (some header data for a network packet, for example) in its
-/constructor but also allocations of buffers that might be reallocated in the future
-/(the data to be sent through the network). Instead of allocating all the data
-/independently, the constructor might use `allocate_many()` to speed up the
-/initialization, but it still can deallocate and expand the memory of the variable
-/size element.
-/
-/In general, `allocate_many` is useful with large values of N. Overuse
-/of `allocate_many` can increase the effective memory usage,
-/because it can't reuse existing non-contiguous memory fragments that
-/might be available for some of the elements.
-/
+/Allocating N buffers of the same size improves the performance of pools/and node containers (for example STL-like lists):/when inserting a range of forward iterators in a STL-like/list, the insertion function can detect the number of needed elements/and allocate in a single call. The nodes still can be deallocated.//Allocating N buffers of different sizes can be used to speed up allocation in/cases where several objects must always be allocated at the same time but/deallocated at different times. For example, a class might perform several initial/allocations (some header data for a network packet, for example) in its/constructor but also allocations of buffers that might be reallocated in the future/(the data to be sent through the network). Instead of allocating all the data/independently, the constructor might use `allocate_many()` to speed up the/initialization, but it still can deallocate and expand the memory of the variable/size element.//In general, `allocate_many` is useful with large values of N.
Overuse/of `allocate_many` can increase the effective memory usage,/because it can't reuse existing non-contiguous memory fragments that/might be available for some of the elements./
/[endsect]
]
@@ -3834,6 +3890,215 @@
[endsect]
+[section:managed_heap_memory_external_buffer Managed Heap Memory And Managed External Buffer]
+
+[*Boost.Interprocess] offers managed shared memory between processes using
+`managed_shared_memory` or `managed_mapped_file`. Two processes just map the same
+the memory mappable resoure and read from and write to that object.
+
+Many times, we don't want to use that shared memory approach and we prefer
+to send serialized data through network, local socket or message queues. Serialization
+can be done through [*Boost.Serialization] or similar library. However, if two processes
+share the same ABI (application binary interface), we could use the same object and
+container construction capabilities of `managed_shared_memory` or `managed_heap_memory`
+to build all the information in a single buffer that will be sent, for example,
+though message queues. The receiver would just copy the data to a local buffer, and it
+could read or modify it directly without deserializing the data . This approach can be
+much more efficient that a complex serialization mechanism.
+
+Applications for [*Boost.Interprocess] services using non-shared memory buffers:
+
+* Create and use STL compatible containers and allocators,
+ in systems where dynamic memory is not recommendable.
+
+* Build complex, easily serializable databases in a single buffer:
+
+ * To share data between threads
+
+ * To save and load information from/to files.
+
+* Duplicate information (containers, allocators, etc...) just copying the contents of
+ one buffer to another one.
+
+* Send complex information and objects/databases using serial/inter-process/network
+ communications.
+
+To help with this management, [*Boost.Interprocess] provides two useful classes,
+`basic_managed_heap_memory` and `basic_managed_external_buffer`:
+
+[section:managed_external_buffer Managed External Buffer: Constructing all Boost.Interprocess objects in a user provided buffer]
+
+Sometimes, the user wants to create simple objects, STL compatible containers, STL compatible
+strings and more, all in a single buffer. This buffer could be a big static buffer,
+a memory-mapped auxiliary device or any other user buffer.
+
+This would allow an easy serialization and we-ll just need to copy the buffer to duplicate
+all the objects created in the original buffer, including complex objects like
+maps, lists.... [*Boost.Interprocess] offers managed memory segment classes to handle user
+provided buffers that allow the same functionality as shared memory classes:
+
+[c++]
+
+ //Named object creation managed memory segment
+ //All objects are constructed in a a user provided buffer
+ template <
+ class CharType,
+ class MemoryAlgorithm,
+ template<class IndexConfig> class IndexType
+ >
+ class basic_managed_external_buffer;
+
+ //Named object creation managed memory segment
+ //All objects are constructed in a a user provided buffer
+ // Names are c-strings,
+ // Default memory management algorithm
+ // (rbtree_best_fit with no mutexes and relative pointers)
+ // Name-object mappings are stored in the default index type (flat_map)
+ typedef basic_managed_external_buffer <
+ char,
+ rbtree_best_fit<null_mutex_family, offset_ptr<void> >,
+ flat_map_index
+ > managed_external_buffer;
+
+ //Named object creation managed memory segment
+ //All objects are constructed in a a user provided buffer
+ // Names are wide-strings,
+ // Default memory management algorithm
+ // (rbtree_best_fit with no mutexes and relative pointers)
+ // Name-object mappings are stored in the default index type (flat_map)
+ typedef basic_managed_external_buffer<
+ wchar_t,
+ rbtree_best_fit<null_mutex_family, offset_ptr<void> >,
+ flat_map_index
+ > wmanaged_external_buffer;
+
+To use a managed external buffer, you must include the following header:
+
+[c++]
+
+ #include <boost/interprocess/managed_external_buffer.hpp>
+
+Let's see an example of the use of managed_external_buffer:
+
+[import ../example/doc_managed_external_buffer.cpp]
+[doc_managed_external_buffer]
+
+[*Boost.Interprocess] STL compatible allocators can also be used to place STL
+compatible containers in the user segment.
+
+[classref boost::interprocess::basic_managed_external_buffer basic_managed_external_buffer] can
+be also useful to build small databases for embedded systems limiting the size of
+the used memory to a predefined memory chunk, instead of letting the database
+fragment the heap memory.
+
+[endsect]
+
+[section:managed_heap_memory Managed Heap Memory: Boost.Interprocess machinery in heap memory]
+
+The use of heap memory (new/delete) to obtain a buffer where the user wants to store all
+his data is very common, so [*Boost.Interprocess] provides some specialized
+classes that work exclusively with heap memory.
+
+These are the classes:
+
+[c++]
+
+ //Named object creation managed memory segment
+ //All objects are constructed in a single buffer allocated via new[]
+ template <
+ class CharType,
+ class MemoryAlgorithm,
+ template<class IndexConfig> class IndexType
+ >
+ class basic_managed_heap_memory;
+
+ //Named object creation managed memory segment
+ //All objects are constructed in a single buffer allocated via new[]
+ // Names are c-strings,
+ // Default memory management algorithm
+ // (rbtree_best_fit with no mutexes and relative pointers)
+ // Name-object mappings are stored in the default index type (flat_map)
+ typedef basic_managed_heap_memory <
+ char,
+ rbtree_best_fit<null_mutex_family>,
+ flat_map_index
+ > managed_heap_memory;
+
+ //Named object creation managed memory segment
+ //All objects are constructed in a single buffer allocated via new[]
+ // Names are wide-strings,
+ // Default memory management algorithm
+ // (rbtree_best_fit with no mutexes and relative pointers)
+ // Name-object mappings are stored in the default index type (flat_map)
+ typedef basic_managed_heap_memory<
+ wchar_t,
+ rbtree_best_fit<null_mutex_family>,
+ flat_map_index
+ > wmanaged_heap_memory;
+
+To use a managed heap memory, you must include the following header:
+
+[c++]
+
+ #include <boost/interprocess/managed_heap_memory.hpp>
+
+The use is exactly the same as
+[classref boost::interprocess::basic_managed_external_buffer],
+except that memory is created by
+the managed memory segment itself using dynamic (new/delete) memory.
+
+[*basic_managed_heap_memory] also offers a `grow(std::size_t extra_bytes)` function that
+tries to resize internal heap memory so that we have room for more objects.
+But *be careful*, if memory is reallocated, the old buffer will be copied into
+the new one so all the objects will be binary-copied to the new buffer.
+To be able to use this function, all pointers constructed in the heap buffer that
+point to objects in the heap buffer must be relative pointers (for example `offset_ptr`).
+Otherwise, the result is undefined. Here is an example:
+
+[import ../example/doc_managed_heap_memory.cpp]
+[doc_managed_heap_memory]
+
+[endsect]
+
+[section:managed_heap_memory_external_buffer_diff Differences between managed memory segments]
+
+All managed memory segments have similar capabilities
+(memory allocation inside the memory segment, named object construction...),
+but there are some remarkable differences between [*managed_shared_memory],
+[*managed_mapped_file] and [*managed_heap_memory], [*managed_external_file].
+
+* Default specializations of managed shared memory and mapped file use process-shared
+ mutexes. Heap memory and external buffer have no internal synchronization by default.
+ The cause is that the first two are thought to be shared between processes (although
+ memory mapped files could be used just to obtain a persistent object data-base for a
+ process) whereas the last two are thought to be used inside one process to construct
+ a serialized named object data-base that can be sent though serial interprocess
+ communications (like message queues, localhost network...).
+
+* The first two create a system-global object (a shared memory object or a file) shared
+ by several processes, whereas the last two are objects that don't create system-wide
+ resources.
+
+[endsect]
+
+[section:shared_message_queue_ex Example: Serializing a database through the message queue]
+
+To see the utility of managed heap memory and managed external buffer classes,
+the following example shows how a message queue can be used to serialize a whole
+database constructed in a memory buffer using [*Boost.Interprocess], send the database
+through a message queue and duplicated in another buffer:
+
+[import ../test/message_queue_test.cpp]
+[message_queue_test_test_serialize_db]
+
+[endsect]
+
+[endsect]
+
+[endsect]
+
+[section:allocators_containers Allocators, containers and memory allocation algorithms]
+
[section:allocator_introduction Introduction to Interprocess allocators]
As seen, [*Boost.Interprocess] offers raw memory allocation and object construction
@@ -3997,7 +4262,7 @@
To know the details of the implementation of
of the segregated storage pools see the
-[link interprocess.architecture_2.implementation_segregated_storage_pools Implementation of [*Boost.Interprocess] segregated storage pools]
+[link interprocess.architecture.allocators_containers.implementation_segregated_storage_pools Implementation of [*Boost.Interprocess] segregated storage pools]
section.
[section:segregated_allocators_common Additional parameters and functions of segregated storage node allocators]
@@ -4006,7 +4271,7 @@
[classref boost::interprocess::private_node_allocator private_node_allocator] and
[classref boost::interprocess::cached_node_allocator cached_node_allocator] implement
the standard allocator interface and the functions explained in the
-[link interprocess.allocator_introduction.allocator_properties Properties of Boost.Interprocess allocators].
+[link interprocess.allocators_containers.allocator_introduction.allocator_properties Properties of Boost.Interprocess allocators].
All these allocators are templatized by 3 parameters:
@@ -4033,7 +4298,7 @@
a node allocator between processes. To achieve this sharing
[classref boost::interprocess::node_allocator node_allocator]
uses the segment manager's unique type allocation service
-(see [link interprocess.managed_memory_segment_features.unique Unique instance construction] section).
+(see [link interprocess.managed_memory_segments.managed_memory_segment_features.unique Unique instance construction] section).
In the initialization, a
[classref boost::interprocess::node_allocator node_allocator]
@@ -4228,7 +4493,7 @@
of nodes to the memory segment, so that they can be used by any other container or managed
object construction. To know the details of the implementation of
of "adaptive pools" see the
-[link interprocess.architecture_2.implementation_adaptive_pools Implementation of [*Boost.Intrusive] adaptive pools]
+[link interprocess.architecture.allocators_containers.implementation_adaptive_pools Implementation of [*Boost.Intrusive] adaptive pools]
section.
Like with segregated storage based node allocators, Boost.Interprocess offers
@@ -4242,7 +4507,7 @@
[classref boost::interprocess::private_adaptive_pool private_adaptive_pool] and
[classref boost::interprocess::cached_adaptive_pool cached_adaptive_pool] implement
the standard allocator interface and the functions explained in the
-[link interprocess.allocator_introduction.allocator_properties Properties of Boost.Interprocess allocators].
+[link interprocess.allocators_containers.allocator_introduction.allocator_properties Properties of Boost.Interprocess allocators].
All these allocators are templatized by 4 parameters:
@@ -4623,232 +4888,27 @@
[endsect]
-[section:managed_heap_memory_external_buffer Managed Heap Memory And Managed External Buffer]
-
-[*Boost.Interprocess] offers managed shared memory between processes using
-`managed_shared_memory` or `managed_mapped_file`. Two processes just map the same
-the memory mappable resoure and read from and write to that object.
-
-Many times, we don't want to use that shared memory approach and we prefer
-to send serialized data through network, local socket or message queues. Serialization
-can be done through [*Boost.Serialization] or similar library. However, if two processes
-share the same ABI (application binary interface), we could use the same object and
-container construction capabilities of `managed_shared_memory` or `managed_heap_memory`
-to build all the information in a single buffer that will be sent, for example,
-though message queues. The receiver would just copy the data to a local buffer, and it
-could read or modify it directly without deserializing the data . This approach can be
-much more efficient that a complex serialization mechanism.
-
-Applications for [*Boost.Interprocess] services using non-shared memory buffers:
-
-* Create and use STL compatible containers and allocators,
- in systems where dynamic memory is not suggested.
+[section:memory_algorithms Memory allocation algorithms]
-* Build complex, easily serializable databases in a single buffer:
+[section:simple_seq_fit simple_seq_fit: A simple shared memory management algorithm]
- * To share data between threads
+The algorithm is a variation of sequential fit using singly
+linked list of free memory buffers. The algorithm is based
+on the article about shared memory titled
+[@http://home.earthlink.net/~joshwalker1/writing/SharedMemory.html ['"Taming Shared Memory"] ].
+The algorithm is as follows:
- * To save and load information from/to files.
+The shared memory is divided in blocks of free shared memory,
+each one with some control data and several bytes of memory
+ready to be used. The control data contains a pointer (in
+our case offset_ptr) to the next free block and the size of
+the block. The allocator consists of a singly linked list
+of free blocks, ordered by address. The last block, points
+always to the first block:
-* Duplicate information (containers, allocators, etc...) just copying the contents of
- one buffer to another one.
+[c++]
-* Send complex information and objects/databases using serial/inter-process/network
- communications.
-
-To help with this management, [*Boost.Interprocess] provides two useful classes,
-`basic_managed_heap_memory` and `basic_managed_external_buffer`:
-
-[section:managed_external_buffer Managed External Buffer: Constructing all Boost.Interprocess objects in a user provided buffer]
-
-Sometimes, the user wants to create simple objects, STL compatible containers, STL compatible
-strings and more, all in a single buffer. This buffer could be a big static buffer,
-a memory-mapped auxiliary device or any other user buffer.
-
-This would allow an easy serialization and we-ll just need to copy the buffer to duplicate
-all the objects created in the original buffer, including complex objects like
-maps, lists.... [*Boost.Interprocess] offers managed memory segment classes to handle user
-provided buffers that allow the same functionality as shared memory classes:
-
-[c++]
-
- //Named object creation managed memory segment
- //All objects are constructed in a a user provided buffer
- template <
- class CharType,
- class MemoryAlgorithm,
- template<class IndexConfig> class IndexType
- >
- class basic_managed_external_buffer;
-
- //Named object creation managed memory segment
- //All objects are constructed in a a user provided buffer
- // Names are c-strings,
- // Default memory management algorithm
- // (rbtree_best_fit with no mutexes and relative pointers)
- // Name-object mappings are stored in the default index type (flat_map)
- typedef basic_managed_external_buffer <
- char,
- rbtree_best_fit<null_mutex_family, offset_ptr<void> >,
- flat_map_index
- > managed_external_buffer;
-
- //Named object creation managed memory segment
- //All objects are constructed in a a user provided buffer
- // Names are wide-strings,
- // Default memory management algorithm
- // (rbtree_best_fit with no mutexes and relative pointers)
- // Name-object mappings are stored in the default index type (flat_map)
- typedef basic_managed_external_buffer<
- wchar_t,
- rbtree_best_fit<null_mutex_family, offset_ptr<void> >,
- flat_map_index
- > wmanaged_external_buffer;
-
-To use a managed external buffer, you must include the following header:
-
-[c++]
-
- #include <boost/interprocess/managed_external_buffer.hpp>
-
-Let's see an example of the use of managed_external_buffer:
-
-[import ../example/doc_managed_external_buffer.cpp]
-[doc_managed_external_buffer]
-
-[*Boost.Interprocess] STL compatible allocators can also be used to place STL
-compatible containers in the user segment.
-
-[classref boost::interprocess::basic_managed_external_buffer basic_managed_external_buffer] can
-be also useful to build small databases for embedded systems limiting the size of
-the used memory to a predefined memory chunk, instead of letting the database
-fragment the heap memory.
-
-[endsect]
-
-[section:managed_heap_memory Managed Heap Memory: Boost.Interprocess machinery in heap memory]
-
-The use of heap memory (new/delete) to obtain a buffer where the user wants to store all
-his data is very common, so [*Boost.Interprocess] provides some specialized
-classes that work exclusively with heap memory.
-
-These are the classes:
-
-[c++]
-
- //Named object creation managed memory segment
- //All objects are constructed in a single buffer allocated via new[]
- template <
- class CharType,
- class MemoryAlgorithm,
- template<class IndexConfig> class IndexType
- >
- class basic_managed_heap_memory;
-
- //Named object creation managed memory segment
- //All objects are constructed in a single buffer allocated via new[]
- // Names are c-strings,
- // Default memory management algorithm
- // (rbtree_best_fit with no mutexes and relative pointers)
- // Name-object mappings are stored in the default index type (flat_map)
- typedef basic_managed_heap_memory <
- char,
- rbtree_best_fit<null_mutex_family>,
- flat_map_index
- > managed_heap_memory;
-
- //Named object creation managed memory segment
- //All objects are constructed in a single buffer allocated via new[]
- // Names are wide-strings,
- // Default memory management algorithm
- // (rbtree_best_fit with no mutexes and relative pointers)
- // Name-object mappings are stored in the default index type (flat_map)
- typedef basic_managed_heap_memory<
- wchar_t,
- rbtree_best_fit<null_mutex_family>,
- flat_map_index
- > wmanaged_heap_memory;
-
-To use a managed heap memory, you must include the following header:
-
-[c++]
-
- #include <boost/interprocess/managed_heap_memory.hpp>
-
-The use is exactly the same as
-[classref boost::interprocess::basic_managed_external_buffer],
-except that memory is created by
-the managed memory segment itself using dynamic (new/delete) memory.
-
-[*basic_managed_heap_memory] also offers a `grow(std::size_t extra_bytes)` function that
-tries to resize internal heap memory so that we have room for more objects.
-But *be careful*, if memory is reallocated, the old buffer will be copied into
-the new one so all the objects will be binary-copied to the new buffer.
-To be able to use this function, all pointers constructed in the heap buffer that
-point to objects in the heap buffer must be relative pointers (for example `offset_ptr`).
-Otherwise, the result is undefined. Here is an example:
-
-[import ../example/doc_managed_heap_memory.cpp]
-[doc_managed_heap_memory]
-
-[endsect]
-
-[section:managed_heap_memory_external_buffer_diff Differences between managed memory segments]
-
-All managed memory segments have similar capabilities
-(memory allocation inside the memory segment, named object construction...),
-but there are some remarkable differences between [*managed_shared_memory],
-[*managed_mapped_file] and [*managed_heap_memory], [*managed_external_file].
-
-* Default specializations of managed shared memory and mapped file use process-shared
- mutexes. Heap memory and external buffer have no internal synchronization by default.
- The cause is that the first two are thought to be shared between processes (although
- memory mapped files could be used just to obtain a persistent object data-base for a
- process) whereas the last two are thought to be used inside one process to construct
- a serialized named object data-base that can be sent though serial interprocess
- communications (like message queues, localhost network...).
-
-* The first two create a system-global object (a shared memory object or a file) shared
- by several processes, whereas the last two are objects that don't create system-wide
- resources.
-
-[endsect]
-
-[section:shared_message_queue_ex Example: Serializing a database through the message queue]
-
-To see the utility of managed heap memory and managed external buffer classes,
-the following example shows how a message queue can be used to serialize a whole
-database constructed in a memory buffer using [*Boost.Interprocess], send the database
-through a message queue and duplicated in another buffer:
-
-[import ../test/message_queue_test.cpp]
-[message_queue_test_test_serialize_db]
-
-[endsect]
-
-[endsect]
-
-[section:memory_algorithms Boost.Interprocess memory allocation algorithms]
-
-[section:simple_seq_fit simple_seq_fit: A simple shared memory management algorithm]
-
-The algorithm is a variation of sequential fit using singly
-linked list of free memory buffers. The algorithm is based
-on the article about shared memory titled
-[@http://home.earthlink.net/~joshwalker1/writing/SharedMemory.html ['"Taming Shared Memory"] ].
-The algorithm is as follows:
-
-The shared memory is divided in blocks of free shared memory,
-each one with some control data and several bytes of memory
-ready to be used. The control data contains a pointer (in
-our case offset_ptr) to the next free block and the size of
-the block. The allocator consists of a singly linked list
-of free blocks, ordered by address. The last block, points
-always to the first block:
-
-[c++]
-
- simple_seq_fit memory layout:
+ simple_seq_fit memory layout:
main extra allocated free_block_1 allocated free_block_2 allocated free_block_3
header header block ctrl usr block ctrl usr block ctrl usr
@@ -4945,6 +5005,8 @@
[endsect]
+[endsect]
+
[section:streams Direct iostream formatting: vectorstream and bufferstream]
Shared memory, memory-mapped files and all [*Boost.Interprocess] mechanisms are focused
@@ -5154,7 +5216,7 @@
[endsect]
-[section:interprocess_smart_ptr Boost.Interprocess ownership smart pointers]
+[section:interprocess_smart_ptr Ownership smart pointers]
C++ users know the importance of ownership smart pointers when dealing with resources.
Boost offers a wide range of such type of pointers: `intrusive_ptr<>`,
@@ -5174,90 +5236,28 @@
[section:intrusive_ptr Intrusive pointer]
[classref boost::interprocess::intrusive_ptr] is the generalization of `boost::intrusive_ptr<>`
-to allow non-raw pointers as intrusive pointer members. As the known
+to allow non-raw pointers as intrusive pointer members. As the well-known
`boost::intrusive_ptr` we must specify the pointee type but we also must also specify
the pointer type to be stored in the intrusive_ptr:
[c++]
- /*!The intrusive_ptr class template stores a pointer to an object
- with an embedded reference count. intrusive_ptr is parameterized on
- T (the type of the object pointed to) and VoidPointer(a void pointer type
- that defines the type of pointer that intrusive_ptr will store).
- intrusive_ptr<T, void *> defines a class with a T* member whereas
- intrusive_ptr<T, offset_ptr<void> > defines a class with a offset_ptr<T> member.
- Relies on unqualified calls to:
-
- void intrusive_ptr_add_ref(T * p);
- void intrusive_ptr_release(T * p);
-
- with (p != 0)
-
- The object is responsible for destroying itself.*/
+ //!The intrusive_ptr class template stores a pointer to an object
+ //!with an embedded reference count. intrusive_ptr is parameterized on
+ //!T (the type of the object pointed to) and VoidPointer(a void pointer type
+ //!that defines the type of pointer that intrusive_ptr will store).
+ //!intrusive_ptr<T, void *> defines a class with a T* member whereas
+ //!intrusive_ptr<T, offset_ptr<void> > defines a class with a offset_ptr<T> member.
+ //!Relies on unqualified calls to:
+ //!
+ //!void intrusive_ptr_add_ref(T * p);
+ //!void intrusive_ptr_release(T * p);
+ //!
+ //!with (p != 0)
+ //!
+ //!The object is responsible for destroying itself.
template<class T, class VoidPointer>
- class intrusive_ptr
- {
- public:
- /*!Provides the type of the internal stored pointer.*/
- typedef typename /*...*/ pointer;
- /*!Provides the type of the stored pointer.*/
- typedef T element_type;
-
- /*!Constructor. Initializes internal pointer to 0. Does not throw*/
- intrusive_ptr();
-
- /*!Constructor. Copies pointer and if "p" is not zero and
- "add_ref" is true calls intrusive_ptr_add_ref(get_pointer(p)).
- Does not throw*/
- intrusive_ptr(const pointer &p, bool add_ref = true);
-
- /*!Copy constructor. Copies the internal pointer and if "p" is not
- zero calls intrusive_ptr_add_ref(get_pointer(p)). Does not throw*/
- intrusive_ptr(intrusive_ptr const & rhs);
-
- /*!Constructor from related. Copies the internal pointer and if "p" is not
- zero calls intrusive_ptr_add_ref(get_pointer(p)). Does not throw*/
- template<class U> intrusive_ptr (intrusive_ptr<U, VP> const & rhs);
-
- /*!Destructor. If internal pointer is not 0, calls
- intrusive_ptr_release(get_pointer(m_ptr)). Does not throw*/
- ~intrusive_ptr();
-
- /*!Assignment operator. Equivalent to intrusive_ptr(r).swap(*this).
- Does not throw*/
- intrusive_ptr & operator=(intrusive_ptr const & rhs);
-
- /*!Assignment from related. Equivalent to intrusive_ptr(r).swap(*this).
- Does not throw*/
- template<class U> intrusive_ptr & operator= (intrusive_ptr<U, VP> const & rhs);
-
- /*!Assignment from pointer. Equivalent to intrusive_ptr(r).swap(*this).
- Does not throw*/
- intrusive_ptr & operator=(pointer rhs);
-
- /*!Returns a reference to the internal pointer. Does not throw*/
- pointer &get();
-
- /*!Returns a reference to the internal pointer. Does not throw*/
- const pointer &get() const;
-
- /*!Returns *get(). Does not throw*/
- T & operator*() const;
-
- /*!Returns *get(). Does not throw*/
- const pointer &operator->() const;
-
- /*!Returns get(). Does not throw*/
- pointer &operator->();
-
- operator unspecified_bool_type () const;
-
- /*!Not operator. Does not throw*/
- bool operator! () const;
-
- /*!Exchanges the contents of the two smart pointers. Does not throw*/
- void swap(intrusive_ptr & rhs);
- };
+ class intrusive_ptr;
So `boost::interprocess::intrusive_ptr<MyClass, void*>` is equivalent to
`boost::instrusive_ptr<MyClass>`. But if we want to place the intrusive_ptr in
@@ -5277,84 +5277,193 @@
[c++]
- /*!scoped_ptr stores a pointer to a dynamically allocated object.
- The object pointed to is guaranteed to be deleted, either on destruction
- of the scoped_ptr, or via an explicit reset. The user can avoid this
- deletion using release().
- scoped_ptr is parameterized on T (the type of the object pointed to) and
- Deleter (the functor to be executed to delete the internal pointer).
- The internal pointer will be of the same pointer type as typename
- Deleter::pointer type (that is, if typename Deleter::pointer is
- offset_ptr<void>, the internal pointer will be offset_ptr<T>).*/
+ //!scoped_ptr stores a pointer to a dynamically allocated object.
+ //!The object pointed to is guaranteed to be deleted, either on destruction
+ //!of the scoped_ptr, or via an explicit reset. The user can avoid this
+ //!deletion using release().
+ //!scoped_ptr is parameterized on T (the type of the object pointed to) and
+ //!Deleter (the functor to be executed to delete the internal pointer).
+ //!The internal pointer will be of the same pointer type as typename
+ //!Deleter::pointer type (that is, if typename Deleter::pointer is
+ //!offset_ptr<void>, the internal pointer will be offset_ptr<T>).
template<class T, class Deleter>
- class scoped_ptr
- {
- public:
+ class scoped_ptr;
+
+`scoped_ptr<>` comes handy to implement *rollbacks* with exceptions: if an exception
+is thrown or we call `return` in the scope of `scoped_ptr<>` the deleter is
+automatically called so that *the deleter can be considered as a rollback* function.
+If all goes well, we call `release()` member function to avoid rollback when
+the `scoped_ptr` goes out of scope.
- /*!Provides the type of the stored pointer.*/
- typedef T element_type;
+[import ../example/doc_scoped_ptr.cpp]
+[doc_scoped_ptr]
- /*!Provides the type of the internal stored pointer.*/
- typedef /*...*/ pointer;
+[endsect]
- /*!Constructs a scoped_ptr, storing a copy of p(which can be 0) and d.
- Does not throw.*/
- explicit scoped_ptr(const pointer &p = 0, const Deleter &d = Deleter());
+[section:shared_ptr Shared pointer and weak pointer]
- /*!If the stored pointer is not 0, destroys the object pointed to by the stored pointer.
- calling the operator() of the stored deleter.*/
- ~scoped_ptr();
+[*Boost.Interprocess] also offers the possibility of creating non-intrusive
+reference-counted objects in managed shared memory or mapped files.
- /*!Deletes the object pointed to by the stored pointer and then
- stores a copy of p. Never throws*/
- void reset(const pointer &p = 0);
+Unlike
+[@http://www.boost.org/libs/smart_ptr/shared_ptr.htm boost::shared_ptr],
+due to limitations of mapped segments [classref boost::interprocess::shared_ptr]
+can not take advantage of virtual functions to maintain the same shared pointer
+type while providing user-defined allocators and deleters. The allocator
+and the deleter are template parameters of the shared pointer.
- /*!Deletes the object pointed to by the stored pointer and then
- stores a copy of p and a copy of d.*/
- void reset(const pointer &p, const Deleter &d);
+Since the reference count and other auxiliary data needed by
+[classref boost::interprocess::shared_ptr shared_ptr] must be created also in
+the managed segment, and the deleter has to delete the object from
+the segment, the user must specify an allocator object and a deleter object
+when constructing a non-empty instance of
+[classref boost::interprocess::shared_ptr shared_ptr], just like
+[*Boost.Interprocess] containers need to pass allocators in their constructors.
- /*!Assigns internal pointer as 0 and returns previous pointer. This will
- avoid deletion on destructor*/
- pointer release():
+Here's is the declaration of [classref boost::interprocess::shared_ptr shared_ptr]:
- /*!Returns a reference to the object pointed to by the stored pointer.
- Never throws.*/
- reference operator*() const;
+[c++]
- /*!Returns the internal stored pointer. Never throws*/
- pointer &operator->();
+ template<class T, class VoidAllocator, class Deleter>
+ class shared_ptr;
- /*!Returns the internal stored pointer. Never throws.*/
- const pointer &operator->() const;
+* T is the type of the pointed type.
+* VoidAllocator is the allocator to be used to allocate auxiliary
+ elements such as the reference count, the deleter...
+ The internal `pointer` typedef of the allocator will determine
+ the type of pointer that shared_ptr will internally use, so
+ allocators defining `pointer` as `offset_ptr<void>` will
+ make all internal pointers used by `shared_ptr` to be
+ also relative pointers. See [classref boost::interprocess::allocator]
+ for a working allocator.
+* Deleter is the function object that will be used to destroy
+ the pointed object when the last reference to the object
+ is destroyed. The deleter functor will take a pointer to T
+ of the same category as the void pointer defined by
+ `VoidAllocator::pointer`. See [classref boost::interprocess::deleter]
+ for a generic deleter that erases a object from a managed segment.
- /*!Returns the stored pointer. Never throws.*/
- pointer & get();
+With correctly specified parameters, [*Boost.Interprocess] users
+can create objects in shared memory that hold shared pointers pointing
+to other objects also in shared memory, obtaining the benefits of
+reference counting. Let's see how to create a shared pointer in a managed shared memory:
- /*!Returns the stored pointer. Never throws.*/
- const pointer & get() const;
+[import ../example/doc_shared_ptr_explicit.cpp]
+[doc_shared_ptr_explicit]
- /*!Returns true if the stored pointer is 0. Never throws.*/
- bool operator! () const;
+[classref boost::interprocess::shared_ptr] is very flexible and
+configurable (we can specify the allocator and the deleter, for example),
+but as shown the creation of a shared pointer in managed segments
+need too much typing.
- /*!Exchanges the internal pointer and deleter with other scoped_ptr
- Never throws.*/
- void swap(scoped_ptr & b);
- };
-
-`scoped_ptr<>` comes handy to implement *rollbacks* with exceptions: if an exception
-is thrown or we call `return` in the scope of `scoped_ptr<>` the deleter is
-automatically called so that *the deleter can be considered as a rollback* function.
-If all goes well, we call `release()` member function to avoid rollback when
-the `scoped_ptr` goes out of scope.
+To simplify this usage, [classref boost::interprocess::shared_ptr] header
+offers a shared pointer definition helper class
+([classref boost::interprocess::managed_shared_ptr managed_shared_ptr]) and a function
+([funcref boost::interprocess::make_managed_shared_ptr make_managed_shared_ptr])
+to easily construct a shared pointer from a type allocated in a managed segment
+with an allocator that will allocate the reference count also in the managed
+segment and a deleter that will erase the object from the segment.
-[import ../example/doc_scoped_ptr.cpp]
-[doc_scoped_ptr]
+These utilities will use the a [*Boost.Interprocess] allocator
+([classref boost::interprocess::allocator])
+and deleter ([classref boost::interprocess::deleter]) to do their job.
+The definition of the previous shared pointer
+could be simplified to the following:
+
+[c++]
+
+ typedef managed_shared_ptr<MyType, managed_shared_memory>::type my_shared_ptr;
+
+And the creation of a shared pointer can be simplified to this:
+
+[c++]
+
+ my_shared_ptr sh_ptr = make_managed_shared_ptr
+ (segment.construct<MyType>("object to share")(), segment);
+
+[*Boost.Interprocess] also offers a weak pointer named
+[classref boost::interprocess::weak_ptr weak_ptr] (with its corresponding
+[classref boost::interprocess::managed_weak_ptr managed_weak_ptr] and
+[funcref boost::interprocess::make_managed_weak_ptr make_managed_weak_ptr] utilities)
+to implement non-owning observers of an object owned by
+[classref boost::interprocess::shared_ptr shared_ptr].
+
+Now let's see a detailed example of the use of
+[classref boost::interprocess::shared_ptr shared_ptr]:
+and
+[classref boost::interprocess::weak_ptr weak_ptr]
+
+[import ../example/doc_shared_ptr.cpp]
+[doc_shared_ptr]
+
+In general, using [*Boost.Interprocess]' [classref boost::interprocess::shared_ptr shared_ptr]
+and [classref boost::interprocess::weak_ptr weak_ptr] is very similar to their
+counterparts [@http://www.boost.org/libs/smart_ptr/shared_ptr.htm boost::shared_ptr]
+and [@http://www.boost.org/libs/smart_ptr/weak_ptr.htm boost::weak_ptr], but
+they need more template parameters and more run-time parameters in their constructors.
+
+Just like [@http://www.boost.org/libs/smart_ptr/shared_ptr.htm boost::shared_ptr]
+can be stored in a STL container, [classref boost::interprocess::shared_ptr shared_ptr]
+can also be stored in [*Boost.Interprocess] containers.
+
+If a programmer just uses [classref boost::interprocess::shared_ptr shared_ptr]
+to be able to insert objects dynamically constructed in the managed segment
+in a container, but does not need to share the ownership of that object with
+other objects [classref boost::interprocess::unique_ptr unique_ptr] is a much
+faster and easier to use alternative.
+
+[endsect]
+
+[section:unique_ptr Unique pointer]
+
+Unique ownership smart pointers are really useful to free programmers from
+manual resource liberation of non-shared objects. [*Boost.Interprocess]'
+[classref boost::interprocess::unique_ptr unique_ptr] is much like
+[classref boost::interprocess::scoped_ptr scoped_ptr] but it's [*moveable]
+and can be easily inserted in [*Boost.Interprocess] containers.
+Here is the declaration of the unique pointer class:
+
+[c++]
+
+ template <class T, class D>
+ class unique_ptr;
+
+* T is the type of the object pointed by [classref boost::interprocess::unique_ptr unique_ptr].
+* D is the deleter that will erase the object type of the object pointed by
+ [classref boost::interprocess::unique_ptr unique_ptr] when the unique pointer
+ is destroyed (and if still owns ownership of the object). If the deleter defines
+ an internal `pointer` typedef, [classref boost::interprocess::unique_ptr unique_ptr]
+ will use an internal pointer of the same type. So if `D::pointer` is `offset_ptr<T>`
+ the unique pointer will store a relative pointer instead of a raw one. This
+ allows placing [classref boost::interprocess::unique_ptr unique_ptr] in shared
+ memory and memory-mapped files.
+
+[classref boost::interprocess::unique_ptr unique_ptr] can release the ownership of
+the stored pointer so it's useful also to be used as a rollback function. One of the main
+properties of the class is that [*is not copyable, but only moveable]. When a unique
+pointer is moved to another one, the ownership of the pointer is transferred from
+the source unique pointer to the target unique pointer. If the target unique pointer
+owned an object, that object is first deleted before taking ownership of the new object.
+
+[classref boost::interprocess::unique_ptr unique_ptr] also offers auxiliary types to
+easily define and construct unique pointers that can be placed in managed segments
+and will correctly delete the owned object from the segment:
+[classref boost::interprocess::managed_unique_ptr managed_unique_ptr]
+and
+[funcref boost::interprocess::make_managed_unique_ptr make_managed_unique_ptr]
+utilities.
+
+Here we see an example of the use [classref boost::interprocess::unique_ptr unique_ptr]
+including creating containers of such objects:
+
+[import ../example/doc_unique_ptr.cpp]
+[doc_unique_ptr]
[endsect]
[endsect]
-[section:architecture Boost.Interprocess architecture and internals (I)]
+[section:architecture Architecture and internals]
[section:basic_guidelines Basic guidelines]
@@ -5391,6 +5500,8 @@
[endsect]
+[section:architecture_algorithm_to_managed From the memory algorithm to the managed segment]
+
[section:architecture_memory_algorithm The memory algorithm]
The [*memory algorithm] is an object that is placed in the first bytes of a
@@ -5560,9 +5671,9 @@
[endsect]
[endsect]
-[section:architecture_2 Boost.Interprocess architecture and internals (II)]
+[section:allocators_containers Allocators and containers]
-[section:architecture_allocators Boost.Interprocess allocators]
+[section:allocators Boost.Interprocess allocators]
The [*Boost.Interprocess] STL-like allocators are fairly simple and follow the usual C++
allocator approach. Normally, allocators for STL containers are based above new/delete
@@ -5674,7 +5785,140 @@
[endsect]
-[section:customizing_interprocess Customizing Boost.Interprocess]
+[section:performance Performance of Boost.Interprocess]
+
+This section tries to explain the performance characteristics of [*Boost.Interprocess],
+so that you can optimize [*Boost.Interprocess] usage if you need more performance.
+
+[section:performance_allocations Performance of raw memory allocations]
+
+You can have two types of raw memory allocations with [*Boost.Interprocess] classes:
+
+* [*Explicit]: The user calls `allocate()` and `deallocate()` functions of
+ managed_shared_memory/managed_mapped_file... managed memory segments. This call is
+ translated to a `MemoryAlgorithm::allocate()` function, which means that you
+ will need just the time that the memory algorithm associated with the managed memory segment
+ needs to allocate data.
+
+* [*Implicit]: For example, you are using `boost::interprocess::allocator<...>` with
+ [*Boost.Interprocess] containers. This allocator calls the same `MemoryAlgorithm::allocate()`
+ function than the explicit method, [*every] time a vector/string has to reallocate its
+ buffer or [*every] time you insert an object in a node container.
+
+If you see that memory allocation is a bottleneck in your application, you have
+these alternatives:
+
+* If you use map/set associative containers, try using `flat_map` family instead
+ of the map family if you mainly do searches and the insertion/removal is mainly done
+ in an initialization phase. The overhead is now when the ordered vector has to
+ reallocate its storage and move data. You can also call the `reserve()` method
+ of these containers when you know beforehand how much data you will insert.
+ However in these containers iterators are invalidated in insertions so this
+ substitution is only effective in some applications.
+
+* Use a [*Boost.Interprocess] pooled allocator for node containers, because pooled
+ allocators call `allocate()` only when the pool runs out of nodes. This is pretty
+ efficient (much more than the current default general-purpose algorithm) and this
+ can save a lot of memory. See
+ [link interprocess.allocators_containers.stl_allocators_segregated_storage Segregated storage node allocators] and
+ [link interprocess.allocators_containers.stl_allocators_adaptive Adaptive node allocators] for more information.
+
+* Write your own memory algorithm. If you have experience with memory allocation algorithms
+ and you think another algorithm is better suited than the default one for your application,
+ you can specify it in all [*Boost.Interprocess] managed memory segments. See the section
+ [link interprocess.customizing_interprocess.custom_interprocess_alloc Writing a new shared memory allocation algorithm]
+ to know how to do this. If you think its better than the default one for general-purpose
+ applications, be polite and donate it to [*Boost.Interprocess] to make it default!
+
+[endsect]
+
+[section:performance_named_allocation Performance of named allocations]
+
+[*Boost.Interprocess] allows the same paralelism as two threads writing to a common
+structure, except when the user creates/searches named/unique objects. The steps
+when creating a named object are these:
+
+* Lock a recursive mutex (so that you can make named allocations inside
+ the constructor of the object to be created).
+
+* Try to insert the [name pointer, object information] in the name/object index.
+ This lookup has to assure that the name has not been used before.
+ This is achieved calling `insert()` function in the index. So the time this
+ requires is dependent on the index type (ordered vector, tree, hash...).
+ This can require a call to the memory algorithm allocation function if
+ the index has to be reallocated, it's a node allocator, uses pooled allocations...
+
+* Allocate a single buffer to hold the name of the object, the object itself,
+ and meta-data for destruction (number of objects, etc...).
+
+* Call the constructors of the object being created. If it's an array, one
+ construtor per array element.
+
+* Unlock the recursive mutex.
+
+The steps when destroying a named object using the name of the object
+(`destroy<T>(name)`) are these:
+
+* Lock a recursive mutex .
+
+* Search in the index the entry associated to that name. Copy that information and
+ erase the index entry. This is done using `find(const key_type &)` and `erase(iterator)`
+ members of the index. This can require element reordering if the index is a
+ balanced tree, an ordered vector...
+
+* Call the destructor of the object (many if it's an array).
+
+* Deallocate the memory buffer containing the name, metadata and the object itself
+ using the allocation algorithm.
+
+* Unlock the recursive mutex.
+
+The steps when destroying a named object using the pointer of the object
+(`destroy_ptr(T *ptr)`) are these:
+
+* Lock a recursive mutex .
+
+* Depending on the index type, this can be different:
+
+ * If the index is a node index, (marked with `boost::interprocess::is_node_index`
+ specialization): Take the iterator stored near the object and call
+ `erase(iterator)`. This can require element reordering if the index is a
+ balanced tree, an ordered vector...
+
+ * If it's not an node index: Take the name stored near the object and erase
+ the index entry calling `erase(const key &). This can require element reordering
+ if the index is a balanced tree, an ordered vector...
+
+* Call the destructor of the object (many if it's an array).
+
+* Deallocate the memory buffer containing the name, metadata and the object itself
+ using the allocation algorithm.
+
+* Unlock the recursive mutex.
+
+If you see that the performance is not good enough you have these alternatives:
+
+* Maybe the problem is that the lock time is too big and it hurts paralelism.
+ Try to reduce the number of named objects in the global index and if your
+ application serves several clients try to build a new managed memory segment
+ for each one instead of using a common one.
+
+* Use another [*Boost.Interprocess] index type if you feel the default one is
+ not fast enough. If you are not still satisfied, write your own index type. See
+ [link interprocess.customizing_interprocess.custom_indexes Building custom indexes] for this.
+
+* Destruction via pointer is at least as fast as using the name of the object and
+ can be faster (in node containers, for example). So if your problem is that you
+ make at lot of named destructions, try to use the pointer. If the index is a
+ node index you can save some time.
+
+[endsect]
+
+[endsect]
+
+[endsect]
+
+[section:customizing_interprocess Customizing Boost.Interprocess]
[section:custom_interprocess_alloc Writing a new shared memory allocation algorithm]
@@ -5925,8 +6169,8 @@
[c++]
- /*!The key of the the named allocation information index. Stores a to
- a null string and the length of the string to speed up sorting*/
+ //!The key of the the named allocation information index. Stores a to
+ //!a null string and the length of the string to speed up sorting
template<...>
struct index_key
{
@@ -5939,13 +6183,13 @@
//Length of the name buffer (null NOT included)
std::size_t m_len;
- /*!Constructor of the key*/
+ //!Constructor of the key
index_key (const CharT *name, std::size_t length);
- /*!Less than function for index ordering*/
+ //!Less than function for index ordering
bool operator < (const index_key & right) const;
- /*!Equal to function for index ordering*/
+ //!Equal to function for index ordering
bool operator == (const index_key & right) const;
};
@@ -5986,9 +6230,9 @@
[c++]
- /*!Trait classes to detect if an index is a node
- index. This allows more efficient operations
- when deallocating named objects.*/
+ //!Trait classes to detect if an index is a node
+ //!index. This allows more efficient operations
+ //!when deallocating named objects.
template<class MapConfig>
struct is_node_index
<my_index<MapConfig> >
@@ -6008,10 +6252,10 @@
[c++]
- /*!Defines a managed shared memory with a c-strings as
- a keys, the red-black tree best fit algorithm (with process-shared mutexes
- and offset_ptr pointers) as raw shared memory management algorithm
- and a custom index*/
+ //!Defines a managed shared memory with a c-strings as
+ //!a keys, the red-black tree best fit algorithm (with process-shared mutexes
+ //!and offset_ptr pointers) as raw shared memory management algorithm
+ //!and a custom index
typedef
basic_managed_shared_memory <
char,
@@ -6024,207 +6268,8 @@
[endsect]
-[section:performance Performance of Boost.Interprocess]
-
-This section tries to explain the performance characteristics of [*Boost.Interprocess],
-so that you can optimize [*Boost.Interprocess] usage if you need more performance.
-
-[section:performance_allocations Performance of raw memory allocations]
-
-You can have two types of raw memory allocations with [*Boost.Interprocess] classes:
-
-* [*Explicit]: The user calls `allocate()` and `deallocate()` functions of
- managed_shared_memory/managed_mapped_file... managed memory segments. This call is
- translated to a `MemoryAlgorithm::allocate()` function, which means that you
- will need just the time that the memory algorithm associated with the managed memory segment
- needs to allocate data.
-
-* [*Implicit]: For example, you are using `boost::interprocess::allocator<...>` with
- [*Boost.Interprocess] containers. This allocator calls the same `MemoryAlgorithm::allocate()`
- function than the explicit method, [*every] time a vector/string has to reallocate its
- buffer or [*every] time you insert an object in a node container.
-
-If you see that memory allocation is a bottleneck in your application, you have
-these alternatives:
-
-* If you use map/set associative containers, try using `flat_map` family instead
- of the map family if you mainly do searches and the insertion/removal is mainly done
- in an initialization phase. The overhead is now when the ordered vector has to
- reallocate its storage and move data. You can also call the `reserve()` method
- of these containers when you know beforehand how much data you will insert.
- However in these containers iterators are invalidated in insertions so this
- substitution is only effective in some applications.
-
-* Use a [*Boost.Interprocess] pooled allocator for node containers, because pooled
- allocators call `allocate()` only when the pool runs out of nodes. This is pretty
- efficient (much more than the current default general-purpose algorithm) and this
- can save a lot of memory. See
- [link interprocess.stl_allocators_segregated_storage Segregated storage node allocators] and
- [link interprocess.stl_allocators_adaptive Adaptive node allocators] for more information.
-
-* Write your own memory algorithm. If you have experience with memory allocation algorithms
- and you think another algorithm is better suited than the default one for your application,
- you can specify it in all [*Boost.Interprocess] managed memory segments. See the section
- [link interprocess.customizing_interprocess.custom_interprocess_alloc Writing a new shared memory allocation algorithm]
- to know how to do this. If you think its better than the default one for general-purpose
- applications, be polite and donate it to [*Boost.Interprocess] to make it default!
-
-[endsect]
-
-[section:performance_named_allocation Performance of named allocations]
-[*Boost.Interprocess] allows the same paralelism as two threads writing to a common
-structure, except when the user creates/searches named/unique objects. The steps
-when creating a named object are these:
-
-* Lock a recursive mutex (so that you can make named allocations inside
- the constructor of the object to be created).
-
-* Try to insert the [name pointer, object information] in the name/object index.
- This lookup has to assure that the name has not been used before.
- This is achieved calling `insert()` function in the index. So the time this
- requires is dependent on the index type (ordered vector, tree, hash...).
- This can require a call to the memory algorithm allocation function if
- the index has to be reallocated, it's a node allocator, uses pooled allocations...
-
-* Allocate a single buffer to hold the name of the object, the object itself,
- and meta-data for destruction (number of objects, etc...).
-
-* Call the constructors of the object being created. If it's an array, one
- construtor per array element.
-
-* Unlock the recursive mutex.
-
-The steps when destroying a named object using the name of the object
-(`destroy<T>(name)`) are these:
-
-* Lock a recursive mutex .
-
-* Search in the index the entry associated to that name. Copy that information and
- erase the index entry. This is done using `find(const key_type &)` and `erase(iterator)`
- members of the index. This can require element reordering if the index is a
- balanced tree, an ordered vector...
-
-* Call the destructor of the object (many if it's an array).
-
-* Deallocate the memory buffer containing the name, metadata and the object itself
- using the allocation algorithm.
-
-* Unlock the recursive mutex.
-
-The steps when destroying a named object using the pointer of the object
-(`destroy_ptr(T *ptr)`) are these:
-
-* Lock a recursive mutex .
-
-* Depending on the index type, this can be different:
-
- * If the index is a node index, (marked with `boost::interprocess::is_node_index`
- specialization): Take the iterator stored near the object and call
- `erase(iterator)`. This can require element reordering if the index is a
- balanced tree, an ordered vector...
-
- * If it's not an node index: Take the name stored near the object and erase
- the index entry calling `erase(const key &). This can require element reordering
- if the index is a balanced tree, an ordered vector...
-
-* Call the destructor of the object (many if it's an array).
-
-* Deallocate the memory buffer containing the name, metadata and the object itself
- using the allocation algorithm.
-
-* Unlock the recursive mutex.
-
-If you see that the performance is not good enough you have these alternatives:
-
-* Maybe the problem is that the lock time is too big and it hurts paralelism.
- Try to reduce the number of named objects in the global index and if your
- application serves several clients try to build a new managed memory segment
- for each one instead of using a common one.
-
-* Use another [*Boost.Interprocess] index type if you feel the default one is
- not fast enough. If you are not still satisfied, write your own index type. See
- [link interprocess.customizing_interprocess.custom_indexes Building custom indexes] for this.
-
-* Destruction via pointer is at least as fast as using the name of the object and
- can be faster (in node containers, for example). So if your problem is that you
- make at lot of named destructions, try to use the pointer. If the index is a
- node index you can save some time.
-
-[endsect]
-
-[endsect]
-
-[section:future_improvements Future Improvements...]
-
-There are some Interprocess features that I would like to implement and some
-[*Boost.Interprocess] code that can be much better. Let's see some ideas:
-
-[section:win32_sync Win32 synchronization is too basic]
-
-Win32 version of shared mutexes and shared conditions are based on "spin and wait"
-atomic instructions. This leads to poor performance and does not manage any issues
-like priority inversions. We would need very serious help from threading experts on
-this. And I'm not sure that this can be achieved in user-level software. Posix based
-implementations use PTHREAD_PROCESS_SHARED attribute to place mutexes in shared memory,
-so there are no such problems. I'm not aware of any implementation that simulates
-PTHREAD_PROCESS_SHARED attribute for Win32. We should be able to construct these
-primitives in memory mapped files, so that we can get filesystem persistence just like
-with POSIX primitives.
-
-[endsect]
-
-[section:future_objectnames Use of wide character names on Boost.Interprocess basic resources]
-
-Currently Interprocess only allows *char* based names for basic named
-objects. However, several operating systems use *wchar_t* names for resources
-(mapped files, for example).
-In the future Interprocess should try to present a portable narrow/wide char interface.
-To do this, it would be useful to have a boost wstring <-> string conversion
-utilities to translate resource names (escaping needed characters
-that can conflict with OS names) in a portable way. It would be interesting also
-the use of [*boost::filesystem] paths to avoid operating system specific issues.
-
-[endsect]
-
-[section:future_security Security attributes]
-
-[*Boost.Interprocess] does not define security attributes for shared memory and
-synchronization objects. Standard C++ also ignores security attributes with files
-so adding security attributes would require some serious work.
-
-[endsect]
-
-[section:future_ipc Future inter-process communications]
-
-[*Boost.Interprocess] offers a process-shared message queue based on
-[*Boost.Interprocess] primitives like mutexes and conditions. I would want to
-develop more mechanisms, like stream-oriented named fifo so that we can use it
-with a iostream-interface wrapper (we can imitate Unix pipes).
-
-C++ needs more complex mechanisms and it would be nice to have a stream and
-datagram oriented PF_UNIX-like mechanism in C++. And for very fast inter-process
-remote calls Solaris doors is an interesting alternative to implement for C++.
-But the work to implement PF_UNIX-like sockets and doors would be huge
-(and it might be difficult in a user-level library). Any network expert volunteer?
-
-[endsect]
-
-[section:future_containers Unordered associative containers and other containers]
-
-We should be able to construct boost::unordered_xxx family in managed memory segments,
-so that there is no code duplication in boost. So [*Boost.Interprocess] should cooperate
-with boost container developers instead of duplicating effort writing it's own containers.
-
-A very interesting project is making [*boost::multi_index] compatible with
-[*Boost.Interprocess] ready for shared memory. This could be a good basis for memory
-mapped data-bases. The work to achieve this, however, can be huge. It would be
-interesting a collaboration with [*Intrusive] library to achieve shared memory
-intrusive containers.
-
-[endsect]
-
-[endsect]
+[section:acknowledgements_notes Acknowledgements, notes and links]
[section:thanks_to Thanks to...]
@@ -6313,8 +6358,38 @@
[section:release_notes_boost_1_35_00 Boost 1.35 Release]
+* Added auxiliary utilities to ease the definition and construction of
+ [classref boost::interprocess::shared_ptr shared_ptr],
+ [classref boost::interprocess::weak_ptr weak_ptr] and
+ [classref boost::interprocess::unique_ptr unique_ptr]. Added explanations
+ and examples of these smart pointers in the documenation.
+
+* Optimized vector:
+ * 1) Now works with raw pointers as much as possible when
+ using allocators defining `pointer` as an smart pointer. This increases
+ performance and improves compilation times.
+ * 2) A bit of metaprogramming
+ to avoid using move_iterator when the type has trivial copy constructor
+ or assignment and improve performance.
+ * 3) Changed custom algorithms
+ with standard ones to take advantage of optimized standard algorithms.
+ * 4) Removed unused code.
+
+* [*ABI breaking]: Containers don't derive from allocators, to avoid problems with allocators
+ that might define virtual functions with the same names as container
+ member functions. That would convert container functions in virtual functions
+ and might disallow some of them if the returned type does not lead to a covariant return.
+ Allocators are now stored as base clases of internal structs.
+
+* Implemented [classref boost::interprocess::named_mutex named_mutex] and
+ [classref boost::interprocess::named_semaphore named_semaphore] with POSIX
+ named semaphores in systems supporting that option.
+ [classref boost::interprocess::named_condition named_condition] has been
+ accordingly changed to support interoperability with
+ [classref boost::interprocess::named_mutex named_mutex].
+
* Reduced template bloat for node and adaptive allocators extracting node
- implementation to a class only depends on the memory algorithm, instead of
+ implementation to a class taht only depends on the memory algorithm, instead of
the segment manager + node size + node number...
* Fixed bug in `mapped_region` in UNIX when mapping address was provided but
@@ -6324,6 +6399,10 @@
* Improved documentation about managed memory segments.
+* [*Boost.Interprocess] containers are now documented in the Reference section.
+
+* Correction of typos and documentation errors.
+
* Added `get_instance_name`, `get_instance_length` and `get_instance_type` functions
to managed memory segments.
@@ -6338,8 +6417,6 @@
* Optimized [classref boost::interprocess::segment_manager segment_manager]
to avoid code bloat associated with templated instantiations.
-* Correction of typos and documentation errors.
-
* Fixed bug for UNIX: No slash ('/') was being added as the first character
for shared memory names, leading to errors in some UNIX systems.
@@ -6358,8 +6435,6 @@
* Improved (multi)map/(multi)set constructors taking iterators. Now those have
linear time if the iterator range is already sorted.
-* Documented Boost.Interprocess containers. Containers are now documented in the Reference section.
-
* [*ABI breaking]: (multi)map/(multi)set now reduce their node size. The color
bit is embedded in the parent pointer. Now, the size of a node is the size of
3 pointers in most systems. This optimization is activated for raw and `offset_ptr`
@@ -6411,21 +6486,17 @@
* Added adaptive pools.
* [*Source breaking]: Changed node allocators' template parameter order
- to make them more easy to use.
+ to make them easier to use.
* Added support for native windows shared memory.
* Added more tests.
-* Documentation improved and expanded.
-
* Corrected the presence of private functions in the reference section.
* Added function (`deallocate_free_chunks()`) to manually deallocate completely free
chunks from node allocators.
-* Minor bugfixes.
-
* Implemented N1780 proposal to LWG issue 233: ['Insertion hints in associative containers]
in interprocess [classref boost::interprocess::multiset multiset] and
[classref boost::interprocess::multimap multimap] classes.
@@ -6450,7 +6521,7 @@
* [*ABI breaking]: Reimplemented and optimized small string optimization. The narrow
string class has zero byte overhead with an internal 11 byte buffer in 32 systems!
-* Added move semantics to containers. Experimental and not documented yet. Improves
+* Added move semantics to containers. Improves
performance when using containers of containers.
* [*ABI breaking]: End nodes of node containers (list, slist, map/set) are now
@@ -6464,10 +6535,10 @@
[endsect]
-[section:references References and interesting links]
+[section:books_and_links Books and interesting links]
-Some useful references about C++ language, C++ internals, shared memory,
-allocators and containers, I've used to design Interprocess.
+Some useful references about the C++ programming language, C++ internals,
+shared memory, allocators and containers used to design [*Boost.Interprocess].
[section:references_books Books]
@@ -6489,7 +6560,7 @@
[section:references_links Links]
-* A framework to put STL in shared memory: [@http://allocator.sourceforge.net/ ['"A C++ Standard Allocator for the Standard Template Library"] ].
+* A framework to put the STL in shared memory: [@http://allocator.sourceforge.net/ ['"A C++ Standard Allocator for the Standard Template Library"] ].
* Instantiating C++ objects in shared memory: [@http://www.cs.ubc.ca/local/reading/proceedings/cascon94/htm/english/abs/hon.htm ['"Using objects in shared memory for C++ application"] ].
@@ -6499,4 +6570,77 @@
[endsect]
+[section:future_improvements Future improvements...]
+
+There are some Interprocess features that I would like to implement and some
+[*Boost.Interprocess] code that can be much better. Let's see some ideas:
+
+[section:win32_sync Win32 synchronization is too basic]
+
+Win32 version of shared mutexes and shared conditions are based on "spin and wait"
+atomic instructions. This leads to poor performance and does not manage any issues
+like priority inversions. We would need very serious help from threading experts on
+this. And I'm not sure that this can be achieved in user-level software. Posix based
+implementations use PTHREAD_PROCESS_SHARED attribute to place mutexes in shared memory,
+so there are no such problems. I'm not aware of any implementation that simulates
+PTHREAD_PROCESS_SHARED attribute for Win32. We should be able to construct these
+primitives in memory mapped files, so that we can get filesystem persistence just like
+with POSIX primitives.
+
+[endsect]
+
+[section:future_objectnames Use of wide character names on Boost.Interprocess basic resources]
+
+Currently Interprocess only allows *char* based names for basic named
+objects. However, several operating systems use *wchar_t* names for resources
+(mapped files, for example).
+In the future Interprocess should try to present a portable narrow/wide char interface.
+To do this, it would be useful to have a boost wstring <-> string conversion
+utilities to translate resource names (escaping needed characters
+that can conflict with OS names) in a portable way. It would be interesting also
+the use of [*boost::filesystem] paths to avoid operating system specific issues.
+
+[endsect]
+
+[section:future_security Security attributes]
+
+[*Boost.Interprocess] does not define security attributes for shared memory and
+synchronization objects. Standard C++ also ignores security attributes with files
+so adding security attributes would require some serious work.
+
+[endsect]
+
+[section:future_ipc Future inter-process communications]
+
+[*Boost.Interprocess] offers a process-shared message queue based on
+[*Boost.Interprocess] primitives like mutexes and conditions. I would want to
+develop more mechanisms, like stream-oriented named fifo so that we can use it
+with a iostream-interface wrapper (we can imitate Unix pipes).
+
+C++ needs more complex mechanisms and it would be nice to have a stream and
+datagram oriented PF_UNIX-like mechanism in C++. And for very fast inter-process
+remote calls Solaris doors is an interesting alternative to implement for C++.
+But the work to implement PF_UNIX-like sockets and doors would be huge
+(and it might be difficult in a user-level library). Any network expert volunteer?
+
+[endsect]
+
+[section:future_containers Unordered associative containers and other containers]
+
+We should be able to construct boost::unordered_xxx family in managed memory segments,
+so that there is no code duplication in boost. So [*Boost.Interprocess] should cooperate
+with boost container developers instead of duplicating effort writing it's own containers.
+
+A very interesting project is making [*boost::multi_index] compatible with
+[*Boost.Interprocess] ready for shared memory. This could be a good basis for memory
+mapped data-bases. The work to achieve this, however, can be huge. It would be
+interesting a collaboration with [*Intrusive] library to achieve shared memory
+intrusive containers.
+
+[endsect]
+
+[endsect]
+
+[endsect]
+
[xinclude autodoc.xml]
Deleted: branches/bcbboost/libs/interprocess/example/alloc_example.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/alloc_example.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,65 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/interprocess/managed_shared_memory.hpp>
-#include <cstddef>
-
-int main ()
-{
- using namespace boost::interprocess;
-
- shared_memory_object::remove("MySharedMemory");
-
- //Create managed shared memory
- managed_shared_memory segment(create_only,
- "MySharedMemory",//segment name
- 65536); //segment size in bytes;
-
- //Allocate a portion of the segment
- void * shptr = segment.allocate(1024);
- managed_shared_memory::handle_t handle = segment.get_handle_from_address(shptr);
- (void)handle;
-
- // Copy message to buffer
- // . . .
- // Send handle to other process
- // . . .
- // Wait response from other process
- // . . .
-
- {
- using namespace boost::interprocess;
-
- //Named allocate capable shared memory allocator
- managed_shared_memory segment(open_only, "MySharedMemory");
-
- managed_shared_memory::handle_t handle = 0;
- (void)handle;
-
- //Wait handle msg from other process and put it in
- //"handle" local variable
-
- //Get buffer local address from handle
- void *msg = segment.get_address_from_handle(handle);
- (void)msg;
-
- //Do anything with msg
- //. . .
- //Send ack to sender process
- }
-
- segment.deallocate(shptr);
- return 0;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
Modified: branches/bcbboost/libs/interprocess/example/doc_managed_multiple_allocation.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/doc_managed_multiple_allocation.cpp (original)
+++ branches/bcbboost/libs/interprocess/example/doc_managed_multiple_allocation.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -12,6 +12,7 @@
#include <cassert>//assert
#include <cstring>//std::memset
#include <new> //std::nothrow
+#include <vector> //std::vector
int main()
{
@@ -23,24 +24,33 @@
try{
managed_shared_memory managed_shm(create_only, "MyManagedShm", 65536);
- std::size_t received_size;
+
//Allocate 16 elements of 100 bytes in a single call. Non-throwing version.
- multiallocation_iterator beg_it = managed_shm.allocate_many(100, 16, 16, received_size, std::nothrow);
+ multiallocation_iterator beg_it = managed_shm.allocate_many(100, 16, std::nothrow);
- //To check for an error, we can use a boolean expresssion
+ //To check for an error, we can use a boolean expression
//or compare it with a default constructed iterator
assert(!beg_it == (beg_it == multiallocation_iterator()));
//Check if the memory allocation was successful
if(!beg_it) return 1;
+ //Allocated buffers
+ std::vector<char*> allocated_buffers;
+
//Initialize our data
- for( multiallocation_iterator it = beg_it, end_it; it != end_it; )
+ for( multiallocation_iterator it = beg_it, end_it; it != end_it; ){
+ allocated_buffers.push_back(*it);
+ //The iterator must be incremented before overwriting memory
+ //because otherwise, the iterator is invalidated.
std::memset(*it++, 0, 100);
+ }
//Now deallocate
- for(multiallocation_iterator it = beg_it, end_it; it != end_it;)
- managed_shm.deallocate(*it++);
+ while(!allocated_buffers.empty()){
+ managed_shm.deallocate(allocated_buffers.back());
+ allocated_buffers.pop_back();
+ }
//Allocate 10 buffers of different sizes in a single call. Throwing version
std::size_t sizes[10];
@@ -51,8 +61,11 @@
//Iterate each allocated buffer and deallocate
//The "end" condition can be also checked with operator!
- for(multiallocation_iterator it = beg_it; it;)
+ for(multiallocation_iterator it = beg_it; it;){
+ //The iterator must be incremented before overwriting memory
+ //because otherwise, the iterator is invalidated.
managed_shm.deallocate(*it++);
+ }
}
catch(...){
shared_memory_object::remove("MyManagedShm");
Deleted: branches/bcbboost/libs/interprocess/example/doc_named_conditionA.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/doc_named_conditionA.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,76 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2006-2007. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/shared_memory_object.hpp>
-#include <boost/interprocess/mapped_region.hpp>
-#include <boost/interprocess/sync/scoped_lock.hpp>
-#include <iostream>
-#include <cstdio>
-#include "doc_anonymous_condition_shared_data.hpp"
-
-using namespace boost::interprocess;
-
-int main ()
-{
- try{
- //Erase previous shared memory
- shared_memory_object::remove("shared_memory");
-
- //Create a shared memory object.
- shared_memory_object shm
- (create_only //only create
- ,"shared_memory" //name
- ,read_write //read-write mode
- );
-
- //Set size
- shm.truncate(sizeof(trace_queue));
-
- //Map the whole shared memory in this process
- mapped_region region
- (shm //What to map
- ,read_write //Map it as read-write
- );
-
- //Get the address of the mapped region
- void * addr = region.get_address();
-
- //Construct the shared structure in memory
- trace_queue * data = new (addr) trace_queue;
-
- const int NumMsg = 100;
-
- for(int i = 0; i < NumMsg; ++i){
- scoped_lock<interprocess_mutex> lock(data->mutex);
- if(data->message_in){
- data->cond_full.wait(lock);
- }
- if(i == (NumMsg-1))
- std::sprintf(data->items, "%s", "last message");
- else
- std::sprintf(data->items, "%s_%d", "my_trace", i);
-
- //Notify to the other process that there is a message
- data->cond_empty.notify_one();
-
- //Mark message buffer as full
- data->message_in = true;
- }
- }
- catch(interprocess_exception &ex){
- shared_memory_object::remove("shared_memory");
- std::cout << ex.what() << std::endl;
- return 1;
- }
-
- //Erase shared memory
- shared_memory_object::remove("shared_memory");
-
- return 0;
-}
Deleted: branches/bcbboost/libs/interprocess/example/doc_named_conditionB.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/doc_named_conditionB.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,73 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2006-2007. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/shared_memory_object.hpp>
-#include <boost/interprocess/mapped_region.hpp>
-#include <boost/interprocess/sync/scoped_lock.hpp>
-#include <iostream>
-#include <cstring>
-#include "doc_anonymous_condition_shared_data.hpp"
-
-using namespace boost::interprocess;
-
-int main ()
-{
- try{
- //Erase previous shared memory
- shared_memory_object::remove("shared_memory");
-
- //Create a shared memory object.
- shared_memory_object shm
- (open_only //only create
- ,"shared_memory" //name
- ,read_write //read-write mode
- );
-
- //Map the whole shared memory in this process
- mapped_region region
- (shm //What to map
- ,read_write //Map it as read-write
- );
-
- //Get the address of the mapped region
- void * addr = region.get_address();
-
- //Obtain a pointer to the shared structure
- trace_queue * data = static_cast<trace_queue*>(addr);
-
- //Print messages until the other process marks the end
- bool end_loop = false;
- do{
- scoped_lock<interprocess_mutex> lock(data->mutex);
- if(!data->message_in){
- data->cond_empty.wait(lock);
- }
- if(std::strcmp(data->items, "last message") == 0){
- end_loop = true;
- }
- else{
- //Print the message
- std::cout << data->items << std::endl;
- //Notify the other process that the buffer is empty
- data->message_in = false;
- data->cond_full.notify_one();
- }
- }
- while(!end_loop);
- }
- catch(interprocess_exception &ex){
- shared_memory_object::remove("MySharedMemory");
- std::cout << ex.what() << std::endl;
- return 1;
- }
-
- //Erase shared memory
- shared_memory_object::remove("shared_memory");
- return 0;
-}
Modified: branches/bcbboost/libs/interprocess/example/doc_offset_ptr.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/doc_offset_ptr.cpp (original)
+++ branches/bcbboost/libs/interprocess/example/doc_offset_ptr.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -31,7 +31,7 @@
try{
managed_shared_memory segment(
create_only,
- "MySharedMemory",//segment name
+ "MySharedMemory", //segment name
65536); //segment size in bytes
//Create linked list with 10 nodes in shared memory
Modified: branches/bcbboost/libs/interprocess/example/doc_vectorstream.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/doc_vectorstream.cpp (original)
+++ branches/bcbboost/libs/interprocess/example/doc_vectorstream.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -35,7 +35,7 @@
try{
managed_shared_memory segment(
create_only,
- "MySharedMemory",//segment name
+ "MySharedMemory", //segment name
65536); //segment size in bytes
//Construct shared memory vector
Deleted: branches/bcbboost/libs/interprocess/example/named_alloc_example.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/named_alloc_example.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,96 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/interprocess/managed_shared_memory.hpp>
-#include <cstddef>
-
-int main ()
-{
- using namespace boost::interprocess;
- typedef std::pair<double, int> MyType;
-
- //Named allocate capable shared mem allocator
- //Create shared memory
- shared_memory_object::remove("MySharedMemory");
- managed_shared_memory segment
- (create_only,
- "MySharedMemory",//segment name
- 65536); //segment size in bytes
-
- //Create an object of MyType initialized to {0, 0}
- segment.construct<MyType>
- ("MyType instance") /*name of the object*/
- (0 /*ctor first argument*/,
- 0 /*ctor second argument*/);
-
- //Create an array of 10 elements of MyType initialized to {0, 0}
- segment.construct<MyType>
- ("MyType array") /*name of the object*/
- [10] /*number of elements*/
- (0 /*ctor first argument*/,
- 0 /*ctor second argument*/);
-
-
- //Let's simulate other process
- {
- using namespace boost::interprocess;
- typedef std::pair<double, int> MyType;
-
- //Named allocate capable shared mem allocator
- //Create shared memory
- managed_shared_memory segment
- (open_only, "MySharedMemory"); //segment name
-
- //Find the array and object
- std::pair<MyType*, std::size_t> res;
- res = segment.find<MyType> ("MyType array");
-
- std::size_t array_len = res.second;
- //Length should be 1
- assert(array_len == 10);
-
- //Find the array and the object
- res = segment.find<MyType> ("MyType instance");
-
- std::size_t len = res.second;
-
- //Length should be 1
- assert(len == 1);
-
- //Change data
- // . . .
-
- //We're done, delete array from memory
- segment.destroy<MyType>("MyType array");
- //We're done, delete object from memory
- segment.destroy<MyType>("MyType instance");
- }
-
- MyType *anonymous = segment.construct<MyType>(anonymous_instance)
- [10] //number of elements
- (1, //ctor first argument
- 1); //ctor second argument
-
- segment.destroy_ptr(anonymous);
-
- segment.construct<MyType>(unique_instance)
- [10] //number of elements
- (1, //ctor first argument
- 1); //ctor second argument
-
- std::pair<MyType *,std::size_t> ret = segment.find<MyType>(unique_instance);
-
- segment.destroy<MyType>(unique_instance);
- return 0;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
Deleted: branches/bcbboost/libs/interprocess/example/print_container.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/print_container.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,38 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_PRINTCONTAINER_HPP
-#define BOOST_PRINTCONTAINER_HPP
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <functional>
-#include <iostream>
-#include <algorithm>
-
-struct PrintValues : public std::unary_function<int, void>
-{
- void operator() (int value) const
- {
- std::cout << value << " ";
- }
-};
-
-template<class Container>
-void PrintContents(const Container &cont, const char *contName)
-{
- std::cout<< "Printing contents of " << contName << std::endl;
- std::for_each(cont.begin(), cont.end(), PrintValues());
- std::cout<< std::endl << std::endl;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
-
-#endif //#ifndef BOOST_PRINTCONTAINER_HPP
Deleted: branches/bcbboost/libs/interprocess/example/printcontainer.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/printcontainer.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,38 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_PRINTCONTAINER_HPP
-#define BOOST_PRINTCONTAINER_HPP
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <functional>
-#include <iostream>
-#include <algorithm>
-
-struct PrintValues : public std::unary_function<int, void>
-{
- void operator() (int value) const
- {
- std::cout << value << " ";
- }
-};
-
-template<class Container>
-void PrintContents(const Container &cont, const char *contName)
-{
- std::cout<< "Printing contents of " << contName << std::endl;
- std::for_each(cont.begin(), cont.end(), PrintValues());
- std::cout<< std::endl << std::endl;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
-
-#endif //#ifndef BOOST_PRINTCONTAINER_HPP
Deleted: branches/bcbboost/libs/interprocess/example/process_a_example.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/process_a_example.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,81 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/interprocess/offset_ptr.hpp>
-#include <boost/interprocess/allocators/allocator.hpp>
-#include <boost/interprocess/managed_shared_memory.hpp>
-#include "print_container.hpp"
-#include <algorithm>
-#include <boost/interprocess/sync/named_semaphore.hpp>
-#include <boost/interprocess/containers/vector.hpp>
-#include <boost/interprocess/sync/interprocess_condition.hpp>
-
-using namespace boost::interprocess;
-
-int main ()
-{
- //Shared memory attributes
- const int memsize = 65536;
- const char *const shMemName = "MySharedMemory";
-
- //Create sems for synchronization
- named_semaphore semA(open_or_create, "processAsem", 0);
- named_semaphore semB(open_or_create, "processBsem", 0);
-
- //Create shared memory
- managed_shared_memory segment(open_or_create, shMemName, memsize);
-
- //STL compatible allocator object, uses allocate(), deallocate() functions
- typedef allocator<int, managed_shared_memory::segment_manager>
- shmem_allocator_int_t;
-
- const int num_elements = 100;
-
- //Type of shared memory vector
- typedef vector<int, shmem_allocator_int_t > MyVect;
-
- const shmem_allocator_int_t &alloc_ref (segment.get_segment_manager());
-
- //Creating the vector in shared memory
- std::cout << "Named New of ShmVect\n\n";
- MyVect *shmem_vect = segment.construct<MyVect> ("ShmVect")(alloc_ref);
-
- offset_ptr<MyVect> shmptr_vect = 0;
- offset_ptr<MyVect> other_shmptr_vect = 0;
-
- //Fill the vector
- std::cout << "Filling ShmVect\n\n";
- int i;
- for(i = 0; i < num_elements; ++i){
- shmem_vect->push_back(i);
- }
-
- //Printing contents before waiting to second process
- PrintContents(*shmem_vect, "ShmVect");
-
- //Wake up other process and sleeping until notified
- semB.post();
- std::cout << "Waking up processB and waiting sorting\n\n";
- semA.wait();
-
- //Notification received, let's see the changes
- std::cout << "processB sorting complete\n\n";
- PrintContents(*shmem_vect, "ShmVect");
-
- //Let's delete the vector from memory
- std::cout << "Deleting the vector with destroy\n\n";
- segment.destroy<MyVect> ("ShmVect");
- std::cout << "vector deleted\n\n";
- return 0;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
Deleted: branches/bcbboost/libs/interprocess/example/process_a_fixed_example.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/process_a_fixed_example.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,82 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/interprocess/offset_ptr.hpp>
-#include <boost/interprocess/allocators/allocator.hpp>
-#include <boost/interprocess/managed_shared_memory.hpp>
-#include <boost/interprocess/mem_algo/simple_seq_fit.hpp>
-#include "print_container.hpp"
-#include <boost/interprocess/sync/named_semaphore.hpp>
-#include <boost/interprocess/sync/interprocess_condition.hpp>
-#include <algorithm>
-#include <vector>
-
-using namespace boost::interprocess;
-
-int main ()
-{
- //Shared memory attributes
- const int memsize = 65536;
- const char *const shMemName = "MySharedMemory";
- const void *const map_addr = reinterpret_cast<const void*>(0x30000000);
-
- //Create sems for synchronization
- named_semaphore semA(open_or_create, "processAsem", 0);
- named_semaphore semB(open_or_create, "processBsem", 0);
-
- //Create shared memory
- fixed_managed_shared_memory segment(create_only, shMemName, memsize, map_addr);
-
- //STL compatible allocator object, uses allocate(), deallocate() functions
- typedef allocator<int, fixed_managed_shared_memory::segment_manager>
- shmem_allocator_int_t;
- const int num_elements = 100;
-
- //Type of shared memory vector
- typedef std::vector<int, shmem_allocator_int_t > MyVect;
-
- const shmem_allocator_int_t alloc_inst (segment.get_segment_manager());
-
- //Creating the vector in shared memory
- std::cout << "Named New of ShmVect\n\n";
- MyVect *shmem_vect = segment.construct<MyVect> ("ShmVect")(alloc_inst);
-
- offset_ptr<MyVect> shmptr_vect = 0;
- offset_ptr<MyVect> other_shmptr_vect = 0;
-
- //Fill the vector
- std::cout << "Filling ShmVect\n\n";
- int i;
- for(i = 0; i < num_elements; ++i){
- shmem_vect->push_back(i);
- }
-
- //Printing contents before waiting to second process
- PrintContents(*shmem_vect, "ShmVect");
-
- //Wake up other process and sleeping until notified
- semB.post();
- std::cout << "Waking up processB and waiting sorting\n\n";
- semA.wait();
-
- //Notification received, let's see the changes
- std::cout << "processB sorting complete\n\n";
- PrintContents(*shmem_vect, "ShmVect");
-
- //Let's delete the vector from memory
- std::cout << "Deleting the vector with destroy\n\n";
- segment.destroy<MyVect> ("ShmVect");
- std::cout << "vector deleted\n\n";
- return 0;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
Deleted: branches/bcbboost/libs/interprocess/example/process_b_example.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/process_b_example.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,71 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/interprocess/allocators/allocator.hpp>
-#include <boost/interprocess/managed_shared_memory.hpp>
-#include <boost/interprocess/containers/vector.hpp>
-#include <boost/interprocess/sync/named_semaphore.hpp>
-
-#include "print_container.hpp"
-#include <algorithm>
-
-using namespace boost::interprocess;
-
-int main ()
-{
- //Shared memory attributes
- const char *const shMemName = "MySharedMemory";
-
- //Create sems for synchronization
- named_semaphore semA(open_or_create, "processAsem", 0);
- named_semaphore semB(open_or_create, "processBsem", 0);
-
- //Wait until the shared memory is ready
- semB.wait();
-
- //Create shared memory
- managed_shared_memory segment(open_or_create, shMemName, 65536);
-
- //STL compatible allocator object, uses allocate(), deallocate() functions
- typedef allocator<int, managed_shared_memory::segment_manager>
- shmem_allocator_int_t;
-
- //This is the shared memory vector type
- typedef vector<int, shmem_allocator_int_t > MyVect;
-
- //Finding vector in shared memory and printing contents
- std::cout << "Connecting to object ShmVect\n\n";
- MyVect *shmem_vect = segment.find<MyVect>("ShmVect").first;
- PrintContents(*shmem_vect, "ShmVect");
-
- //Reverse sorting the vector with std::sort
- std::cout << "Reverse sorting ShmVect\n\n";
- MyVect::reverse_iterator rbeg =
- shmem_vect->rbegin(), rend = shmem_vect->rend();
- std::sort(shmem_vect->rbegin(), shmem_vect->rend());
- std::sort(rbeg, rend);
-
- //Printing values after sorting
- std::cout << "Sorting complete\n\n";
- PrintContents(*shmem_vect, "ShmVect");
-
- //Waking up process A
- std::cout << "Waking up processA\n\n";
- semA.post();
-
- //We're done, closing shared memory
- std::cout << "Closing shmem segment\n\n";
-
- return 0;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
Deleted: branches/bcbboost/libs/interprocess/example/process_b_fixed_example.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/example/process_b_fixed_example.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,69 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-#include <boost/interprocess/detail/config_begin.hpp>
-#include <boost/interprocess/detail/workaround.hpp>
-
-#include <boost/interprocess/allocators/allocator.hpp>
-#include <boost/interprocess/managed_shared_memory.hpp>
-#include <boost/interprocess/sync/named_semaphore.hpp>
-
-#include "print_container.hpp"
-#include <vector>
-#include <algorithm>
-
-using namespace boost::interprocess;
-
-int main ()
-{
- //Shared memory attributes
- const char *const shMemName = "MySharedMemory";
- const void *const map_addr = reinterpret_cast<const void*>(0x30000000);
-
- //Create sems for synchronization
- named_semaphore semA(open_or_create, "processAsem", 1);
- named_semaphore semB(open_or_create, "processBsem", 1);
-
- //Wait until the shared memory is ready
- semB.wait();
-
- //Create shared memory
- fixed_managed_shared_memory segment(open_only, shMemName, map_addr);
-
- //STL compatible allocator object, uses allocate(), deallocate() functions
- typedef allocator<int,fixed_managed_shared_memory::segment_manager>
- shmem_allocator_int_t;
-
- //This is the shared memory vector type
- typedef std::vector<int, shmem_allocator_int_t > MyVect;
-
- //Finding vector in shared memory and printing contents
- std::cout << "Connecting to object ShmVect\n\n";
- MyVect *shmem_vect = segment.find<MyVect>("ShmVect").first;
- PrintContents(*shmem_vect, "ShmVect");
-
- //Reverse sorting the vector with std::sort
- std::cout << "Reverse sorting ShmVect\n\n";
- std::sort(shmem_vect->rbegin(), shmem_vect->rend());
-
- //Printing values after sorting
- std::cout << "Sorting complete\n\n";
- PrintContents(*shmem_vect, "ShmVect");
-
- //Waking up process A
- std::cout << "Waking up processA\n\n";
- semA.post();
-
- //We're done, closing shared memory
- std::cout << "Closing shmem segment\n\n";
- return 0;
-}
-
-#include <boost/interprocess/detail/config_end.hpp>
-
Modified: branches/bcbboost/libs/interprocess/proj/conceptgcc/MakeAll
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/conceptgcc/MakeAll (original)
+++ branches/bcbboost/libs/interprocess/proj/conceptgcc/MakeAll 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,35 +1,35 @@
-
-#ifndef CC
-CC=i686-pc-cygwin-conceptg++.exe
-#endif
-
-BOOST_ROOT=../../../..
-
-INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
-INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
-
-INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
-INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/conceptgcc/test_%.out, $(INTERPROCESSTEST_CPP))
-
-INTERPROCESSDOC_CPP := $(wildcard ../../example/*.cpp)
-INTERPROCESSDOC_OUT := $(patsubst ../../example/%.cpp, ../../bin/conceptgcc/ex_%.out, $(INTERPROCESSDOC_CPP))
-
-LIBDIR:= ../../../../stage/lib
-
-.PHONY: createdir clean
-
-all: createdir $(INTERPROCESSTEST_OUT) $(INTERPROCESSDOC_OUT)
- @cd .
-
-createdir:
- @mkdir -p ../../bin/conceptgcc
-
-../../bin/conceptgcc/test_%.out: ../../test/%.cpp
- $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR) -lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
-
-../../bin/conceptgcc/ex_%.out: ../../example/%.cpp
- $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR)-lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
-
-clean:
- rm -f *.o
- rm -f ../../bin/conceptgcc/*
+
+#ifndef CC
+CC=i686-pc-cygwin-conceptg++.exe
+#endif
+
+BOOST_ROOT=../../../..
+
+INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
+INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
+
+INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
+INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/conceptgcc/test_%.out, $(INTERPROCESSTEST_CPP))
+
+INTERPROCESSDOC_CPP := $(wildcard ../../example/*.cpp)
+INTERPROCESSDOC_OUT := $(patsubst ../../example/%.cpp, ../../bin/conceptgcc/ex_%.out, $(INTERPROCESSDOC_CPP))
+
+LIBDIR:= ../../../../stage/lib
+
+.PHONY: createdir clean
+
+all: createdir $(INTERPROCESSTEST_OUT) $(INTERPROCESSDOC_OUT)
+ @cd .
+
+createdir:
+ @mkdir -p ../../bin/conceptgcc
+
+../../bin/conceptgcc/test_%.out: ../../test/%.cpp
+ $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR) -lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
+
+../../bin/conceptgcc/ex_%.out: ../../example/%.cpp
+ $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR)-lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
+
+clean:
+ rm -f *.o
+ rm -f ../../bin/conceptgcc/*
Modified: branches/bcbboost/libs/interprocess/proj/cygwin/MakeAll
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/cygwin/MakeAll (original)
+++ branches/bcbboost/libs/interprocess/proj/cygwin/MakeAll 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,39 +1,39 @@
-
-ifndef CC
-CC=g++
-endif
-
-BOOST_ROOT=../../../..
-
-INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
-INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
-
-INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
-INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/cygwin/test_%.out, $(INTERPROCESSTEST_CPP))
-
-INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
-INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/cygwin/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
-
-INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
-INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/cygwin/ex__%.out, $(INTERPROCESSEXAMPLE_CPP))
-
-LIBDIR:= ../../../../stage/lib
-
-.PHONY: createdir clean
-
-all: createdir $(INTERPROCESSEXAMPLE_OUT) $(INTERPROCESSTEST_OUT) $(INTERPROCESSEXAMPLE_OUT)
- @cd .
-
-createdir:
- @mkdir -p ../../bin/cygwin
-
-../../bin/cygwin/test_%.out: ../../test/%.cpp
- $(CC) -g $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR) -lboost_thread-gcc-mt -I$(BOOST_ROOT) -lstdc++ -o $@
-
-../../bin/cygwin/ex_%.out: ../../example/%.cpp
- $(CC) -g $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR)-lboost_thread-gcc-mt -I$(BOOST_ROOT) -lstdc++ -o $@
-
-
-clean:
- rm -f *.o
- rm -f ../../bin/cygwin/*
+
+ifndef CC
+CC=g++
+endif
+
+BOOST_ROOT=../../../..
+
+INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
+INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
+
+INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
+INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/cygwin/test_%.out, $(INTERPROCESSTEST_CPP))
+
+INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
+INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/cygwin/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
+
+INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
+INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/cygwin/ex__%.out, $(INTERPROCESSEXAMPLE_CPP))
+
+LIBDIR:= ../../../../stage/lib
+
+.PHONY: createdir clean
+
+all: createdir $(INTERPROCESSEXAMPLE_OUT) $(INTERPROCESSTEST_OUT) $(INTERPROCESSEXAMPLE_OUT)
+ @cd .
+
+createdir:
+ @mkdir -p ../../bin/cygwin
+
+../../bin/cygwin/test_%.out: ../../test/%.cpp
+ $(CC) -g $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR) -lboost_thread-gcc-mt -I$(BOOST_ROOT) -lstdc++ -o $@
+
+../../bin/cygwin/ex_%.out: ../../example/%.cpp
+ $(CC) -g $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR)-lboost_thread-gcc-mt -I$(BOOST_ROOT) -lstdc++ -o $@
+
+
+clean:
+ rm -f *.o
+ rm -f ../../bin/cygwin/*
Modified: branches/bcbboost/libs/interprocess/proj/linux/MakeAll
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/linux/MakeAll (original)
+++ branches/bcbboost/libs/interprocess/proj/linux/MakeAll 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,32 +1,32 @@
-
-ifndef CC
-CC=g++
-endif
-
-BOOST_ROOT=../../../..
-BOOST_LIBS=/usr/local/lib
-
-
-INTERPROCESS_CPP := $(wildcard ../../test/*.cpp)
-INTERPROCESS_OUT := $(patsubst ../../test/%.cpp, ../../bin/linux/test_%.out, $(INTERPROCESS_CPP))
-
-INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
-INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/linux/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
-
-.PHONY: createdir clean
-
-all: createdir $(INTERPROCESS_OUT) $(INTERPROCESSEXAMPLE_OUT)
- @cd .
-
-createdir:
- @mkdir -p ../../bin/linux
-
-../../bin/linux/test_%.out: ../../test/%.cpp
- $(CC) $< -Wall -pedantic -g -pthread -DBOOST_DATE_TIME_NO_LIB -lstdc++ -lrt -lboost_thread-gcc-mt -I$(BOOST_ROOT) -L$(BOOST_LIBS) -o $@
-
-../../bin/linux/ex_%.out: ../../example/%.cpp
- $(CC) $< -Wall -pedantic -g -pthread -DBOOST_DATE_TIME_NO_LIB -lstdc++ -lrt -lboost_thread-gcc-mt -I$(BOOST_ROOT) -L$(BOOST_LIBS) -o $@
-
-clean:
- rm -f *.o
- rm -f ../../bin/linux/*
+
+ifndef CC
+CC=g++
+endif
+
+BOOST_ROOT=../../../..
+BOOST_LIBS=/usr/local/lib
+
+
+INTERPROCESS_CPP := $(wildcard ../../test/*.cpp)
+INTERPROCESS_OUT := $(patsubst ../../test/%.cpp, ../../bin/linux/test_%.out, $(INTERPROCESS_CPP))
+
+INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
+INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/linux/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
+
+.PHONY: createdir clean
+
+all: createdir $(INTERPROCESS_OUT) $(INTERPROCESSEXAMPLE_OUT)
+ @cd .
+
+createdir:
+ @mkdir -p ../../bin/linux
+
+../../bin/linux/test_%.out: ../../test/%.cpp
+ $(CC) $< -Wall -pedantic -g -pthread -DBOOST_DATE_TIME_NO_LIB -lstdc++ -lrt -lboost_thread-gcc-mt -I$(BOOST_ROOT) -L$(BOOST_LIBS) -o $@
+
+../../bin/linux/ex_%.out: ../../example/%.cpp
+ $(CC) $< -Wall -pedantic -g -pthread -DBOOST_DATE_TIME_NO_LIB -lstdc++ -lrt -lboost_thread-gcc-mt -I$(BOOST_ROOT) -L$(BOOST_LIBS) -o $@
+
+clean:
+ rm -f *.o
+ rm -f ../../bin/linux/*
Modified: branches/bcbboost/libs/interprocess/proj/mingw/MakeAll
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/mingw/MakeAll (original)
+++ branches/bcbboost/libs/interprocess/proj/mingw/MakeAll 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,35 +1,35 @@
-
-ifndef CC
-CC=g++
-endif
-
-BOOST_ROOT=../../../..
-
-INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
-INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
-
-INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
-INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/mingw/test_%.out, $(INTERPROCESSTEST_CPP))
-
-INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
-INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/mingw/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
-
-LIBDIR:= ../../../../stage/lib
-
-.PHONY: createdir clean
-
-all: createdir $(INTERPROCESSTEST_OUT) $(INTERPROCESSEXAMPLE_OUT)
- @cd .
-
-createdir:
- @mkdir -p ../../bin/mingw
-
-../../bin/mingw/test_%.out: ../../test/%.cpp
- $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR) -lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
-
-../../bin/mingw/ex_%.out: ../../example/%.cpp
- $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR)-lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
-
-clean:
- rm -f *.o
- rm -f ../../bin/mingw/*
+
+ifndef CC
+CC=g++
+endif
+
+BOOST_ROOT=../../../..
+
+INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
+INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
+
+INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
+INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/mingw/test_%.out, $(INTERPROCESSTEST_CPP))
+
+INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
+INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/mingw/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
+
+LIBDIR:= ../../../../stage/lib
+
+.PHONY: createdir clean
+
+all: createdir $(INTERPROCESSTEST_OUT) $(INTERPROCESSEXAMPLE_OUT)
+ @cd .
+
+createdir:
+ @mkdir -p ../../bin/mingw
+
+../../bin/mingw/test_%.out: ../../test/%.cpp
+ $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR) -lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
+
+../../bin/mingw/ex_%.out: ../../example/%.cpp
+ $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -L$(LIBDIR)-lboost_thread-mgw-mt -I$(BOOST_ROOT) -lstdc++ -o $@
+
+clean:
+ rm -f *.o
+ rm -f ../../bin/mingw/*
Modified: branches/bcbboost/libs/interprocess/proj/qnx/MakeAll
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/qnx/MakeAll (original)
+++ branches/bcbboost/libs/interprocess/proj/qnx/MakeAll 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,33 +1,33 @@
-
-ifndef CC
-CC=g++
-endif
-
-BOOST_ROOT=../../../..
-
-INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
-INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
-
-INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
-INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/qnx/test_%.out, $(INTERPROCESSTEST_CPP))
-
-INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
-INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/qnx/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
-
-.PHONY: createdir clean
-
-all: createdir $(INTERPROCESSTEST_OUT) $(INTERPROCESSEXAMPLE_OUT)
- @cd .
-
-createdir:
- @mkdir -p ../../bin/qnx
-
-../../bin/qnx/test_%.out: ../../test/%.cpp
- $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -lboost_thread-gcc-mt-s -I$(BOOST_ROOT) -o $@
-
-../../bin/qnx/ex_%.out: ../../example/%.cpp
- $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -lboost_thread-gcc-mt-s -I$(BOOST_ROOT) -o $@
-
-clean:
- rm -f *.o
- rm -f ../../bin/qnx/*
+
+ifndef CC
+CC=g++
+endif
+
+BOOST_ROOT=../../../..
+
+INTERPROCESS_CPP := $(wildcard ../../src/*.cpp)
+INTERPROCESS_OBJ := $(patsubst ../../src/%.cpp, lib_%.o, $(INTERPROCESS_CPP))
+
+INTERPROCESSTEST_CPP := $(wildcard ../../test/*.cpp)
+INTERPROCESSTEST_OUT := $(patsubst ../../test/%.cpp, ../../bin/qnx/test_%.out, $(INTERPROCESSTEST_CPP))
+
+INTERPROCESSEXAMPLE_CPP := $(wildcard ../../example/*.cpp)
+INTERPROCESSEXAMPLE_OUT := $(patsubst ../../example/%.cpp, ../../bin/qnx/ex_%.out, $(INTERPROCESSEXAMPLE_CPP))
+
+.PHONY: createdir clean
+
+all: createdir $(INTERPROCESSTEST_OUT) $(INTERPROCESSEXAMPLE_OUT)
+ @cd .
+
+createdir:
+ @mkdir -p ../../bin/qnx
+
+../../bin/qnx/test_%.out: ../../test/%.cpp
+ $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -lboost_thread-gcc-mt-s -I$(BOOST_ROOT) -o $@
+
+../../bin/qnx/ex_%.out: ../../example/%.cpp
+ $(CC) $< -Wall -DBOOST_DATE_TIME_NO_LIB -lboost_thread-gcc-mt-s -I$(BOOST_ROOT) -o $@
+
+clean:
+ rm -f *.o
+ rm -f ../../bin/qnx/*
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/Interprocess.sln
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/Interprocess.sln (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/Interprocess.sln 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,799 +1,823 @@
-Microsoft Visual Studio Solution File, Format Version 8.00
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared_memory_mapping_test", "shared_memory_mappable_test.vcproj", "{5CE18C83-6025-36FE-A4F7-BA09176D3A11}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared_memory_test", "shared_memory_test.vcproj", "{5E2838CC-0916-8F4E-A4F7-93506BA0D310}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared_ptr_test", "shared_ptr_test.vcproj", "{5371C383-6092-1238-A877-BAEB37867609}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "slist_test", "slist_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792608}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "string_test", "string_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D4A792607}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tree_test", "tree_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792606}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "upgradable_mutex_test", "upgradable_mutex.vcproj", "{4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "user_buffer_test", "user_buffer_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792603}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "vectorstream_test", "vectorstream_test.vcproj", "{58CCE183-6032-12FE-A4F7-BA893A767601}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "vector_test", "vector_test.vcproj", "{5CE11C83-096A-84FE-4FA2-D3A6BA792002}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_condition_test", "named_condition_test.vcproj", "{58CC2563-6092-48FE-FAF7-BA046A792658}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_mutexA", "doc_anonymous_mutexA.vcproj", "{58C1B183-9026-4E63-12F2-005412200054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_mutexB", "doc_anonymous_mutexB.vcproj", "{58C1B183-9026-4E63-12F2-005202441254}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_mutex", "doc_named_mutex.vcproj", "{58C181B3-9516-463E-2F12-122155400054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_conditionA", "doc_anonymous_conditionA.vcproj", "{5C1B8183-0296-4F83-1F22-001005220544}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_conditionB", "doc_anonymous_conditionB.vcproj", "{58C1FE83-2906-E643-2F12-024410052254}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_conditionA", "doc_named_conditionA.vcproj", "{58EB1CB3-1354-364E-12F2-154356612054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_conditionB", "doc_named_conditionB.vcproj", "{58181CB3-5134-634E-12F2-155435622054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_semaphoreA", "doc_anonymous_semaphoreA.vcproj", "{5CB81183-29FB-F843-24FF-022050100544}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_semaphoreB", "doc_anonymous_semaphoreB.vcproj", "{58FBE8C3-9026-FAB2-E643-000522441254}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_upgradable_mutex_test", "named_upgradable_mutex.vcproj", "{48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_upgradable_mutexA", "doc_anonymous_upgradable_mutexA.vcproj", "{5C18831B-F162-FA96-E6C3-FA5122040054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_upgradable_mutexB", "doc_anonymous_upgradable_mutexB.vcproj", "{5C1B1043-1EFF-2793-4E63-245241283054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_message_queueA", "doc_message_queueA.vcproj", "{51B189C3-4E63-9026-12F2-12200AF54054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_message_queueB", "doc_message_queueB.vcproj", "{5C1B1813-12C2-0296-4E63-244549126520}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_cont", "doc_cont.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792653}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_contA", "doc_contA.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792652}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_contB", "doc_contB.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792651}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_shared_memory", "doc_shared_memory.vcproj", "{58CCE183-6032-12FE-4FC7-83A79F760B61}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unique_ptr_test", "unique_ptr_test.vcproj", "{571C3383-6092-A877-1238-B3786BAE7605}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_move_containers", "doc_move_containers.vcproj", "{58C1B183-0296-EA42-EF04-005120054104}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "map_index_allocation_test", "map_index_allocation_test.vcproj", "{588CCD13-2962-83FE-F4B7-92230DB73629}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flat_map_index_allocation_test", "flat_map_index_allocation_test.vcproj", "{51D8E9C3-2D65-48FE-3AA7-7922C0E36329}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "iset_index_allocation_test", "iset_index_allocation_test.vcproj", "{58BD1CC3-6972-F3F7-84BE-0DB736035922}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "iunordered_set_index_allocation_test", "iunordered_set_index_allocation_test.vcproj", "{5BD1C7C3-3F7F-6972-84BE-B731D9236035}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_shared_memory2", "doc_shared_memory2.vcproj", "{58CE1D83-F31E-4FD7-6132-8A79F6307B61}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_file_mapping2", "doc_file_mapping2.vcproj", "{5CE19883-F413-7EFD-6342-B79639F7B611}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_file_mapping", "doc_file_mapping.vcproj", "{58DE18C3-3261-2F3E-FD47-83760B9FA761}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_map", "doc_map.vcproj", "{59CEC183-8192-8F6D-4FB7-BA260A79D352}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "windows_shared_memory_test", "windows_shared_memory_test.vcproj", "{E385C28C-0691-4FA7-F48E-935BA0D06310}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "windows_shared_memory_mapping_test", "windows_shared_memory_mapping_test.vcproj", "{518CE8C3-6512-FA75-46EF-B917A3A116D1}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "managed_windows_shared_memory_test", "managed_windows_shared_memory.vcproj", "{5D18CE83-1926-7AE4-FE94-B606D9B23131}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "adaptive_pool_test", "adaptive_pool_test.vcproj", "{58CE1D84-1962-4FE9-BA0D-A4F7973A4652}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "cached_adaptive_pool_test", "cached_adaptive_pool_test.vcproj", "{5188E3CE-2964-F43E-FB87-B037AC692D59}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "private_adaptive_pool_test", "private_adaptive_pool_test.vcproj", "{5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_allocator", "doc_allocator.vcproj", "{581B1C83-4E12-9526-020F-012482540054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_node_allocator", "doc_node_allocator.vcproj", "{51B17C83-E172-5396-0FA2-825472008554}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_private_node_allocator", "doc_private_node_allocator.vcproj", "{2B75C833-17D2-4956-A23F-820854254175}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_cached_node_allocator", "doc_cached_node_allocator.vcproj", "{283AD375-7D12-5866-23BF-854308651275}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_adaptive_pool", "doc_adaptive_pool.vcproj", "{57C832B1-17D2-9537-FA12-827220448554}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_cached_adaptive_pool", "doc_cached_adaptive_pool.vcproj", "{536C8251-7E12-9537-A1E2-822073258554}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_private_adaptive_pool", "doc_private_adaptive_pool.vcproj", "{83258CB1-127E-9375-F872-8324A1054454}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_raw_allocation", "doc_managed_raw_allocation.vcproj", "{5198EFC3-2731-F34E-4FD8-1859AC94F761}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_aligned_allocation", "doc_managed_aligned_allocation.vcproj", "{58DE18C3-3261-2F3E-FD47-83760B9FA761}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "_interprocesslib", "interprocesslib.vcproj", "{FFAA56F1-32EC-4B22-B6BD-95A311A67C35}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_windows_shared_memory", "doc_windows_shared_memory.vcproj", "{5E17C9C3-1362-2E1E-C84F-8A76B6739F21}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_windows_shared_memory2", "doc_windows_shared_memory2.vcproj", "{5E1D6C83-31DE-4F6F-6132-87A9FB663041}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "adaptive_node_pool_test", "adaptive_node_pool_test.vcproj", "{CD57C283-1862-42FE-BF87-B96D3A2A7912}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "node_pool_test", "node_pool_test.vcproj", "{8A519DC3-6092-A4FE-F748-BA91328D6522}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "deque_test", "deque_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792655}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "barrier_test", "barrier_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792661}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "bufferstream_test", "bufferstream_test.vcproj", "{58C183CE-6203-FE12-A237-BA8976695960}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "cached_node_allocator_test", "cached_node_allocator_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792659}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "private_node_allocator_test", "private_node_allocator_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792620}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "node_allocator_test", "node_allocator_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792622}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_mutex_test", "named_mutex_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792625}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_recursive_mutex_test", "named_recursive_mutex_test.vcproj", "{5C83CE18-4F48-A7FE-6092-B7920AD3A624}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_semaphore_test", "named_semaphore_test.vcproj", "{58CCE283-1609-48FE-A4F7-BA0D3A793523}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_heap_memory", "doc_managed_heap_memory.vcproj", "{58CCE183-6092-48FE-A4FC-BA0D3A792647}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "allocexcept_test", "allocexcept_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792662}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "condition_test", "condition_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792658}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "data_test", "data_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792657}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_bufferstream", "doc_bufferstream.vcproj", "{58C1B183-9026-4E12-00F2-001200540054}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_intrusive", "doc_intrusive.vcproj", "{5E18CC83-6092-48FE-A677-B832A0D3A650}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_ipc_messageA", "doc_ipc_messageA.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792649}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_ipc_messageB", "doc_ipc_messageB.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792648}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_mapped_file", "doc_managed_mapped_file.vcproj", "{58CCE183-5091-48FE-A4FC-BA0D3A792446}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_allocA", "doc_named_allocA.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792645}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_allocB", "doc_named_allocB.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792644}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_offset_ptr", "doc_offset_ptr.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792643}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_scoped_ptr", "doc_scoped_ptr.vcproj", "{58CC8E13-0962-8F4E-77A6-BD3A6832A042}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_vectorstream", "doc_vectorstream.vcproj", "{58C1B183-9260-4E8F-F200-000000000041}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_where_allocate", "doc_where_allocate.vcproj", "{58CCE183-6092-48FE-A677-BA0D3A832640}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "file_mapping_test", "file_mapping_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792638}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flat_tree_test", "flat_tree_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792637}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "intrusive_ptr_test", "intrusive_ptr_test.vcproj", "{5821C383-6092-12FE-A877-BA0D33467633}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "list_test", "list_ex.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792632}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "managed_mapped_file_test", "managed_mapped_file_test.vcproj", "{5CCE1883-0926-F7A4-8FE4-BA0606D92331}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "mapped_file_test", "mapped_file_test.vcproj", "{5C6D9CE1-2609-F7A4-8FE4-BA0883602330}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "memory_algorithm_test", "memory_algorithm_test.vcproj", "{58E18CC3-6092-8F4E-A3E7-A792230D3629}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "message_queue_test", "message_queue.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792628}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "mutex_test", "mutex_test.vcproj", "{83581CCE-487E-3292-A4E7-BA07926D3A27}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "null_index_test", "null_index_test.vcproj", "{0000058C-0000-0000-0000-000000000021}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "recursive_mutex_test", "recursive_mutex_test.vcproj", "{83581CCE-487E-3292-A4E7-BA07926D3A14}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "semaphore_test", "semaphore_test.vcproj", "{5CE28C83-48FE-1676-4FA7-B50D3A76A013}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_multiple_allocation", "doc_managed_multiple_allocation.vcproj", "{818C43EE-3561-F3AE-4FD7-8A2076E76A31}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_allocation_command", "doc_managed_allocation_command.vcproj", "{5189DEA3-3261-F33E-47ED-83BC69F66061}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_construction_info", "doc_managed_construction_info.vcproj", "{5C82D1D3-3861-3AF1-03EF-89AED4716761}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Global
- GlobalSection(SolutionConfiguration) = preSolution
- Debug = Debug
- Release = Release
- EndGlobalSection
- GlobalSection(ProjectDependencies) = postSolution
- EndGlobalSection
- GlobalSection(ProjectConfiguration) = postSolution
- {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Debug.ActiveCfg = Debug|Win32
- {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Debug.Build.0 = Debug|Win32
- {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Release.ActiveCfg = Release|Win32
- {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Release.Build.0 = Release|Win32
- {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Debug.ActiveCfg = Debug|Win32
- {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Debug.Build.0 = Debug|Win32
- {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Release.ActiveCfg = Release|Win32
- {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Release.Build.0 = Release|Win32
- {5371C383-6092-1238-A877-BAEB37867609}.Debug.ActiveCfg = Debug|Win32
- {5371C383-6092-1238-A877-BAEB37867609}.Debug.Build.0 = Debug|Win32
- {5371C383-6092-1238-A877-BAEB37867609}.Release.ActiveCfg = Release|Win32
- {5371C383-6092-1238-A877-BAEB37867609}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Release.Build.0 = Release|Win32
- {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Debug.ActiveCfg = Debug|Win32
- {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Debug.Build.0 = Debug|Win32
- {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Release.ActiveCfg = Release|Win32
- {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Release.Build.0 = Release|Win32
- {58CCE183-6032-12FE-A4F7-BA893A767601}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6032-12FE-A4F7-BA893A767601}.Debug.Build.0 = Debug|Win32
- {58CCE183-6032-12FE-A4F7-BA893A767601}.Release.ActiveCfg = Release|Win32
- {58CCE183-6032-12FE-A4F7-BA893A767601}.Release.Build.0 = Release|Win32
- {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Debug.ActiveCfg = Debug|Win32
- {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Debug.Build.0 = Debug|Win32
- {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Release.ActiveCfg = Release|Win32
- {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Release.Build.0 = Release|Win32
- {58CC2563-6092-48FE-FAF7-BA046A792658}.Debug.ActiveCfg = Debug|Win32
- {58CC2563-6092-48FE-FAF7-BA046A792658}.Debug.Build.0 = Debug|Win32
- {58CC2563-6092-48FE-FAF7-BA046A792658}.Release.ActiveCfg = Release|Win32
- {58CC2563-6092-48FE-FAF7-BA046A792658}.Release.Build.0 = Release|Win32
- {58C1B183-9026-4E63-12F2-005412200054}.Debug.ActiveCfg = Debug|Win32
- {58C1B183-9026-4E63-12F2-005412200054}.Debug.Build.0 = Debug|Win32
- {58C1B183-9026-4E63-12F2-005412200054}.Release.ActiveCfg = Release|Win32
- {58C1B183-9026-4E63-12F2-005412200054}.Release.Build.0 = Release|Win32
- {58C1B183-9026-4E63-12F2-005202441254}.Debug.ActiveCfg = Debug|Win32
- {58C1B183-9026-4E63-12F2-005202441254}.Debug.Build.0 = Debug|Win32
- {58C1B183-9026-4E63-12F2-005202441254}.Release.ActiveCfg = Release|Win32
- {58C1B183-9026-4E63-12F2-005202441254}.Release.Build.0 = Release|Win32
- {58C181B3-9516-463E-2F12-122155400054}.Debug.ActiveCfg = Debug|Win32
- {58C181B3-9516-463E-2F12-122155400054}.Debug.Build.0 = Debug|Win32
- {58C181B3-9516-463E-2F12-122155400054}.Release.ActiveCfg = Release|Win32
- {58C181B3-9516-463E-2F12-122155400054}.Release.Build.0 = Release|Win32
- {5C1B8183-0296-4F83-1F22-001005220544}.Debug.ActiveCfg = Debug|Win32
- {5C1B8183-0296-4F83-1F22-001005220544}.Debug.Build.0 = Debug|Win32
- {5C1B8183-0296-4F83-1F22-001005220544}.Release.ActiveCfg = Release|Win32
- {5C1B8183-0296-4F83-1F22-001005220544}.Release.Build.0 = Release|Win32
- {58C1FE83-2906-E643-2F12-024410052254}.Debug.ActiveCfg = Debug|Win32
- {58C1FE83-2906-E643-2F12-024410052254}.Debug.Build.0 = Debug|Win32
- {58C1FE83-2906-E643-2F12-024410052254}.Release.ActiveCfg = Release|Win32
- {58C1FE83-2906-E643-2F12-024410052254}.Release.Build.0 = Release|Win32
- {58EB1CB3-1354-364E-12F2-154356612054}.Debug.ActiveCfg = Debug|Win32
- {58EB1CB3-1354-364E-12F2-154356612054}.Debug.Build.0 = Debug|Win32
- {58EB1CB3-1354-364E-12F2-154356612054}.Release.ActiveCfg = Release|Win32
- {58EB1CB3-1354-364E-12F2-154356612054}.Release.Build.0 = Release|Win32
- {58181CB3-5134-634E-12F2-155435622054}.Debug.ActiveCfg = Debug|Win32
- {58181CB3-5134-634E-12F2-155435622054}.Debug.Build.0 = Debug|Win32
- {58181CB3-5134-634E-12F2-155435622054}.Release.ActiveCfg = Release|Win32
- {58181CB3-5134-634E-12F2-155435622054}.Release.Build.0 = Release|Win32
- {5CB81183-29FB-F843-24FF-022050100544}.Debug.ActiveCfg = Debug|Win32
- {5CB81183-29FB-F843-24FF-022050100544}.Debug.Build.0 = Debug|Win32
- {5CB81183-29FB-F843-24FF-022050100544}.Release.ActiveCfg = Release|Win32
- {5CB81183-29FB-F843-24FF-022050100544}.Release.Build.0 = Release|Win32
- {58FBE8C3-9026-FAB2-E643-000522441254}.Debug.ActiveCfg = Debug|Win32
- {58FBE8C3-9026-FAB2-E643-000522441254}.Debug.Build.0 = Debug|Win32
- {58FBE8C3-9026-FAB2-E643-000522441254}.Release.ActiveCfg = Release|Win32
- {58FBE8C3-9026-FAB2-E643-000522441254}.Release.Build.0 = Release|Win32
- {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Debug.ActiveCfg = Debug|Win32
- {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Debug.Build.0 = Debug|Win32
- {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Release.ActiveCfg = Release|Win32
- {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Release.Build.0 = Release|Win32
- {5C18831B-F162-FA96-E6C3-FA5122040054}.Debug.ActiveCfg = Debug|Win32
- {5C18831B-F162-FA96-E6C3-FA5122040054}.Debug.Build.0 = Debug|Win32
- {5C18831B-F162-FA96-E6C3-FA5122040054}.Release.ActiveCfg = Release|Win32
- {5C18831B-F162-FA96-E6C3-FA5122040054}.Release.Build.0 = Release|Win32
- {5C1B1043-1EFF-2793-4E63-245241283054}.Debug.ActiveCfg = Debug|Win32
- {5C1B1043-1EFF-2793-4E63-245241283054}.Debug.Build.0 = Debug|Win32
- {5C1B1043-1EFF-2793-4E63-245241283054}.Release.ActiveCfg = Release|Win32
- {5C1B1043-1EFF-2793-4E63-245241283054}.Release.Build.0 = Release|Win32
- {51B189C3-4E63-9026-12F2-12200AF54054}.Debug.ActiveCfg = Debug|Win32
- {51B189C3-4E63-9026-12F2-12200AF54054}.Debug.Build.0 = Debug|Win32
- {51B189C3-4E63-9026-12F2-12200AF54054}.Release.ActiveCfg = Release|Win32
- {51B189C3-4E63-9026-12F2-12200AF54054}.Release.Build.0 = Release|Win32
- {5C1B1813-12C2-0296-4E63-244549126520}.Debug.ActiveCfg = Debug|Win32
- {5C1B1813-12C2-0296-4E63-244549126520}.Debug.Build.0 = Debug|Win32
- {5C1B1813-12C2-0296-4E63-244549126520}.Release.ActiveCfg = Release|Win32
- {5C1B1813-12C2-0296-4E63-244549126520}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Release.Build.0 = Release|Win32
- {58CCE183-6032-12FE-4FC7-83A79F760B61}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6032-12FE-4FC7-83A79F760B61}.Debug.Build.0 = Debug|Win32
- {58CCE183-6032-12FE-4FC7-83A79F760B61}.Release.ActiveCfg = Release|Win32
- {58CCE183-6032-12FE-4FC7-83A79F760B61}.Release.Build.0 = Release|Win32
- {571C3383-6092-A877-1238-B3786BAE7605}.Debug.ActiveCfg = Debug|Win32
- {571C3383-6092-A877-1238-B3786BAE7605}.Debug.Build.0 = Debug|Win32
- {571C3383-6092-A877-1238-B3786BAE7605}.Release.ActiveCfg = Release|Win32
- {571C3383-6092-A877-1238-B3786BAE7605}.Release.Build.0 = Release|Win32
- {58C1B183-0296-EA42-EF04-005120054104}.Debug.ActiveCfg = Debug|Win32
- {58C1B183-0296-EA42-EF04-005120054104}.Debug.Build.0 = Debug|Win32
- {58C1B183-0296-EA42-EF04-005120054104}.Release.ActiveCfg = Release|Win32
- {58C1B183-0296-EA42-EF04-005120054104}.Release.Build.0 = Release|Win32
- {588CCD13-2962-83FE-F4B7-92230DB73629}.Debug.ActiveCfg = Debug|Win32
- {588CCD13-2962-83FE-F4B7-92230DB73629}.Debug.Build.0 = Debug|Win32
- {588CCD13-2962-83FE-F4B7-92230DB73629}.Release.ActiveCfg = Release|Win32
- {588CCD13-2962-83FE-F4B7-92230DB73629}.Release.Build.0 = Release|Win32
- {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Debug.ActiveCfg = Debug|Win32
- {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Debug.Build.0 = Debug|Win32
- {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Release.ActiveCfg = Release|Win32
- {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Release.Build.0 = Release|Win32
- {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Debug.ActiveCfg = Debug|Win32
- {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Debug.Build.0 = Debug|Win32
- {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Release.ActiveCfg = Release|Win32
- {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Release.Build.0 = Release|Win32
- {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Debug.ActiveCfg = Debug|Win32
- {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Debug.Build.0 = Debug|Win32
- {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Release.ActiveCfg = Release|Win32
- {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Release.Build.0 = Release|Win32
- {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Debug.ActiveCfg = Debug|Win32
- {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Debug.Build.0 = Debug|Win32
- {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Release.ActiveCfg = Release|Win32
- {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Release.Build.0 = Release|Win32
- {5CE19883-F413-7EFD-6342-B79639F7B611}.Debug.ActiveCfg = Debug|Win32
- {5CE19883-F413-7EFD-6342-B79639F7B611}.Debug.Build.0 = Debug|Win32
- {5CE19883-F413-7EFD-6342-B79639F7B611}.Release.ActiveCfg = Release|Win32
- {5CE19883-F413-7EFD-6342-B79639F7B611}.Release.Build.0 = Release|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.ActiveCfg = Debug|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.Build.0 = Debug|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.ActiveCfg = Release|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.Build.0 = Release|Win32
- {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Debug.ActiveCfg = Debug|Win32
- {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Debug.Build.0 = Debug|Win32
- {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Release.ActiveCfg = Release|Win32
- {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Release.Build.0 = Release|Win32
- {E385C28C-0691-4FA7-F48E-935BA0D06310}.Debug.ActiveCfg = Debug|Win32
- {E385C28C-0691-4FA7-F48E-935BA0D06310}.Debug.Build.0 = Debug|Win32
- {E385C28C-0691-4FA7-F48E-935BA0D06310}.Release.ActiveCfg = Release|Win32
- {E385C28C-0691-4FA7-F48E-935BA0D06310}.Release.Build.0 = Release|Win32
- {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Debug.ActiveCfg = Debug|Win32
- {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Debug.Build.0 = Debug|Win32
- {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Release.ActiveCfg = Release|Win32
- {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Release.Build.0 = Release|Win32
- {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Debug.ActiveCfg = Debug|Win32
- {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Debug.Build.0 = Debug|Win32
- {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Release.ActiveCfg = Release|Win32
- {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Release.Build.0 = Release|Win32
- {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Debug.ActiveCfg = Debug|Win32
- {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Debug.Build.0 = Debug|Win32
- {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Release.ActiveCfg = Release|Win32
- {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Release.Build.0 = Release|Win32
- {5188E3CE-2964-F43E-FB87-B037AC692D59}.Debug.ActiveCfg = Debug|Win32
- {5188E3CE-2964-F43E-FB87-B037AC692D59}.Debug.Build.0 = Debug|Win32
- {5188E3CE-2964-F43E-FB87-B037AC692D59}.Release.ActiveCfg = Release|Win32
- {5188E3CE-2964-F43E-FB87-B037AC692D59}.Release.Build.0 = Release|Win32
- {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Debug.ActiveCfg = Debug|Win32
- {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Debug.Build.0 = Debug|Win32
- {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Release.ActiveCfg = Release|Win32
- {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Release.Build.0 = Release|Win32
- {581B1C83-4E12-9526-020F-012482540054}.Debug.ActiveCfg = Debug|Win32
- {581B1C83-4E12-9526-020F-012482540054}.Debug.Build.0 = Debug|Win32
- {581B1C83-4E12-9526-020F-012482540054}.Release.ActiveCfg = Release|Win32
- {581B1C83-4E12-9526-020F-012482540054}.Release.Build.0 = Release|Win32
- {51B17C83-E172-5396-0FA2-825472008554}.Debug.ActiveCfg = Debug|Win32
- {51B17C83-E172-5396-0FA2-825472008554}.Debug.Build.0 = Debug|Win32
- {51B17C83-E172-5396-0FA2-825472008554}.Release.ActiveCfg = Release|Win32
- {51B17C83-E172-5396-0FA2-825472008554}.Release.Build.0 = Release|Win32
- {2B75C833-17D2-4956-A23F-820854254175}.Debug.ActiveCfg = Debug|Win32
- {2B75C833-17D2-4956-A23F-820854254175}.Debug.Build.0 = Debug|Win32
- {2B75C833-17D2-4956-A23F-820854254175}.Release.ActiveCfg = Release|Win32
- {2B75C833-17D2-4956-A23F-820854254175}.Release.Build.0 = Release|Win32
- {283AD375-7D12-5866-23BF-854308651275}.Debug.ActiveCfg = Debug|Win32
- {283AD375-7D12-5866-23BF-854308651275}.Debug.Build.0 = Debug|Win32
- {283AD375-7D12-5866-23BF-854308651275}.Release.ActiveCfg = Release|Win32
- {283AD375-7D12-5866-23BF-854308651275}.Release.Build.0 = Release|Win32
- {57C832B1-17D2-9537-FA12-827220448554}.Debug.ActiveCfg = Debug|Win32
- {57C832B1-17D2-9537-FA12-827220448554}.Debug.Build.0 = Debug|Win32
- {57C832B1-17D2-9537-FA12-827220448554}.Release.ActiveCfg = Release|Win32
- {57C832B1-17D2-9537-FA12-827220448554}.Release.Build.0 = Release|Win32
- {536C8251-7E12-9537-A1E2-822073258554}.Debug.ActiveCfg = Debug|Win32
- {536C8251-7E12-9537-A1E2-822073258554}.Debug.Build.0 = Debug|Win32
- {536C8251-7E12-9537-A1E2-822073258554}.Release.ActiveCfg = Release|Win32
- {536C8251-7E12-9537-A1E2-822073258554}.Release.Build.0 = Release|Win32
- {83258CB1-127E-9375-F872-8324A1054454}.Debug.ActiveCfg = Debug|Win32
- {83258CB1-127E-9375-F872-8324A1054454}.Debug.Build.0 = Debug|Win32
- {83258CB1-127E-9375-F872-8324A1054454}.Release.ActiveCfg = Release|Win32
- {83258CB1-127E-9375-F872-8324A1054454}.Release.Build.0 = Release|Win32
- {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Debug.ActiveCfg = Debug|Win32
- {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Debug.Build.0 = Debug|Win32
- {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Release.ActiveCfg = Release|Win32
- {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Release.Build.0 = Release|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.ActiveCfg = Debug|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.Build.0 = Debug|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.ActiveCfg = Release|Win32
- {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.Build.0 = Release|Win32
- {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Debug.ActiveCfg = Debug|Win32
- {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Debug.Build.0 = Debug|Win32
- {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Release.ActiveCfg = Release|Win32
- {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Release.Build.0 = Release|Win32
- {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Debug.ActiveCfg = Debug|Win32
- {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Debug.Build.0 = Debug|Win32
- {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Release.ActiveCfg = Release|Win32
- {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Release.Build.0 = Release|Win32
- {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Debug.ActiveCfg = Debug|Win32
- {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Debug.Build.0 = Debug|Win32
- {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Release.ActiveCfg = Release|Win32
- {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Release.Build.0 = Release|Win32
- {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Debug.ActiveCfg = Debug|Win32
- {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Debug.Build.0 = Debug|Win32
- {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Release.ActiveCfg = Release|Win32
- {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Release.Build.0 = Release|Win32
- {8A519DC3-6092-A4FE-F748-BA91328D6522}.Debug.ActiveCfg = Debug|Win32
- {8A519DC3-6092-A4FE-F748-BA91328D6522}.Debug.Build.0 = Debug|Win32
- {8A519DC3-6092-A4FE-F748-BA91328D6522}.Release.ActiveCfg = Release|Win32
- {8A519DC3-6092-A4FE-F748-BA91328D6522}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Release.Build.0 = Release|Win32
- {58C183CE-6203-FE12-A237-BA8976695960}.Debug.ActiveCfg = Debug|Win32
- {58C183CE-6203-FE12-A237-BA8976695960}.Debug.Build.0 = Debug|Win32
- {58C183CE-6203-FE12-A237-BA8976695960}.Release.ActiveCfg = Release|Win32
- {58C183CE-6203-FE12-A237-BA8976695960}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Release.Build.0 = Release|Win32
- {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Debug.ActiveCfg = Debug|Win32
- {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Debug.Build.0 = Debug|Win32
- {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Release.ActiveCfg = Release|Win32
- {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Release.Build.0 = Release|Win32
- {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Debug.ActiveCfg = Debug|Win32
- {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Debug.Build.0 = Debug|Win32
- {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Release.ActiveCfg = Release|Win32
- {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Release.Build.0 = Release|Win32
- {58C1B183-9026-4E12-00F2-001200540054}.Debug.ActiveCfg = Debug|Win32
- {58C1B183-9026-4E12-00F2-001200540054}.Debug.Build.0 = Debug|Win32
- {58C1B183-9026-4E12-00F2-001200540054}.Release.ActiveCfg = Release|Win32
- {58C1B183-9026-4E12-00F2-001200540054}.Release.Build.0 = Release|Win32
- {5E18CC83-6092-48FE-A677-B832A0D3A650}.Debug.ActiveCfg = Debug|Win32
- {5E18CC83-6092-48FE-A677-B832A0D3A650}.Debug.Build.0 = Debug|Win32
- {5E18CC83-6092-48FE-A677-B832A0D3A650}.Release.ActiveCfg = Release|Win32
- {5E18CC83-6092-48FE-A677-B832A0D3A650}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Release.Build.0 = Release|Win32
- {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Debug.Build.0 = Debug|Win32
- {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Release.ActiveCfg = Release|Win32
- {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Release.Build.0 = Release|Win32
- {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Debug.ActiveCfg = Debug|Win32
- {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Debug.Build.0 = Debug|Win32
- {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Release.ActiveCfg = Release|Win32
- {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Release.Build.0 = Release|Win32
- {58C1B183-9260-4E8F-F200-000000000041}.Debug.ActiveCfg = Debug|Win32
- {58C1B183-9260-4E8F-F200-000000000041}.Debug.Build.0 = Debug|Win32
- {58C1B183-9260-4E8F-F200-000000000041}.Release.ActiveCfg = Release|Win32
- {58C1B183-9260-4E8F-F200-000000000041}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A677-BA0D3A832640}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A677-BA0D3A832640}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A677-BA0D3A832640}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A677-BA0D3A832640}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Release.Build.0 = Release|Win32
- {5821C383-6092-12FE-A877-BA0D33467633}.Debug.ActiveCfg = Debug|Win32
- {5821C383-6092-12FE-A877-BA0D33467633}.Debug.Build.0 = Debug|Win32
- {5821C383-6092-12FE-A877-BA0D33467633}.Release.ActiveCfg = Release|Win32
- {5821C383-6092-12FE-A877-BA0D33467633}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Release.Build.0 = Release|Win32
- {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Debug.ActiveCfg = Debug|Win32
- {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Debug.Build.0 = Debug|Win32
- {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Release.ActiveCfg = Release|Win32
- {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Release.Build.0 = Release|Win32
- {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Debug.ActiveCfg = Debug|Win32
- {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Debug.Build.0 = Debug|Win32
- {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Release.ActiveCfg = Release|Win32
- {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Release.Build.0 = Release|Win32
- {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Debug.ActiveCfg = Debug|Win32
- {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Debug.Build.0 = Debug|Win32
- {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Release.ActiveCfg = Release|Win32
- {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Release.Build.0 = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Debug.ActiveCfg = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Debug.Build.0 = Debug|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Release.ActiveCfg = Release|Win32
- {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Release.Build.0 = Release|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A27}.Debug.ActiveCfg = Debug|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A27}.Debug.Build.0 = Debug|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A27}.Release.ActiveCfg = Release|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A27}.Release.Build.0 = Release|Win32
- {0000058C-0000-0000-0000-000000000021}.Debug.ActiveCfg = Debug|Win32
- {0000058C-0000-0000-0000-000000000021}.Debug.Build.0 = Debug|Win32
- {0000058C-0000-0000-0000-000000000021}.Release.ActiveCfg = Release|Win32
- {0000058C-0000-0000-0000-000000000021}.Release.Build.0 = Release|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A14}.Debug.ActiveCfg = Debug|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A14}.Debug.Build.0 = Debug|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A14}.Release.ActiveCfg = Release|Win32
- {83581CCE-487E-3292-A4E7-BA07926D3A14}.Release.Build.0 = Release|Win32
- {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Debug.ActiveCfg = Debug|Win32
- {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Debug.Build.0 = Debug|Win32
- {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Release.ActiveCfg = Release|Win32
- {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Release.Build.0 = Release|Win32
- {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Debug.ActiveCfg = Debug|Win32
- {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Debug.Build.0 = Debug|Win32
- {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Release.ActiveCfg = Release|Win32
- {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Release.Build.0 = Release|Win32
- {5189DEA3-3261-F33E-47ED-83BC69F66061}.Debug.ActiveCfg = Debug|Win32
- {5189DEA3-3261-F33E-47ED-83BC69F66061}.Debug.Build.0 = Debug|Win32
- {5189DEA3-3261-F33E-47ED-83BC69F66061}.Release.ActiveCfg = Release|Win32
- {5189DEA3-3261-F33E-47ED-83BC69F66061}.Release.Build.0 = Release|Win32
- {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Debug.ActiveCfg = Debug|Win32
- {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Debug.Build.0 = Debug|Win32
- {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Release.ActiveCfg = Release|Win32
- {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Release.Build.0 = Release|Win32
- EndGlobalSection
- GlobalSection(ExtensibilityGlobals) = postSolution
- EndGlobalSection
- GlobalSection(ExtensibilityAddIns) = postSolution
- EndGlobalSection
-EndGlobal
+Microsoft Visual Studio Solution File, Format Version 8.00
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared_memory_mapping_test", "shared_memory_mappable_test.vcproj", "{5CE18C83-6025-36FE-A4F7-BA09176D3A11}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared_memory_test", "shared_memory_test.vcproj", "{5E2838CC-0916-8F4E-A4F7-93506BA0D310}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared_ptr_test", "shared_ptr_test.vcproj", "{5371C383-6092-1238-A877-BAEB37867609}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "slist_test", "slist_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792608}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "string_test", "string_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D4A792607}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tree_test", "tree_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792606}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "upgradable_mutex_test", "upgradable_mutex.vcproj", "{4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "user_buffer_test", "user_buffer_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792603}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "vectorstream_test", "vectorstream_test.vcproj", "{58CCE183-6032-12FE-A4F7-BA893A767601}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "vector_test", "vector_test.vcproj", "{5CE11C83-096A-84FE-4FA2-D3A6BA792002}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_condition_test", "named_condition_test.vcproj", "{58CC2563-6092-48FE-FAF7-BA046A792658}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_mutexA", "doc_anonymous_mutexA.vcproj", "{58C1B183-9026-4E63-12F2-005412200054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_mutexB", "doc_anonymous_mutexB.vcproj", "{58C1B183-9026-4E63-12F2-005202441254}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_mutex", "doc_named_mutex.vcproj", "{58C181B3-9516-463E-2F12-122155400054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_conditionA", "doc_anonymous_conditionA.vcproj", "{5C1B8183-0296-4F83-1F22-001005220544}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_conditionB", "doc_anonymous_conditionB.vcproj", "{58C1FE83-2906-E643-2F12-024410052254}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_conditionA", "doc_named_conditionA.vcproj", "{58EB1CB3-1354-364E-12F2-154356612054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_conditionB", "doc_named_conditionB.vcproj", "{58181CB3-5134-634E-12F2-155435622054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_semaphoreA", "doc_anonymous_semaphoreA.vcproj", "{5CB81183-29FB-F843-24FF-022050100544}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_semaphoreB", "doc_anonymous_semaphoreB.vcproj", "{58FBE8C3-9026-FAB2-E643-000522441254}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_upgradable_mutex_test", "named_upgradable_mutex.vcproj", "{48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_upgradable_mutexA", "doc_anonymous_upgradable_mutexA.vcproj", "{5C18831B-F162-FA96-E6C3-FA5122040054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_anonymous_upgradable_mutexB", "doc_anonymous_upgradable_mutexB.vcproj", "{5C1B1043-1EFF-2793-4E63-245241283054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_message_queueA", "doc_message_queueA.vcproj", "{51B189C3-4E63-9026-12F2-12200AF54054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_message_queueB", "doc_message_queueB.vcproj", "{5C1B1813-12C2-0296-4E63-244549126520}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_cont", "doc_cont.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792653}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_contA", "doc_contA.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792652}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_contB", "doc_contB.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792651}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_shared_memory", "doc_shared_memory.vcproj", "{58CCE183-6032-12FE-4FC7-83A79F760B61}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unique_ptr_test", "unique_ptr_test.vcproj", "{571C3383-6092-A877-1238-B3786BAE7605}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_move_containers", "doc_move_containers.vcproj", "{58C1B183-0296-EA42-EF04-005120054104}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "map_index_allocation_test", "map_index_allocation_test.vcproj", "{588CCD13-2962-83FE-F4B7-92230DB73629}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flat_map_index_allocation_test", "flat_map_index_allocation_test.vcproj", "{51D8E9C3-2D65-48FE-3AA7-7922C0E36329}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "iset_index_allocation_test", "iset_index_allocation_test.vcproj", "{58BD1CC3-6972-F3F7-84BE-0DB736035922}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "iunordered_set_index_allocation_test", "iunordered_set_index_allocation_test.vcproj", "{5BD1C7C3-3F7F-6972-84BE-B731D9236035}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_shared_memory2", "doc_shared_memory2.vcproj", "{58CE1D83-F31E-4FD7-6132-8A79F6307B61}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_file_mapping2", "doc_file_mapping2.vcproj", "{5CE19883-F413-7EFD-6342-B79639F7B611}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_file_mapping", "doc_file_mapping.vcproj", "{58DE18C3-3261-2F3E-FD47-83760B9FA761}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_map", "doc_map.vcproj", "{59CEC183-8192-8F6D-4FB7-BA260A79D352}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "windows_shared_memory_test", "windows_shared_memory_test.vcproj", "{E385C28C-0691-4FA7-F48E-935BA0D06310}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "windows_shared_memory_mapping_test", "windows_shared_memory_mapping_test.vcproj", "{518CE8C3-6512-FA75-46EF-B917A3A116D1}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "managed_windows_shared_memory_test", "managed_windows_shared_memory.vcproj", "{5D18CE83-1926-7AE4-FE94-B606D9B23131}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "adaptive_pool_test", "adaptive_pool_test.vcproj", "{58CE1D84-1962-4FE9-BA0D-A4F7973A4652}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "cached_adaptive_pool_test", "cached_adaptive_pool_test.vcproj", "{5188E3CE-2964-F43E-FB87-B037AC692D59}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "private_adaptive_pool_test", "private_adaptive_pool_test.vcproj", "{5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_allocator", "doc_allocator.vcproj", "{581B1C83-4E12-9526-020F-012482540054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_node_allocator", "doc_node_allocator.vcproj", "{51B17C83-E172-5396-0FA2-825472008554}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_private_node_allocator", "doc_private_node_allocator.vcproj", "{2B75C833-17D2-4956-A23F-820854254175}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_cached_node_allocator", "doc_cached_node_allocator.vcproj", "{283AD375-7D12-5866-23BF-854308651275}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_adaptive_pool", "doc_adaptive_pool.vcproj", "{57C832B1-17D2-9537-FA12-827220448554}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_cached_adaptive_pool", "doc_cached_adaptive_pool.vcproj", "{536C8251-7E12-9537-A1E2-822073258554}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_private_adaptive_pool", "doc_private_adaptive_pool.vcproj", "{83258CB1-127E-9375-F872-8324A1054454}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_raw_allocation", "doc_managed_raw_allocation.vcproj", "{5198EFC3-2731-F34E-4FD8-1859AC94F761}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_aligned_allocation", "doc_managed_aligned_allocation.vcproj", "{58DE18C3-3261-2F3E-FD47-83760B9FA761}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "_interprocesslib", "interprocesslib.vcproj", "{FFAA56F1-32EC-4B22-B6BD-95A311A67C35}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_windows_shared_memory", "doc_windows_shared_memory.vcproj", "{5E17C9C3-1362-2E1E-C84F-8A76B6739F21}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_windows_shared_memory2", "doc_windows_shared_memory2.vcproj", "{5E1D6C83-31DE-4F6F-6132-87A9FB663041}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "adaptive_node_pool_test", "adaptive_node_pool_test.vcproj", "{CD57C283-1862-42FE-BF87-B96D3A2A7912}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "node_pool_test", "node_pool_test.vcproj", "{8A519DC3-6092-A4FE-F748-BA91328D6522}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "deque_test", "deque_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792655}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "barrier_test", "barrier_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792661}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "bufferstream_test", "bufferstream_test.vcproj", "{58C183CE-6203-FE12-A237-BA8976695960}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "cached_node_allocator_test", "cached_node_allocator_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792659}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "private_node_allocator_test", "private_node_allocator_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792620}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "node_allocator_test", "node_allocator_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792622}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_mutex_test", "named_mutex_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792625}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_recursive_mutex_test", "named_recursive_mutex_test.vcproj", "{5C83CE18-4F48-A7FE-6092-B7920AD3A624}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "named_semaphore_test", "named_semaphore_test.vcproj", "{58CCE283-1609-48FE-A4F7-BA0D3A793523}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_heap_memory", "doc_managed_heap_memory.vcproj", "{58CCE183-6092-48FE-A4FC-BA0D3A792647}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "allocexcept_test", "allocexcept_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792662}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "condition_test", "condition_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792658}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "data_test", "data_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792657}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_bufferstream", "doc_bufferstream.vcproj", "{58C1B183-9026-4E12-00F2-001200540054}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_intrusive", "doc_intrusive.vcproj", "{5E18CC83-6092-48FE-A677-B832A0D3A650}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_ipc_messageA", "doc_ipc_messageA.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792649}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_ipc_messageB", "doc_ipc_messageB.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792648}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_mapped_file", "doc_managed_mapped_file.vcproj", "{58CCE183-5091-48FE-A4FC-BA0D3A792446}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_allocA", "doc_named_allocA.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792645}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_named_allocB", "doc_named_allocB.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792644}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_offset_ptr", "doc_offset_ptr.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792643}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_scoped_ptr", "doc_scoped_ptr.vcproj", "{58CC8E13-0962-8F4E-77A6-BD3A6832A042}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_vectorstream", "doc_vectorstream.vcproj", "{58C1B183-9260-4E8F-F200-000000000041}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_where_allocate", "doc_where_allocate.vcproj", "{58CCE183-6092-48FE-A677-BA0D3A832640}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "file_mapping_test", "file_mapping_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792638}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flat_tree_test", "flat_tree_test.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792637}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "intrusive_ptr_test", "intrusive_ptr_test.vcproj", "{5821C383-6092-12FE-A877-BA0D33467633}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "list_test", "list_ex.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792632}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "managed_mapped_file_test", "managed_mapped_file_test.vcproj", "{5CCE1883-0926-F7A4-8FE4-BA0606D92331}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "mapped_file_test", "mapped_file_test.vcproj", "{5C6D9CE1-2609-F7A4-8FE4-BA0883602330}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "memory_algorithm_test", "memory_algorithm_test.vcproj", "{58E18CC3-6092-8F4E-A3E7-A792230D3629}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "message_queue_test", "message_queue.vcproj", "{58CCE183-6092-48FE-A4F7-BA0D3A792628}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "mutex_test", "mutex_test.vcproj", "{83581CCE-487E-3292-A4E7-BA07926D3A27}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "null_index_test", "null_index_test.vcproj", "{0000058C-0000-0000-0000-000000000021}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "recursive_mutex_test", "recursive_mutex_test.vcproj", "{83581CCE-487E-3292-A4E7-BA07926D3A14}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "semaphore_test", "semaphore_test.vcproj", "{5CE28C83-48FE-1676-4FA7-B50D3A76A013}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_multiple_allocation", "doc_managed_multiple_allocation.vcproj", "{818C43EE-3561-F3AE-4FD7-8A2076E76A31}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_allocation_command", "doc_managed_allocation_command.vcproj", "{5189DEA3-3261-F33E-47ED-83BC69F66061}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_managed_construction_info", "doc_managed_construction_info.vcproj", "{5C82D1D3-3861-3AF1-03EF-89AED4716761}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_shared_ptr_explicit", "doc_shared_ptr_explicit.vcproj", "{4E887AC3-F8EA-6923-A744-C264A398C913}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_unique_ptr", "doc_unique_ptr.vcproj", "{589C2EB3-8A57-1862-F4EA-A6B14C7329A3}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "doc_shared_ptr", "doc_shared_ptr.vcproj", "{51CE89A3-6092-F4EA-48A7-B4B9AC326093}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Global
+ GlobalSection(SolutionConfiguration) = preSolution
+ Debug = Debug
+ Release = Release
+ EndGlobalSection
+ GlobalSection(ProjectDependencies) = postSolution
+ EndGlobalSection
+ GlobalSection(ProjectConfiguration) = postSolution
+ {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Debug.ActiveCfg = Debug|Win32
+ {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Debug.Build.0 = Debug|Win32
+ {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Release.ActiveCfg = Release|Win32
+ {5CE18C83-6025-36FE-A4F7-BA09176D3A11}.Release.Build.0 = Release|Win32
+ {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Debug.ActiveCfg = Debug|Win32
+ {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Debug.Build.0 = Debug|Win32
+ {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Release.ActiveCfg = Release|Win32
+ {5E2838CC-0916-8F4E-A4F7-93506BA0D310}.Release.Build.0 = Release|Win32
+ {5371C383-6092-1238-A877-BAEB37867609}.Debug.ActiveCfg = Debug|Win32
+ {5371C383-6092-1238-A877-BAEB37867609}.Debug.Build.0 = Debug|Win32
+ {5371C383-6092-1238-A877-BAEB37867609}.Release.ActiveCfg = Release|Win32
+ {5371C383-6092-1238-A877-BAEB37867609}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792608}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D4A792607}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792606}.Release.Build.0 = Release|Win32
+ {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Debug.ActiveCfg = Debug|Win32
+ {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Debug.Build.0 = Debug|Win32
+ {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Release.ActiveCfg = Release|Win32
+ {4E88C1C2-0961-F7A4-F48E-A6A7D3B06004}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792603}.Release.Build.0 = Release|Win32
+ {58CCE183-6032-12FE-A4F7-BA893A767601}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6032-12FE-A4F7-BA893A767601}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6032-12FE-A4F7-BA893A767601}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6032-12FE-A4F7-BA893A767601}.Release.Build.0 = Release|Win32
+ {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Debug.ActiveCfg = Debug|Win32
+ {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Debug.Build.0 = Debug|Win32
+ {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Release.ActiveCfg = Release|Win32
+ {5CE11C83-096A-84FE-4FA2-D3A6BA792002}.Release.Build.0 = Release|Win32
+ {58CC2563-6092-48FE-FAF7-BA046A792658}.Debug.ActiveCfg = Debug|Win32
+ {58CC2563-6092-48FE-FAF7-BA046A792658}.Debug.Build.0 = Debug|Win32
+ {58CC2563-6092-48FE-FAF7-BA046A792658}.Release.ActiveCfg = Release|Win32
+ {58CC2563-6092-48FE-FAF7-BA046A792658}.Release.Build.0 = Release|Win32
+ {58C1B183-9026-4E63-12F2-005412200054}.Debug.ActiveCfg = Debug|Win32
+ {58C1B183-9026-4E63-12F2-005412200054}.Debug.Build.0 = Debug|Win32
+ {58C1B183-9026-4E63-12F2-005412200054}.Release.ActiveCfg = Release|Win32
+ {58C1B183-9026-4E63-12F2-005412200054}.Release.Build.0 = Release|Win32
+ {58C1B183-9026-4E63-12F2-005202441254}.Debug.ActiveCfg = Debug|Win32
+ {58C1B183-9026-4E63-12F2-005202441254}.Debug.Build.0 = Debug|Win32
+ {58C1B183-9026-4E63-12F2-005202441254}.Release.ActiveCfg = Release|Win32
+ {58C1B183-9026-4E63-12F2-005202441254}.Release.Build.0 = Release|Win32
+ {58C181B3-9516-463E-2F12-122155400054}.Debug.ActiveCfg = Debug|Win32
+ {58C181B3-9516-463E-2F12-122155400054}.Debug.Build.0 = Debug|Win32
+ {58C181B3-9516-463E-2F12-122155400054}.Release.ActiveCfg = Release|Win32
+ {58C181B3-9516-463E-2F12-122155400054}.Release.Build.0 = Release|Win32
+ {5C1B8183-0296-4F83-1F22-001005220544}.Debug.ActiveCfg = Debug|Win32
+ {5C1B8183-0296-4F83-1F22-001005220544}.Debug.Build.0 = Debug|Win32
+ {5C1B8183-0296-4F83-1F22-001005220544}.Release.ActiveCfg = Release|Win32
+ {5C1B8183-0296-4F83-1F22-001005220544}.Release.Build.0 = Release|Win32
+ {58C1FE83-2906-E643-2F12-024410052254}.Debug.ActiveCfg = Debug|Win32
+ {58C1FE83-2906-E643-2F12-024410052254}.Debug.Build.0 = Debug|Win32
+ {58C1FE83-2906-E643-2F12-024410052254}.Release.ActiveCfg = Release|Win32
+ {58C1FE83-2906-E643-2F12-024410052254}.Release.Build.0 = Release|Win32
+ {58EB1CB3-1354-364E-12F2-154356612054}.Debug.ActiveCfg = Debug|Win32
+ {58EB1CB3-1354-364E-12F2-154356612054}.Debug.Build.0 = Debug|Win32
+ {58EB1CB3-1354-364E-12F2-154356612054}.Release.ActiveCfg = Release|Win32
+ {58EB1CB3-1354-364E-12F2-154356612054}.Release.Build.0 = Release|Win32
+ {58181CB3-5134-634E-12F2-155435622054}.Debug.ActiveCfg = Debug|Win32
+ {58181CB3-5134-634E-12F2-155435622054}.Debug.Build.0 = Debug|Win32
+ {58181CB3-5134-634E-12F2-155435622054}.Release.ActiveCfg = Release|Win32
+ {58181CB3-5134-634E-12F2-155435622054}.Release.Build.0 = Release|Win32
+ {5CB81183-29FB-F843-24FF-022050100544}.Debug.ActiveCfg = Debug|Win32
+ {5CB81183-29FB-F843-24FF-022050100544}.Debug.Build.0 = Debug|Win32
+ {5CB81183-29FB-F843-24FF-022050100544}.Release.ActiveCfg = Release|Win32
+ {5CB81183-29FB-F843-24FF-022050100544}.Release.Build.0 = Release|Win32
+ {58FBE8C3-9026-FAB2-E643-000522441254}.Debug.ActiveCfg = Debug|Win32
+ {58FBE8C3-9026-FAB2-E643-000522441254}.Debug.Build.0 = Debug|Win32
+ {58FBE8C3-9026-FAB2-E643-000522441254}.Release.ActiveCfg = Release|Win32
+ {58FBE8C3-9026-FAB2-E643-000522441254}.Release.Build.0 = Release|Win32
+ {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Debug.ActiveCfg = Debug|Win32
+ {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Debug.Build.0 = Debug|Win32
+ {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Release.ActiveCfg = Release|Win32
+ {48C1FBE8-F7A4-0961-48FE-7D93A63B0A04}.Release.Build.0 = Release|Win32
+ {5C18831B-F162-FA96-E6C3-FA5122040054}.Debug.ActiveCfg = Debug|Win32
+ {5C18831B-F162-FA96-E6C3-FA5122040054}.Debug.Build.0 = Debug|Win32
+ {5C18831B-F162-FA96-E6C3-FA5122040054}.Release.ActiveCfg = Release|Win32
+ {5C18831B-F162-FA96-E6C3-FA5122040054}.Release.Build.0 = Release|Win32
+ {5C1B1043-1EFF-2793-4E63-245241283054}.Debug.ActiveCfg = Debug|Win32
+ {5C1B1043-1EFF-2793-4E63-245241283054}.Debug.Build.0 = Debug|Win32
+ {5C1B1043-1EFF-2793-4E63-245241283054}.Release.ActiveCfg = Release|Win32
+ {5C1B1043-1EFF-2793-4E63-245241283054}.Release.Build.0 = Release|Win32
+ {51B189C3-4E63-9026-12F2-12200AF54054}.Debug.ActiveCfg = Debug|Win32
+ {51B189C3-4E63-9026-12F2-12200AF54054}.Debug.Build.0 = Debug|Win32
+ {51B189C3-4E63-9026-12F2-12200AF54054}.Release.ActiveCfg = Release|Win32
+ {51B189C3-4E63-9026-12F2-12200AF54054}.Release.Build.0 = Release|Win32
+ {5C1B1813-12C2-0296-4E63-244549126520}.Debug.ActiveCfg = Debug|Win32
+ {5C1B1813-12C2-0296-4E63-244549126520}.Debug.Build.0 = Debug|Win32
+ {5C1B1813-12C2-0296-4E63-244549126520}.Release.ActiveCfg = Release|Win32
+ {5C1B1813-12C2-0296-4E63-244549126520}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792653}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792652}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792651}.Release.Build.0 = Release|Win32
+ {58CCE183-6032-12FE-4FC7-83A79F760B61}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6032-12FE-4FC7-83A79F760B61}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6032-12FE-4FC7-83A79F760B61}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6032-12FE-4FC7-83A79F760B61}.Release.Build.0 = Release|Win32
+ {571C3383-6092-A877-1238-B3786BAE7605}.Debug.ActiveCfg = Debug|Win32
+ {571C3383-6092-A877-1238-B3786BAE7605}.Debug.Build.0 = Debug|Win32
+ {571C3383-6092-A877-1238-B3786BAE7605}.Release.ActiveCfg = Release|Win32
+ {571C3383-6092-A877-1238-B3786BAE7605}.Release.Build.0 = Release|Win32
+ {58C1B183-0296-EA42-EF04-005120054104}.Debug.ActiveCfg = Debug|Win32
+ {58C1B183-0296-EA42-EF04-005120054104}.Debug.Build.0 = Debug|Win32
+ {58C1B183-0296-EA42-EF04-005120054104}.Release.ActiveCfg = Release|Win32
+ {58C1B183-0296-EA42-EF04-005120054104}.Release.Build.0 = Release|Win32
+ {588CCD13-2962-83FE-F4B7-92230DB73629}.Debug.ActiveCfg = Debug|Win32
+ {588CCD13-2962-83FE-F4B7-92230DB73629}.Debug.Build.0 = Debug|Win32
+ {588CCD13-2962-83FE-F4B7-92230DB73629}.Release.ActiveCfg = Release|Win32
+ {588CCD13-2962-83FE-F4B7-92230DB73629}.Release.Build.0 = Release|Win32
+ {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Debug.ActiveCfg = Debug|Win32
+ {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Debug.Build.0 = Debug|Win32
+ {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Release.ActiveCfg = Release|Win32
+ {51D8E9C3-2D65-48FE-3AA7-7922C0E36329}.Release.Build.0 = Release|Win32
+ {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Debug.ActiveCfg = Debug|Win32
+ {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Debug.Build.0 = Debug|Win32
+ {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Release.ActiveCfg = Release|Win32
+ {58BD1CC3-6972-F3F7-84BE-0DB736035922}.Release.Build.0 = Release|Win32
+ {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Debug.ActiveCfg = Debug|Win32
+ {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Debug.Build.0 = Debug|Win32
+ {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Release.ActiveCfg = Release|Win32
+ {5BD1C7C3-3F7F-6972-84BE-B731D9236035}.Release.Build.0 = Release|Win32
+ {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Debug.ActiveCfg = Debug|Win32
+ {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Debug.Build.0 = Debug|Win32
+ {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Release.ActiveCfg = Release|Win32
+ {58CE1D83-F31E-4FD7-6132-8A79F6307B61}.Release.Build.0 = Release|Win32
+ {5CE19883-F413-7EFD-6342-B79639F7B611}.Debug.ActiveCfg = Debug|Win32
+ {5CE19883-F413-7EFD-6342-B79639F7B611}.Debug.Build.0 = Debug|Win32
+ {5CE19883-F413-7EFD-6342-B79639F7B611}.Release.ActiveCfg = Release|Win32
+ {5CE19883-F413-7EFD-6342-B79639F7B611}.Release.Build.0 = Release|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.ActiveCfg = Debug|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.Build.0 = Debug|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.ActiveCfg = Release|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.Build.0 = Release|Win32
+ {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Debug.ActiveCfg = Debug|Win32
+ {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Debug.Build.0 = Debug|Win32
+ {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Release.ActiveCfg = Release|Win32
+ {59CEC183-8192-8F6D-4FB7-BA260A79D352}.Release.Build.0 = Release|Win32
+ {E385C28C-0691-4FA7-F48E-935BA0D06310}.Debug.ActiveCfg = Debug|Win32
+ {E385C28C-0691-4FA7-F48E-935BA0D06310}.Debug.Build.0 = Debug|Win32
+ {E385C28C-0691-4FA7-F48E-935BA0D06310}.Release.ActiveCfg = Release|Win32
+ {E385C28C-0691-4FA7-F48E-935BA0D06310}.Release.Build.0 = Release|Win32
+ {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Debug.ActiveCfg = Debug|Win32
+ {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Debug.Build.0 = Debug|Win32
+ {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Release.ActiveCfg = Release|Win32
+ {518CE8C3-6512-FA75-46EF-B917A3A116D1}.Release.Build.0 = Release|Win32
+ {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Debug.ActiveCfg = Debug|Win32
+ {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Debug.Build.0 = Debug|Win32
+ {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Release.ActiveCfg = Release|Win32
+ {5D18CE83-1926-7AE4-FE94-B606D9B23131}.Release.Build.0 = Release|Win32
+ {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Debug.ActiveCfg = Debug|Win32
+ {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Debug.Build.0 = Debug|Win32
+ {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Release.ActiveCfg = Release|Win32
+ {58CE1D84-1962-4FE9-BA0D-A4F7973A4652}.Release.Build.0 = Release|Win32
+ {5188E3CE-2964-F43E-FB87-B037AC692D59}.Debug.ActiveCfg = Debug|Win32
+ {5188E3CE-2964-F43E-FB87-B037AC692D59}.Debug.Build.0 = Debug|Win32
+ {5188E3CE-2964-F43E-FB87-B037AC692D59}.Release.ActiveCfg = Release|Win32
+ {5188E3CE-2964-F43E-FB87-B037AC692D59}.Release.Build.0 = Release|Win32
+ {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Debug.ActiveCfg = Debug|Win32
+ {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Debug.Build.0 = Debug|Win32
+ {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Release.ActiveCfg = Release|Win32
+ {5CE14C83-4962-8F5E-4FA7-B0D3A7B93635}.Release.Build.0 = Release|Win32
+ {581B1C83-4E12-9526-020F-012482540054}.Debug.ActiveCfg = Debug|Win32
+ {581B1C83-4E12-9526-020F-012482540054}.Debug.Build.0 = Debug|Win32
+ {581B1C83-4E12-9526-020F-012482540054}.Release.ActiveCfg = Release|Win32
+ {581B1C83-4E12-9526-020F-012482540054}.Release.Build.0 = Release|Win32
+ {51B17C83-E172-5396-0FA2-825472008554}.Debug.ActiveCfg = Debug|Win32
+ {51B17C83-E172-5396-0FA2-825472008554}.Debug.Build.0 = Debug|Win32
+ {51B17C83-E172-5396-0FA2-825472008554}.Release.ActiveCfg = Release|Win32
+ {51B17C83-E172-5396-0FA2-825472008554}.Release.Build.0 = Release|Win32
+ {2B75C833-17D2-4956-A23F-820854254175}.Debug.ActiveCfg = Debug|Win32
+ {2B75C833-17D2-4956-A23F-820854254175}.Debug.Build.0 = Debug|Win32
+ {2B75C833-17D2-4956-A23F-820854254175}.Release.ActiveCfg = Release|Win32
+ {2B75C833-17D2-4956-A23F-820854254175}.Release.Build.0 = Release|Win32
+ {283AD375-7D12-5866-23BF-854308651275}.Debug.ActiveCfg = Debug|Win32
+ {283AD375-7D12-5866-23BF-854308651275}.Debug.Build.0 = Debug|Win32
+ {283AD375-7D12-5866-23BF-854308651275}.Release.ActiveCfg = Release|Win32
+ {283AD375-7D12-5866-23BF-854308651275}.Release.Build.0 = Release|Win32
+ {57C832B1-17D2-9537-FA12-827220448554}.Debug.ActiveCfg = Debug|Win32
+ {57C832B1-17D2-9537-FA12-827220448554}.Debug.Build.0 = Debug|Win32
+ {57C832B1-17D2-9537-FA12-827220448554}.Release.ActiveCfg = Release|Win32
+ {57C832B1-17D2-9537-FA12-827220448554}.Release.Build.0 = Release|Win32
+ {536C8251-7E12-9537-A1E2-822073258554}.Debug.ActiveCfg = Debug|Win32
+ {536C8251-7E12-9537-A1E2-822073258554}.Debug.Build.0 = Debug|Win32
+ {536C8251-7E12-9537-A1E2-822073258554}.Release.ActiveCfg = Release|Win32
+ {536C8251-7E12-9537-A1E2-822073258554}.Release.Build.0 = Release|Win32
+ {83258CB1-127E-9375-F872-8324A1054454}.Debug.ActiveCfg = Debug|Win32
+ {83258CB1-127E-9375-F872-8324A1054454}.Debug.Build.0 = Debug|Win32
+ {83258CB1-127E-9375-F872-8324A1054454}.Release.ActiveCfg = Release|Win32
+ {83258CB1-127E-9375-F872-8324A1054454}.Release.Build.0 = Release|Win32
+ {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Debug.ActiveCfg = Debug|Win32
+ {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Debug.Build.0 = Debug|Win32
+ {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Release.ActiveCfg = Release|Win32
+ {5198EFC3-2731-F34E-4FD8-1859AC94F761}.Release.Build.0 = Release|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.ActiveCfg = Debug|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Debug.Build.0 = Debug|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.ActiveCfg = Release|Win32
+ {58DE18C3-3261-2F3E-FD47-83760B9FA761}.Release.Build.0 = Release|Win32
+ {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Debug.ActiveCfg = Debug|Win32
+ {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Debug.Build.0 = Debug|Win32
+ {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Release.ActiveCfg = Release|Win32
+ {FFAA56F1-32EC-4B22-B6BD-95A311A67C35}.Release.Build.0 = Release|Win32
+ {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Debug.ActiveCfg = Debug|Win32
+ {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Debug.Build.0 = Debug|Win32
+ {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Release.ActiveCfg = Release|Win32
+ {5E17C9C3-1362-2E1E-C84F-8A76B6739F21}.Release.Build.0 = Release|Win32
+ {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Debug.ActiveCfg = Debug|Win32
+ {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Debug.Build.0 = Debug|Win32
+ {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Release.ActiveCfg = Release|Win32
+ {5E1D6C83-31DE-4F6F-6132-87A9FB663041}.Release.Build.0 = Release|Win32
+ {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Debug.ActiveCfg = Debug|Win32
+ {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Debug.Build.0 = Debug|Win32
+ {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Release.ActiveCfg = Release|Win32
+ {CD57C283-1862-42FE-BF87-B96D3A2A7912}.Release.Build.0 = Release|Win32
+ {8A519DC3-6092-A4FE-F748-BA91328D6522}.Debug.ActiveCfg = Debug|Win32
+ {8A519DC3-6092-A4FE-F748-BA91328D6522}.Debug.Build.0 = Debug|Win32
+ {8A519DC3-6092-A4FE-F748-BA91328D6522}.Release.ActiveCfg = Release|Win32
+ {8A519DC3-6092-A4FE-F748-BA91328D6522}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792655}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792661}.Release.Build.0 = Release|Win32
+ {58C183CE-6203-FE12-A237-BA8976695960}.Debug.ActiveCfg = Debug|Win32
+ {58C183CE-6203-FE12-A237-BA8976695960}.Debug.Build.0 = Debug|Win32
+ {58C183CE-6203-FE12-A237-BA8976695960}.Release.ActiveCfg = Release|Win32
+ {58C183CE-6203-FE12-A237-BA8976695960}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792659}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792620}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792622}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792625}.Release.Build.0 = Release|Win32
+ {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Debug.ActiveCfg = Debug|Win32
+ {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Debug.Build.0 = Debug|Win32
+ {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Release.ActiveCfg = Release|Win32
+ {5C83CE18-4F48-A7FE-6092-B7920AD3A624}.Release.Build.0 = Release|Win32
+ {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Debug.ActiveCfg = Debug|Win32
+ {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Debug.Build.0 = Debug|Win32
+ {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Release.ActiveCfg = Release|Win32
+ {58CCE283-1609-48FE-A4F7-BA0D3A793523}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4FC-BA0D3A792647}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792662}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792658}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792657}.Release.Build.0 = Release|Win32
+ {58C1B183-9026-4E12-00F2-001200540054}.Debug.ActiveCfg = Debug|Win32
+ {58C1B183-9026-4E12-00F2-001200540054}.Debug.Build.0 = Debug|Win32
+ {58C1B183-9026-4E12-00F2-001200540054}.Release.ActiveCfg = Release|Win32
+ {58C1B183-9026-4E12-00F2-001200540054}.Release.Build.0 = Release|Win32
+ {5E18CC83-6092-48FE-A677-B832A0D3A650}.Debug.ActiveCfg = Debug|Win32
+ {5E18CC83-6092-48FE-A677-B832A0D3A650}.Debug.Build.0 = Debug|Win32
+ {5E18CC83-6092-48FE-A677-B832A0D3A650}.Release.ActiveCfg = Release|Win32
+ {5E18CC83-6092-48FE-A677-B832A0D3A650}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792649}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792648}.Release.Build.0 = Release|Win32
+ {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Debug.Build.0 = Debug|Win32
+ {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Release.ActiveCfg = Release|Win32
+ {58CCE183-5091-48FE-A4FC-BA0D3A792446}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792645}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792644}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792643}.Release.Build.0 = Release|Win32
+ {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Debug.ActiveCfg = Debug|Win32
+ {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Debug.Build.0 = Debug|Win32
+ {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Release.ActiveCfg = Release|Win32
+ {58CC8E13-0962-8F4E-77A6-BD3A6832A042}.Release.Build.0 = Release|Win32
+ {58C1B183-9260-4E8F-F200-000000000041}.Debug.ActiveCfg = Debug|Win32
+ {58C1B183-9260-4E8F-F200-000000000041}.Debug.Build.0 = Debug|Win32
+ {58C1B183-9260-4E8F-F200-000000000041}.Release.ActiveCfg = Release|Win32
+ {58C1B183-9260-4E8F-F200-000000000041}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A677-BA0D3A832640}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A677-BA0D3A832640}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A677-BA0D3A832640}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A677-BA0D3A832640}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792638}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792637}.Release.Build.0 = Release|Win32
+ {5821C383-6092-12FE-A877-BA0D33467633}.Debug.ActiveCfg = Debug|Win32
+ {5821C383-6092-12FE-A877-BA0D33467633}.Debug.Build.0 = Debug|Win32
+ {5821C383-6092-12FE-A877-BA0D33467633}.Release.ActiveCfg = Release|Win32
+ {5821C383-6092-12FE-A877-BA0D33467633}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792632}.Release.Build.0 = Release|Win32
+ {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Debug.ActiveCfg = Debug|Win32
+ {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Debug.Build.0 = Debug|Win32
+ {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Release.ActiveCfg = Release|Win32
+ {5CCE1883-0926-F7A4-8FE4-BA0606D92331}.Release.Build.0 = Release|Win32
+ {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Debug.ActiveCfg = Debug|Win32
+ {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Debug.Build.0 = Debug|Win32
+ {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Release.ActiveCfg = Release|Win32
+ {5C6D9CE1-2609-F7A4-8FE4-BA0883602330}.Release.Build.0 = Release|Win32
+ {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Debug.ActiveCfg = Debug|Win32
+ {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Debug.Build.0 = Debug|Win32
+ {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Release.ActiveCfg = Release|Win32
+ {58E18CC3-6092-8F4E-A3E7-A792230D3629}.Release.Build.0 = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Debug.ActiveCfg = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Debug.Build.0 = Debug|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Release.ActiveCfg = Release|Win32
+ {58CCE183-6092-48FE-A4F7-BA0D3A792628}.Release.Build.0 = Release|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A27}.Debug.ActiveCfg = Debug|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A27}.Debug.Build.0 = Debug|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A27}.Release.ActiveCfg = Release|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A27}.Release.Build.0 = Release|Win32
+ {0000058C-0000-0000-0000-000000000021}.Debug.ActiveCfg = Debug|Win32
+ {0000058C-0000-0000-0000-000000000021}.Debug.Build.0 = Debug|Win32
+ {0000058C-0000-0000-0000-000000000021}.Release.ActiveCfg = Release|Win32
+ {0000058C-0000-0000-0000-000000000021}.Release.Build.0 = Release|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A14}.Debug.ActiveCfg = Debug|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A14}.Debug.Build.0 = Debug|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A14}.Release.ActiveCfg = Release|Win32
+ {83581CCE-487E-3292-A4E7-BA07926D3A14}.Release.Build.0 = Release|Win32
+ {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Debug.ActiveCfg = Debug|Win32
+ {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Debug.Build.0 = Debug|Win32
+ {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Release.ActiveCfg = Release|Win32
+ {5CE28C83-48FE-1676-4FA7-B50D3A76A013}.Release.Build.0 = Release|Win32
+ {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Debug.ActiveCfg = Debug|Win32
+ {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Debug.Build.0 = Debug|Win32
+ {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Release.ActiveCfg = Release|Win32
+ {818C43EE-3561-F3AE-4FD7-8A2076E76A31}.Release.Build.0 = Release|Win32
+ {5189DEA3-3261-F33E-47ED-83BC69F66061}.Debug.ActiveCfg = Debug|Win32
+ {5189DEA3-3261-F33E-47ED-83BC69F66061}.Debug.Build.0 = Debug|Win32
+ {5189DEA3-3261-F33E-47ED-83BC69F66061}.Release.ActiveCfg = Release|Win32
+ {5189DEA3-3261-F33E-47ED-83BC69F66061}.Release.Build.0 = Release|Win32
+ {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Debug.ActiveCfg = Debug|Win32
+ {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Debug.Build.0 = Debug|Win32
+ {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Release.ActiveCfg = Release|Win32
+ {5C82D1D3-3861-3AF1-03EF-89AED4716761}.Release.Build.0 = Release|Win32
+ {4E887AC3-F8EA-6923-A744-C264A398C913}.Debug.ActiveCfg = Debug|Win32
+ {4E887AC3-F8EA-6923-A744-C264A398C913}.Debug.Build.0 = Debug|Win32
+ {4E887AC3-F8EA-6923-A744-C264A398C913}.Release.ActiveCfg = Release|Win32
+ {4E887AC3-F8EA-6923-A744-C264A398C913}.Release.Build.0 = Release|Win32
+ {589C2EB3-8A57-1862-F4EA-A6B14C7329A3}.Debug.ActiveCfg = Debug|Win32
+ {589C2EB3-8A57-1862-F4EA-A6B14C7329A3}.Debug.Build.0 = Debug|Win32
+ {589C2EB3-8A57-1862-F4EA-A6B14C7329A3}.Release.ActiveCfg = Release|Win32
+ {589C2EB3-8A57-1862-F4EA-A6B14C7329A3}.Release.Build.0 = Release|Win32
+ {51CE89A3-6092-F4EA-48A7-B4B9AC326093}.Debug.ActiveCfg = Debug|Win32
+ {51CE89A3-6092-F4EA-48A7-B4B9AC326093}.Debug.Build.0 = Debug|Win32
+ {51CE89A3-6092-F4EA-48A7-B4B9AC326093}.Release.ActiveCfg = Release|Win32
+ {51CE89A3-6092-F4EA-48A7-B4B9AC326093}.Release.Build.0 = Release|Win32
+ EndGlobalSection
+ GlobalSection(ExtensibilityGlobals) = postSolution
+ EndGlobalSection
+ GlobalSection(ExtensibilityAddIns) = postSolution
+ EndGlobalSection
+EndGlobal
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,133 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="ProcessA"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792619}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/ProcessA"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="4"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessA_d.exe"
- LinkIncremental="2"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/ProcessA.pdb"
- SubSystem="1"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/ProcessA"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessA.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\example\process_a_example.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessAFixed.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessAFixed.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,133 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="ProcessAFixed"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792618}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/ProcessAFixed"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="4"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessAFixed_d.exe"
- LinkIncremental="2"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/ProcessAFixed.pdb"
- SubSystem="1"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/ProcessAFixed"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessAFixed.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\example\process_a_fixed_example.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,132 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="ProcessB"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792617}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/ProcessB"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="4"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessB_d.exe"
- LinkIncremental="2"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/ProcessB.pdb"
- SubSystem="1"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/ProcessB"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessB.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\example\process_b_example.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessBFixed.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/ProcessBFixed.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,132 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="ProcessBFixed"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792616}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/ProcessBFixed"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="4"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessBFixed_d.exe"
- LinkIncremental="2"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/ProcessBFixed.pdb"
- SubSystem="1"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/ProcessBFixed"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/ProcessBFixed.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\example\process_b_fixed_example.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_node_pool_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_node_pool_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_node_pool_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_pool_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_pool_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/adaptive_pool_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/allocate_ex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/allocate_ex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,134 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="allocate_ex"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792663}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/allocate_ex"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/allocate_ex_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/allocate_ex.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/allocate_ex"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/allocate_ex.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\example\alloc_example.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/allocexcept_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/allocexcept_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/allocexcept_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/barrier_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/barrier_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/barrier_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/bufferstream_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/bufferstream_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/bufferstream_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/cached_adaptive_pool_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/cached_adaptive_pool_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/cached_adaptive_pool_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/cached_node_allocator_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/cached_node_allocator_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/cached_node_allocator_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/condition_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/condition_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/condition_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/data_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/data_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/data_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/deque_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/deque_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/deque_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_adaptive_pool.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_adaptive_pool.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_adaptive_pool.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_allocator.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_allocator.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_allocator.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_conditionB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_mutexB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_semaphoreB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_anonymous_upgradable_mutexB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_bufferstream.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_bufferstream.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_bufferstream.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_adaptive_pool.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_adaptive_pool.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_adaptive_pool.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_node_allocator.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_node_allocator.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cached_node_allocator.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cont.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cont.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_cont.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_contB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping2.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping2.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_file_mapping2.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_intrusive.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_intrusive.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_intrusive.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_ipc_messageB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_aligned_allocation.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_aligned_allocation.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_aligned_allocation.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_allocation_command.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_allocation_command.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_allocation_command.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_construction_info.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_construction_info.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_construction_info.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_heap_memory.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_heap_memory.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_heap_memory.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_mapped_file.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_mapped_file.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_mapped_file.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_multiple_allocation.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_multiple_allocation.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_multiple_allocation.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -75,6 +75,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_raw_allocation.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_raw_allocation.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_managed_raw_allocation.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_map.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_map.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_map.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_message_queueB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_move_containers.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_move_containers.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_move_containers.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_allocB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionA.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionA.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionA.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionB.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionB.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_conditionB.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_mutex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_mutex.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_named_mutex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_node_allocator.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_node_allocator.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_node_allocator.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_offset_ptr.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_offset_ptr.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_offset_ptr.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_adaptive_pool.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_adaptive_pool.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_adaptive_pool.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_node_allocator.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_node_allocator.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_private_node_allocator.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_scoped_ptr.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_scoped_ptr.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_scoped_ptr.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory2.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory2.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_shared_memory2.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_vectorstream.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_vectorstream.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_vectorstream.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_where_allocate.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_where_allocate.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_where_allocate.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory2.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory2.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/doc_windows_shared_memory2.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/file_lock_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/file_lock_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,134 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="file_lock_test"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792639}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/file_lock_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/file_lock_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/file_lock_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/file_lock_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/file_lock_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{7FCFEF41-3746-C7A5-8B8E-A352A2F22D7F}">
- <File
- RelativePath="..\..\test\file_lock_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{95393980-8912-4b74-66A0-607BE52EB5FB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/file_mapping_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/file_mapping_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/file_mapping_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -74,6 +75,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/flat_map_index_allocation_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/flat_map_index_allocation_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/flat_map_index_allocation_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/flat_tree_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/flat_tree_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/flat_tree_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -26,6 +26,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -75,6 +76,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/hash_table_ex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/hash_table_ex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,134 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="hash_table_test"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792636}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/hash_table_ex"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/hash_table_ex_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/hash_table_ex.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/hash_table_ex"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/hash_table_ex.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\test\hash_table_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/interprocesslib.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/interprocesslib.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/interprocesslib.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -3,7 +3,7 @@
ProjectType="Visual C++"
Version="7.10"
Name="_interprocesslib"
- ProjectGUID="{FFAA56F1-32EC-4B22-B6BD-95A311A67C35}"
+ ProjectGUID="{FF56BAF1-32EC-4B22-B6BD-95A3A67C3135}"
Keyword="Win32Proj">
<Platforms>
<Platform
@@ -96,48 +96,6 @@
</References>
<Files>
<Filter
- Name="Smart Pointer"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\enable_shared_from_this.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\intrusive_ptr.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\offset_ptr.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\scoped_ptr.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\shared_ptr.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\unique_ptr.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\weak_ptr.hpp">
- </File>
- <Filter
- Name="detail"
- Filter="">
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\shared_count.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\sp_counted_base.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\sp_counted_base_atomic.hpp">
- </File>
- <File
- RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\sp_counted_impl.hpp">
- </File>
- </Filter>
- </Filter>
- <Filter
Name="Containers"
Filter="">
<File
@@ -329,6 +287,9 @@
<File
RelativePath="..\..\..\..\boost\interprocess\sync\emulation\interprocess_semaphore.hpp">
</File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\sync\emulation\named_creation_functor.hpp">
+ </File>
</Filter>
</Filter>
<Filter
@@ -344,6 +305,9 @@
Name="detail"
Filter="">
<File
+ RelativePath="..\..\..\..\boost\interprocess\mem_algo\detail\mem_algo_common.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\boost\interprocess\mem_algo\detail\simple_seq_fit_impl.hpp">
</File>
</Filter>
@@ -432,6 +396,9 @@
RelativePath="..\..\..\..\boost\interprocess\detail\managed_open_or_create_impl.hpp">
</File>
<File
+ RelativePath="..\..\..\..\boost\interprocess\detail\math_functions.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\boost\interprocess\detail\min_max.hpp">
</File>
<File
@@ -447,9 +414,6 @@
RelativePath="..\..\..\..\boost\interprocess\detail\named_proxy.hpp">
</File>
<File
- RelativePath="..\..\..\..\boost\interprocess\detail\null_create_func.hpp">
- </File>
- <File
RelativePath="..\..\..\..\boost\interprocess\detail\os_file_functions.hpp">
</File>
<File
@@ -465,6 +429,9 @@
RelativePath="..\..\..\..\boost\interprocess\detail\ptime_wrk.hpp">
</File>
<File
+ RelativePath="..\..\..\..\boost\interprocess\detail\segment_manager_helper.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\boost\interprocess\detail\type_traits.hpp">
</File>
<File
@@ -561,6 +528,9 @@
RelativePath="..\..\test\get_compiler_name.hpp">
</File>
<File
+ RelativePath="..\..\test\get_process_id_name.hpp">
+ </File>
+ <File
RelativePath="..\..\test\itestvalue.hpp">
</File>
<File
@@ -629,22 +599,508 @@
Name="Example"
Filter="">
<File
+ RelativePath="..\..\example\doc_adaptive_pool.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_allocator.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
RelativePath="..\..\example\doc_anonymous_condition_shared_data.hpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCustomBuildTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_conditionA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_conditionB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
</File>
<File
RelativePath="..\..\example\doc_anonymous_mutex_shared_data.hpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCustomBuildTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_mutexA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_mutexB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
</File>
<File
RelativePath="..\..\example\doc_anonymous_semaphore_shared_data.hpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCustomBuildTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_semaphoreA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_semaphoreB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_upgradable_mutexA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_anonymous_upgradable_mutexB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_bufferstream.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_cached_adaptive_pool.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_cached_node_allocator.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_cont.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_contA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_contB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_file_mapping.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_file_mapping2.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_intrusive.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_ipc_messageA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_ipc_messageB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_aligned_allocation.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_allocation_command.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_construction_info.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_external_buffer.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_heap_memory.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_mapped_file.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_multiple_allocation.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_managed_raw_allocation.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_map.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_message_queueA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_message_queueB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_move_containers.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_named_allocA.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_named_allocB.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
</File>
<File
RelativePath="..\..\example\doc_named_condition_shared_data.hpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCustomBuildTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_named_mutex.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_node_allocator.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_offset_ptr.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_private_adaptive_pool.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_private_node_allocator.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_scoped_ptr.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_shared_memory.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_shared_memory2.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_shared_ptr.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_shared_ptr_explicit.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_unique_ptr.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
</File>
<File
RelativePath="..\..\example\doc_upgradable_mutex_shared_data.hpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCustomBuildTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_vectorstream.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_where_allocate.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_windows_shared_memory.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
+ </File>
+ <File
+ RelativePath="..\..\example\doc_windows_shared_memory2.cpp">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCLCompilerTool"/>
+ </FileConfiguration>
</File>
<File
RelativePath="..\..\example\Jamfile.v2">
+ <FileConfiguration
+ Name="Debug|Win32"
+ ExcludedFromBuild="TRUE">
+ <Tool
+ Name="VCCustomBuildTool"/>
+ </FileConfiguration>
</File>
</Filter>
<Filter
@@ -654,6 +1110,51 @@
RelativePath="..\..\..\..\boost\interprocess\ipc\message_queue.hpp">
</File>
</Filter>
+ <Filter
+ Name="Smart Pointer"
+ Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
+ UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\deleter.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\enable_shared_from_this.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\intrusive_ptr.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\offset_ptr.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\scoped_ptr.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\shared_ptr.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\unique_ptr.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\weak_ptr.hpp">
+ </File>
+ <Filter
+ Name="detail"
+ Filter="">
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\shared_count.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\sp_counted_base.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\sp_counted_base_atomic.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\..\boost\interprocess\smart_ptr\detail\sp_counted_impl.hpp">
+ </File>
+ </Filter>
+ </Filter>
<File
RelativePath="..\..\..\..\boost\interprocess\interprocess_fwd.hpp">
</File>
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/intersegment_ptr_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/intersegment_ptr_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,137 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="intersegment_ptr_test"
- ProjectGUID="{58CCE183-6092-12FE-A4F7-BA0D3A767634}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/intersegment_ptr_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- ExceptionHandling="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- RuntimeTypeInfo="TRUE"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/intersegment_ptr_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/intersegment_ptr_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/intersegment_ptr_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- RuntimeTypeInfo="TRUE"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/intersegment_ptr_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-CAA5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\test\intersegment_ptr_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-8ABD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/intrusive_ptr_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/intrusive_ptr_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/intrusive_ptr_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -25,6 +25,7 @@
ExceptionHandling="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
RuntimeTypeInfo="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
@@ -75,6 +76,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
RuntimeTypeInfo="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/iset_index_allocation_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/iset_index_allocation_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/iset_index_allocation_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/iunordered_set_index_allocation_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/iunordered_set_index_allocation_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/iunordered_set_index_allocation_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,134 +1,136 @@
<?xml version="1.0" encoding="Windows-1252"?>
<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="iunordered_set_index_allocation_test"
- ProjectGUID="{5BD1C7C3-3F7F-6972-84BE-B731D9236035}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/iunordered_set_index_allocation_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/iunordered_set_index_allocation_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/iunordered_set_index_allocation_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/iunordered_set_index_allocation_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/iunordered_set_index_allocation_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{3970F791-3846-AC77-FA86-2A55EBB74E2F}">
- <File
- RelativePath="..\..\test\iunordered_set_index_allocation_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{84F45E90-841A-D59D-3D14-6FA22EF62012}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
+ ProjectType="Visual C++"
+ Version="7.10"
+ Name="iunordered_set_index_allocation_test"
+ ProjectGUID="{5BD1C7C3-3F7F-6972-84BE-B731D9236035}"
+ Keyword="Win32Proj">
+ <Platforms>
+ <Platform
+ Name="Win32"/>
+ </Platforms>
+ <Configurations>
+ <Configuration
+ Name="Debug|Win32"
+ OutputDirectory="../../Bin/Win32/Debug"
+ IntermediateDirectory="Debug/iunordered_set_index_allocation_test"
+ ConfigurationType="1"
+ CharacterSet="2">
+ <Tool
+ Name="VCCLCompilerTool"
+ Optimization="0"
+ AdditionalIncludeDirectories="../../../.."
+ PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
+ MinimalRebuild="TRUE"
+ BasicRuntimeChecks="3"
+ RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
+ UsePrecompiledHeader="0"
+ WarningLevel="3"
+ Detect64BitPortabilityProblems="TRUE"
+ DebugInformationFormat="3"/>
+ <Tool
+ Name="VCCustomBuildTool"/>
+ <Tool
+ Name="VCLinkerTool"
+ AdditionalDependencies="winmm.lib"
+ OutputFile="$(OutDir)/iunordered_set_index_allocation_test_d.exe"
+ LinkIncremental="1"
+ AdditionalLibraryDirectories="../../../../stage/lib"
+ GenerateDebugInformation="TRUE"
+ ProgramDatabaseFile="$(OutDir)/iunordered_set_index_allocation_test.pdb"
+ SubSystem="1"
+ TargetMachine="1"
+ FixedBaseAddress="1"/>
+ <Tool
+ Name="VCMIDLTool"/>
+ <Tool
+ Name="VCPostBuildEventTool"/>
+ <Tool
+ Name="VCPreBuildEventTool"/>
+ <Tool
+ Name="VCPreLinkEventTool"/>
+ <Tool
+ Name="VCResourceCompilerTool"/>
+ <Tool
+ Name="VCWebServiceProxyGeneratorTool"/>
+ <Tool
+ Name="VCXMLDataGeneratorTool"/>
+ <Tool
+ Name="VCWebDeploymentTool"/>
+ <Tool
+ Name="VCManagedWrapperGeneratorTool"/>
+ <Tool
+ Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
+ </Configuration>
+ <Configuration
+ Name="Release|Win32"
+ OutputDirectory="../../Bin/Win32/Release"
+ IntermediateDirectory="Release/iunordered_set_index_allocation_test"
+ ConfigurationType="1"
+ CharacterSet="2">
+ <Tool
+ Name="VCCLCompilerTool"
+ AdditionalIncludeDirectories="../../../.."
+ PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
+ RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
+ UsePrecompiledHeader="0"
+ WarningLevel="3"
+ Detect64BitPortabilityProblems="TRUE"
+ DebugInformationFormat="0"/>
+ <Tool
+ Name="VCCustomBuildTool"/>
+ <Tool
+ Name="VCLinkerTool"
+ AdditionalDependencies="winmm.lib"
+ OutputFile="$(OutDir)/iunordered_set_index_allocation_test.exe"
+ LinkIncremental="1"
+ AdditionalLibraryDirectories="../../../../stage/lib"
+ GenerateDebugInformation="TRUE"
+ SubSystem="1"
+ OptimizeReferences="2"
+ EnableCOMDATFolding="2"
+ TargetMachine="1"/>
+ <Tool
+ Name="VCMIDLTool"/>
+ <Tool
+ Name="VCPostBuildEventTool"/>
+ <Tool
+ Name="VCPreBuildEventTool"/>
+ <Tool
+ Name="VCPreLinkEventTool"/>
+ <Tool
+ Name="VCResourceCompilerTool"/>
+ <Tool
+ Name="VCWebServiceProxyGeneratorTool"/>
+ <Tool
+ Name="VCXMLDataGeneratorTool"/>
+ <Tool
+ Name="VCWebDeploymentTool"/>
+ <Tool
+ Name="VCManagedWrapperGeneratorTool"/>
+ <Tool
+ Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
+ </Configuration>
+ </Configurations>
+ <References>
+ </References>
+ <Files>
+ <Filter
+ Name="Source Files"
+ Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
+ UniqueIdentifier="{3970F791-3846-AC77-FA86-2A55EBB74E2F}">
+ <File
+ RelativePath="..\..\test\iunordered_set_index_allocation_test.cpp">
+ </File>
+ </Filter>
+ <Filter
+ Name="Header Files"
+ Filter="h;hpp;hxx;hm;inl;inc;xsd"
+ UniqueIdentifier="{84F45E90-841A-D59D-3D14-6FA22EF62012}">
+ </Filter>
+ </Files>
+ <Globals>
+ </Globals>
</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/list_ex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/list_ex.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/list_ex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -26,6 +26,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -75,6 +76,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/managed_mapped_file_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/managed_mapped_file_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/managed_mapped_file_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/managed_windows_shared_memory.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/managed_windows_shared_memory.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/managed_windows_shared_memory.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/map_index_allocation_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/map_index_allocation_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/map_index_allocation_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/mapped_file_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/mapped_file_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/mapped_file_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/memory_algorithm_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/memory_algorithm_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/memory_algorithm_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,8 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ TreatWChar_tAsBuiltInType="TRUE"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +75,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/message_queue.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/message_queue.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/message_queue.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/mutex_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/mutex_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/mutex_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/named_allocate_ex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/named_allocate_ex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,134 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="named_allocate_ex"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792626}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/named_allocate_ex"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/named_allocate_ex_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/named_allocate_ex.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/named_allocate_ex"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/named_allocate_ex.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\example\named_alloc_example.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/named_condition_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/named_condition_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/named_condition_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/named_mutex_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/named_mutex_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/named_mutex_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/named_recursive_mutex_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/named_recursive_mutex_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/named_recursive_mutex_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/named_semaphore_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/named_semaphore_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/named_semaphore_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/named_upgradable_mutex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/named_upgradable_mutex.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/named_upgradable_mutex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/node_allocator_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/node_allocator_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/node_allocator_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/node_pool_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/node_pool_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/node_pool_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/null_index_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/null_index_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/null_index_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/private_adaptive_pool_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/private_adaptive_pool_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/private_adaptive_pool_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/private_node_allocator_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/private_node_allocator_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/private_node_allocator_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/read_write_mutex_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/read_write_mutex_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,134 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="read_write_mutex_test"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792615}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/shared_read_write_mutex_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/shared_read_write_mutex_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/shared_read_write_mutex_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/shared_read_write_mutex_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/shared_read_write_mutex_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\test\read_write_mutex_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/recursive_mutex_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/recursive_mutex_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/recursive_mutex_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/semaphore_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/semaphore_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/semaphore_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/sharable_mutex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/sharable_mutex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,134 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="sharable_mutex_test"
- ProjectGUID="{5E188CC3-0962-F7A4-8F4E-A0D3B606A712}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/sharable_mutex_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/sharable_mutex_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/sharable_mutex_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/sharable_mutex_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/sharable_mutex_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4737FCF1-C7A5-A606-4376-2A3252AD72FF}">
- <File
- RelativePath="..\..\test\sharable_mutex_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{98903953-8D9B-88EB-4b04-6BBF2E52E5FB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mappable_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mappable_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mappable_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -25,6 +25,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -75,6 +76,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mapping_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_mapping_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,135 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="shared_memory_mapping_test"
- ProjectGUID="{5CE18C83-6025-36FE-A4F7-BA09176D3A11}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/shared_memory_mapping_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/mapped_file_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/shared_memory_mapping_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/shared_memory_mapping_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="3"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/shared_memory_mapping_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4F737F1-C7A5-3256-66A0-2A352A22D7FF}">
- <File
- RelativePath="..\..\test\shared_memory_mapping_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{5CE18253-89BD-b044-826B-62B5F2EBFBE5}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/shared_memory_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/shared_ptr_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/shared_ptr_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/shared_ptr_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -25,6 +25,7 @@
ExceptionHandling="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
RuntimeTypeInfo="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
@@ -75,6 +76,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
RuntimeTypeInfo="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/slist_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/slist_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/slist_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/string_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/string_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/string_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/tree_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/tree_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/tree_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,134 +1,136 @@
<?xml version="1.0" encoding="Windows-1252"?>
<VisualStudioProject
- ProjectType="Visual C++"
- Version="7.10"
- Name="tree_test"
- ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792606}"
- Keyword="Win32Proj">
- <Platforms>
- <Platform
- Name="Win32"/>
- </Platforms>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="../../Bin/Win32/Debug"
- IntermediateDirectory="Debug/tree_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- MinimalRebuild="TRUE"
- BasicRuntimeChecks="3"
- RuntimeLibrary="3"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="3"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/tree_test_d.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- ProgramDatabaseFile="$(OutDir)/tree_test.pdb"
- SubSystem="1"
- TargetMachine="1"
- FixedBaseAddress="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="../../Bin/Win32/Release"
- IntermediateDirectory="Release/tree_test"
- ConfigurationType="1"
- CharacterSet="2">
- <Tool
- Name="VCCLCompilerTool"
- AdditionalIncludeDirectories="../../../.."
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
- RuntimeLibrary="2"
- UsePrecompiledHeader="0"
- WarningLevel="3"
- Detect64BitPortabilityProblems="TRUE"
- DebugInformationFormat="0"/>
- <Tool
- Name="VCCustomBuildTool"/>
- <Tool
- Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib"
- OutputFile="$(OutDir)/tree_test.exe"
- LinkIncremental="1"
- AdditionalLibraryDirectories="../../../../stage/lib"
- GenerateDebugInformation="TRUE"
- SubSystem="1"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- TargetMachine="1"/>
- <Tool
- Name="VCMIDLTool"/>
- <Tool
- Name="VCPostBuildEventTool"/>
- <Tool
- Name="VCPreBuildEventTool"/>
- <Tool
- Name="VCPreLinkEventTool"/>
- <Tool
- Name="VCResourceCompilerTool"/>
- <Tool
- Name="VCWebServiceProxyGeneratorTool"/>
- <Tool
- Name="VCXMLDataGeneratorTool"/>
- <Tool
- Name="VCWebDeploymentTool"/>
- <Tool
- Name="VCManagedWrapperGeneratorTool"/>
- <Tool
- Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
- <File
- RelativePath="..\..\test\tree_test.cpp">
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
- </Filter>
- </Files>
- <Globals>
- </Globals>
+ ProjectType="Visual C++"
+ Version="7.10"
+ Name="tree_test"
+ ProjectGUID="{58CCE183-6092-48FE-A4F7-BA0D3A792606}"
+ Keyword="Win32Proj">
+ <Platforms>
+ <Platform
+ Name="Win32"/>
+ </Platforms>
+ <Configurations>
+ <Configuration
+ Name="Debug|Win32"
+ OutputDirectory="../../Bin/Win32/Debug"
+ IntermediateDirectory="Debug/tree_test"
+ ConfigurationType="1"
+ CharacterSet="2">
+ <Tool
+ Name="VCCLCompilerTool"
+ Optimization="0"
+ AdditionalIncludeDirectories="../../../.."
+ PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
+ MinimalRebuild="TRUE"
+ BasicRuntimeChecks="3"
+ RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
+ UsePrecompiledHeader="0"
+ WarningLevel="3"
+ Detect64BitPortabilityProblems="TRUE"
+ DebugInformationFormat="3"/>
+ <Tool
+ Name="VCCustomBuildTool"/>
+ <Tool
+ Name="VCLinkerTool"
+ AdditionalDependencies="winmm.lib"
+ OutputFile="$(OutDir)/tree_test_d.exe"
+ LinkIncremental="1"
+ AdditionalLibraryDirectories="../../../../stage/lib"
+ GenerateDebugInformation="TRUE"
+ ProgramDatabaseFile="$(OutDir)/tree_test.pdb"
+ SubSystem="1"
+ TargetMachine="1"
+ FixedBaseAddress="1"/>
+ <Tool
+ Name="VCMIDLTool"/>
+ <Tool
+ Name="VCPostBuildEventTool"/>
+ <Tool
+ Name="VCPreBuildEventTool"/>
+ <Tool
+ Name="VCPreLinkEventTool"/>
+ <Tool
+ Name="VCResourceCompilerTool"/>
+ <Tool
+ Name="VCWebServiceProxyGeneratorTool"/>
+ <Tool
+ Name="VCXMLDataGeneratorTool"/>
+ <Tool
+ Name="VCWebDeploymentTool"/>
+ <Tool
+ Name="VCManagedWrapperGeneratorTool"/>
+ <Tool
+ Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
+ </Configuration>
+ <Configuration
+ Name="Release|Win32"
+ OutputDirectory="../../Bin/Win32/Release"
+ IntermediateDirectory="Release/tree_test"
+ ConfigurationType="1"
+ CharacterSet="2">
+ <Tool
+ Name="VCCLCompilerTool"
+ AdditionalIncludeDirectories="../../../.."
+ PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
+ RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
+ UsePrecompiledHeader="0"
+ WarningLevel="3"
+ Detect64BitPortabilityProblems="TRUE"
+ DebugInformationFormat="0"/>
+ <Tool
+ Name="VCCustomBuildTool"/>
+ <Tool
+ Name="VCLinkerTool"
+ AdditionalDependencies="winmm.lib"
+ OutputFile="$(OutDir)/tree_test.exe"
+ LinkIncremental="1"
+ AdditionalLibraryDirectories="../../../../stage/lib"
+ GenerateDebugInformation="TRUE"
+ SubSystem="1"
+ OptimizeReferences="2"
+ EnableCOMDATFolding="2"
+ TargetMachine="1"/>
+ <Tool
+ Name="VCMIDLTool"/>
+ <Tool
+ Name="VCPostBuildEventTool"/>
+ <Tool
+ Name="VCPreBuildEventTool"/>
+ <Tool
+ Name="VCPreLinkEventTool"/>
+ <Tool
+ Name="VCResourceCompilerTool"/>
+ <Tool
+ Name="VCWebServiceProxyGeneratorTool"/>
+ <Tool
+ Name="VCXMLDataGeneratorTool"/>
+ <Tool
+ Name="VCWebDeploymentTool"/>
+ <Tool
+ Name="VCManagedWrapperGeneratorTool"/>
+ <Tool
+ Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
+ </Configuration>
+ </Configurations>
+ <References>
+ </References>
+ <Files>
+ <Filter
+ Name="Source Files"
+ Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
+ UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
+ <File
+ RelativePath="..\..\test\tree_test.cpp">
+ </File>
+ </Filter>
+ <Filter
+ Name="Header Files"
+ Filter="h;hpp;hxx;hm;inl;inc;xsd"
+ UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
+ </Filter>
+ </Files>
+ <Globals>
+ </Globals>
</VisualStudioProject>
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/unique_ptr_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/unique_ptr_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/unique_ptr_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -25,6 +25,7 @@
ExceptionHandling="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
RuntimeTypeInfo="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
@@ -75,6 +76,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
RuntimeTypeInfo="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/upgradable_mutex.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/upgradable_mutex.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/upgradable_mutex.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/user_buffer_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/user_buffer_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/user_buffer_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/vector_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/vector_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/vector_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/vectorstream_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/vectorstream_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/vectorstream_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_mapping_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_mapping_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_mapping_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -74,6 +75,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_test.vcproj
==============================================================================
--- branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_test.vcproj (original)
+++ branches/bcbboost/libs/interprocess/proj/vc7ide/windows_shared_memory_test.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -24,6 +24,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="3"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
@@ -73,6 +74,7 @@
AdditionalIncludeDirectories="../../../.."
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="2"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Deleted: branches/bcbboost/libs/interprocess/test/allocation_test_template.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/allocation_test_template.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,371 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_INTERPROCESS_TEST_ALLOCATION_TEST_TEMPLATE_HEADER
-#define BOOST_INTERPROCESS_TEST_ALLOCATION_TEST_TEMPLATE_HEADER
-
-#include <vector>
-#include <iostream>
-#include <new>
-#include <utility>
-
-namespace boost { namespace interprocess { namespace test {
-
-//This test allocates until there is no more memory
-//and after that deallocates all in the inverse order
-template<class Allocator>
-bool test_allocation_inverse_deallocation(Allocator &a)
-{
- std::vector<void*> buffers;
-
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- for(int j = (int)buffers.size()
- ;j--
- ;){
- a.deallocate(buffers[j]);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that deallocates all in the same order
-template<class Allocator>
-bool test_allocation_direct_deallocation(Allocator &a)
-{
- std::vector<void*> buffers;
-
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- a.deallocate(buffers[j]);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that deallocates all following a pattern
-template<class Allocator>
-bool test_allocation_mixed_deallocation(Allocator &a)
-{
- std::vector<void*> buffers;
-
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that tries to shrink all the buffers to the
-//half of the original size
-template<class Allocator>
-bool test_allocation_shrink(Allocator &a)
-{
- std::vector<void*> buffers;
-
- //Allocate buffers with extra memory
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i*2, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- //Now shrink to half
- for(int i = 0, max = (int)buffers.size()
- ;i < max
- ; ++i){
- std::size_t received_size;
- if(a.allocation_command( shrink_in_place | nothrow_allocation, i*2
- , i, received_size, buffers[i]).first){
- if(received_size > std::size_t(i*2)){
- return false;
- }
- if(received_size < std::size_t(i)){
- return false;
- }
- }
- }
-
- //Deallocate it in non sequential order
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that tries to expand all the buffers to
-//avoid the wasted internal fragmentation
-template<class Allocator>
-bool test_allocation_expand(Allocator &a)
-{
- std::vector<void*> buffers;
-
- //Allocate buffers with extra memory
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- //Now try to expand to the double of the size
- for(int i = 0, max = (int)buffers.size()
- ;i < max
- ;++i){
- std::size_t received_size;
- std::size_t min_size = i+1;
- std::size_t preferred_size = i*2;
- preferred_size = min_size > preferred_size ? min_size : preferred_size;
-
- while(a.allocation_command( expand_fwd | nothrow_allocation, min_size
- , preferred_size, received_size, buffers[i]).first){
- //Check received size is bigger than minimum
- if(received_size < min_size){
- return false;
- }
- //Now, try to expand further
- min_size = received_size+1;
- preferred_size = min_size*2;
- }
- }
-
- //Deallocate it in non sequential order
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that deallocates the odd buffers to
-//make room for expansions. The expansion will probably
-//success since the deallocation left room for that.
-template<class Allocator>
-bool test_allocation_deallocation_expand(Allocator &a)
-{
- std::vector<void*> buffers;
-
- //Allocate buffers with extra memory
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- //Now deallocate the half of the blocks
- //so expand maybe can merge new free blocks
- for(int i = 0, max = (int)buffers.size()
- ;i < max
- ;++i){
- if(i%2){
- a.deallocate(buffers[i]);
- buffers[i] = 0;
- }
- }
-
- //Now try to expand to the double of the size
- for(int i = 0, max = (int)buffers.size()
- ;i < max
- ;++i){
- //
- if(buffers[i]){
- std::size_t received_size;
- std::size_t min_size = i+1;
- std::size_t preferred_size = i*2;
- preferred_size = min_size > preferred_size ? min_size : preferred_size;
-
- while(a.allocation_command( expand_fwd | nothrow_allocation, min_size
- , preferred_size, received_size, buffers[i]).first){
- //Check received size is bigger than minimum
- if(received_size < min_size){
- return false;
- }
- //Now, try to expand further
- min_size = received_size+1;
- preferred_size = min_size*2;
- }
- }
- }
-
- //Now erase null values from the vector
- buffers.erase(std::remove(buffers.begin(), buffers.end(), (void*)0)
- ,buffers.end());
-
- //Deallocate it in non sequential order
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that deallocates all except the last.
-//If the allocation algorithm is a bottom-up algorithm
-//the last buffer will be in the end of the segment.
-//Then the test will start expanding backwards, until
-//the buffer fills all the memory
-template<class Allocator>
-bool test_allocation_with_reuse(Allocator &a)
-{
- std::vector<void*> buffers;
-
- //Allocate buffers with extra memory
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- //Now deallocate all except the latest
- //Now try to expand to the double of the size
- for(int i = 0, max = (int)buffers.size() - 1
- ;i < max
- ;++i){
- a.deallocate(buffers[i]);
- }
-
- //Save the unique buffer and clear vector
- void *ptr = buffers.back();
- buffers.clear();
-
- //Now allocate with reuse
- std::size_t received_size = 0;
- for(int i = 0; true; ++i){
- std::pair<void*, bool> ret =
- a.allocation_command( expand_bwd | nothrow_allocation, received_size+1
- , received_size+(i+1)*2, received_size, ptr);
- if(!ret.first)
- break;
- //If we have memory, this must be a buffer reuse
- if(!ret.second)
- return 1;
- ptr = ret.first;
- }
- //There is only a single block so deallocate it
- a.deallocate(ptr);
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This function calls all tests
-template<class Allocator>
-bool test_all_allocation(Allocator &a)
-{
-
- std::cout << "Starting test_allocation_direct_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_allocation_direct_deallocation(a)){
- std::cout << "test_allocation_direct_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_allocation_inverse_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_allocation_inverse_deallocation(a)){
- std::cout << "test_allocation_inverse_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_allocation_mixed_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_allocation_mixed_deallocation(a)){
- std::cout << "test_allocation_mixed_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_allocation_shrink. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_allocation_shrink(a)){
- std::cout << "test_allocation_shrink failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_allocation_expand. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_allocation_expand(a)){
- std::cout << "test_allocation_expand failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- if(!test_allocation_deallocation_expand(a)){
- std::cout << "test_allocation_deallocation_expand failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- if(!test_allocation_with_reuse(a)){
- std::cout << "test_allocation_with_reuse failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- return true;
-}
-
-}}} //namespace boost { namespace interprocess { namespace test {
-
-#endif //BOOST_INTERPROCESS_TEST_ALLOCATION_TEST_TEMPLATE_HEADER
-
Modified: branches/bcbboost/libs/interprocess/test/check_equal_containers.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/check_equal_containers.hpp (original)
+++ branches/bcbboost/libs/interprocess/test/check_equal_containers.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -32,7 +32,7 @@
typename MyShmCont::iterator itshm(shmcont->begin()), itshmend(shmcont->end());
typename MyStdCont::iterator itstd(stdcont->begin());
- if((typename MyShmCont::size_type)std::distance(itshm, itshmend) != shmcont->size()){
+ if((typename MyStdCont::size_type)std::distance(itshm, itshmend) != shmcont->size()){
return false;
}
for(; itshm != itshmend; ++itshm, ++itstd){
Deleted: branches/bcbboost/libs/interprocess/test/get_compiler_name.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/get_compiler_name.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,48 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztanaga 2004-2007. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_GET_COMPILER_NAME_HPP
-#define BOOST_GET_COMPILER_NAME_HPP
-
-#include <boost/config.hpp>
-#include <string>
-#include <algorithm>
-
-namespace boost{
-namespace interprocess{
-namespace test{
-
-inline void get_compiler_name(std::string &str)
-{
- str = BOOST_COMPILER;
- std::replace(str.begin(), str.end(), ' ', '_');
- std::replace(str.begin(), str.end(), '.', '_');
-}
-
-inline const char *get_compiler_name()
-{
- static std::string str;
- get_compiler_name(str);
- return str.c_str();
-}
-
-inline const char *add_to_compiler_name(const char *name)
-{
- static std::string str;
- get_compiler_name(str);
- str += name;
- return str.c_str();
-}
-
-} //namespace test{
-} //namespace interprocess{
-} //namespace boost{
-
-#endif //#ifndef BOOST_GET_COMPILER_NAME_HPP
Modified: branches/bcbboost/libs/interprocess/test/memory_algorithm_test_template.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/memory_algorithm_test_template.hpp (original)
+++ branches/bcbboost/libs/interprocess/test/memory_algorithm_test_template.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -20,77 +20,64 @@
namespace boost { namespace interprocess { namespace test {
+enum deallocation_type { DirectDeallocation, InverseDeallocation, MixedDeallocation, EndDeallocationType };
+
//This test allocates until there is no more memory
//and after that deallocates all in the inverse order
template<class Allocator>
-bool test_allocation_inverse_deallocation(Allocator &a)
+bool test_allocation(Allocator &a)
{
- std::vector<void*> buffers;
-
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
- break;
- buffers.push_back(ptr);
- }
-
- for(int j = (int)buffers.size()
- ;j--
- ;){
- a.deallocate(buffers[j]);
- }
-
- return a.all_memory_deallocated() && a.check_sanity();
-}
+ for( deallocation_type t = DirectDeallocation
+ ; t != EndDeallocationType
+ ; t = (deallocation_type)((int)t + 1)){
+ std::vector<void*> buffers;
+ std::size_t free_memory = a.get_free_memory();
-//This test allocates until there is no more memory
-//and after that deallocates all in the same order
-template<class Allocator>
-bool test_allocation_direct_deallocation(Allocator &a)
-{
- std::vector<void*> buffers;
- std::size_t free_memory = a.get_free_memory();
+ for(int i = 0; true; ++i){
+ void *ptr = a.allocate(i, std::nothrow);
+ if(!ptr)
+ break;
+ buffers.push_back(ptr);
+ }
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
+ switch(t){
+ case DirectDeallocation:
+ {
+ for(int j = 0, max = (int)buffers.size()
+ ;j < max
+ ;++j){
+ a.deallocate(buffers[j]);
+ }
+ }
break;
- buffers.push_back(ptr);
- }
-
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- a.deallocate(buffers[j]);
- }
-
- return free_memory == a.get_free_memory() &&
- a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates until there is no more memory
-//and after that deallocates all following a pattern
-template<class Allocator>
-bool test_allocation_mixed_deallocation(Allocator &a)
-{
- std::vector<void*> buffers;
-
- for(int i = 0; true; ++i){
- void *ptr = a.allocate(i, std::nothrow);
- if(!ptr)
+ case InverseDeallocation:
+ {
+ for(int j = (int)buffers.size()
+ ;j--
+ ;){
+ a.deallocate(buffers[j]);
+ }
+ }
break;
- buffers.push_back(ptr);
- }
-
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
+ case MixedDeallocation:
+ {
+ for(int j = 0, max = (int)buffers.size()
+ ;j < max
+ ;++j){
+ int pos = (j%4)*((int)buffers.size())/4;
+ a.deallocate(buffers[pos]);
+ buffers.erase(buffers.begin()+pos);
+ }
+ }
+ break;
+ default:
+ break;
+ }
+ bool ok = free_memory == a.get_free_memory() &&
+ a.all_memory_deallocated() && a.check_sanity();
+ if(!ok) return ok;
}
-
- return a.all_memory_deallocated() && a.check_sanity();
+ return true;
}
//This test allocates until there is no more memory
@@ -524,98 +511,106 @@
//This test allocates multiple values until there is no more memory
//and after that deallocates all in the inverse order
template<class Allocator>
-bool test_many_equal_allocation_inverse_deallocation(Allocator &a)
+bool test_many_equal_allocation(Allocator &a)
{
typedef typename Allocator::multiallocation_iterator multiallocation_iterator;
+ for( deallocation_type t = DirectDeallocation
+ ; t != EndDeallocationType
+ ; t = (deallocation_type)((int)t + 1)){
+ std::size_t free_memory = a.get_free_memory();
- std::vector<void*> buffers;
- for(int i = 0; true; ++i){
- std::size_t received_size;
- multiallocation_iterator it = a.allocate_many(i+1, i+1, (i+1)*2, received_size, std::nothrow);
- if(!it)
- break;
- multiallocation_iterator itend;
+ std::vector<void*> buffers2;
- for(; it != itend; ++it){
- buffers.push_back(*it);
+ //Allocate buffers with extra memory
+ for(int i = 0; true; ++i){
+ void *ptr = a.allocate(i, std::nothrow);
+ if(!ptr)
+ break;
+ buffers2.push_back(ptr);
}
- }
- for(int j = (int)buffers.size()
- ;j--
- ;){
- a.deallocate(buffers[j]);
- }
+ //Now deallocate the half of the blocks
+ //so expand maybe can merge new free blocks
+ for(int i = 0, max = (int)buffers2.size()
+ ;i < max
+ ;++i){
+ if(i%2){
+ a.deallocate(buffers2[i]);
+ buffers2[i] = 0;
+ }
+ }
- return a.all_memory_deallocated() && a.check_sanity();
-}
+ std::vector<void*> buffers;
+ for(int i = 0; true; ++i){
+ multiallocation_iterator it = a.allocate_many(i+1, (i+1)*2, std::nothrow);
+ if(!it)
+ break;
+ multiallocation_iterator itend;
-//This test allocates multiple values until there is no more memory
-//and after that deallocates all in the same order
-template<class Allocator>
-bool test_many_equal_allocation_direct_deallocation(Allocator &a)
-{
- typedef typename Allocator::multiallocation_iterator multiallocation_iterator;
- std::vector<void*> buffers;
- std::size_t free_memory = a.get_free_memory();
+ std::size_t n = 0;
+ for(; it != itend; ++n){
+ buffers.push_back(*it++);
+ }
+ if(n != std::size_t((i+1)*2))
+ return false;
+ }
- for(int i = 0; true; ++i){
- std::size_t received_size;
- multiallocation_iterator it = a.allocate_many(i+1, i+1, (i+1)*2, received_size, std::nothrow);
- if(!it)
+ switch(t){
+ case DirectDeallocation:
+ {
+ for(int j = 0, max = (int)buffers.size()
+ ;j < max
+ ;++j){
+ a.deallocate(buffers[j]);
+ }
+ }
+ break;
+ case InverseDeallocation:
+ {
+ for(int j = (int)buffers.size()
+ ;j--
+ ;){
+ a.deallocate(buffers[j]);
+ }
+ }
+ break;
+ case MixedDeallocation:
+ {
+ for(int j = 0, max = (int)buffers.size()
+ ;j < max
+ ;++j){
+ int pos = (j%4)*((int)buffers.size())/4;
+ a.deallocate(buffers[pos]);
+ buffers.erase(buffers.begin()+pos);
+ }
+ }
+ break;
+ default:
break;
- multiallocation_iterator itend;
-
- for(; it != itend; ++it){
- buffers.push_back(*it);
}
- }
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- a.deallocate(buffers[j]);
- }
-
- return free_memory == a.get_free_memory() &&
- a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates multiple values until there is no more memory
-//and after that deallocates all following a pattern
-template<class Allocator>
-bool test_many_equal_allocation_mixed_deallocation(Allocator &a)
-{
- typedef typename Allocator::multiallocation_iterator multiallocation_iterator;
- std::vector<void*> buffers;
-
- for(int i = 0; true; ++i){
- std::size_t received_size;
- multiallocation_iterator it = a.allocate_many(i+1, i+1, (i+1)*2, received_size, std::nothrow);
- if(!it)
- break;
- multiallocation_iterator itend;
+ //Deallocate the rest of the blocks
- for(; it != itend; ++it){
- buffers.push_back(*it);
+ //Deallocate it in non sequential order
+ for(int j = 0, max = (int)buffers2.size()
+ ;j < max
+ ;++j){
+ int pos = (j%4)*((int)buffers2.size())/4;
+ a.deallocate(buffers2[pos]);
+ buffers2.erase(buffers2.begin()+pos);
}
- }
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
+ bool ok = free_memory == a.get_free_memory() &&
+ a.all_memory_deallocated() && a.check_sanity();
+ if(!ok) return ok;
}
-
- return a.all_memory_deallocated() && a.check_sanity();
+ return true;
}
//This test allocates multiple values until there is no more memory
//and after that deallocates all in the inverse order
template<class Allocator>
-bool test_many_different_allocation_inverse_deallocation(Allocator &a)
+bool test_many_different_allocation(Allocator &a)
{
typedef typename Allocator::multiallocation_iterator multiallocation_iterator;
const std::size_t ArraySize = 11;
@@ -624,178 +619,125 @@
requested_sizes[i] = 4*i;
}
- std::vector<void*> buffers;
- for(int i = 0; true; ++i){
- multiallocation_iterator it = a.allocate_many(requested_sizes, ArraySize, 1, std::nothrow);
- if(!it)
- break;
- multiallocation_iterator itend;
+ for( deallocation_type t = DirectDeallocation
+ ; t != EndDeallocationType
+ ; t = (deallocation_type)((int)t + 1)){
+ std::size_t free_memory = a.get_free_memory();
- for(; it != itend; ++it){
- buffers.push_back(*it);
- }
- }
+ std::vector<void*> buffers2;
- for(int j = (int)buffers.size()
- ;j--
- ;){
- a.deallocate(buffers[j]);
- }
+ //Allocate buffers with extra memory
+ for(int i = 0; true; ++i){
+ void *ptr = a.allocate(i, std::nothrow);
+ if(!ptr)
+ break;
+ buffers2.push_back(ptr);
+ }
- return a.all_memory_deallocated() && a.check_sanity();
-}
+ //Now deallocate the half of the blocks
+ //so expand maybe can merge new free blocks
+ for(int i = 0, max = (int)buffers2.size()
+ ;i < max
+ ;++i){
+ if(i%2){
+ a.deallocate(buffers2[i]);
+ buffers2[i] = 0;
+ }
+ }
-//This test allocates multiple values until there is no more memory
-//and after that deallocates all in the same order
-template<class Allocator>
-bool test_many_different_allocation_direct_deallocation(Allocator &a)
-{
- std::size_t free_memory = a.get_free_memory();
- typedef typename Allocator::multiallocation_iterator multiallocation_iterator;
- const std::size_t ArraySize = 11;
- std::size_t requested_sizes[ArraySize];
- for(std::size_t i = 0; i < ArraySize; ++i){
- requested_sizes[i] = 4*i;
- }
+ std::vector<void*> buffers;
+ for(int i = 0; true; ++i){
+ multiallocation_iterator it = a.allocate_many(requested_sizes, ArraySize, 1, std::nothrow);
+ if(!it)
+ break;
+ multiallocation_iterator itend;
+ std::size_t n = 0;
+ for(; it != itend; ++n){
+ buffers.push_back(*it++);
+ }
+ if(n != ArraySize)
+ return false;
+ }
- std::vector<void*> buffers;
- for(int i = 0; true; ++i){
- multiallocation_iterator it = a.allocate_many(requested_sizes, ArraySize, 1, std::nothrow);
- if(!it)
+ switch(t){
+ case DirectDeallocation:
+ {
+ for(int j = 0, max = (int)buffers.size()
+ ;j < max
+ ;++j){
+ a.deallocate(buffers[j]);
+ }
+ }
+ break;
+ case InverseDeallocation:
+ {
+ for(int j = (int)buffers.size()
+ ;j--
+ ;){
+ a.deallocate(buffers[j]);
+ }
+ }
+ break;
+ case MixedDeallocation:
+ {
+ for(int j = 0, max = (int)buffers.size()
+ ;j < max
+ ;++j){
+ int pos = (j%4)*((int)buffers.size())/4;
+ a.deallocate(buffers[pos]);
+ buffers.erase(buffers.begin()+pos);
+ }
+ }
+ break;
+ default:
break;
- multiallocation_iterator itend;
-
- for(; it != itend; ++it){
- buffers.push_back(*it);
}
- }
-
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- a.deallocate(buffers[j]);
- }
-
- return free_memory == a.get_free_memory() &&
- a.all_memory_deallocated() && a.check_sanity();
-}
-
-//This test allocates multiple values until there is no more memory
-//and after that deallocates all following a pattern
-template<class Allocator>
-bool test_many_different_allocation_mixed_deallocation(Allocator &a)
-{
- typedef typename Allocator::multiallocation_iterator multiallocation_iterator;
- const std::size_t ArraySize = 11;
- std::size_t requested_sizes[ArraySize];
- for(std::size_t i = 0; i < ArraySize; ++i){
- requested_sizes[i] = 4*i;
- }
- std::vector<void*> buffers;
- for(int i = 0; true; ++i){
- multiallocation_iterator it = a.allocate_many(requested_sizes, ArraySize, 1, std::nothrow);
- if(!it)
- break;
- multiallocation_iterator itend;
+ //Deallocate the rest of the blocks
- for(; it != itend; ++it){
- buffers.push_back(*it);
+ //Deallocate it in non sequential order
+ for(int j = 0, max = (int)buffers2.size()
+ ;j < max
+ ;++j){
+ int pos = (j%4)*((int)buffers2.size())/4;
+ a.deallocate(buffers2[pos]);
+ buffers2.erase(buffers2.begin()+pos);
}
- }
- for(int j = 0, max = (int)buffers.size()
- ;j < max
- ;++j){
- int pos = (j%4)*((int)buffers.size())/4;
- a.deallocate(buffers[pos]);
- buffers.erase(buffers.begin()+pos);
+ bool ok = free_memory == a.get_free_memory() &&
+ a.all_memory_deallocated() && a.check_sanity();
+ if(!ok) return ok;
}
-
- return a.all_memory_deallocated() && a.check_sanity();
+ return true;
}
//This function calls all tests
template<class Allocator>
bool test_all_allocation(Allocator &a)
{
- std::cout << "Starting test_allocation_direct_deallocation. Class: "
+ std::cout << "Starting test_allocation. Class: "
<< typeid(a).name() << std::endl;
- if(!test_allocation_direct_deallocation(a)){
+ if(!test_allocation(a)){
std::cout << "test_allocation_direct_deallocation failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
- std::cout << "Starting test_allocation_inverse_deallocation. Class: "
+ std::cout << "Starting test_many_equal_allocation. Class: "
<< typeid(a).name() << std::endl;
- if(!test_allocation_inverse_deallocation(a)){
- std::cout << "test_allocation_inverse_deallocation failed. Class: "
+ if(!test_many_equal_allocation(a)){
+ std::cout << "test_many_equal_allocation failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
- std::cout << "Starting test_allocation_mixed_deallocation. Class: "
+ std::cout << "Starting test_many_different_allocation. Class: "
<< typeid(a).name() << std::endl;
- if(!test_allocation_mixed_deallocation(a)){
- std::cout << "test_allocation_mixed_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_many_equal_allocation_direct_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_many_equal_allocation_direct_deallocation(a)){
- std::cout << "test_many_equal_allocation_direct_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_many_equal_allocation_inverse_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_many_equal_allocation_inverse_deallocation(a)){
- std::cout << "test_many_equal_allocation_inverse_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_many_equal_allocation_mixed_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_many_equal_allocation_mixed_deallocation(a)){
- std::cout << "test_many_equal_allocation_mixed_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_many_different_allocation_direct_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_many_different_allocation_direct_deallocation(a)){
- std::cout << "test_many_different_allocation_direct_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_many_different_allocation_inverse_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_many_different_allocation_inverse_deallocation(a)){
- std::cout << "test_many_different_allocation_inverse_deallocation failed. Class: "
- << typeid(a).name() << std::endl;
- return false;
- }
-
- std::cout << "Starting test_many_different_allocation_mixed_deallocation. Class: "
- << typeid(a).name() << std::endl;
-
- if(!test_many_different_allocation_mixed_deallocation(a)){
- std::cout << "test_many_different_allocation_mixed_deallocation failed. Class: "
+ if(!test_many_different_allocation(a)){
+ std::cout << "test_many_different_allocation failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
@@ -824,30 +766,45 @@
return false;
}
+ std::cout << "Starting test_allocation_deallocation_expand. Class: "
+ << typeid(a).name() << std::endl;
+
if(!test_allocation_deallocation_expand(a)){
std::cout << "test_allocation_deallocation_expand failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
+ std::cout << "Starting test_allocation_with_reuse. Class: "
+ << typeid(a).name() << std::endl;
+
if(!test_allocation_with_reuse(a)){
std::cout << "test_allocation_with_reuse failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
+ std::cout << "Starting test_aligned_allocation. Class: "
+ << typeid(a).name() << std::endl;
+
if(!test_aligned_allocation(a)){
std::cout << "test_aligned_allocation failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
+ std::cout << "Starting test_continuous_aligned_allocation. Class: "
+ << typeid(a).name() << std::endl;
+
if(!test_continuous_aligned_allocation(a)){
std::cout << "test_continuous_aligned_allocation failed. Class: "
<< typeid(a).name() << std::endl;
return false;
}
+ std::cout << "Starting test_clear_free_memory. Class: "
+ << typeid(a).name() << std::endl;
+
if(!test_clear_free_memory(a)){
std::cout << "test_clear_free_memory failed. Class: "
<< typeid(a).name() << std::endl;
Modified: branches/bcbboost/libs/interprocess/test/node_pool_test.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/node_pool_test.cpp (original)
+++ branches/bcbboost/libs/interprocess/test/node_pool_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -7,7 +7,6 @@
// See http://www.boost.org/libs/interprocess for documentation.
//
//////////////////////////////////////////////////////////////////////////////
-/*
#include <boost/interprocess/detail/config_begin.hpp>
#include <boost/interprocess/managed_shared_memory.hpp>
#include <boost/interprocess/allocators/detail/node_pool.hpp>
@@ -165,13 +164,3 @@
}
#include <boost/interprocess/detail/config_end.hpp>
-*/
-
-#include<stdlib.h>
-
-int main()
-{
- void *addr = malloc(100);
- free(addr);
- return 0;
-}
\ No newline at end of file
Deleted: branches/bcbboost/libs/interprocess/test/printcontainer.hpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/printcontainer.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
+++ (empty file)
@@ -1,45 +0,0 @@
-//////////////////////////////////////////////////////////////////////////////
-//
-// (C) Copyright Ion Gaztañaga 2004-2006. 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)
-//
-// See http://www.boost.org/libs/interprocess for documentation.
-//
-//////////////////////////////////////////////////////////////////////////////
-
-#ifndef BOOST_PRINTCONTAINER_HPP
-#define BOOST_PRINTCONTAINER_HPP
-
-#include <functional>
-#include <iostream>
-#include <algorithm>
-#include <boost/interprocess/detail/config_begin.hpp>
-
-namespace boost{
-namespace interprocess{
-namespace test{
-
-struct PrintValues : public std::unary_function<int, void>
-{
- void operator() (int value) const
- {
- std::cout << value << " ";
- }
-};
-
-template<class Container>
-void PrintContents(const Container &cont, const char *contName)
-{
- std::cout<< "Printing contents of " << contName << std::endl;
- std::for_each(cont.begin(), cont.end(), PrintValues());
- std::cout<< std::endl << std::endl;
-}
-
-} //namespace test{
-} //namespace interprocess{
-} //namespace boost{
-
-#include <boost/interprocess/detail/config_end.hpp>
-
-#endif //#ifndef BOOST_PRINTCONTAINER_HPP
Modified: branches/bcbboost/libs/interprocess/test/shared_ptr_test.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/shared_ptr_test.cpp (original)
+++ branches/bcbboost/libs/interprocess/test/shared_ptr_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -19,7 +19,6 @@
#include <boost/interprocess/allocators/allocator.hpp>
#include <boost/interprocess/containers/string.hpp>
#include <boost/interprocess/containers/vector.hpp>
-#include <boost/interprocess/detail/utilities.hpp>
#include <boost/interprocess/smart_ptr/deleter.hpp>
#include <boost/interprocess/smart_ptr/scoped_ptr.hpp>
#include <boost/detail/lightweight_test.hpp>
Modified: branches/bcbboost/libs/interprocess/test/unique_ptr_test.cpp
==============================================================================
--- branches/bcbboost/libs/interprocess/test/unique_ptr_test.cpp (original)
+++ branches/bcbboost/libs/interprocess/test/unique_ptr_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -31,8 +31,7 @@
{}
};
-typedef deleter<MyClass, managed_shared_memory::segment_manager> my_deleter_type;
-typedef unique_ptr<MyClass, my_deleter_type> my_unique_ptr_class;
+typedef managed_unique_ptr<MyClass, managed_shared_memory>::type my_unique_ptr_class;
typedef set <my_unique_ptr_class
,std::less<my_unique_ptr_class>
,allocator <my_unique_ptr_class
@@ -58,19 +57,19 @@
shared_memory_object::remove(process_name.c_str());
{
managed_shared_memory segment(create_only, process_name.c_str(), 10000);
- my_deleter_type my_deleter(segment.get_segment_manager());
+
//Create unique_ptr using dynamic allocation
my_unique_ptr_class my_ptr (segment.construct<MyClass>(anonymous_instance)()
- ,my_deleter);
+ ,segment.get_deleter<MyClass>());
my_unique_ptr_class my_ptr2(segment.construct<MyClass>(anonymous_instance)()
- ,my_deleter);
+ ,segment.get_deleter<MyClass>());
//Backup relative pointers to future tests
offset_ptr<MyClass> ptr1 = my_ptr.get();
offset_ptr<MyClass> ptr2 = my_ptr2.get();
//Test some copy constructors
- my_unique_ptr_class my_ptr3(0, my_deleter);
+ my_unique_ptr_class my_ptr3(0, segment.get_deleter<MyClass>());
my_unique_ptr_class my_ptr4(move(my_ptr3));
//Construct a list and fill
@@ -141,7 +140,7 @@
assert(vector.begin()->get() == ptr1);
assert(vector.rbegin()->get() == ptr2);
- my_unique_ptr_class a(0, my_deleter), b(0, my_deleter);
+ my_unique_ptr_class a(0, segment.get_deleter<MyClass>()), b(0, segment.get_deleter<MyClass>());
a = move(b);
}
shared_memory_object::remove(process_name.c_str());
Modified: branches/bcbboost/libs/intrusive/doc/Jamfile.v2
==============================================================================
--- branches/bcbboost/libs/intrusive/doc/Jamfile.v2 (original)
+++ branches/bcbboost/libs/intrusive/doc/Jamfile.v2 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -16,12 +16,24 @@
[ glob ../../../boost/intrusive/*.hpp ]
:
<doxygen:param>HIDE_UNDOC_MEMBERS=YES
+ <doxygen:param>HIDE_UNDOC_MEMBERS=YES
<doxygen:param>HIDE_UNDOC_CLASSES=YES
<doxygen:param>EXTRACT_PRIVATE=NO
<doxygen:param>ENABLE_PREPROCESSING=YES
<doxygen:param>MACRO_EXPANSION=YES
- <doxygen:param>EXPAND_ONLY_PREDEF=YES
- <doxygen:param>SEARCH_INCLUDES=YES
+# <doxygen:param>EXPAND_ONLY_PREDEF=YES
+# <doxygen:param>SEARCH_INCLUDES=YES
+# <doxygen:param>INCLUDE_PATH=$(BOOST_ROOT)
+ <doxygen:param>"PREDEFINED=\"BOOST_INTRUSIVE_DOXYGEN_INVOKED\" \\
+ \"list_impl=list\" \\
+ \"slist_impl=slist\" \\
+ \"set_impl=set\" \\
+ \"multiset_impl=multiset\" \\
+ \"rbtree_impl=rbtree\" \\
+ \"unordered_set_impl=unordered_set\" \\
+ \"unordered_multiset_impl=unordered_multiset\" \\
+ \"hashtable_impl=hashtable\" \\
+ "
;
xml intrusive : intrusive.qbk ;
Modified: branches/bcbboost/libs/intrusive/doc/intrusive.qbk
==============================================================================
--- branches/bcbboost/libs/intrusive/doc/intrusive.qbk (original)
+++ branches/bcbboost/libs/intrusive/doc/intrusive.qbk 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -230,7 +230,7 @@
[section:usage How to use Boost.Intrusive]
-If you plan to use a class in an intrusive container, you have to make some decisions
+If you plan to insert a class in an intrusive container, you have to make some decisions
influencing the class definition itself. Each class that will be used in an intrusive
container needs some appropriate data members storing the information needed by the
container. We will take a simple intrusive container, like an intrusive list
@@ -251,29 +251,37 @@
[section:usage_base_hook Using base hooks]
For [classref boost::intrusive::list list], you can publicly derive from
-[classref boost::intrusive::list_base_hook list_base_hook]. This class takes
-three template arguments:
+[classref boost::intrusive::list_base_hook list_base_hook].
[c++]
- template < class Tag = tag
- , linking_policy Policy = safe_link
- , class VoidPointer = void *>
+ template <class ...Options>
class list_base_hook;
-* The first template argument serves as a tag, so you can derive from more than one
+The class can take several options. [*Boost.Intrusive] classes receive arguments in the
+form `option_name<option_value>`. You can specify the following options:
+
+* [*`tag<class Tag>`]: this argument serves as a tag, so you can derive from more than one
[classref boost::intrusive::list_base_hook list_base_hook] and hence put an object in
multiple intrusive lists at the same time. An incomplete type can serve as a tag.
+ If you specify two base hooks, you [*must] specify a different
+ tag for each one. Example: `list_base_hook< tag<tag1> >`. If no tag is specified
+ a default one will be used (more on default tags later).
+
+* [*`link_mode<link_mode_type LinkMode>`]: The second template argument controls the
+ linking policy. [*Boost.Intrusive] currently supports
+ 3 modes: `normal_link`, `safe_link` and `auto_unlink`. By default, `safe_link`
+ mode is used. More about these in sections
+ [link intrusive.safe_hook Safe hooks] and [link intrusive.auto_unlink_hooks Auto-unlink hooks].
+ Example: `list_base_hook< link_mode<auto_unlink> >`
+
+* [*`void_pointer<class VoidPointer>`]: this option is the pointer type to be used
+ internally in the hook. The default value is `void *`, which means that raw pointers
+ will be used in the hook. More about this in the section titled
+ [link intrusive.using_smart_pointers Using smart pointers with Boost.Intrusive containers].
+ Example: `list_base_hook< void_pointer< my_smart_ptr<void> >`
-* The second template argument controls the linking policy. [*Boost.Intrusive] currently supports
- 3 policies: `normal_link`, `safe_link`, `auto_unlink`. More about these in the sections
- [link intrusive.safe_hook Safe hooks] and [link intrusive.auto_unlink_hooks Auto-unlink hooks]
-
-* The third template argument is the pointer type to be used internally in the hook.
- The default value is `void *`, which means that raw pointers will be used in the hook.
- More about this in the section titled [link intrusive.using_smart_pointers Using smart pointers with Boost.Intrusive containers]
-
-Example:
+For the following examples, let's forget the options and use the default values:
[c++]
@@ -281,56 +289,78 @@
using namespace boost::intrusive;
- class Foo : public list_base_hook<>
+ class Foo
+ //Base hook with default tag, raw pointers and safe_link mode
+ : public list_base_hook<>
{ /**/ };
-Once we derive our class from `list_base_hook<>` we have to obtain the `ValueTraits`
-information to configure the intrusive list. `ValueTraits` tell the container
-the needed information to insert the object in the container (if the hook is
-a base or member object, whether is an auto-unlink hook...
-To obtain the needed value traits, just use the `value_traits` subtype
-[classref boost::intrusive::list_base_hook list_base_hook]
-defines passing the type of the user class as an argument:
+After that, we can define the intrusive list:
[c++]
- typedef list_base_hook<>::value_traits<Foo>
- FooValueTraits;
-
-After that, we can define the intrusive list. The intrusive list has the following
-template parameters:
-
-[c++]
-
- template < class ValueTraits
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t>
+ template <class T, class ...Options>
class list;
-* The first template argument is the value traits class. Contains information about the value
- to be inserted: the type, the type of hook, the type of the pointers to be used,
- whether the safe mode is being used...
-
-* The second boolean template argument specifies if a constant time `size()`
- function is demanded. This will tell the intrusive container to insert an
- additional member in the intrusive container that offers this information.
+`list` receives the type to be inserted in the container (`T`) as the first parameter
+and optionally, the user can specify options. We have 3 option types:
-* The third template argument specifies the type that will hold
+* [*`base_hook<class Hook>`] / [*`member_hook<class T, class Hook, Hook T::* PtrToMember>`] /
+ [*`value_traits<class ValueTraits>`]: All these options specify the relationship
+ between the type `T` to be inserted in the list and the hook (since we can
+ have several hooks in the same `T` type). `member_hook` will be explained
+ a bit later and `value_traits` will be explained in the
+ [link intrusive.value_traits Containers with custom ValueTraits] section.
+ [*If no option is specified, the container will be configured to use the base
+ hook with the default tag].
+ Some options configured for the hook (the type of the pointers, link mode...)
+ will be propagated to the container.
+
+* [*`constant_time_size<bool Enabled>`]: Specifies if a constant time `size()`
+ function is demanded for the container. This will instruct the intrusive
+ container to store an additional member to keep track of the current size of the
+ container. By default, contant-time size is activated.
+
+* [*`size_type<bool Enabled>`]: Specifies a type that can hold
the size of the container. This type will be the type returned by `list.size()`
- and the type stored in the intrusive container if `ConstantTimeSize` is requested.
+ and the type stored in the intrusive container if `constant_time_size<true>`
+ is requested.
The user normally will not need to change this type, but some
- containers can have a `size_type` that might be different from std::size_t
+ containers can have a `size_type` that might be different from `std::size_t`
(for example, STL-like containers, use the `size_type` defined by their allocator).
[*Boost.Intrusive] can be used to implement such containers specifying the
- `SizeType` type.
+ the type of the size. By default the type is `std::size_t`.
-Example of a constant-time size intrusive list that will store Foo objects:
+Example of a constant-time size intrusive list that will store Foo objects, using
+the base hook with the default tag:
[c++]
- typedef list<FooValueTraits> FooList;
+ typedef list<Foo> FooList;
+
+Example of a intrusive list with non constant-time size that will store Foo objects:
+
+[c++]
+
+ typedef list<Foo, constant_time_size<false> > FooList;
+
+Remember that the user must specify the base hook if the base hook has no default tag
+(e.g: if more than one base hook is used):
+
+[c++]
+
+ #include <boost/intrusive/list.hpp>
+
+ using namespace boost::intrusive;
+
+ struct my_tag;
+
+ typedef list_base_hook< tag<my_tag> > BaseHook;
+ class Foo : public BaseHook
+ { /**/ };
-Now we can just use the container:
+ typedef list< Foo, base_hook<BaseHook> > FooList;
+
+Once the list is defined, we can use it:
[c++]
@@ -350,12 +380,12 @@
is not desirable. In this case, using a member hook as a data member instead of
'disturbing' the hierarchy might be the right way: you can add a public data
member `list_member_hook<...>` to your class.
-This class takes two template parameters:
+This class can be configured with the same options as `list_base_hook`
+except the option `tag`:
[c++]
- template < linking_policy Policy = safe_link
- , class VoidPointer = void *>
+ template <class ...Options>
class list_member_hook;
Example:
@@ -367,24 +397,22 @@
class Foo
{
public:
- list_member_hook<> m_hook_;
+ list_member_hook<> hook_;
//...
};
-To obtain the `ValueTraits` information to configure the list, use the internal
-templatized `value_traits` type and pass the class to be inserted and a pointer
-to the member hook as template parameters.
+When member hooks are used, the `member_hook` option is used to configure the
+list:
[c++]
- //Obtain ValueTraits to configure the list
- typedef list_member_hook<>::value_traits
- <Foo, &Foo::m_hook_> FooValueTraits;
+ //This option will configure "list" to use the member hook
+ typedef member_hook<Foo, list_member_hook<>, &Foo::hook_> MemberHookOption;
//This list will use the member hook
- typedef list<FooValueTraits> FooList;
+ typedef list<Foo, MemberHookOption> FooList;
-Now we can just use the container:
+Now we can use the container:
[c++]
@@ -401,7 +429,7 @@
[section:usage_both_hooks Using both hooks]
You can insert the same object in several intrusive containers at the same time, just
-using one hook for each containers. This is a full example using base and member hooks:
+using one hook for each container. This is a full example using base and member hooks:
[import ../example/doc_how_to_use.cpp]
[doc_how_to_use_code]
@@ -415,10 +443,10 @@
you directly store objects in intrusive containers, not copies. The lifetime of a
stored object is not bound to or managed by the container:
-* When the container gets disposed before the object, the object is not disposed,
+* When the container gets destroyed before the object, the object is not destroyed,
so you have to be careful to avoid resource leaks.
-* When the object is disposed before the container, your program is likely to crash,
+* When the object is destroyed before the container, your program is likely to crash,
because the container contains a pointer to an non-existing object.
[endsect]
@@ -561,15 +589,16 @@
[section:features Features of the safe mode]
[*Boost.Intrusive] hooks can be configured to operate in safe-link mode.
-The safe mode is activated by default:
+The safe mode is activated by default, but it can be also explicitly activated:
[c++]
- template <class Tag = tag, linking_policy Policy = safe_link, class VoidPointer = void *>
- class list_base_hook;
+ //Configuring explicity the safe mode
+ class Foo : public list_base_hook< link_mode<safe_link> >
+ {};
Thanks to the safe-mode the user can detect without any external reference, if the object
-is actually inserted in any container. Let's review the basic features of the safe-mode:
+is actually inserted in a container. Let's review the basic features of the safe-mode:
* Hooks' constructor puts the hook in a well-known default state.
@@ -577,7 +606,7 @@
an assertion is raised.
* Every time an object is being inserted in the intrusive container, the container
- checks if the hook is the well-known default state. If not,
+ checks if the hook is in the well-known default state. If not,
an assertion is raised.
* Every time an object is being erased from the intrusive container, the container
@@ -586,7 +615,7 @@
With these features, without any external reference the user can know if the object
has been inserted in a container calling the `is_linked()` member function.
If the object is not actually inserted
-in a container, the hook is the default state and if it's inserted in a container, the
+in a container, the hook is in the default state and if it's inserted in a container, the
hook is not in the default state.
[endsect]
@@ -598,7 +627,7 @@
the user. See [@http://www.boost.org/libs/utility/assert.html] for more
information about `BOOST_ASSERT`.
-`BOOST_ASSERT` is globally configured for all the libraries, so the user might
+`BOOST_ASSERT` is globally configured, so the user might
want to redefine intrusive safe-mode assertions without modifying the global
`BOOST_ASSERT`. This can be achieved redefining the following macros:
@@ -608,7 +637,7 @@
* `BOOST_INTRUSIVE_SAFE_HOOK_DESTRUCTOR_ASSERT`: This assertion will be
used in hooks' destructors to check that the hook is in a default state.
-If any of these macros is not redefined, it will be defaulted to `BOOST_ASSERT`.
+If any of these macros is not redefined, the assertion will be defaul to `BOOST_ASSERT`.
[endsect]
@@ -677,12 +706,14 @@
#include <boost/intrusive/list.hpp>
+ using boost::intrusive;
+
struct MyTag;
- class MyClass : public boost::intrusive::list_base_hook<tag, auto_unlink>
+ class MyClass : public list_base_hook< link_mode<auto_unlink> >
{/**/};
- boost::intrusive::list <MyClass::value_traits<MyClass>, true> bad_list;
+ list <MyClass, constant_time_size<true> > bad_list;
int main()
{
@@ -696,13 +727,12 @@
error : use of undefined type 'boost::STATIC_ASSERTION_FAILURE<false>'
]
-
Pointing to code like this:
[c++]
//Constant-time size is incompatible with auto-unlink hooks!
- BOOST_STATIC_ASSERT(!(ConstantTimeSize && ((int)ValueTraits::linking_policy == (int)auto_unlink)));
+ BOOST_STATIC_ASSERT(!(constant_time_size && ((int)value_traits::link_mode == (int)auto_unlink)));
This way, there is no way to compile a program if you try to use auto-unlink hooks
in constant-time size containers.
@@ -730,11 +760,12 @@
[section:slist_hooks slist hooks]
-Like the rest of [*Boost.Intrusive] containers, [classref boost::intrusive::slist slist] has two hook types:
+Like the rest of [*Boost.Intrusive] containers,
+[classref boost::intrusive::slist slist] has two hook types:
[c++]
- template <class Tag = tag, linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class slist_base_hook;
* [classref boost::intrusive::slist_base_hook slist_base_hook]:
@@ -744,7 +775,7 @@
[c++]
- template <linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class slist_member_hook;
* [classref boost::intrusive::slist_member_hook slist_member_hook]:
@@ -752,28 +783,43 @@
[classref boost::intrusive::slist_member_hook slist_member_hook] to make
it [classref boost::intrusive::slist slist]-compatible.
+[classref boost::intrusive::slist_base_hook slist_base_hook] and
+[classref boost::intrusive::slist_member_hook slist_member_hook] receive the same options explained in
+the section [link intrusive.usage How to use Boost.Intrusive]:
+
+* [*`tag<class Tag>`] (for base hooks only): This argument serves as a tag,
+ so you can derive from more than one list hook.
+ Default: `tag<default_tag>`.
+
+* [*`link_mode<link_mode_type LinkMode>`]: The linking policy.
+ Default: `link_mode<safe_link>`.
+
+* [*`void_pointer<class VoidPointer>`]: The pointer type to be used
+ internally in the hook and propagated to the container.
+ Default: `void_pointer<void*>`.
+
[endsect]
[section:slist_container slist container]
-[classref boost::intrusive::slist slist] receives 3 template parameters:
-
[c++]
- template<class ValueTraits, bool ConstantTimeSize = true, class SizeType = std::size_t>
+ template <class T, class ...Options>
class slist;
-* The first template is the value traits class. Contains information about the
- value to be inserted: the type, the type of hook, the type of the pointers to
- be used, whether the safe mode is being used...
-
-* The second boolean template argument specifies if a constant time `size()`
- function is demanded. This will tell the intrusive container to insert an
- additional member in the intrusive container that offers this information.
+[classref boost::intrusive::slist slist] receives the same options explained in
+the section [link intrusive.usage How to use Boost.Intrusive]:
-* The third template argument specifies the type that will hold
- the size of the container. This type will be the type returned by `list.size()`
- and the type stored in the intrusive container if `ConstantTimeSize` is requested.
+* [*`base_hook<class Hook>`] / [*`member_hook<class T, class Hook, Hook T::* PtrToMember>`] /
+ [*`value_traits<class ValueTraits>`]: To specify the hook type or value traits used
+ to configure the container (to know about value traits go to the section
+ titled [link intrusive.value_traits Containers with custom ValueTraits].
+
+* [*`constant_time_size<bool Enabled>`]: To activate the constant-time `size()` operation.
+ Default: `constant_time_size<true>`
+
+* [*`size_type<bool Enabled>`]: To specify the type that will be used to store the size
+ of the container. Default: `size_type<std::size_t>`
[endsect]
@@ -805,7 +851,7 @@
[c++]
- template <class Tag = tag, linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class list_base_hook;
* [classref boost::intrusive::list_base_hook list_base_hook]: the user class
@@ -814,7 +860,7 @@
[c++]
- template <linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class list_member_hook;
* [classref boost::intrusive::list_member_hook list_member_hook]:
@@ -822,28 +868,44 @@
[classref boost::intrusive::list_member_hook list_member_hook] to make
it [classref boost::intrusive::list list]-compatible.
+[classref boost::intrusive::list_base_hook list_base_hook] and
+[classref boost::intrusive::list_member_hook list_member_hook] receive
+the same options explained in the section
+[link intrusive.usage How to use Boost.Intrusive]:
+
+* [*`tag<class Tag>`] (for base hooks only): This argument serves as a tag,
+ so you can derive from more than one list hook.
+ Default: `tag<default_tag>`.
+
+* [*`link_mode<link_mode_type LinkMode>`]: The linking policy.
+ Default: `link_mode<safe_link>`.
+
+* [*`void_pointer<class VoidPointer>`]: The pointer type to be used
+ internally in the hook and propagated to the container.
+ Default: `void_pointer<void*>`.
+
[endsect]
[section:list_container list container]
-[classref boost::intrusive::list list] receives 3 template parameters:
-
[c++]
- template<class ValueTraits, bool ConstantTimeSize = true, class SizeType = std::size_t>
+ template <class T, class ...Options>
class list;
-* The first template is the value traits class. Contains information about the
- value to be inserted: the type, the type of hook, the type of the pointers to
- be used, whether the safe mode is being used...
-
-* The second boolean template argument specifies if a constant time `size()`
- function is demanded. This will tell the intrusive container to insert an
- additional member in the intrusive container that offers this information.
+[classref boost::intrusive::list list] receives the same options explained in
+the section [link intrusive.usage How to use Boost.Intrusive]:
-* The third template argument specifies the type that will hold
- the size of the container. This type will be the type returned by `list.size()`
- and the type stored in the intrusive container if `ConstantTimeSize` is requested.
+* [*`base_hook<class Hook>`] / [*`member_hook<class T, class Hook, Hook T::* PtrToMember>`] /
+ [*`value_traits<class ValueTraits>`]: To specify the hook type or value traits used
+ to configure the container (to know about value traits go to the section
+ titled [link intrusive.value_traits Containers with custom ValueTraits].
+
+* [*`constant_time_size<bool Enabled>`]: To activate the constant-time `size()` operation.
+ Default: `constant_time_size<true>`
+
+* [*`size_type<bool Enabled>`]: To specify the type that will be used to store the size
+ of the container. Default: `size_type<std::size_t>`
[endsect]
@@ -888,7 +950,7 @@
[c++]
- template <class Tag = tag, linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class set_base_hook;
* [classref boost::intrusive::set_base_hook set_base_hook]:
@@ -898,7 +960,7 @@
[c++]
- template <linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class set_member_hook;
* [classref boost::intrusive::set_member_hook set_member_hook]:
@@ -906,41 +968,53 @@
[classref boost::intrusive::set_member_hook set_member_hook] to make
it [classref boost::intrusive::set set]/[classref boost::intrusive::multiset multiset]-compatible.
+[classref boost::intrusive::set_base_hook set_base_hook] and
+[classref boost::intrusive::set_member_hook set_member_hook] receive
+the same options explained in the section
+[link intrusive.usage How to use Boost.Intrusive]:
+
+* [*`tag<class Tag>`] (for base hooks only): This argument serves as a tag,
+ so you can derive from more than one list hook.
+ Default: `tag<default_tag>`.
+
+* [*`link_mode<link_mode_type LinkMode>`]: The linking policy.
+ Default: `link_mode<safe_link>`.
+
+* [*`void_pointer<class VoidPointer>`]: The pointer type to be used
+ internally in the hook and propagated to the container.
+ Default: `void_pointer<void*>`.
+
[endsect]
[section:set_multiset_containers set and multiset containers]
-[classref boost::intrusive::set set] and
-[classref boost::intrusive::multiset multiset] receive 4 template parameters:
-
[c++]
- template < class ValueTraits
- , class Compare = std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t >
+ template <class T, class ...Options>
class set;
- template < class ValueTraits
- , class Compare = std::less<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t >
+ template <class T, class ...Options>
class multiset;
-* The first template is the value traits class. Contains information about the
- value to be inserted: the type, the type of hook, the type of the pointers to
- be used, whether the safe mode is being used...
-
-* The second template is the ordering function of the associative container.
- By default, the ordering function is `std::less<...>` of the user value.
-
-* The third boolean template argument specifies if a constant time `size()`
- function is demanded. This will tell the intrusive container to insert an
- additional member in the intrusive container that offers this information.
+[classref boost::intrusive::set set] and [classref boost::intrusive::multiset multiset]
+receive the same options explained in the section [link intrusive.usage How to use Boost.Intrusive]:
-* The fourth template argument specifies the type that will hold
- the size of the container. This type will be the type returned by `list.size()`
- and the type stored in the intrusive container if `ConstantTimeSize` is requested.
+* [*`base_hook<class Hook>`] / [*`member_hook<class T, class Hook, Hook T::* PtrToMember>`] /
+ [*`value_traits<class ValueTraits>`]: To specify the hook type or value traits used
+ to configure the container (to know about value traits go to the section
+ titled [link intrusive.value_traits Containers with custom ValueTraits].
+
+* [*`constant_time_size<bool Enabled>`]: To activate the constant-time `size()` operation.
+ Default: `constant_time_size<true>`
+
+* [*`size_type<bool Enabled>`]: To specify the type that will be used to store the size
+ of the container. Default: `size_type<std::size_t>`
+
+And they also can receive an additional option:
+
+* [*`compare<class Compare>`]: Comparison function for the objects to be inserted
+ in containers. The comparison functor must induce a strict weak ordering.
+ Default: `compare< std::less<T> >`
[endsect]
@@ -957,11 +1031,11 @@
[section:unordered_set_unordered_multiset Pseudo-Intrusive unordered associative containers: unordered_set, unordered_multiset]
-[*Boost.Intrusive] also offers hashed containers that can be very useful develop
-fast-lookup intrusive containers. These containers
+[*Boost.Intrusive] also offers hashed containers that can be very useful to implement
+fast-lookup containers. These containers
([classref boost::intrusive::unordered_set unordered_set] and [classref boost::intrusive::unordered_multiset unordered_multiset])
are pseudo-intrusive containers: they need additional memory apart from the hook
-that the value_type of the container must add as a base or member. This additional
+stored in the `value_type`. This additional
memory must be passed in the constructor of the container.
Unlike C++ TR1 unordered associative containers (which are also hashed containers),
@@ -969,48 +1043,16 @@
load factor: that would require memory management and intrusive containers don't
implement any memory management at all. However, the user can request an explicit
rehashing passing a new bucket array.
-
This also offers an additional guarantee over TR1 unordered associative containers:
[*iterators are not invalidated when inserting an element] in the container.
As with TR1 unordered associative containers, rehashing invalidates iterators,
-changes ordering between elements, and changes which buckets elements appear in,
+changes ordering between elements and changes which buckets elements appear in,
but does not invalidate pointers or references to elements.
-[*Boost.Intrusive] unordered associative containers need five arguments to be passed in
-their constructors: A pointer to an array of elements whose type is called `bucket_type`,
-the length of that array, the hash function to be used with the values and an
-equality functor for those values:
-
-[c++]
-
- template< class ValueTraits
- , class Hash = boost::hash<typename ValueTraits::value_type>
- , class Equal = std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
- class unordered_set
- {
- // ...
-
- typedef /*implementation defined*/ bucket_type;
- typedef /*implementation defined*/ bucket_ptr;
- typedef /*implementation defined*/ size_type;
-
- //Constructor
- unordered_set ( bucket_ptr buckets
- , size_type buckets_len
- , const Hash &hasher = Hash()
- , const Equal &equal = Equal()) ;
-
- // ...
- };
-
-Each hashed container needs [*its own bucket array]. Two hashed containers
-[*can't] share the same `bucket_type` elements. The bucket array [*must] be
-disposed [*after] the container using it is disposed, otherwise, the result
-is undefined.
+Apart from expected hash and equality function objects, [*Boost.Intrusive] unordered
+associative containers' constructors take an argument specifying an auxiliary
+bucket vector to be used by the container.
[section:unordered_set_unordered_multiset_performance unordered_set and unordered_multiset performance notes]
@@ -1044,7 +1086,7 @@
[c++]
- template <class Tag = tag, linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class unordered_set_base_hook;
* [classref boost::intrusive::unordered_set_base_hook unordered_set_base_hook]:
@@ -1054,7 +1096,7 @@
[c++]
- template <linking_policy Policy = safe_link, class VoidPointer = void*>
+ template <class ...Options>
class unordered_set_member_hook;
* [classref boost::intrusive::unordered_set_member_hook unordered_set_member_hook]:
@@ -1062,51 +1104,100 @@
[classref boost::intrusive::unordered_set_member_hook unordered_set_member_hook] to make
it [classref boost::intrusive::unordered_set unordered_set]/[classref boost::intrusive::unordered_multiset unordered_multiset]-compatible.
+[classref boost::intrusive::unordered_set_base_hook unordered_set_base_hook] and
+[classref boost::intrusive::unordered_set_member_hook unordered_set_member_hook] receive
+the same options explained in the section
+[link intrusive.usage How to use Boost.Intrusive]:
+
+* [*`tag<class Tag>`] (for base hooks only): This argument serves as a tag,
+ so you can derive from more than one list hook.
+ Default: `tag<default_tag>`.
+
+* [*`link_mode<link_mode_type LinkMode>`]: The linking policy.
+ Default: `link_mode<safe_link>`.
+
+* [*`void_pointer<class VoidPointer>`]: The pointer type to be used
+ internally in the hook and propagated to the container.
+ Default: `void_pointer<void*>`.
+
[endsect]
[section:unordered_set_unordered_multiset_containers unordered_set and unordered_multiset containers]
-[classref boost::intrusive::unordered_set unordered_set] and
-[classref boost::intrusive::unordered_multiset unordered_multiset] receive 5 template parameters:
-
[c++]
- template< class ValueTraits
- , class Hash = boost::hash<typename ValueTraits::value_type>
- , class Equal = std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
+ template<class T, class ...Options>
class unordered_set;
- template< class ValueTraits
- , class Hash = boost::hash<typename ValueTraits::value_type>
- , class Equal = std::equal_to<typename ValueTraits::value_type>
- , bool ConstantTimeSize = true
- , class SizeType = std::size_t
- >
+ template<class T, class ...Options>
class unordered_multiset;
-* The first template is the value traits class. Contains information about the
- value to be inserted: the type, the type of hook, the type of the pointers to
- be used, whether the safe mode is being used...
-
-* The second template is the hash function of the associative container.
- It takes a value_type argument and returns a std::size_t.
- By default, the hash function is `boost::hash<...>` of the user value.
-
-* The third template is the equality function of the associative container.
- By default, the equality function is `std::equal_to<...>` of the user value.
-
-* The fourth boolean template argument specifies if a constant time `size()`
- function is demanded. This will tell the intrusive container to insert an
- additional member in the intrusive container that offers this information.
- [*Be careful with non constant-time size() hashed containers] since they
- have a linear complexity `empty()` function.
+As mentioned, unordered containers need an auxiliary array to work. [*Boost.Intrusive]
+unordered containers receive this auxiliary array packed in a type called `bucket_traits`
+(which can be also customized by a container option). All unordered containers receive
+a `bucket_traits` object in their constructors. The default `bucket_traits` class
+is initialized with a pointer to an array of buckets and its size:
-* The fifth template argument specifies the type that will hold
- the size of the container. This type will be the type returned by `list.size()`
- and the type stored in the intrusive container if `ConstantTimeSize` is requested.
+[c++]
+
+ #include <boost/intrusive/unordered_set.hpp>
+
+ using namespace boost::intrusive;
+
+ struct MyClass : public unordered_set_base_hook<>
+ {};
+
+ typedef unordered_set<MyClass>::bucket_type bucket_type;
+ typedef unordered_set<MyClass>::bucket_traits bucket_traits;
+
+ int main()
+ {
+ bucket_type buckets[100];
+ unordered_set<MyClass> uset(bucket_traits(buckets, 100));
+ return 0;
+ }
+
+Each hashed container needs [*its own bucket traits], that is, [*its own
+bucket vector]. Two hashed containers
+[*can't] share the same `bucket_type` elements. The bucket array [*must] be
+destroyed [*after] the container using it is destroyed, otherwise, the result
+is undefined.
+
+[classref boost::intrusive::unordered_set unordered_set] and
+[classref boost::intrusive::unordered_multiset unordered_multiset]
+receive the same options explained in the section
+[link intrusive.usage How to use Boost.Intrusive]:
+
+* [*`base_hook<class Hook>`] / [*`member_hook<class T, class Hook, Hook T::* PtrToMember>`] /
+ [*`value_traits<class ValueTraits>`]: To specify the hook type or value traits used
+ to configure the container (to know about value traits go to the section
+ titled [link intrusive.value_traits Containers with custom ValueTraits].
+
+* [*`constant_time_size<bool Enabled>`]: To activate the constant-time `size()` operation.
+ Default: `constant_time_size<true>`
+
+* [*`size_type<bool Enabled>`]: To specify the type that will be used to store the size
+ of the container. Default: `size_type<std::size_t>`
+
+And they also can receive two additional options:
+
+* [*`equal<class Equal>`]: Equality function for the objects to be inserted
+ in containers. Default: `equal< std::equal_to<T> >`
+
+* [*`hash<class Hash>`]: Hash function to be used in the container.
+ Default: `hash< boost::hash<T> >`
+
+* [*`bucket_traits<class BucketTraits>`]: A type that wraps the bucket vector to
+ be used by the unordered container. Default: a type initialized by the address
+ and size of a bucket array and stores both variables internally.
+
+* [*`power_2_buckets<bool Enabled>`]: The user guarantees that only bucket arrays
+ with power of two length will be used. The container will then use masks instead of modulo
+ operations to obtain the bucket number from the hash value. Masks are faster than
+ modulo operations and for some applications modulo operations can impose
+ a considerable overhead. In debug mode an assertion will be raised if the user
+ provides a bucket length that is not power of two.
+ Default: `constant_time_size<false>`.
[endsect]
@@ -1119,6 +1210,34 @@
[endsect]
+[section:custom_bucket_traits Custom bucket traits]
+
+Instead of using the default `bucket_traits` class to store the bucket array, a user
+can define his own class to store the bucket array using the [*['bucket_traits<>]]
+option. A user-defined bucket-traits must fulfill the following interface:
+
+[c++]
+
+ class my_bucket_traits
+ {
+ bucket_ptr bucket_begin();
+ const_bucket_ptr bucket_begin() const;
+ std::size_t bucket_count() const;
+ };
+
+
+The following bucket traits just stores a pointer to the bucket
+array but the size is a compile-time constant. Note the use of the auxiliary
+[classref boost::intrusive::unordered_bucket unordered_bucket] and
+[classref boost::intrusive::unordered_bucket_ptr unordered_bucket_ptr]
+utilities to obtain the type of the bucket and its pointer before defining
+the unordered container:
+
+[import ../example/doc_bucket_traits.cpp]
+[doc_bucket_traits]
+
+[endsect]
+
[endsect]
[section:advanced_lookups_insertions Advanced lookup and insertion functions for associative containers]
@@ -1174,10 +1293,10 @@
* find
* erase
-Check [classref boost::intrusive::set],
-[classref boost::intrusive::multiset],
-[classref boost::intrusive::unordered_set],
-[classref boost::intrusive::unordered_multiset]
+Check [classref boost::intrusive::set set],
+[classref boost::intrusive::multiset multiset],
+[classref boost::intrusive::unordered_set unordered_set],
+[classref boost::intrusive::unordered_multiset unordered_multiset]
references to know more about those functions.
[endsect]
@@ -1312,7 +1431,8 @@
* First clears and disposes all the elements from *this using the disposer function object.
* After that starts cloning all the elements of the source container using the cloner function object.
-* If any operation in the cloning function (for example, the cloner function object) throws, all the constructed elements are disposed using the disposer function object.
+* If any operation in the cloning function (for example, the cloner function object) throws,
+ all the constructed elements are disposed using the disposer function object.
Here's an example of `clone_from`:
@@ -1351,14 +1471,14 @@
resource management smart pointers (like `boost::shared_ptr`) can't be used.
The conversion from the smart pointer to a raw pointer must be implemented following
-Boost smart pointer `get_pointer()` function. This function will be found using
-ADL. For example, for `boost::interprocess::offset_ptr` `get_pointer` is defined
+Boost smart pointer `detail::get_pointer()` function. This function will be found using
+ADL. For example, for `boost::interprocess::offset_ptr` `detail::get_pointer` is defined
as follows:
[c++]
template<class T>
- T * get_pointer(boost::interprocess::offset_ptr<T> const & p)
+ T * detail::get_pointer(boost::interprocess::offset_ptr<T> const & p)
{ return p.get(); }
[endsect]
@@ -1383,22 +1503,29 @@
[c++]
local_iterator local_iterator_to(reference value);
- const_local_iterator local_iterator_to(const_reference value);
+ const_local_iterator local_iterator_to(const_reference value) const;
For most [*Boost.Intrusive] containers
([classref boost::intrusive::list list],
[classref boost::intrusive::slist slist],
[classref boost::intrusive::set set],
-[classref boost::intrusive::multiset multiset])
-`iterator_to` is an static function so we don't need a reference to the
-container to obtain the iterator. For unordered associative containers
+[classref boost::intrusive::multiset multiset]) we have an alternative
+static `s_iterator_to` function.
+
+For unordered associative containers
([classref boost::intrusive::unordered_set unordered_set],
[classref boost::intrusive::multiset multiset]),
-`iterator_to` is not an static function, so there is need
-to have a reference to the container. On the other hand, `local_iterator_to` functions
-are static.
+`iterator_to` has no static alternative function.
+On the other hand, `local_iterator_to` functions
+have their `s_local_iterator_to` static alternatives.
+
+Alternative static functions are available under certain circunstances
+explained in the [link: stateful_value_traits Stateful value traits] section,
+but the programmer uses hooks provided by [*Boost.Intrusive], those functions
+will be available.
-Let's see an small function that shows the use of `iterator_to` and `local_iterator_to`:
+Let's see an small function that shows the use of `iterator_to` and
+`local_iterator_to`:
[import ../example/doc_iterator_from_value.cpp]
[doc_iterator_from_value]
@@ -1411,7 +1538,7 @@
before explaining the customization options of [*Boost.Intrusive].
* [*Node Algorithms]: A set of static functions that implement basic operations
- on a group of nodes: initialize a node, link a node to a group of nodes,
+ on a group of nodes: initialize a node, link_mode_type a node to a group of nodes,
unlink a node from another group of nodes... For example, a circular
singly linked list is a group of nodes, where each node has a pointer to the
next node. [*Node Algorithms] just require a [*NodeTraits]
@@ -1784,7 +1911,10 @@
[section:value_traits Containers with custom ValueTraits]
As explained in the [link intrusive.concepts Concepts] section, [*Boost.Intrusive]
-containers are templatized using a `ValueTraits` parameter. This parameter contains
+containers need a `ValueTraits` class to perform transformations between nodes and
+user values. `ValueTraits` can be explicitly configured (using the `value_traits<>` option)
+or implicitly configured (using hooks and their `base_hook<>`/`member_hook<>` options).
+`ValueTraits` contains
all the information to glue the `value_type` of the containers and the node to be
used in node algorithms, since these types can be different. Apart from this,
`ValueTraits` also store information about the link policy of the values to be inserted.
@@ -1795,7 +1925,9 @@
application or that are compatible with a a legacy ABI. A user might want
to have only two additional pointers in his class and insert the class in a doubly
linked list sometimes and in a singly linked list in other situations. You can't
-achieve this using [*Boost.Intrusive] predefined hooks.
+achieve this using [*Boost.Intrusive] predefined hooks. Now, instead of using
+`base_hook<...>` or `member_hook<...>` options the user will specify the
+`value_traits<...>` options. Let's see how we can do this:
[section:value_traits_interface ValueTraits interface]
@@ -1804,7 +1936,7 @@
[c++]
#include <boost/pointer_to_other.hpp>
- #include <boost/intrusive/linking_policy.hpp>
+ #include <boost/intrusive/link_mode.hpp>
struct my_value_traits
{
@@ -1814,8 +1946,8 @@
typedef node_traits::const_node_ptr const_node_ptr;
typedef boost::pointer_to_other<node_ptr, value_type>::type pointer;
typedef boost::pointer_to_other<node_ptr, const value_type>::type const_pointer;
-
- enum { linking_policy = some_linking_policy };
+
+ static const link_mode_type link_mode = some_linking_policy;
static node_ptr to_node_ptr (value_type &value);
static const_node_ptr to_node_ptr (const value_type &value);
@@ -1825,7 +1957,7 @@
Let's explain each type and function:
-* ['node_traits]: The node configuration that it's needed by node algorithms.
+* [*['node_traits]]: The node configuration that it's needed by node algorithms.
These node traits and algorithms are
described in the previous chapter: [link intrusive.node_algorithms Nodes Algorithms].
@@ -1845,57 +1977,57 @@
[classref boost::intrusive::unordered_multiset unordered_multiset], `node_traits`
should follow the interface needed by [classref boost::intrusive::circular_slist_algorithms circular_slist_algorithms].
-* ['node_ptr]: A typedef for `node_traits::node_ptr`.
+* [*['node_ptr]]: A typedef for `node_traits::node_ptr`.
-* ['const_node_ptr]: A typedef for `node_traits::const_node_ptr`.
+* [*['const_node_ptr]]: A typedef for `node_traits::const_node_ptr`.
-* ['value_type]: The type that the user wants to insert in the container. This type can be
+* [*['value_type]]: The type that the user wants to insert in the container. This type can be
the same as `node_traits::node` but it can be different (for example, `node_traits::node`
can be a member type of `value_type`). If `value_type` and `node_traits::node` are the
same type, the `to_node_ptr` and `to_value_ptr` functions are trivial.
-* ['pointer]: The type of a pointer to a `value_type`. It must be the same pointer type
+* [*['pointer]]: The type of a pointer to a `value_type`. It must be the same pointer type
as `node_ptr`: If `node_ptr` is `node *` `pointer` must be `value_type*`. If
`node_ptr` is `smart_ptr<node_traits::node>`, `pointer` must be `smart_ptr<value_type>`.
This can be generically achieved using `boost::pointer_to_other` utility from [*Boost SmartPointers]
defined in `<boost/pointer_to_other.hpp>`.
-* ['const_pointer]: The type of a pointer to a `const value_type`. It must be the same pointer type
+* [*['const_pointer]]: The type of a pointer to a `const value_type`. It must be the same pointer type
as `node_ptr`: If `node_ptr` is `node *` `const_pointer` must be `const value_type*`. If
`node_ptr` is `smart_ptr<node_traits::node>`, `const_pointer` must be `smart_ptr<const value_type>`
This can be generically achieved using `boost::pointer_to_other` utility from [*Boost SmartPointers]
defined in `<boost/pointer_to_other.hpp>`.
-* ['linking_policy]: Indicates that `value_traits` needs some additional work or checks from the
- container. The types are enumerations defined in the `value_traits_type.hpp` header.
+* [*['link_mode]]: Indicates that `value_traits` needs some additional work or checks from the
+ container. The types are enumerations defined in the `link_mode.hpp` header.
These are the possible types:
- * `normal_link`: If this linking policy is specified in a `ValueTraits` class
- as the linking_policy, containers
+ * [*`normal_link`]: If this linking policy is specified in a `ValueTraits` class
+ as the link, containers
configured with such `ValueTraits` won't set the hooks
of the erased values to a default state. Containers also won't
check that the hooks of the new values are default initialized.
normal_link,
- * `safe_link`: If this linking policy is specified in a `ValueTraits` class
- as the linking_policy, containers
+ * [*`safe_link`]: If this linking policy is specified in a `ValueTraits` class
+ as the link, containers
configured with such `ValueTraits` will set the hooks
of the erased values to a default state. Containers also will
check that the hooks of the new values are default initialized.
- * `auto_unlink`: Same as "safe_link" but containers with
+ * [*`auto_unlink`]: Same as "safe_link" but containers with
constant-time size features won't be
compatible with `ValueTraits` configured with this policy.
Containers also know that the a value can be silently erased from
the container without using any function provided by the containers.
-* ['static node_ptr to_node_ptr (value_type &value)] and
- ['static const_node_ptr to_node_ptr (const value_type &value)]:
+* [*['static node_ptr to_node_ptr (value_type &value)]] and
+ [*['static const_node_ptr to_node_ptr (const value_type &value)]]:
These function take a reference to a value_type and return a pointer to the node
to be used with node algorithms.
-* ['static pointer to_value_ptr (node_ptr n)] and
- ['static const_pointer to_value_ptr (const_node_ptr n)]:
+* [*['static pointer to_value_ptr (node_ptr n)]] and
+ [*['static const_pointer to_value_ptr (const_node_ptr n)]]:
These function take a pointer to a node and return a pointer to the value
that contains the node.
@@ -2000,8 +2132,8 @@
typedef derivation_value_traits<value_2, simple_node_traits, normal_link> ValueTraits2;
//Now define the containers
- typedef list <ValueTraits1> Value1List;
- typedef list <ValueTraits2> Value2List;
+ typedef list <value1, value_traits<ValueTraits1> > Value1List;
+ typedef list <value2, value_traits<ValueTraits2> > Value2List;
We can even choose to store `simple_node` as a member of `value_1` and `value_2`
classes and use [classref boost::intrusive::member_value_traits member_value_traits]
@@ -2012,13 +2144,58 @@
[endsect]
+[section:stateful_value_traits Stateful value traits]
+
+Until now all shown custom value traits are stateless, that is, [*the transformation between nodes
+and values is implemented in terms of static functions]. It's possible to use [*stateful] value traits
+so that we can even separate nodes and values and [*avoid modifying types to insert nodes].
+[*Boost.Intrusive] differentiates between stateful and stateless value traits checking if the ValueTraits
+class is empty:
+
+* If the class is empty, a [*stateless] value traits is assumed.
+ Node <-> Value transformations must be static functions.
+* If the class is not empty, a [*stateful] value traits is assumed.
+ Node <-> Value transformations must be non-static functions.
+
+Using stateful value traits it's possible to create containers of non-copyable/moveble objects [*without modifying]
+the definition of the class to be inserted. This interesting property is achieved without using global variables
+(stateless value traits could use global variables to achieve the same property), so:
+
+* [*Thread-safety guarantees]: Better thread-safety guarantees can be achieved with stateful
+ value traits, since accessing to global resources might require syncronization primitives that
+ can be avoided when using the internal state.
+* [*Flexibility]: A stateful value traits type can be configured at run-time.
+* [*Run-time polimorphism]: A value traits might implement node <-> value
+ transformations as virtual functions. A single container type could be
+ configured at run-time to use different node <-> value relatioships.
+
+Stateful value traits have many advantages but also some downsides:
+
+* [*Performance]: Value traits operations should be very efficient since they are basic operations used by containers.
+ [*A heavy node <-> value transformation can downgrade intrusive containers' performance].
+* [*Exception guarantees]: The stateful ValueTraits must maintain no-throw guarantees, otherwise, the
+ container invariants won't be preserved.
+* [*Static functions]: Some static functions offered by intrusive containers are not
+ available because node <-> value transformations are not static.
+* [*Bigger iterators]: The size of some iterators is increased because the iterator
+ needs to store a pointer to the stateful value traits to implement node to value
+ tranformations (e.g. `operator*()` and `operator->()`).
+
+An easy and useful example of stateful value traits is when an array of values can be indirectly introduced
+in a list guaranteeing no additional allocation apart from the initial resource reservation:
+
+[import ../example/doc_stateful_value_traits.cpp]
+[doc_stateful_value_traits]
+
+[endsect]
+
[endsect]
[section:thread_safety Thread safety guarantees]
Intrusive containers have similar same thread-safety guarantees than STL containers.
-* Serveral threads can have read or write access to different instances is safe as long as inserted
+* Several threads can have read or write access to different instances is safe as long as inserted
objects are different.
* Concurrent read-only access to the same container is safe.
@@ -2045,6 +2222,60 @@
[endsect]
+[section:obtaining_same_type_reducing_space Obtaining the same types and reducing symbol length]
+
+The flexible option specification mechanism used by [*Boost.Intrusive] for hooks and containers
+has also a couple of downsides:
+
+* If a user specifies the same options in different order or specifies some options and lefts the
+ rest as defaults the type of the created container/hook will be different. Sometimes
+ this is annoying, because two programmers specifying the same options might end with incompatible
+ types. For example, the following two lists, although they're using the same options, have not
+ the same type:
+
+[c++]
+
+ #include <boost/intrusive/list.hpp>
+
+ using namespace boost::intrusive;
+
+ //Explicitly specify constant-time size and size type
+ typedef list<T, constant_time_size<true>, size_type<std::size_t> List1;
+
+ //Implicitly specify constant-time size and size type
+ typedef list<T> List2;
+
+* Option specifiers lead to long template symbols for classes and functions. Option specifiers themselves
+ are verbose and without variadic templates, several default template parameters are assigned for
+ non-specified options. Object and debugging information files can grow and compilation times
+ might suffer a bit if long names are produced.
+
+To solve these issues [*Boost.Intrusive] offers some helper metafunctions that that reduce symbol lengths
+and create the same type if the same options (either explicitly or implicitly) are used. This also
+improves compilation times. All containers and hooks have their respective `make_xxx` versions.
+Previous shown example can be rewritten like this to obtain the same list type:
+
+[c++]
+
+ #include <boost/intrusive/list.hpp>
+
+ using namespace boost::intrusive;
+
+ #include <boost/intrusive/list.hpp>
+
+ using namespace boost::intrusive;
+
+ //Explicitly specify constant-time size and size type
+ typedef make_list<T, constant_time_size<true>, size_type<std::size_t>::type List1;
+
+ //Implicitly specify constant-time size and size type
+ typedef make_list<T>::type List2;
+
+Produced symbol lengths and compilation times are usually shorter and object/debug files are smaller.
+If you are a programmer concerned with file sizes and compilation times, this option is your choice.
+
+[endsect]
+
[section:design_notes Design Notes]
When designing [*Boost.Intrusive] the following guidelines have been taken into account:
@@ -2126,7 +2357,7 @@
* `sort` and `write access` tests will show the advantage of intrusive containers
minimizing the memory accesses when comparing them with containers of pointers.
-Given an object of type `T`, [classref boost::intrusive::list boost::intrusive::list<...>]
+Given an object of type `T`, [classref boost::intrusive::list boost::intrusive::list<T>]
can replace `std::list<T>` to avoid memory allocation overhead,
or it can replace `std::list<T*>` when the user wants to obtain containers with
polymorphic values or wants to share values between several containers.
@@ -2236,9 +2467,9 @@
lagging behind. The `disperse pointer list` needs to make `NumElements*2` allocations,
so the result is not surprising.
-Linux test shows that standard containers are do very well against intrusive containers
+Linux test shows that standard containers perform very well against intrusive containers
with big objects. Nearly the same GCC version in MinGW performs worse, so maybe the
-a good operating system memory allocator is the reason for this good results.
+a good memory allocator is the reason for these excelent results.
[endsect]
@@ -2308,7 +2539,7 @@
l.push_back(&objects.back());
}
-For big values the compact pointer list wins because when reversing does need access
+For big values the compact pointer list wins because when reversing doesn't need access
to the values stored in another container. Since all the allocations for nodes of
this pointer list are likely to be near (since there is no other allocation in the
process until the pointer list is created) locality is better than with intrusive
@@ -2487,14 +2718,13 @@
* GCC 3.4.4/Cygwin
* Intel 9.1/WinXP
* GCC 4.1.2/Linux
-* Codewarrior 9.4/WinXP
* GCC 3.4.3/Solaris 11
* GCC 4.0/Mac Os 10.4.1
* SunCC 5.8/Solaris 11
[endsect]
-[section:acknowledgments Acknowledgments]
+[section:acknowledgments Acknowledgements]
[*Olaf Krzikalla] would like to thank:
@@ -2504,7 +2734,7 @@
* [*Udo Steinbach] for encouragements to present this work for boost, a lot of fixes and
helpful discussions.
-* [*Jaap Suter] for the initial hint, which eventually leads to the member value_traits.
+* [*Jaap Suter] for the initial hint, which eventually lead to the member value_traits.
[*Ion Gaztanaga] would like to thank:
@@ -2519,18 +2749,37 @@
[*Tom Brinkman] and [*Steven Watanabe]
for their comments and reviews in the Boost.Intrusive formal review.
+* Thanks to of Julienne Walker and The EC Team ([@http://eternallyconfuzzled.com]) for their
+ great algorithms.
+
+* Special thanks to [*Steven Watanabe] and [*Tobias Schwinger] for their
+ invaluable suggestions and improvements.
+
[endsect]
[xinclude autodoc.xml]
[section:license_notices License notices]
-The internal implementation of red-black trees is based on that of SGI STL stl_tree.h file:
+Most of the internal implementation of red-black trees is based on that of SGI STL stl_tree.h file:
+
+['Copyright (c) 1996,1997 Silicon Graphics Computer Systems, Inc.
+Permission to use, copy, modify, distribute and sell this software and its documentation for any purpose is hereby granted without fee, provided that the above copyright notice appear in all copies and that both that copyright notice and this permission notice appear in supporting documentation. Silicon Graphics makes no representations about the suitability of this software for any purpose. It is provided "as is" without express or implied warranty.]
-Copyright (c) 1996,1997 Silicon Graphics Computer Systems, Inc.
-Permission to use, copy, modify, distribute and sell this software and its documentation for any purpose is hereby granted without fee, provided that the above copyright notice appear in all copies and that both that copyright notice and this permission notice appear in supporting documentation. Silicon Graphics makes no representations about the suitability of this software for any purpose. It is provided "as is" without express or implied warranty.
+['Copyright (c) 1994 Hewlett-Packard Company
+Permission to use, copy, modify, distribute and sell this software and its documentation for any purpose is hereby granted without fee, provided that the above copyright notice appear in all copies and that both that copyright notice and this permission notice appear in supporting documentation. Hewlett-Packard Company makes no representations about the suitability of this software for any purpose. It is provided "as is" without express or implied warranty.]
-Copyright (c) 1994 Hewlett-Packard Company
-Permission to use, copy, modify, distribute and sell this software and its documentation for any purpose is hereby granted without fee, provided that the above copyright notice appear in all copies and that both that copyright notice and this permission notice appear in supporting documentation. Hewlett-Packard Company makes no representations about the suitability of this software for any purpose. It is provided "as is" without express or implied warranty.
+The tree destruction algorithm is based on Julienne Walker and The EC Team code:
+
+['This code is in the public domain. Anyone may
+use it or change it in any way that they see
+fit. The author assumes no responsibility for
+damages incurred through use of the original
+code or any variations thereof.]
+
+['It is requested, but not required, that due
+credit is given to the original author and
+anyone who has modified the code through
+a header comment, such as this one.]
[endsect]
Modified: branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,7 +10,7 @@
//
/////////////////////////////////////////////////////////////////////////////
//[doc_advanced_value_traits_code
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <boost/intrusive/list.hpp>
#include <vector>
@@ -46,7 +46,7 @@
//A templatized value traits for value_1 and value_2
template<class ValueType>
-struct value_traits
+struct simple_value_traits
{
typedef simple_node_traits node_traits;
typedef node_traits::node_ptr node_ptr;
@@ -54,7 +54,7 @@
typedef ValueType value_type;
typedef ValueType * pointer;
typedef const ValueType * const_pointer;
- enum { linking_policy = boost::intrusive::normal_link };
+ static const boost::intrusive::link_mode_type link_mode = boost::intrusive::normal_link;
static node_ptr to_node_ptr (value_type &value) { return node_ptr(&value); }
static const_node_ptr to_node_ptr (const value_type &value) { return const_node_ptr(&value); }
static pointer to_value_ptr(node_ptr n) { return static_cast<value_type*>(n); }
@@ -65,8 +65,10 @@
//[doc_advanced_value_traits_containers
//Now define two intrusive lists. Both lists will use the same algorithms:
// circular_list_algorithms<simple_node_traits>
-typedef boost::intrusive::list <value_traits<value_1> > Value1List;
-typedef boost::intrusive::list <value_traits<value_2> > Value2List;
+
+using namespace boost::intrusive;
+typedef list <value_1, value_traits<simple_value_traits<value_1> > > Value1List;
+typedef list <value_2, value_traits<simple_value_traits<value_2> > > Value2List;
//]
//[doc_advanced_value_traits_test
Modified: branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits2.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits2.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_advanced_value_traits2.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -9,7 +9,7 @@
// See http://www.boost.org/libs/intrusive for documentation.
//
/////////////////////////////////////////////////////////////////////////////
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <boost/intrusive/list.hpp>
#include <boost/intrusive/member_value_traits.hpp>
#include <vector>
@@ -57,8 +57,8 @@
//Now define two intrusive lists. Both lists will use the same algorithms:
// circular_list_algorithms<simple_node_traits>
-typedef boost::intrusive::list <ValueTraits1> Value1List;
-typedef boost::intrusive::list <ValueTraits2> Value2List;
+typedef list <value_1, value_traits<ValueTraits1> > Value1List;
+typedef list <value_2, value_traits<ValueTraits2> > Value2List;
//]
//[doc_advanced_value_traits2_test
Modified: branches/bcbboost/libs/intrusive/example/doc_assoc_optimized_code.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_assoc_optimized_code.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_assoc_optimized_code.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -51,24 +51,21 @@
};
// A set and unordered_set that store Expensive objects
-typedef set<set_base_hook<>::value_traits<Expensive> > Set;
-typedef unordered_set<unordered_set_base_hook<>::
- value_traits<Expensive> > UnorderedSet;
+typedef set<Expensive> Set;
+typedef unordered_set<Expensive> UnorderedSet;
// Search functions
-Expensive *get_from_set(const char* key, Set &set)
+Expensive *get_from_set(const char* key, Set &set_object)
{
- Set::iterator it = set.find(Expensive(key));
- if( it == set.end() ) return 0;
+ Set::iterator it = set_object.find(Expensive(key));
+ if( it == set_object.end() ) return 0;
return &*it;
}
-Expensive *get_from_unordered_set
- (const char* key, UnorderedSet &unordered_set)
+Expensive *get_from_uset(const char* key, UnorderedSet &uset_object)
{
- UnorderedSet::iterator it =
- unordered_set.find(Expensive (key));
- if( it == unordered_set.end() ) return 0;
+ UnorderedSet::iterator it = uset_object.find(Expensive (key));
+ if( it == uset_object.end() ) return 0;
return &*it;
}
//]
@@ -94,38 +91,35 @@
};
// Optimized search functions
-Expensive *get_from_set_optimized(const char* key, Set &set)
+Expensive *get_from_set_optimized(const char* key, Set &set_object)
{
- Set::iterator it = set.find(key, StrExpComp());
- if( it == set.end() ) return 0;
+ Set::iterator it = set_object.find(key, StrExpComp());
+ if( it == set_object.end() ) return 0;
return &*it;
}
-Expensive *get_from_unordered_set_optimized
- (const char* key, UnorderedSet &unordered_set)
+Expensive *get_from_uset_optimized(const char* key, UnorderedSet &uset_object)
{
- UnorderedSet::iterator it =
- unordered_set.find(key, StrHasher(), StrExpEqual());
- if( it == unordered_set.end() ) return 0;
+ UnorderedSet::iterator it = uset_object.find(key, StrHasher(), StrExpEqual());
+ if( it == uset_object.end() ) return 0;
return &*it;
}
//]
//[doc_assoc_optimized_code_normal_insert
// Insertion functions
-bool insert_to_set(const char* key, Set &set)
+bool insert_to_set(const char* key, Set &set_object)
{
Expensive *pobject = new Expensive(key);
- bool success = set.insert(*pobject).second;
+ bool success = set_object.insert(*pobject).second;
if(!success) delete pobject;
return success;
}
-bool insert_to_unordered_set
- (const char* key, UnorderedSet &unordered_set)
+bool insert_to_uset(const char* key, UnorderedSet &uset_object)
{
Expensive *pobject = new Expensive(key);
- bool success = unordered_set.insert(*pobject).second;
+ bool success = uset_object.insert(*pobject).second;
if(!success) delete pobject;
return success;
}
@@ -133,24 +127,20 @@
//[doc_assoc_optimized_code_optimized_insert
// Optimized insertion functions
-bool insert_to_set_optimized(const char* key, Set &set)
+bool insert_to_set_optimized(const char* key, Set &set_object)
{
Set::insert_commit_data insert_data;
- bool success = set.insert_check
- (key, StrExpComp(), insert_data).second;
- if(success)
- set.insert_commit(*new Expensive(key), insert_data);
+ bool success = set_object.insert_check(key, StrExpComp(), insert_data).second;
+ if(success) set_object.insert_commit(*new Expensive(key), insert_data);
return success;
}
-bool insert_to_unordered_set_optimized
- (const char* key, UnorderedSet &unordered_set)
+bool insert_to_uset_optimized(const char* key, UnorderedSet &uset_object)
{
UnorderedSet::insert_commit_data insert_data;
- bool success = unordered_set.insert_check
+ bool success = uset_object.insert_check
(key, StrHasher(), StrExpEqual(), insert_data).second;
- if(success)
- unordered_set.insert_commit(*new Expensive(key), insert_data);
+ if(success) uset_object.insert_commit(*new Expensive(key), insert_data);
return success;
}
//]
@@ -159,7 +149,7 @@
{
Set set;
UnorderedSet::bucket_type buckets[10];
- UnorderedSet unordered_set(buckets, 10);
+ UnorderedSet unordered_set(UnorderedSet::bucket_traits(buckets, 10));
const char * const expensive_key
= "A long string that avoids small string optimization";
@@ -170,7 +160,7 @@
return 1;
}
- if(get_from_unordered_set(expensive_key, unordered_set)){
+ if(get_from_uset(expensive_key, unordered_set)){
return 1;
}
@@ -178,7 +168,7 @@
return 1;
}
- if(get_from_unordered_set_optimized(expensive_key, unordered_set)){
+ if(get_from_uset_optimized(expensive_key, unordered_set)){
return 1;
}
@@ -189,7 +179,7 @@
return 1;
}
- if(!get_from_unordered_set(expensive_key, unordered_set)){
+ if(!get_from_uset(expensive_key, unordered_set)){
return 1;
}
@@ -197,7 +187,7 @@
return 1;
}
- if(!get_from_unordered_set_optimized(expensive_key, unordered_set)){
+ if(!get_from_uset_optimized(expensive_key, unordered_set)){
return 1;
}
@@ -208,7 +198,7 @@
return 1;
}
- if(!insert_to_unordered_set(expensive_key, unordered_set)){
+ if(!insert_to_uset(expensive_key, unordered_set)){
return 1;
}
@@ -228,7 +218,7 @@
return 1;
}
- if(!insert_to_unordered_set_optimized(expensive_key, unordered_set)){
+ if(!insert_to_uset_optimized(expensive_key, unordered_set)){
return 1;
}
@@ -251,7 +241,7 @@
return 1;
}
- if(insert_to_unordered_set(expensive_key, unordered_set)){
+ if(insert_to_uset(expensive_key, unordered_set)){
return 1;
}
@@ -259,7 +249,7 @@
return 1;
}
- if(insert_to_unordered_set_optimized(expensive_key, unordered_set)){
+ if(insert_to_uset_optimized(expensive_key, unordered_set)){
return 1;
}
Modified: branches/bcbboost/libs/intrusive/example/doc_auto_unlink.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_auto_unlink.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_auto_unlink.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -15,39 +15,38 @@
using namespace boost::intrusive;
-class MyClass : public list_base_hook<tag, auto_unlink>
+typedef list_base_hook<link_mode<auto_unlink> > auto_unlink_hook;
+
+class MyClass : public auto_unlink_hook
//This hook removes the node in the destructor
{
int int_;
public:
MyClass(int i = 0) : int_(i) {}
- void unlink() { list_base_hook<tag, auto_unlink>::unlink(); }
- bool is_linked() { return list_base_hook<tag, auto_unlink>::is_linked(); }
- int get() const { return int_; }
+ void unlink() { auto_unlink_hook::unlink(); }
+ bool is_linked() { return auto_unlink_hook::is_linked(); }
};
-//Define a list that will store MyClass
-//using the public base hook
+//Define a list that will store values using the base hook
//The list can't have constant-time size!
-typedef list< list_base_hook<tag, auto_unlink>::
- value_traits<MyClass>, false > List;
+typedef list< MyClass, constant_time_size<false> > List;
int main()
{
//Create the list
- List list;
+ List l;
{
//Create myclass and check it's linked
MyClass myclass;
assert(myclass.is_linked() == false);
//Insert the object
- list.push_back(myclass);
+ l.push_back(myclass);
//Check that we have inserted the object
- assert(list.empty() == false);
- assert(&list.front() == &myclass);
+ assert(l.empty() == false);
+ assert(&l.front() == &myclass);
assert(myclass.is_linked() == true);
//Now myclass' destructor will unlink it
@@ -55,7 +54,7 @@
}
//Check auto-unlink has been executed
- assert(list.empty() == true);
+ assert(l.empty() == true);
{
//Now test the unlink() function
@@ -65,18 +64,18 @@
assert(myclass.is_linked() == false);
//Insert the object
- list.push_back(myclass);
+ l.push_back(myclass);
//Check that we have inserted the object
- assert(list.empty() == false);
- assert(&list.front() == &myclass);
+ assert(l.empty() == false);
+ assert(&l.front() == &myclass);
assert(myclass.is_linked() == true);
//Now unlink the node
myclass.unlink();
//Check auto-unlink has been executed
- assert(list.empty() == true);
+ assert(l.empty() == true);
}
return 0;
}
Modified: branches/bcbboost/libs/intrusive/example/doc_clone_from.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_clone_from.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_clone_from.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -14,9 +14,10 @@
#include <iostream>
#include <vector>
+using namespace boost::intrusive;
+
//A class that can be inserted in an intrusive list
-class my_class
- : public boost::intrusive::list_base_hook<>
+class my_class : public list_base_hook<>
{
public:
friend bool operator==(const my_class &a, const my_class &b)
@@ -28,20 +29,18 @@
};
//Definition of the intrusive list
-typedef boost::intrusive::list< my_class::value_traits<my_class> > my_class_list;
+typedef list<my_class> my_class_list;
//Cloner object function
-class new_cloner
+struct new_cloner
{
- public:
my_class *operator()(const my_class &clone_this)
{ return new my_class(clone_this); }
};
//The disposer object function
-class delete_disposer
+struct delete_disposer
{
- public:
void operator()(my_class *delete_this)
{ delete delete_this; }
};
@@ -54,9 +53,8 @@
//Fill all the nodes and insert them in the list
my_class_list list;
- for(int i = 0; i < MaxElem; ++i){
- nodes[i].int_ = i;
- }
+ for(int i = 0; i < MaxElem; ++i) nodes[i].int_ = i;
+
list.insert(list.end(), nodes.begin(), nodes.end());
//Now clone "list" using "new" and "delete" object functions
@@ -64,12 +62,10 @@
cloned_list.clone_from(list, new_cloner(), delete_disposer());
//Test that both are equal
- if(cloned_list != list){
+ if(cloned_list != list)
std::cout << "Both lists are different" << std::endl;
- }
- else{
+ else
std::cout << "Both lists are equal" << std::endl;
- }
//Don't forget to free the memory from the second list
cloned_list.clear_and_dispose(delete_disposer());
Modified: branches/bcbboost/libs/intrusive/example/doc_entity.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_entity.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_entity.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -12,9 +12,10 @@
//[doc_entity_code
#include <boost/intrusive/list.hpp>
+using namespace boost::intrusive;
+
//A class that can be inserted in an intrusive list
-class entity
- : public boost::intrusive::list_base_hook<>
+class entity : public list_base_hook<>
{
public:
virtual ~entity();
@@ -26,25 +27,25 @@
{/**/};
//Definition of the intrusive list
-typedef boost::intrusive::list< entity::value_traits<entity> > entity_list;
+typedef list<entity> entity_list;
//A global list
-entity_list list;
+entity_list global_list;
-//The destructor removes itself from the list
+//The destructor removes itself from the global list
entity::~entity()
-{ list.erase(entity_list::iterator_to(*this)); }
+{ global_list.erase(entity_list::s_iterator_to(*this)); }
-//Function to insert a new "some_entity" in the list
+//Function to insert a new "some_entity" in the global list
void insert_some_entity()
-{ list.push_back (*new some_entity(/*...*/)); }
+{ global_list.push_back (*new some_entity(/*...*/)); }
-//Function to clear an entity from the intrusive list
+//Function to clear an entity from the intrusive global list
void clear_list ()
{
- // entity's destructor removes itself from the list implicitly
- while (!list.empty())
- delete &list.front();
+ // entity's destructor removes itself from the global list implicitly
+ while (!global_list.empty())
+ delete &global_list.front();
}
int main()
@@ -52,7 +53,7 @@
//Insert some new entities
insert_some_entity();
insert_some_entity();
- //list's destructor will free objects
+ //global_list's destructor will free objects
return 0;
}
Modified: branches/bcbboost/libs/intrusive/example/doc_erasing_and_disposing.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_erasing_and_disposing.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_erasing_and_disposing.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -12,9 +12,10 @@
//[doc_erasing_and_disposing
#include <boost/intrusive/list.hpp>
+using namespace boost::intrusive;
+
//A class that can be inserted in an intrusive list
-class my_class
- : public boost::intrusive::list_base_hook<>
+class my_class : public list_base_hook<>
{
public:
my_class(int i)
@@ -26,20 +27,18 @@
};
//Definition of the intrusive list
-typedef boost::intrusive::list< my_class::value_traits<my_class> > my_class_list;
+typedef list<my_class> my_class_list;
//The predicate function
-class is_even
+struct is_even
{
- public:
bool operator()(const my_class &c) const
{ return 0 == (c.int_ % 2); }
};
//The disposer object function
-class delete_disposer
+struct delete_disposer
{
- public:
void operator()(my_class *delete_this)
{ delete delete_this; }
};
@@ -53,9 +52,7 @@
try{
//Insert new objects in the container
- for(int i = 0; i < MaxElem; ++i){
- list.push_back(*new my_class(i));
- }
+ for(int i = 0; i < MaxElem; ++i) list.push_back(*new my_class(i));
//Now use remove_and_dispose_if to erase and delete the objects
list.remove_and_dispose_if(is_even(), delete_disposer());
Modified: branches/bcbboost/libs/intrusive/example/doc_how_to_use.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_how_to_use.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_how_to_use.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -15,7 +15,7 @@
using namespace boost::intrusive;
-class MyClass : public list_base_hook<>
+class MyClass : public list_base_hook<>
{
int int_;
@@ -23,62 +23,51 @@
list_member_hook<> member_hook_;
MyClass(int i) : int_(i) {}
- int get() const { return int_; }
};
//Define a list that will store MyClass using the base hook
-typedef list< list_base_hook<>::value_traits<MyClass> >
- BaseList;
+typedef list<MyClass> BaseList;
//Define a list that will store MyClass using the member hook
-typedef list< list_member_hook<>::
- value_traits<MyClass, &MyClass::member_hook_>
- > MemberList;
+typedef member_hook
+ < MyClass, list_member_hook<>, &MyClass::member_hook_> MemberOption;
+typedef list<MyClass, MemberOption> MemberList;
int main()
{
- typedef std::vector<MyClass> Vect;
- typedef Vect::iterator VectIt;
- typedef Vect::reverse_iterator VectRit;
-
- //Create several MyClass objects, each one
- //with a different internal number
- Vect myclassvector;
- for(int i = 0; i < 100; ++i)
- myclassvector.push_back(MyClass(i));
+ typedef std::vector<MyClass>::iterator VectIt;
+ typedef std::vector<MyClass>::reverse_iterator VectRit;
+
+ //Create several MyClass objects, each one with a different value
+ std::vector<MyClass> values;
+ for(int i = 0; i < 100; ++i) values.push_back(MyClass(i));
BaseList baselist;
MemberList memberlist;
- //Now insert them in the reverse order
- //in the base hook intrusive list
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
+ //Now insert them in the reverse order in the base hook list
+ for(VectIt it(values.begin()), itend(values.end())
; it != itend ; ++it){
baselist.push_front(*it);
}
- //Now insert them in the same order as in vector in the
- //member hook intrusive list
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend; ++it){
+ //Now insert them in the same order as in vector in the member hook list
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
memberlist.push_back(*it);
- }
//Now test lists
{
BaseList::reverse_iterator rbit(baselist.rbegin()), rbitend(baselist.rend());
MemberList::iterator mit(memberlist.begin()), mitend(memberlist.end());
- VectIt it(myclassvector.begin()), itend(myclassvector.end());
+ VectIt it(values.begin()), itend(values.end());
//Test the objects inserted in the base hook list
- for(; it != itend; ++it, ++rbit){
+ for(; it != itend; ++it, ++rbit)
if(&*rbit != &*it) return 1;
- }
//Test the objects inserted in the member hook list
- for(it = myclassvector.begin(); it != itend; ++it, ++mit){
+ for(it = values.begin(); it != itend; ++it, ++mit)
if(&*mit != &*it) return 1;
- }
}
return 0;
Modified: branches/bcbboost/libs/intrusive/example/doc_iterator_from_value.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_iterator_from_value.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_iterator_from_value.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -15,43 +15,44 @@
#include <boost/functional/hash.hpp>
#include <vector>
+using namespace boost::intrusive;
+
class intrusive_data
{
int data_id_;
public:
- int get() const { return data_id_; }
void set(int id) { data_id_ = id; }
//This class can be inserted in an intrusive list
- typedef boost::intrusive::
- list_member_hook<> list_member_hook_t;
- list_member_hook_t list_hook_;
+ list_member_hook<> list_hook_;
//This class can be inserted in an intrusive unordered_set
- typedef boost::intrusive::
- unordered_set_member_hook<> unordered_set_member_hook_t;
- unordered_set_member_hook_t unordered_set_hook_;
+ unordered_set_member_hook<> unordered_set_hook_;
//Comparison operators
friend bool operator==(const intrusive_data &a, const intrusive_data &b)
- { return a.get() == b.get(); }
+ { return a.data_id_ == b.data_id_; }
friend bool operator!=(const intrusive_data &a, const intrusive_data &b)
- { return a.get() != b.get(); }
-};
+ { return a.data_id_ != b.data_id_; }
-//The hash function
-std::size_t hash_value(const intrusive_data &i)
-{ return boost::hash<int>()(i.get()); }
+ //The hash function
+ friend std::size_t hash_value(const intrusive_data &i)
+ { return boost::hash<int>()(i.data_id_); }
+};
//Definition of the intrusive list that will hold intrusive_data
-typedef boost::intrusive::list< intrusive_data::list_member_hook_t::
- value_traits<intrusive_data, &intrusive_data::list_hook_> > list_t;
+typedef member_hook<intrusive_data, list_member_hook<>
+ , &intrusive_data::list_hook_> MemberListOption;
+typedef list<intrusive_data, MemberListOption> list_t;
//Definition of the intrusive unordered_set that will hold intrusive_data
-typedef boost::intrusive::unordered_set< intrusive_data::unordered_set_member_hook_t::
- value_traits<intrusive_data, &intrusive_data::unordered_set_hook_> > unordered_set_t;
+typedef member_hook
+ < intrusive_data, unordered_set_member_hook<>
+ , &intrusive_data::unordered_set_hook_> MemberUsetOption;
+typedef boost::intrusive::unordered_set
+ < intrusive_data, MemberUsetOption> unordered_set_t;
int main()
{
@@ -62,30 +63,32 @@
//Declare the intrusive containers
list_t list;
unordered_set_t::bucket_type buckets[MaxElem];
- unordered_set_t unordered_set(buckets, MaxElem);
+ unordered_set_t unordered_set
+ (unordered_set_t::bucket_traits(buckets, MaxElem));
//Initialize all the nodes
- for(int i = 0; i < MaxElem; ++i)
- nodes[i].set(i);
+ for(int i = 0; i < MaxElem; ++i) nodes[i].set(i);
//Now insert them in both intrusive containers
list.insert(list.end(), nodes.begin(), nodes.end());
unordered_set.insert(nodes.begin(), nodes.end());
- //Now check list::iterator_to
- //which is an static member function
+ //Now check the iterator_to function
list_t::iterator list_it(list.begin());
for(int i = 0; i < MaxElem; ++i, ++list_it)
- if(list_t::iterator_to(nodes[i]) != list_it)
+ if(list.iterator_to(nodes[i]) != list_it ||
+ list_t::s_iterator_to(nodes[i]) != list_it)
return 1;
- //Now check unordered_set::iterator_to (which is a member function)
- //and unordered_set::local_current (which is an static member function)
+ //Now check unordered_set::s_iterator_to (which is a member function)
+ //and unordered_set::s_local_iterator_to (which is an static member function)
unordered_set_t::iterator unordered_set_it(unordered_set.begin());
- for(int i = 0; i < MaxElem; ++i, ++unordered_set_it){
- if(unordered_set.iterator_to(nodes[i]) != unordered_set.find(nodes[i]))
+ for(int i = 0; i < MaxElem; ++i){
+ unordered_set_it = unordered_set.find(nodes[i]);
+ if(unordered_set.iterator_to(nodes[i]) != unordered_set_it)
return 1;
- if(*unordered_set_t::local_iterator_to(nodes[i]) != *unordered_set.find(nodes[i]))
+ if(*unordered_set.local_iterator_to(nodes[i]) != *unordered_set_it ||
+ *unordered_set_t::s_local_iterator_to(nodes[i]) != *unordered_set_it )
return 1;
}
Modified: branches/bcbboost/libs/intrusive/example/doc_list.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_list.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_list.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -15,7 +15,7 @@
using namespace boost::intrusive;
-class MyClass : public list_base_hook<> //This is a derivation hook
+class MyClass : public list_base_hook<> //This is a derivation hook
{
int int_;
@@ -26,63 +26,49 @@
MyClass(int i)
: int_(i)
{}
-
- int get() const
- { return int_; }
};
//Define a list that will store MyClass using the public base hook
-typedef list< list_base_hook<>::value_traits<MyClass> > BaseList;
+typedef list<MyClass> BaseList;
//Define a list that will store MyClass using the public member hook
-typedef list< list_member_hook<>::value_traits<MyClass, &MyClass::member_hook_> > MemberList;
+typedef list< MyClass
+ , member_hook< MyClass, list_member_hook<>, &MyClass::member_hook_>
+ > MemberList;
int main()
{
- typedef std::vector<MyClass> Vect;
- typedef Vect::iterator VectIt;
- typedef Vect::reverse_iterator VectRit;
-
- //Create several MyClass objects, each one
- //with a different internal number
- Vect myclassvector;
- for(int i = 0; i < 100; ++i)
- myclassvector.push_back(MyClass(i));
+ typedef std::vector<MyClass>::iterator VectIt;
+ typedef std::vector<MyClass>::reverse_iterator VectRit;
+
+ //Create several MyClass objects, each one with a different value
+ std::vector<MyClass> values;
+ for(int i = 0; i < 100; ++i) values.push_back(MyClass(i));
BaseList baselist;
MemberList memberlist;
- //Now insert them in the reverse order
- //in the base hook intrusive list
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend
- ; ++it){
+ //Now insert them in the reverse order in the base hook list
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
baselist.push_front(*it);
- }
- //Now insert them in the same order as in vector in the
- //member hook intrusive list
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend
- ; ++it){
+ //Now insert them in the same order as in vector in the member hook list
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
memberlist.push_back(*it);
- }
//Now test lists
{
BaseList::reverse_iterator rbit(baselist.rbegin()), rbitend(baselist.rend());
MemberList::iterator mit(memberlist.begin()), mitend(memberlist.end());
- VectIt it(myclassvector.begin()), itend(myclassvector.end());
+ VectIt it(values.begin()), itend(values.end());
//Test the objects inserted in the base hook list
- for(; it != itend; ++it, ++rbit){
+ for(; it != itend; ++it, ++rbit)
if(&*rbit != &*it) return 1;
- }
//Test the objects inserted in the member hook list
- for(it = myclassvector.begin(); it != itend; ++it, ++mit){
+ for(it = values.begin(); it != itend; ++it, ++mit)
if(&*mit != &*it) return 1;
- }
}
return 0;
Modified: branches/bcbboost/libs/intrusive/example/doc_offset_ptr.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_offset_ptr.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_offset_ptr.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -9,35 +9,49 @@
// See http://www.boost.org/libs/intrusive for documentation.
//
/////////////////////////////////////////////////////////////////////////////
+
+//This is needed to allow concurrent test execution in
+//several platforms. The shared memory must be unique
+//for each process...
+#include <boost/interprocess/detail/os_thread_functions.hpp>
+#include <sstream>
+
+const char *get_shared_memory_name()
+{
+ std::stringstream s;
+ s << "process_" << boost::interprocess::detail::get_current_process_id();
+ static std::string str = s.str();
+ return str.c_str();
+}
+
//[doc_offset_ptr_0
#include <boost/intrusive/list.hpp>
#include <boost/interprocess/offset_ptr.hpp>
+using namespace boost::intrusive;
+namespace ip = boost::interprocess;
+
class shared_memory_data
+ //Declare the hook with an offset_ptr from Boost.Interprocess
+ //to make this class compatible with shared memory
+ : public list_base_hook< void_pointer< ip::offset_ptr<void> > >
{
int data_id_;
public:
int get() const { return data_id_; }
void set(int id) { data_id_ = id; }
-
- //Declare the hook with an offset_ptr from Boost.Interprocess
- //to make this class compatible with shared memory
- typedef boost::intrusive::list_member_hook
- < boost::intrusive::safe_link
- , boost::interprocess::offset_ptr<void> > member_hook_t;
- member_hook_t list_hook_;
};
//]
//[doc_offset_ptr_1
#include <boost/interprocess/managed_shared_memory.hpp>
#include <boost/interprocess/containers/vector.hpp>
+#include <boost/interprocess/containers/list.hpp>
#include <boost/interprocess/allocators/allocator.hpp>
//Definition of the shared memory friendly intrusive list
-typedef boost::intrusive::list< shared_memory_data::member_hook_t::
- value_traits<shared_memory_data, &shared_memory_data::list_hook_> > shm_list_t;
+typedef ip::list<shared_memory_data> shm_list_t;
int main()
{
@@ -45,45 +59,42 @@
//nodes and the container itself must be created in shared memory
const int MaxElem = 100;
const int ShmSize = 50000;
- const char *ShmName = "SharedMemoryName";
-
- using namespace boost::interprocess;
-
- //Erase all old shared memory
- shared_memory_object::remove(ShmName);
- managed_shared_memory shm(create_only, ShmName, ShmSize);
-
- //Create all nodes in shared memory using a shared memory vector
- //See Boost.Interprocess documentation for more information on this
- typedef allocator< shared_memory_data
- , managed_shared_memory::segment_manager> shm_allocator_t;
- typedef vector<shared_memory_data, shm_allocator_t> shm_vector_t;
- shm_allocator_t shm_alloc(shm.get_segment_manager());
- shm_vector_t *pshm_vect = shm.construct<shm_vector_t>(anonymous_instance)(shm_alloc);
- pshm_vect->resize(MaxElem);
-
- //Initialize all the nodes
- for(int i = 0; i < MaxElem; ++i){
- (*pshm_vect)[i].set(i);
- }
-
- //Now create the shared memory intrusive list
- shm_list_t *plist = shm.construct<shm_list_t>(anonymous_instance)();
- plist->insert(plist->end(), pshm_vect->begin(), pshm_vect->end());
-
- //Check all the inserted nodes
- int checker = 0;
- for( shm_list_t::const_iterator it = plist->begin(), itend(plist->end())
- ; it != itend
- ; ++it, ++checker){
- if(it->get() != checker){
- return false;
+ const char *ShmName = get_shared_memory_name();
+ {
+ //Erase all old shared memory
+ ip::shared_memory_object::remove(ShmName);
+ ip::managed_shared_memory shm(ip::create_only, ShmName, ShmSize);
+
+ //Create all nodes in shared memory using a shared memory vector
+ //See Boost.Interprocess documentation for more information on this
+ typedef ip::allocator
+ < shared_memory_data, ip::managed_shared_memory::segment_manager>
+ shm_allocator_t;
+ typedef ip::vector<shared_memory_data, shm_allocator_t> shm_vector_t;
+ shm_allocator_t shm_alloc(shm.get_segment_manager());
+ shm_vector_t *pshm_vect =
+ shm.construct<shm_vector_t>(ip::anonymous_instance)(shm_alloc);
+ pshm_vect->resize(MaxElem);
+
+ //Initialize all the nodes
+ for(int i = 0; i < MaxElem; ++i) (*pshm_vect)[i].set(i);
+
+ //Now create the shared memory intrusive list
+ shm_list_t *plist = shm.construct<shm_list_t>(ip::anonymous_instance)();
+ plist->insert(plist->end(), pshm_vect->begin(), pshm_vect->end());
+
+ //Check all the inserted nodes
+ int checker = 0;
+ for( shm_list_t::const_iterator it = plist->begin(), itend(plist->end())
+ ; it != itend; ++it, ++checker){
+ if(it->get() != checker) return false;
}
- }
- //Now delete the list and after that, the nodes
- shm.destroy_ptr(plist);
- shm.destroy_ptr(pshm_vect);
+ //Now delete the list and after that, the nodes
+ shm.destroy_ptr(plist);
+ shm.destroy_ptr(pshm_vect);
+ }
+ ip::shared_memory_object::remove(ShmName);
return 0;
}
//]
Modified: branches/bcbboost/libs/intrusive/example/doc_set.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_set.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_set.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,7 +17,7 @@
using namespace boost::intrusive;
//This is a base hook
-class MyClass : public set_base_hook<>
+class MyClass : public set_base_hook<>
{
int int_;
@@ -28,69 +28,54 @@
MyClass(int i)
: int_(i)
{}
- int get() const
- { return int_; }
friend bool operator< (const MyClass &a, const MyClass &b)
- { return a.get() < b.get(); }
+ { return a.int_ < b.int_; }
friend bool operator> (const MyClass &a, const MyClass &b)
- { return a.get() > b.get(); }
+ { return a.int_ > b.int_; }
friend bool operator== (const MyClass &a, const MyClass &b)
- { return a.get() < b.get(); }
+ { return a.int_ < b.int_; }
};
-//Define an set that will store MyClass
-//in reverse order using the public base hook
-typedef set< set_base_hook<>::value_traits<MyClass>
- , std::greater<MyClass> > BaseSet;
-
-//Define an multiset that will store MyClass
-//using the public member hook
-typedef multiset< set_member_hook<>::
- value_traits<MyClass, &MyClass::member_hook_>
- , std::less<MyClass> > MemberIMultiset;
+//Define an set using the base hook that will store values in reverse order
+typedef set< MyClass, compare<std::greater<MyClass> > > BaseSet;
+
+//Define an multiset using the member hook
+typedef member_hook<MyClass, set_member_hook<>, &MyClass::member_hook_> MemberOption;
+typedef multiset< MyClass, MemberOption> MemberIMultiset;
int main()
{
- typedef std::vector<MyClass> Vect;
- typedef Vect::iterator VectIt;
- typedef Vect::reverse_iterator VectRit;
-
- //Create several MyClass objects, each one
- //with a different internal number
- Vect myclassvector;
- for(int i = 0; i < 100; ++i)
- myclassvector.push_back(MyClass(i));
+ typedef std::vector<MyClass>::iterator VectIt;
+ typedef std::vector<MyClass>::reverse_iterator VectRit;
+
+ //Create several MyClass objects, each one with a different value
+ std::vector<MyClass> values;
+ for(int i = 0; i < 100; ++i) values.push_back(MyClass(i));
BaseSet baseset;
MemberIMultiset membermultiset;
- //Now insert them in the reverse order
- //in the base hook intrusive set
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend; ++it)
+ //Now insert them in the reverse order in the base hook set
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
baseset.insert(*it);
- //Now insert them in the same order as in vector in the
- //member hook intrusive set
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend; ++it)
+ //Now insert them in the same order as in vector in the member hook set
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
membermultiset.insert(*it);
//Now test sets
{
BaseSet::reverse_iterator rbit(baseset.rbegin()), rbitend(baseset.rend());
MemberIMultiset::iterator mit(membermultiset.begin()), mitend(membermultiset.end());
- VectIt it(myclassvector.begin()), itend(myclassvector.end());
+ VectIt it(values.begin()), itend(values.end());
//Test the objects inserted in the base hook set
- for(; it != itend; ++it, ++rbit){
+ for(; it != itend; ++it, ++rbit)
if(&*rbit != &*it) return 1;
- }
//Test the objects inserted in the member hook set
- for(it = myclassvector.begin(); it != itend; ++it, ++mit){
+ for(it = values.begin(); it != itend; ++it, ++mit)
if(&*mit != &*it) return 1;
- }
}
return 0;
}
Modified: branches/bcbboost/libs/intrusive/example/doc_slist.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_slist.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_slist.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -16,7 +16,7 @@
using namespace boost::intrusive;
//This is a base hook
-class MyClass : public slist_base_hook<>
+class MyClass : public slist_base_hook<>
{
int int_;
@@ -27,45 +27,34 @@
MyClass(int i)
: int_(i)
{}
-
- int get() const
- { return int_; }
};
//Define an slist that will store MyClass using the public base hook
-typedef slist< slist_base_hook<>::value_traits<MyClass> > BaseList;
+typedef slist<MyClass> BaseList;
//Define an slist that will store MyClass using the public member hook
-typedef slist< slist_member_hook<>::value_traits<MyClass, &MyClass::member_hook_> > MemberList;
+typedef member_hook<MyClass, slist_member_hook<>, &MyClass::member_hook_> MemberOption;
+typedef slist<MyClass, MemberOption> MemberList;
int main()
{
- typedef std::vector<MyClass> Vect;
- typedef Vect::iterator VectIt;
- typedef Vect::reverse_iterator VectRit;
-
- //Create several MyClass objects, each one
- //with a different internal number
- Vect myclassvector;
- for(int i = 0; i < 100; ++i)
- myclassvector.push_back(MyClass(i));
+ typedef std::vector<MyClass>::iterator VectIt;
+ typedef std::vector<MyClass>::reverse_iterator VectRit;
+
+ //Create several MyClass objects, each one with a different value
+ std::vector<MyClass> values;
+ for(int i = 0; i < 100; ++i) values.push_back(MyClass(i));
BaseList baselist;
MemberList memberlist;
- //Now insert them in the reverse order
- //in the base hook intrusive list
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend
- ; ++it){
+ //Now insert them in the reverse order in the base hook list
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
baselist.push_front(*it);
- }
- //Now insert them in the same order as in vector in the
- //member hook intrusive list
+ //Now insert them in the same order as in vector in the member hook list
for(BaseList::iterator it(baselist.begin()), itend(baselist.end())
- ; it != itend
- ; ++it){
+ ; it != itend; ++it){
memberlist.push_front(*it);
}
@@ -73,18 +62,16 @@
{
BaseList::iterator bit(baselist.begin()), bitend(baselist.end());
MemberList::iterator mit(memberlist.begin()), mitend(memberlist.end());
- VectRit rit(myclassvector.rbegin()), ritend(myclassvector.rend());
- VectIt it(myclassvector.begin()), itend(myclassvector.end());
+ VectRit rit(values.rbegin()), ritend(values.rend());
+ VectIt it(values.begin()), itend(values.end());
//Test the objects inserted in the base hook list
- for(; rit != ritend; ++rit, ++bit){
+ for(; rit != ritend; ++rit, ++bit)
if(&*bit != &*rit) return 1;
- }
//Test the objects inserted in the member hook list
- for(; it != itend; ++it, ++mit){
+ for(; it != itend; ++it, ++mit)
if(&*mit != &*it) return 1;
- }
}
return 0;
Modified: branches/bcbboost/libs/intrusive/example/doc_unordered_set.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_unordered_set.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_unordered_set.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -17,56 +17,43 @@
using namespace boost::intrusive;
- //This is a derivation hook
-class MyClass : public unordered_set_base_hook<>
-{
+class MyClass : public unordered_set_base_hook<>
+{ //This is a derivation hook
int int_;
public:
- //This is a member hook
- unordered_set_member_hook<> member_hook_;
+ unordered_set_member_hook<> member_hook_; //This is a member hook
MyClass(int i)
: int_(i)
{}
- int get() const
- { return int_; }
-
friend bool operator== (const MyClass &a, const MyClass &b)
- { return a.get() == b.get(); }
+ { return a.int_ == b.int_; }
- friend bool operator> (const MyClass &a, const MyClass &b)
- { return a.get() > b.get(); }
+ friend std::size_t hash_value(const MyClass &value)
+ { return std::size_t(value.int_); }
};
-std::size_t hash_value(const MyClass &value)
-{ return std::size_t(value.get()); }
+//Define an unordered_set that will store MyClass objects using the base hook
+typedef unordered_set<MyClass> BaseSet;
-//Define an unordered_set that will store MyClass
-//in reverse order using the public base hook
-typedef unordered_set< unordered_set_base_hook<>::
- value_traits<MyClass> > BaseSet;
-
-//Define an unordered_multiset that will store MyClass
-//using the public member hook
-typedef unordered_multiset< unordered_set_member_hook<>::
- value_traits<MyClass, &MyClass::member_hook_> > MemberMultiSet;
+//Define an unordered_multiset that will store MyClass using the member hook
+typedef member_hook<MyClass, unordered_set_member_hook<>, &MyClass::member_hook_>
+ MemberOption;
+typedef unordered_multiset< MyClass, MemberOption> MemberMultiSet;
int main()
{
- typedef std::vector<MyClass> Vect;
- typedef Vect::iterator VectIt;
- typedef Vect::reverse_iterator VectRit;
-
- //Create a vector with 100 different MyClass objects,
- //each one with a different internal number
- Vect myclassvector;
- for(int i = 0; i < 100; ++i)
- myclassvector.push_back(MyClass(i));
+ typedef std::vector<MyClass>::iterator VectIt;
+ typedef std::vector<MyClass>::reverse_iterator VectRit;
+
+ //Create a vector with 100 different MyClass objects
+ std::vector<MyClass> values;
+ for(int i = 0; i < 100; ++i) values.push_back(MyClass(i));
//Create a copy of the vector
- Vect myclassvector2(myclassvector);
+ std::vector<MyClass> values2(values);
//Create a bucket array for base_set
BaseSet::bucket_type base_buckets[100];
@@ -74,20 +61,18 @@
//Create a bucket array for member_multi_set
MemberMultiSet::bucket_type member_buckets[200];
- //Create a the unordered_set and unordered_multiset,
- //taking buckets as arguments
- BaseSet base_set(base_buckets, 100);
- MemberMultiSet member_multi_set(member_buckets, 200);
-
- //Now insert myclassvector's elements in the unordered_set
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end())
- ; it != itend; ++it){
+ //Create unordered containers taking buckets as arguments
+ BaseSet base_set(BaseSet::bucket_traits(base_buckets, 100));
+ MemberMultiSet member_multi_set
+ (MemberMultiSet::bucket_traits(member_buckets, 200));
+
+ //Now insert values's elements in the unordered_set
+ for(VectIt it(values.begin()), itend(values.end()); it != itend; ++it)
base_set.insert(*it);
- }
- //Now insert myclassvector's and myclassvector2's elements in the unordered_multiset
- for(VectIt it(myclassvector.begin()), itend(myclassvector.end()),
- it2(myclassvector2.begin()),itend2(myclassvector2.end())
+ //Now insert values's and values2's elements in the unordered_multiset
+ for(VectIt it(values.begin()), itend(values.end()),
+ it2(values2.begin()),itend2(values2.end())
; it != itend; ++it, ++it2){
member_multi_set.insert(*it);
member_multi_set.insert(*it2);
@@ -95,7 +80,7 @@
//Now find every element
{
- VectIt it(myclassvector.begin()), itend(myclassvector.end());
+ VectIt it(values.begin()), itend(values.end());
for(; it != itend; ++it){
//base_set should contain one element for each key
Modified: branches/bcbboost/libs/intrusive/example/doc_value_traits.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_value_traits.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_value_traits.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,7 +10,7 @@
//
/////////////////////////////////////////////////////////////////////////////
//[doc_value_traits_code_legacy
-#include <boost/intrusive/linking_policy.hpp>
+#include <boost/intrusive/link_mode.hpp>
#include <boost/intrusive/list.hpp>
#include <boost/intrusive/slist.hpp>
#include <vector>
@@ -30,6 +30,9 @@
//Define our own NodeTraits that will configure singly and doubly linked
//list algorithms. Note that this node traits is compatible with
//circular_slist_algorithms and circular_list_algorithms.
+
+namespace bi = boost::intrusive;
+
struct legacy_node_traits
{
typedef legacy_value node;
@@ -54,7 +57,7 @@
typedef legacy_value value_type;
typedef legacy_value * pointer;
typedef const legacy_value * const_pointer;
- enum { linking_policy = boost::intrusive::normal_link };
+ static const bi::link_mode_type link_mode = bi::normal_link;
static node_ptr to_node_ptr (value_type &value) { return node_ptr(&value); }
static const_node_ptr to_node_ptr (const value_type &value) { return const_node_ptr(&value); }
static pointer to_value_ptr(node_ptr n) { return pointer(n); }
@@ -65,8 +68,9 @@
//[doc_value_traits_test
//Now define an intrusive list and slist that will store legacy_value objects
-typedef boost::intrusive::list <legacy_value_traits> LegacyAbiList;
-typedef boost::intrusive::slist<legacy_value_traits> LegacyAbiSlist;
+typedef bi::value_traits<legacy_value_traits> ValueTraitsOption;
+typedef bi::list<legacy_value, ValueTraitsOption> LegacyAbiList;
+typedef bi::slist<legacy_value, ValueTraitsOption> LegacyAbiSlist;
template<class List>
bool test_list()
@@ -87,9 +91,8 @@
typename Vect::const_iterator it(legacy_vector.begin()), itend(legacy_vector.end());
//Test the objects inserted in our list
- for(; it != itend; ++it, ++bit){
+ for(; it != itend; ++it, ++bit)
if(&*bit != &*it) return false;
- }
return true;
}
Modified: branches/bcbboost/libs/intrusive/example/doc_window.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/example/doc_window.cpp (original)
+++ branches/bcbboost/libs/intrusive/example/doc_window.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -15,11 +15,11 @@
using namespace boost::intrusive;
//An abstract class that can be inserted in an intrusive list
-class Window : public list_base_hook<>
+class Window : public list_base_hook<>
{
public:
//This is a container those value is an abstract class: you can't do this with std::list.
- typedef list< list_base_hook<>::value_traits<Window> > win_list;
+ typedef list<Window> win_list;
//An static intrusive list declaration
static win_list all_windows;
@@ -27,7 +27,7 @@
//Constructor. Includes this window in the list
Window() { all_windows.push_back(*this); }
//Destructor. Removes this node from the list
- virtual ~Window() { all_windows.erase(win_list::iterator_to(*this)); }
+ virtual ~Window() { all_windows.erase(win_list::s_iterator_to(*this)); }
//Pure virtual function to be implemented by derived classes
virtual void Paint() = 0;
};
@@ -71,15 +71,13 @@
//Main function
int main()
{
- //When each Window class is created, is
- //automatically registered in the global list
+ //When a Window class is created, is automatically registered in the global list
MainWindow window;
//Paint all the windows, sub-windows and so on
paint_all_windows();
- //All the windows are automatically unregistered
- //in their destructors.
+ //All the windows are automatically unregistered in their destructors.
return 0;
}
//]
Modified: branches/bcbboost/libs/intrusive/perf/perf_list.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/perf/perf_list.cpp (original)
+++ branches/bcbboost/libs/intrusive/perf/perf_list.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -11,6 +11,7 @@
/////////////////////////////////////////////////////////////////////////////
//Includes for tests
+#include <boost/config.hpp>
#include <list>
#include <functional>
#include <iostream>
@@ -26,11 +27,8 @@
using namespace boost::intrusive;
-template<bool BigSize>
-struct filler { int dummy[10]; };
-
-template <>
-struct filler<false> {};
+template<bool BigSize> struct filler { int dummy[10]; };
+template <> struct filler<false> {};
template<bool BigSize> //The object for non-intrusive containers
struct test_class : private filler<BigSize>
@@ -42,8 +40,9 @@
friend bool operator >(const test_class &l, const test_class &r) { return l.i_ > r.i_; }
};
-template <bool BigSize, linking_policy Policy> //The object for intrusive containers
-struct itest_class : public list_base_hook<tag, Policy>, public test_class<BigSize>
+template <bool BigSize, link_mode_type LinkMode>
+struct itest_class //The object for intrusive containers
+ : public list_base_hook<link_mode<LinkMode> >, public test_class<BigSize>
{
itest_class() {}
itest_class(int i) : test_class<BigSize>(i) {}
@@ -60,11 +59,10 @@
};
//]
-template <bool BigSize, linking_policy Policy>
+template <bool BigSize, link_mode_type LinkMode>
struct get_ilist //Helps to define an intrusive list from a policy
{
- typedef list_base_hook<tag, Policy> hook;
- typedef list<typename hook::template value_traits<itest_class<BigSize, Policy> >, false> type;
+ typedef list<itest_class<BigSize, LinkMode>, constant_time_size<false> > type;
};
template <bool BigSize> //Helps to define an std list
@@ -73,17 +71,16 @@
template <bool BigSize> //Helps to define an std pointer list
struct get_ptrlist { typedef std::list<test_class<BigSize>*> type; };
-
////////////////////////////////////////////////////////////////////////
//
// PUSH_BACK
//
////////////////////////////////////////////////////////////////////////
-template <bool BigSize, linking_policy Policy>
+template <bool BigSize, link_mode_type LinkMode>
void test_intrusive_list_push_back()
{
- typedef typename get_ilist<BigSize, Policy>::type ilist;
+ typedef typename get_ilist<BigSize, LinkMode>::type ilist;
ptime tini = microsec_clock::universal_time();
for(int i = 0; i < NumIter; ++i){
//First create the elements and insert them in the intrusive list
@@ -93,11 +90,12 @@
for(int i = 0; i < NumElements; ++i)
l.push_back(objects[i]);
//Elements are unlinked in ilist's destructor
- //Elements are disposed in vector's destructor
+ //Elements are destroyed in vector's destructor
//]
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "link_mode: " << LinkMode << ", usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -111,11 +109,12 @@
stdlist l;
for(int i = 0; i < NumElements; ++i)
l.push_back(typename stdlist::value_type(i));
- //Elements unlinked and disposed in stdlist's destructor
+ //Elements unlinked and destroyed in stdlist's destructor
//]
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -132,12 +131,13 @@
stdptrlist l;
for(int i = 0; i < NumElements; ++i)
l.push_back(&objects[i]);
- //Pointers to elements unlinked and disposed in stdptrlist's destructor
- //Elements disposed in vector's destructor
+ //Pointers to elements unlinked and destroyed in stdptrlist's destructor
+ //Elements destroyed in vector's destructor
//]
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "compact std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -155,12 +155,13 @@
objects.push_back(typename stdlist::value_type(i));
l.push_back(&objects.back());
}
- //Pointers to elements unlinked and disposed in stdptrlist's destructor
- //Elements unlinked and disposed in stdlist's destructor
+ //Pointers to elements unlinked and destroyed in stdptrlist's destructor
+ //Elements unlinked and destroyed in stdlist's destructor
//]
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "disperse std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
////////////////////////////////////////////////////////////////////////
@@ -170,10 +171,10 @@
////////////////////////////////////////////////////////////////////////
//[perf_list_reverse
-template <bool BigSize, linking_policy Policy>
+template <bool BigSize, link_mode_type LinkMode>
void test_intrusive_list_reverse()
{
- typedef typename get_ilist<BigSize, Policy>::type ilist;
+ typedef typename get_ilist<BigSize, LinkMode>::type ilist;
//First create the elements
std::vector<typename ilist::value_type> objects(NumElements);
@@ -186,7 +187,8 @@
l.reverse();
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "link_mode: " << LinkMode << ", usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -205,7 +207,8 @@
l.reverse();
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -228,7 +231,8 @@
l.reverse();
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "compact std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -252,7 +256,8 @@
l.reverse();
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "disperse std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
//]
@@ -263,10 +268,10 @@
////////////////////////////////////////////////////////////////////////
//[perf_list_sort
-template <bool BigSize, linking_policy Policy>
+template <bool BigSize, link_mode_type LinkMode>
void test_intrusive_list_sort()
{
- typedef typename get_ilist<BigSize, Policy>::type ilist;
+ typedef typename get_ilist<BigSize, LinkMode>::type ilist;
//First create the elements
std::vector<typename ilist::value_type> objects(NumElements);
@@ -287,7 +292,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "link_mode: " << LinkMode << ", usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -311,7 +317,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -340,7 +347,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "compact std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -368,7 +376,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "disperse std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
//]
@@ -378,10 +387,10 @@
//
////////////////////////////////////////////////////////////////////////
//[perf_list_write_access
-template <bool BigSize, linking_policy Policy>
+template <bool BigSize, link_mode_type LinkMode>
void test_intrusive_list_write_access()
{
- typedef typename get_ilist<BigSize, Policy>::type ilist;
+ typedef typename get_ilist<BigSize, LinkMode>::type ilist;
//First create the elements
std::vector<typename ilist::value_type> objects(NumElements);
@@ -401,7 +410,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "link_mode: " << LinkMode << ", usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -423,7 +433,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -452,7 +463,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "compact std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
template <bool BigSize>
@@ -479,7 +491,8 @@
}
}
ptime tend = microsec_clock::universal_time();
- std::cout << "usecs/iteration: " << (tend-tini).total_microseconds()/NumIter << std::endl;
+ std::cout << "disperse std::list usecs/iteration: "
+ << (tend-tini).total_microseconds()/NumIter << std::endl;
}
//]
@@ -491,7 +504,7 @@
template<bool BigSize>
void do_all_tests()
{
- std::cout << "Testing push back() with BigSize:" << BigSize << std::endl;
+ std::cout << "\n\nTesting push back() with BigSize:" << BigSize << std::endl;
test_intrusive_list_push_back<BigSize, normal_link>();
test_intrusive_list_push_back<BigSize, safe_link>();
test_intrusive_list_push_back<BigSize, auto_unlink>();
@@ -499,7 +512,7 @@
test_compact_std_ptrlist_push_back<BigSize>();
test_disperse_std_ptrlist_push_back<BigSize>();
//reverse
- std::cout << "Testing reverse() with BigSize:" << BigSize << std::endl;
+ std::cout << "\n\nTesting reverse() with BigSize:" << BigSize << std::endl;
test_intrusive_list_reverse<BigSize, normal_link>();
test_intrusive_list_reverse<BigSize, safe_link>();
test_intrusive_list_reverse<BigSize, auto_unlink>();
@@ -507,7 +520,7 @@
test_compact_std_ptrlist_reverse<BigSize>();
test_disperse_std_ptrlist_reverse<BigSize>();
//sort
- std::cout << "Testing sort() with BigSize:" << BigSize << std::endl;
+ std::cout << "\n\nTesting sort() with BigSize:" << BigSize << std::endl;
test_intrusive_list_sort<BigSize, normal_link>();
test_intrusive_list_sort<BigSize, safe_link>();
test_intrusive_list_sort<BigSize, auto_unlink>();
@@ -515,7 +528,7 @@
test_compact_std_ptrlist_sort<BigSize>();
test_disperse_std_ptrlist_sort<BigSize>();
//write_access
- std::cout << "Testing write_access() with BigSize:" << BigSize << std::endl;
+ std::cout << "\n\nTesting write_access() with BigSize:" << BigSize << std::endl;
test_intrusive_list_write_access<BigSize, normal_link>();
test_intrusive_list_write_access<BigSize, safe_link>();
test_intrusive_list_write_access<BigSize, auto_unlink>();
Modified: branches/bcbboost/libs/intrusive/proj/vc7ide/Intrusive.sln
==============================================================================
--- branches/bcbboost/libs/intrusive/proj/vc7ide/Intrusive.sln (original)
+++ branches/bcbboost/libs/intrusive/proj/vc7ide/Intrusive.sln 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -1,71 +1,127 @@
-Microsoft Visual Studio Solution File, Format Version 8.00
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "list", "list\list.vcproj", "{977B61B4-9968-497C-9F0B-24A8145473B8}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "slist", "slist\slist.vcproj", "{5A02061D-3728-4C49-AFC8-0130C1F161C0}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "multiset", "multiset\multiset.vcproj", "{961F0E06-C092-4AF7-ABC5-2A49999F3B79}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "_intrusivelib", "_intrusivelib\_intrusivelib.vcproj", "{90F3C5BD-8E6C-4629-BC71-A1009EC88059}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "set", "set\set.vcproj", "{960E01F6-92C1-F74A-BCA5-2A9F3B994979}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unordered_set", "unordered_set\unordered_set.vcproj", "{90E701E6-2C91-F4A7-BA6C-A9F3B0949279}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unordered_multiset", "unordered_multiset\unordered_multiset.vcproj", "{9101EE76-BB6C-2C91-F4B7-A9F3B9490279}"
- ProjectSection(ProjectDependencies) = postProject
- EndProjectSection
-EndProject
-Global
- GlobalSection(SolutionConfiguration) = preSolution
- Debug = Debug
- Release = Release
- EndGlobalSection
- GlobalSection(ProjectDependencies) = postSolution
- EndGlobalSection
- GlobalSection(ProjectConfiguration) = postSolution
- {977B61B4-9968-497C-9F0B-24A8145473B8}.Debug.ActiveCfg = Debug|Win32
- {977B61B4-9968-497C-9F0B-24A8145473B8}.Debug.Build.0 = Debug|Win32
- {977B61B4-9968-497C-9F0B-24A8145473B8}.Release.ActiveCfg = Release|Win32
- {977B61B4-9968-497C-9F0B-24A8145473B8}.Release.Build.0 = Release|Win32
- {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Debug.ActiveCfg = Debug|Win32
- {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Debug.Build.0 = Debug|Win32
- {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Release.ActiveCfg = Release|Win32
- {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Release.Build.0 = Release|Win32
- {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Debug.ActiveCfg = Debug|Win32
- {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Debug.Build.0 = Debug|Win32
- {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Release.ActiveCfg = Release|Win32
- {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Release.Build.0 = Release|Win32
- {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Debug.ActiveCfg = Debug|Win32
- {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Debug.Build.0 = Debug|Win32
- {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Release.ActiveCfg = Release|Win32
- {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Release.Build.0 = Release|Win32
- {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Debug.ActiveCfg = Debug|Win32
- {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Debug.Build.0 = Debug|Win32
- {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Release.ActiveCfg = Release|Win32
- {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Release.Build.0 = Release|Win32
- {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Debug.ActiveCfg = Debug|Win32
- {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Debug.Build.0 = Debug|Win32
- {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Release.ActiveCfg = Release|Win32
- {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Release.Build.0 = Release|Win32
- {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Debug.ActiveCfg = Debug|Win32
- {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Debug.Build.0 = Debug|Win32
- {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Release.ActiveCfg = Release|Win32
- {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Release.Build.0 = Release|Win32
- EndGlobalSection
- GlobalSection(ExtensibilityGlobals) = postSolution
- EndGlobalSection
- GlobalSection(ExtensibilityAddIns) = postSolution
- EndGlobalSection
-EndGlobal
+Microsoft Visual Studio Solution File, Format Version 8.00
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "list", "list\list.vcproj", "{977B61B4-9968-497C-9F0B-24A8145473B8}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "slist", "slist\slist.vcproj", "{5A02061D-3728-4C49-AFC8-0130C1F161C0}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "multiset", "multiset\multiset.vcproj", "{961F0E06-C092-4AF7-ABC5-2A49999F3B79}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "_intrusivelib", "_intrusivelib\_intrusivelib.vcproj", "{90F3C5BD-8E6C-4629-BC71-A1009EC88059}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "set", "set\set.vcproj", "{960E01F6-92C1-F74A-BCA5-2A9F3B994979}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unordered_set", "unordered_set\unordered_set.vcproj", "{90E701E6-2C91-F4A7-BA6C-A9F3B0949279}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unordered_multiset", "unordered_multiset\unordered_multiset.vcproj", "{9101EE76-BB6C-2C91-F4B7-A9F3B9490279}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "perf_test", "perf_test\perf_test.vcproj", "{910E70E6-2C91-AA67-BF4C-A9C74A309927}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "default_hook", "default_hook\default_hook.vcproj", "{761A79B4-9968-CB81-F02B-2A4497345475}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "stateful_value_traits", "stateful_value_traits\stateful_value_traits.vcproj", "{9571A7B4-9968-B9C1-17FB-134547B46975}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "virtual_base", "virtual_base\virtual_base.vcproj", "{3579B1A4-9894-02AB-CB81-297B46154345}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "make_functions", "make_functions\make_functions.vcproj", "{7679B41B-F2B4-9176-CB81-35449467B435}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "custom_bucket_traits", "custom_bucket_traits\custom_bucket_traits.vcproj", "{31C77B84-0B2C-9481-CB81-27A149F33825}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "external_value_traits", "external_value_traits\external_value_traits.vcproj", "{97B69A72-B9D3-7389-17FB-74612F4A9543}"
+ ProjectSection(ProjectDependencies) = postProject
+ EndProjectSection
+EndProject
+Global
+ GlobalSection(SolutionConfiguration) = preSolution
+ Debug = Debug
+ Release = Release
+ EndGlobalSection
+ GlobalSection(ProjectDependencies) = postSolution
+ EndGlobalSection
+ GlobalSection(ProjectConfiguration) = postSolution
+ {977B61B4-9968-497C-9F0B-24A8145473B8}.Debug.ActiveCfg = Debug|Win32
+ {977B61B4-9968-497C-9F0B-24A8145473B8}.Debug.Build.0 = Debug|Win32
+ {977B61B4-9968-497C-9F0B-24A8145473B8}.Release.ActiveCfg = Release|Win32
+ {977B61B4-9968-497C-9F0B-24A8145473B8}.Release.Build.0 = Release|Win32
+ {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Debug.ActiveCfg = Debug|Win32
+ {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Debug.Build.0 = Debug|Win32
+ {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Release.ActiveCfg = Release|Win32
+ {5A02061D-3728-4C49-AFC8-0130C1F161C0}.Release.Build.0 = Release|Win32
+ {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Debug.ActiveCfg = Debug|Win32
+ {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Debug.Build.0 = Debug|Win32
+ {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Release.ActiveCfg = Release|Win32
+ {961F0E06-C092-4AF7-ABC5-2A49999F3B79}.Release.Build.0 = Release|Win32
+ {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Debug.ActiveCfg = Debug|Win32
+ {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Debug.Build.0 = Debug|Win32
+ {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Release.ActiveCfg = Release|Win32
+ {90F3C5BD-8E6C-4629-BC71-A1009EC88059}.Release.Build.0 = Release|Win32
+ {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Debug.ActiveCfg = Debug|Win32
+ {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Debug.Build.0 = Debug|Win32
+ {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Release.ActiveCfg = Release|Win32
+ {960E01F6-92C1-F74A-BCA5-2A9F3B994979}.Release.Build.0 = Release|Win32
+ {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Debug.ActiveCfg = Debug|Win32
+ {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Debug.Build.0 = Debug|Win32
+ {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Release.ActiveCfg = Release|Win32
+ {90E701E6-2C91-F4A7-BA6C-A9F3B0949279}.Release.Build.0 = Release|Win32
+ {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Debug.ActiveCfg = Debug|Win32
+ {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Debug.Build.0 = Debug|Win32
+ {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Release.ActiveCfg = Release|Win32
+ {9101EE76-BB6C-2C91-F4B7-A9F3B9490279}.Release.Build.0 = Release|Win32
+ {910E70E6-2C91-AA67-BF4C-A9C74A309927}.Debug.ActiveCfg = Debug|Win32
+ {910E70E6-2C91-AA67-BF4C-A9C74A309927}.Debug.Build.0 = Debug|Win32
+ {910E70E6-2C91-AA67-BF4C-A9C74A309927}.Release.ActiveCfg = Release|Win32
+ {910E70E6-2C91-AA67-BF4C-A9C74A309927}.Release.Build.0 = Release|Win32
+ {761A79B4-9968-CB81-F02B-2A4497345475}.Debug.ActiveCfg = Debug|Win32
+ {761A79B4-9968-CB81-F02B-2A4497345475}.Debug.Build.0 = Debug|Win32
+ {761A79B4-9968-CB81-F02B-2A4497345475}.Release.ActiveCfg = Release|Win32
+ {761A79B4-9968-CB81-F02B-2A4497345475}.Release.Build.0 = Release|Win32
+ {9571A7B4-9968-B9C1-17FB-134547B46975}.Debug.ActiveCfg = Debug|Win32
+ {9571A7B4-9968-B9C1-17FB-134547B46975}.Debug.Build.0 = Debug|Win32
+ {9571A7B4-9968-B9C1-17FB-134547B46975}.Release.ActiveCfg = Release|Win32
+ {9571A7B4-9968-B9C1-17FB-134547B46975}.Release.Build.0 = Release|Win32
+ {3579B1A4-9894-02AB-CB81-297B46154345}.Debug.ActiveCfg = Debug|Win32
+ {3579B1A4-9894-02AB-CB81-297B46154345}.Debug.Build.0 = Debug|Win32
+ {3579B1A4-9894-02AB-CB81-297B46154345}.Release.ActiveCfg = Release|Win32
+ {3579B1A4-9894-02AB-CB81-297B46154345}.Release.Build.0 = Release|Win32
+ {7679B41B-F2B4-9176-CB81-35449467B435}.Debug.ActiveCfg = Debug|Win32
+ {7679B41B-F2B4-9176-CB81-35449467B435}.Debug.Build.0 = Debug|Win32
+ {7679B41B-F2B4-9176-CB81-35449467B435}.Release.ActiveCfg = Release|Win32
+ {7679B41B-F2B4-9176-CB81-35449467B435}.Release.Build.0 = Release|Win32
+ {31C77B84-0B2C-9481-CB81-27A149F33825}.Debug.ActiveCfg = Debug|Win32
+ {31C77B84-0B2C-9481-CB81-27A149F33825}.Debug.Build.0 = Debug|Win32
+ {31C77B84-0B2C-9481-CB81-27A149F33825}.Release.ActiveCfg = Release|Win32
+ {31C77B84-0B2C-9481-CB81-27A149F33825}.Release.Build.0 = Release|Win32
+ {97B69A72-B9D3-7389-17FB-74612F4A9543}.Debug.ActiveCfg = Debug|Win32
+ {97B69A72-B9D3-7389-17FB-74612F4A9543}.Debug.Build.0 = Debug|Win32
+ {97B69A72-B9D3-7389-17FB-74612F4A9543}.Release.ActiveCfg = Release|Win32
+ {97B69A72-B9D3-7389-17FB-74612F4A9543}.Release.Build.0 = Release|Win32
+ EndGlobalSection
+ GlobalSection(ExtensibilityGlobals) = postSolution
+ EndGlobalSection
+ GlobalSection(ExtensibilityAddIns) = postSolution
+ EndGlobalSection
+EndGlobal
Modified: branches/bcbboost/libs/intrusive/proj/vc7ide/_intrusivelib/_intrusivelib.vcproj
==============================================================================
--- branches/bcbboost/libs/intrusive/proj/vc7ide/_intrusivelib/_intrusivelib.vcproj (original)
+++ branches/bcbboost/libs/intrusive/proj/vc7ide/_intrusivelib/_intrusivelib.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -121,7 +121,7 @@
RelativePath="..\..\..\..\..\boost\intrusive\intrusive_fwd.hpp">
</File>
<File
- RelativePath="..\..\..\..\..\boost\intrusive\linking_policy.hpp">
+ RelativePath="..\..\..\..\..\boost\intrusive\link_mode.hpp">
</File>
<File
RelativePath="..\..\..\..\..\boost\intrusive\list.hpp">
@@ -133,7 +133,7 @@
RelativePath="..\..\..\..\..\boost\intrusive\member_value_traits.hpp">
</File>
<File
- RelativePath="..\..\..\..\..\boost\intrusive\pointer_plus_bit.hpp">
+ RelativePath="..\..\..\..\..\boost\intrusive\options.hpp">
</File>
<File
RelativePath="..\..\..\..\..\boost\intrusive\rbtree.hpp">
@@ -154,9 +154,6 @@
RelativePath="..\..\..\..\..\boost\intrusive\slist_hook.hpp">
</File>
<File
- RelativePath="..\..\..\..\..\boost\intrusive\tag.hpp">
- </File>
- <File
RelativePath="..\..\..\..\..\boost\intrusive\trivial_value_traits.hpp">
</File>
<File
@@ -181,6 +178,9 @@
RelativePath="..\..\..\..\..\boost\intrusive\detail\ebo_functor_holder.hpp">
</File>
<File
+ RelativePath="..\..\..\..\..\boost\intrusive\detail\generic_hook.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\..\boost\intrusive\detail\hashtable_node.hpp">
</File>
<File
@@ -190,9 +190,15 @@
RelativePath="..\..\..\..\..\boost\intrusive\detail\mpl.hpp">
</File>
<File
+ RelativePath="..\..\..\..\..\boost\intrusive\detail\no_exceptions_support.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\..\boost\intrusive\detail\parent_from_member.hpp">
</File>
<File
+ RelativePath="..\..\..\..\..\boost\intrusive\pointer_plus_bit.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\..\boost\intrusive\detail\pointer_to_other.hpp">
</File>
<File
@@ -202,6 +208,9 @@
RelativePath="..\..\..\..\..\boost\intrusive\detail\slist_node.hpp">
</File>
<File
+ RelativePath="..\..\..\..\..\boost\intrusive\detail\transform_iterator.hpp">
+ </File>
+ <File
RelativePath="..\..\..\..\..\boost\intrusive\detail\utilities.hpp">
</File>
</Filter>
@@ -229,10 +238,16 @@
RelativePath="..\..\..\test\smart_ptr.hpp">
</File>
<File
+ RelativePath="..\..\..\test\stateful_value_traits.hpp">
+ </File>
+ <File
RelativePath="..\..\..\test\test_container.hpp">
</File>
<File
- RelativePath="..\..\..\test\testvalue.hpp">
+ RelativePath="..\..\..\test\test_macros.hpp">
+ </File>
+ <File
+ RelativePath="..\..\..\test\test_templates.hpp">
</File>
</Filter>
<Filter
@@ -242,19 +257,28 @@
RelativePath="..\..\..\example\doc_advanced_value_traits.cpp">
</File>
<File
+ RelativePath="..\..\..\example\doc_advanced_value_traits2.cpp">
+ </File>
+ <File
RelativePath="..\..\..\example\doc_assoc_optimized_code.cpp">
</File>
<File
RelativePath="..\..\..\example\doc_auto_unlink.cpp">
</File>
<File
+ RelativePath="..\..\..\example\doc_bucket_traits.cpp">
+ </File>
+ <File
RelativePath="..\..\..\example\doc_clone_from.cpp">
</File>
<File
RelativePath="..\..\..\example\doc_entity.cpp">
</File>
<File
- RelativePath="..\..\..\example\doc_erasing_and_destroying.cpp">
+ RelativePath="..\..\..\example\doc_erasing_and_disposing.cpp">
+ </File>
+ <File
+ RelativePath="..\..\..\example\doc_external_value_traits.cpp">
</File>
<File
RelativePath="..\..\..\example\doc_how_to_use.cpp">
@@ -284,6 +308,9 @@
RelativePath="..\..\..\example\doc_slist_algorithms.cpp">
</File>
<File
+ RelativePath="..\..\..\example\doc_stateful_value_traits.cpp">
+ </File>
+ <File
RelativePath="..\..\..\example\doc_unordered_set.cpp">
</File>
<File
Modified: branches/bcbboost/libs/intrusive/proj/vc7ide/list/list.vcproj
==============================================================================
--- branches/bcbboost/libs/intrusive/proj/vc7ide/list/list.vcproj (original)
+++ branches/bcbboost/libs/intrusive/proj/vc7ide/list/list.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -27,7 +27,7 @@
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="5"
- DisableLanguageExtensions="TRUE"
+ DisableLanguageExtensions="FALSE"
ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
@@ -41,6 +41,7 @@
LinkIncremental="2"
GenerateDebugInformation="TRUE"
ProgramDatabaseFile="$(OutDir)/list.pdb"
+ GenerateMapFile="FALSE"
SubSystem="1"
TargetMachine="1"/>
<Tool
@@ -75,6 +76,8 @@
AdditionalIncludeDirectories="../../../../../"
PreprocessorDefinitions="BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="4"
+ DisableLanguageExtensions="FALSE"
+ ForceConformanceInForLoopScope="TRUE"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
Modified: branches/bcbboost/libs/intrusive/proj/vc7ide/multiset/multiset.vcproj
==============================================================================
--- branches/bcbboost/libs/intrusive/proj/vc7ide/multiset/multiset.vcproj (original)
+++ branches/bcbboost/libs/intrusive/proj/vc7ide/multiset/multiset.vcproj 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -70,7 +70,7 @@
<Tool
Name="VCCLCompilerTool"
AdditionalIncludeDirectories="../../../../../"
- PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
+ PreprocessorDefinitions="_WIN32;NDEBUG;_CONSOLE;BOOST_DATE_TIME_NO_LIB"
RuntimeLibrary="4"
UsePrecompiledHeader="0"
WarningLevel="3"
Modified: branches/bcbboost/libs/intrusive/test/common_functors.hpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/common_functors.hpp (original)
+++ branches/bcbboost/libs/intrusive/test/common_functors.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -14,27 +14,31 @@
#define BOOST_INTRUSIVE_TEST_COMMON_FUNCTORS_HPP
#include<boost/intrusive/detail/utilities.hpp>
+#include<boost/intrusive/detail/mpl.hpp>
namespace boost {
namespace intrusive {
namespace test {
+template<class T>
class delete_disposer
{
-public:
+ public:
template <class Pointer>
void operator()(Pointer p)
{
+ typedef typename std::iterator_traits<Pointer>::value_type value_type;
+ BOOST_INTRUSIVE_INVARIANT_ASSERT(( detail::is_same<T, value_type>::value ));
delete detail::get_pointer(p);
}
};
+template<class T>
class new_cloner
{
-public:
- template<class Type>
- Type *operator()(const Type &t)
- { return new Type(t); }
+ public:
+ T *operator()(const T &t)
+ { return new T(t); }
};
} //namespace test {
Modified: branches/bcbboost/libs/intrusive/test/itestvalue.hpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/itestvalue.hpp (original)
+++ branches/bcbboost/libs/intrusive/test/itestvalue.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,67 +10,136 @@
// See http://www.boost.org/libs/intrusive for documentation.
//
/////////////////////////////////////////////////////////////////////////////
-#ifndef BOOST_INTRUSIVE_ITESTVALUE
-#define BOOST_INTRUSIVE_ITESTVALUE
+#ifndef BOOST_INTRUSIVE_DETAIL_ITESTVALUE_HPP
+#define BOOST_INTRUSIVE_DETAIL_ITESTVALUE_HPP
#include <iostream>
#include <boost/intrusive/set_hook.hpp>
#include <boost/intrusive/list_hook.hpp>
#include <boost/intrusive/slist_hook.hpp>
#include <boost/intrusive/unordered_set_hook.hpp>
+#include <boost/intrusive/options.hpp>
#include "smart_ptr.hpp"
namespace boost{
namespace intrusive{
+struct my_tag;
+
+template<class VoidPointer>
+struct set_base_hook_type
+{ typedef set_base_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct set_auto_base_hook_type
+{ typedef set_base_hook<link_mode<auto_unlink>, void_pointer<VoidPointer>, tag<my_tag> > type; };
+
+template<class VoidPointer>
+struct set_member_hook_type
+{ typedef set_member_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct set_auto_member_hook_type
+{ typedef set_member_hook<link_mode<auto_unlink>, void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct list_base_hook_type
+{ typedef list_base_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct list_auto_base_hook_type
+{ typedef list_base_hook<link_mode<auto_unlink>, void_pointer<VoidPointer>, tag<my_tag> > type; };
+
+template<class VoidPointer>
+struct list_member_hook_type
+{ typedef list_member_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct list_auto_member_hook_type
+{ typedef list_member_hook<link_mode<auto_unlink>, void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct slist_base_hook_type
+{ typedef slist_base_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct slist_auto_base_hook_type
+{ typedef slist_base_hook<link_mode<auto_unlink>, void_pointer<VoidPointer>, tag<my_tag> > type; };
+
+template<class VoidPointer>
+struct slist_member_hook_type
+{ typedef slist_member_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct slist_auto_member_hook_type
+{ typedef slist_member_hook<link_mode<auto_unlink>, void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct uset_base_hook_type
+{ typedef unordered_set_base_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct uset_auto_base_hook_type
+{ typedef unordered_set_base_hook<link_mode<auto_unlink>, void_pointer<VoidPointer>, tag<my_tag> > type; };
+
+template<class VoidPointer>
+struct uset_member_hook_type
+{ typedef unordered_set_member_hook<void_pointer<VoidPointer> > type; };
+
+template<class VoidPointer>
+struct uset_auto_member_hook_type
+{ typedef unordered_set_member_hook<link_mode<auto_unlink>, void_pointer<VoidPointer> > type; };
+
template<class VoidPointer, bool ConstantTimeSize>
struct testvalue
- : set_base_hook<tag, safe_link, VoidPointer>
- , set_base_hook<tag, auto_unlink, VoidPointer>
- , unordered_set_base_hook<tag, safe_link, VoidPointer>
- , unordered_set_base_hook<tag, auto_unlink, VoidPointer>
- , list_base_hook<tag, safe_link, VoidPointer>
- , list_base_hook<tag, auto_unlink, VoidPointer>
- , slist_base_hook<tag, safe_link, VoidPointer>
- , slist_base_hook<tag, auto_unlink, VoidPointer>
+ : set_base_hook_type<VoidPointer>::type
+ , set_auto_base_hook_type<VoidPointer>::type
+ , list_base_hook_type<VoidPointer>::type
+ , list_auto_base_hook_type<VoidPointer>::type
+ , slist_base_hook_type<VoidPointer>::type
+ , slist_auto_base_hook_type<VoidPointer>::type
+ , uset_base_hook_type<VoidPointer>::type
+ , uset_auto_base_hook_type<VoidPointer>::type
{
- typedef set_base_hook<tag, auto_unlink, VoidPointer> set_auto_base_hook_t;
- typedef set_base_hook<tag, safe_link, VoidPointer> set_base_hook_t;
- typedef set_member_hook<auto_unlink, VoidPointer> set_auto_member_hook_t;
- typedef set_member_hook<safe_link, VoidPointer> set_member_hook_t;
-
- typedef unordered_set_base_hook<tag, auto_unlink, VoidPointer> unordered_set_auto_base_hook_t;
- typedef unordered_set_base_hook<tag, safe_link, VoidPointer> unordered_set_base_hook_t;
- typedef unordered_set_member_hook<auto_unlink, VoidPointer> unordered_set_auto_member_hook_t;
- typedef unordered_set_member_hook<safe_link, VoidPointer> unordered_set_member_hook_t;
-
- typedef list_base_hook<tag, auto_unlink, VoidPointer> list_auto_base_hook_t;
- typedef list_base_hook<tag, safe_link, VoidPointer> list_base_hook_t;
- typedef list_member_hook<auto_unlink, VoidPointer> list_auto_member_hook_t;
- typedef list_member_hook<safe_link, VoidPointer> list_member_hook_t;
-
- typedef slist_base_hook<tag, auto_unlink, VoidPointer> slist_auto_base_hook_t;
- typedef slist_base_hook<tag, safe_link, VoidPointer> slist_base_hook_t;
- typedef slist_member_hook<auto_unlink, VoidPointer> slist_auto_member_hook_t;
- typedef slist_member_hook<safe_link, VoidPointer> slist_member_hook_t;
+ typedef typename set_auto_base_hook_type<VoidPointer>::type set_auto_base_hook_t;
+ typedef typename set_base_hook_type<VoidPointer>::type set_base_hook_t;
+ typedef typename set_auto_member_hook_type<VoidPointer>::type set_auto_member_hook_t;
+ typedef typename set_member_hook_type<VoidPointer>::type set_member_hook_t;
+
+ typedef typename uset_auto_base_hook_type<VoidPointer>::type unordered_set_auto_base_hook_t;
+ typedef typename uset_base_hook_type<VoidPointer>::type unordered_set_base_hook_t;
+ typedef typename uset_auto_member_hook_type<VoidPointer>::type unordered_set_auto_member_hook_t;
+ typedef typename uset_member_hook_type<VoidPointer>::type unordered_set_member_hook_t;
+
+ typedef typename list_auto_base_hook_type<VoidPointer>::type list_auto_base_hook_t;
+ typedef typename list_base_hook_type<VoidPointer>::type list_base_hook_t;
+ typedef typename list_auto_member_hook_type<VoidPointer>::type list_auto_member_hook_t;
+ typedef typename list_member_hook_type<VoidPointer>::type list_member_hook_t;
+
+ typedef typename slist_auto_base_hook_type<VoidPointer>::type slist_auto_base_hook_t;
+ typedef typename slist_base_hook_type<VoidPointer>::type slist_base_hook_t;
+ typedef typename slist_auto_member_hook_type<VoidPointer>::type slist_auto_member_hook_t;
+ typedef typename slist_member_hook_type<VoidPointer>::type slist_member_hook_t;
//Set members
- set_member_hook_t set_node_;
- set_auto_member_hook_t set_auto_node_;
- unordered_set_member_hook_t unordered_set_node_;
+ set_member_hook_t set_node_;
+ set_auto_member_hook_t set_auto_node_;
+
+ //Unordered set members
+ unordered_set_member_hook_t unordered_set_node_;
unordered_set_auto_member_hook_t unordered_set_auto_node_;
//List members
- list_member_hook_t list_node_;
- list_auto_member_hook_t list_auto_node_;
+ list_member_hook_t list_node_;
+ list_auto_member_hook_t list_auto_node_;
//Slist members
- slist_member_hook_t slist_node_;
- slist_auto_member_hook_t slist_auto_node_;
+ slist_member_hook_t slist_node_;
+ slist_auto_member_hook_t slist_auto_node_;
int value_;
- enum{ constant_time_size = ConstantTimeSize };
+ static const bool constant_time_size = ConstantTimeSize;
testvalue()
{}
@@ -89,44 +158,53 @@
testvalue & operator= (const testvalue& src)
{
set_base_hook_t::operator=(src);
- this->set_node_ = src.set_node_;
set_auto_base_hook_t::operator=(src);
+ this->set_node_ = src.set_node_;
this->set_auto_node_ = src.set_auto_node_;
unordered_set_base_hook_t::operator=(src);
- this->unordered_set_node_ = src.unordered_set_node_;
unordered_set_auto_base_hook_t::operator=(src);
+ this->unordered_set_node_ = src.unordered_set_node_;
this->unordered_set_auto_node_ = src.unordered_set_auto_node_;
list_base_hook_t::operator=(src);
- this->list_node_ = src.list_node_;
list_auto_base_hook_t::operator=(src);
+ this->list_node_ = src.list_node_;
this->list_auto_node_ = src.list_auto_node_;
slist_base_hook_t::operator=(src);
- this->slist_node_ = src.slist_node_;
slist_auto_base_hook_t::operator=(src);
+ this->slist_node_ = src.slist_node_;
this->slist_auto_node_ = src.slist_auto_node_;
+
value_ = src.value_;
return *this;
}
void swap_nodes(testvalue &other)
{
- //Set has no swapping
-
- //...
+ //Set
+ set_base_hook_t::swap_nodes(other);
+ set_auto_base_hook_t::swap_nodes(other);
+ set_node_.swap_nodes(other.set_node_);
+ set_auto_node_.swap_nodes(other.set_auto_node_);
+
+ //Unordered set
+ unordered_set_base_hook_t::swap_nodes(other);
+ unordered_set_auto_base_hook_t::swap_nodes(other);
+ unordered_set_node_.swap_nodes(other.unordered_set_node_);
+ unordered_set_auto_node_.swap_nodes(other.unordered_set_auto_node_);
//List
list_base_hook_t::swap_nodes(other);
- list_node_.swap_nodes(other.list_node_);
list_auto_base_hook_t::swap_nodes(other);
+ list_node_.swap_nodes(other.list_node_);
list_auto_node_.swap_nodes(other.list_auto_node_);
//Slist
slist_base_hook_t::swap_nodes(other);
- slist_node_.swap_nodes(other.slist_node_);
slist_auto_base_hook_t::swap_nodes(other);
+ slist_node_.swap_nodes(other.slist_node_);
slist_auto_node_.swap_nodes(other.slist_auto_node_);
}
@@ -178,159 +256,6 @@
}
};
-typedef testvalue<void *, false> value_r_f;
-typedef testvalue<smart_ptr<void>, false> value_s_f;
-typedef testvalue<void *, true> value_r_t;
-typedef testvalue<smart_ptr<void>, true> value_s_t;
-
-//Typedefs
-typedef value_r_f::set_base_hook_t::
- value_traits<value_r_f > set_base_raw;
-
-typedef value_r_f::set_member_hook_t::
- value_traits<value_r_f, &value_r_f::set_node_> set_member_raw;
-
-typedef value_r_f::set_auto_base_hook_t::
- value_traits<value_r_f> set_auto_base_raw;
-
-typedef value_r_f::set_auto_member_hook_t::
- value_traits<value_r_f, &value_r_f::set_auto_node_> set_auto_member_raw;
-
-
-typedef value_s_f::set_base_hook_t::
- value_traits<value_s_f > set_base_smart;
-
-typedef value_s_f::set_member_hook_t::
- value_traits<value_s_f, &value_s_f::set_node_> set_member_smart;
-
-typedef value_s_f::set_auto_base_hook_t::
- value_traits<value_s_f> set_auto_base_smart;
-
-typedef value_s_f::set_auto_member_hook_t::
- value_traits<value_s_f, &value_s_f::set_auto_node_> set_auto_member_smart;
-
-typedef value_r_t::set_base_hook_t::
- value_traits<value_r_t > set_base_raw_t;
-
-typedef value_r_t::set_member_hook_t::
- value_traits<value_r_t, &value_r_t::set_node_> set_member_raw_t;
-
-typedef value_s_t::set_base_hook_t::
- value_traits<value_s_t > set_base_smart_t;
-
-typedef value_s_t::set_member_hook_t::
- value_traits<value_s_t, &value_s_t::set_node_> set_member_smart_t;
-
-//Typedefs
-typedef value_r_f::unordered_set_base_hook_t::
- value_traits<value_r_f > unordered_set_base_raw;
-
-typedef value_r_f::unordered_set_member_hook_t::
- value_traits<value_r_f, &value_r_f::unordered_set_node_> unordered_set_member_raw;
-
-typedef value_r_f::unordered_set_auto_base_hook_t::
- value_traits<value_r_f> unordered_set_auto_base_raw;
-
-typedef value_r_f::unordered_set_auto_member_hook_t::
- value_traits<value_r_f, &value_r_f::unordered_set_auto_node_> unordered_set_auto_member_raw;
-
-typedef value_s_f::unordered_set_base_hook_t::
- value_traits<value_s_f > unordered_set_base_smart;
-
-typedef value_s_f::unordered_set_member_hook_t::
- value_traits<value_s_f, &value_s_f::unordered_set_node_> unordered_set_member_smart;
-
-typedef value_s_f::unordered_set_auto_base_hook_t::
- value_traits<value_s_f> unordered_set_auto_base_smart;
-
-typedef value_s_f::unordered_set_auto_member_hook_t::
- value_traits<value_s_f, &value_s_f::unordered_set_auto_node_> unordered_set_auto_member_smart;
-
-typedef value_r_t::unordered_set_base_hook_t::
- value_traits<value_r_t > unordered_set_base_raw_t;
-
-typedef value_r_t::unordered_set_member_hook_t::
- value_traits<value_r_t, &value_r_t::unordered_set_node_> unordered_set_member_raw_t;
-
-typedef value_s_t::unordered_set_base_hook_t::
- value_traits<value_s_t > unordered_set_base_smart_t;
-
-typedef value_s_t::unordered_set_member_hook_t::
- value_traits<value_s_t, &value_s_t::unordered_set_node_> unordered_set_member_smart_t;
-
-//Explicit instantiations
-typedef value_r_f::list_base_hook_t::
- value_traits<value_r_f> list_base_raw;
-
-typedef value_r_f::list_member_hook_t::
- value_traits<value_r_f, &value_r_f::list_node_> list_member_raw;
-
-typedef value_r_f::list_auto_base_hook_t::
- value_traits<value_r_f> list_auto_base_raw;
-
-typedef value_r_f::list_auto_member_hook_t::
- value_traits<value_r_f, &value_r_f::list_auto_node_> list_auto_member_raw;
-
-typedef value_s_f::list_base_hook_t::
- value_traits<value_s_f> list_base_smart;
-
-typedef value_s_f::list_member_hook_t::
- value_traits<value_s_f, &value_s_f::list_node_> list_member_smart;
-
-typedef value_s_f::list_auto_base_hook_t::
- value_traits<value_s_f> list_auto_base_smart;
-
-typedef value_s_f::list_auto_member_hook_t::
- value_traits<value_s_f, &value_s_f::list_auto_node_> list_auto_member_smart;
-
-typedef value_r_t::list_base_hook_t::
- value_traits<value_r_t> list_base_raw_t;
-
-typedef value_r_t::list_member_hook_t::
- value_traits<value_r_t, &value_r_t::list_node_> list_member_raw_t;
-
-typedef value_s_t::list_base_hook_t::
- value_traits<value_s_t> list_base_smart_t;
-
-typedef value_s_t::list_member_hook_t::
- value_traits<value_s_t, &value_s_t::list_node_> list_member_smart_t;
-
-typedef value_r_f::slist_base_hook_t::
- value_traits<value_r_f> slist_base_raw;
-
-typedef value_r_f::slist_member_hook_t::
- value_traits<value_r_f, &value_r_f::slist_node_> slist_member_raw;
-
-typedef value_r_f::slist_auto_base_hook_t::
- value_traits<value_r_f> slist_auto_base_raw;
-
-typedef value_r_f::slist_auto_member_hook_t::
- value_traits<value_r_f, &value_r_f::slist_auto_node_> slist_auto_member_raw;
-
-typedef value_s_f::slist_base_hook_t::
- value_traits<value_s_f> slist_base_smart;
-
-typedef value_s_f::slist_member_hook_t::
- value_traits<value_s_f, &value_s_f::slist_node_> slist_member_smart;
-
-typedef value_s_f::slist_auto_base_hook_t::
- value_traits<value_s_f> slist_auto_base_smart;
-
-typedef value_s_f::slist_auto_member_hook_t::
- value_traits<value_s_f, &value_s_f::slist_auto_node_> slist_auto_member_smart;
-
-typedef value_r_t::slist_base_hook_t::
- value_traits<value_r_t> slist_base_raw_t;
-
-typedef value_r_t::slist_member_hook_t::
- value_traits<value_r_t, &value_r_t::slist_node_> slist_member_raw_t;
-
-typedef value_s_t::slist_base_hook_t::
- value_traits<value_s_t> slist_base_smart_t;
-
-typedef value_s_t::slist_member_hook_t::
- value_traits<value_s_t, &value_s_t::slist_node_> slist_member_smart_t;
-
} //namespace boost{
} //namespace intrusive{
Modified: branches/bcbboost/libs/intrusive/test/list_test.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/list_test.cpp (original)
+++ branches/bcbboost/libs/intrusive/test/list_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -35,17 +35,19 @@
static void test_shift(std::vector<value_type>& values);
static void test_swap(std::vector<value_type>& values);
static void test_clone(std::vector<value_type>& values);
+ static void test_container_from_end(std::vector<value_type>& values);
};
template<class ValueTraits>
void test_list<ValueTraits>::test_all(std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::list
- < ValueTraits
- , ValueTraits::value_type::constant_time_size
- , std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
-
{
list_type list(values.begin(), values.end());
test::test_container(list);
@@ -60,9 +62,15 @@
test_shift(values);
test_swap(values);
test_clone(values);
-
- list_type testlist(values.begin(), values.end());
- list_type testlist2;
+ test_container_from_end(values);
+/*
+ const char *list_name = typeid(list_type).name();
+ std::cout << list_name << std::endl << strlen(list_name) << std::endl;
+ const char *value_t = typeid(typename list_type::value_traits).name();
+ std::cout << value_t << std::endl << strlen(value_t) << std::endl;
+ const char *list_it_name = typeid(typename list_type::iterator).name();
+ std::cout << list_it_name << std::endl << strlen(list_it_name ) << std::endl;
+*/
}
//test: push_front, pop_front, push_back, pop_back, front, back, size, empty:
@@ -70,10 +78,12 @@
void test_list<ValueTraits>
::test_front_back(std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::list
- < ValueTraits
- , ValueTraits::value_type::constant_time_size
- , std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
BOOST_TEST (testlist.empty());
@@ -104,12 +114,12 @@
void test_list<ValueTraits>
::test_sort(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<int> expected;
- typedef boost::intrusive::list
- < ValueTraits
- , ValueTraits::value_type::constant_time_size
- , std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist(values.begin(), values.end());
@@ -125,17 +135,17 @@
TEST_INTRUSIVE_SEQUENCE( init_values, testlist.begin() ); }
}
-//test: assign, insert, const_iterator, const_reverse_iterator, erase, iterator_to:
+//test: assign, insert, const_iterator, const_reverse_iterator, erase, s_iterator_to:
template<class ValueTraits>
void test_list<ValueTraits>
::test_insert(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<int> expected;
- typedef boost::intrusive::list
- < ValueTraits
- , ValueTraits::value_type::constant_time_size
- , std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
testlist.assign (&values[0] + 2, &values[0] + 5);
@@ -159,6 +169,9 @@
i = testlist.iterator_to (values[4]);
BOOST_TEST (&*i == &values[4]);
+ i = list_type::s_iterator_to (values[4]);
+ BOOST_TEST (&*i == &values[4]);
+
i = testlist.erase (i);
BOOST_TEST (i == testlist.end());
@@ -170,15 +183,14 @@
void test_list<ValueTraits>
::test_shift(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::list
- < ValueTraits
- , ValueTraits::value_type::constant_time_size
- , std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
- std::vector<int> expected;
-
const int num_values = (int)values.size();
std::vector<int> expected_values(num_values);
@@ -210,12 +222,13 @@
void test_list<ValueTraits>
::test_swap(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::list
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
- std::vector<int> expected;
{
list_type testlist1 (&values[0], &values[0] + 2);
list_type testlist2;
@@ -269,21 +282,38 @@
template<class ValueTraits>
void test_list<ValueTraits>
- ::test_clone(std::vector<typename ValueTraits::value_type>& values)
+ ::test_container_from_end(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<int> expected;
- typedef boost::intrusive::list
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
+ list_type testlist1 (&values[0], &values[0] + values.size());
+ BOOST_TEST (testlist1 == list_type::container_from_end_iterator(testlist1.end()));
+ BOOST_TEST (testlist1 == list_type::container_from_end_iterator(testlist1.cend()));
+}
+
+template<class ValueTraits>
+void test_list<ValueTraits>
+ ::test_clone(std::vector<typename ValueTraits::value_type>& values)
+{
+ typedef typename ValueTraits::value_type value_type;
+ typedef list
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
+ > list_type;
list_type testlist1 (&values[0], &values[0] + values.size());
list_type testlist2;
- testlist2.clone_from(testlist1, test::new_cloner(), test::delete_disposer());
+ testlist2.clone_from(testlist1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
BOOST_TEST (testlist2 == testlist1);
- testlist2.clear_and_dispose(test::delete_disposer());
+ testlist2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testlist2.empty());
}
@@ -293,17 +323,24 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, constant_time_size> testvalue_t;
- std::vector<testvalue_t> data (5);
+ typedef testvalue<VoidPointer, constant_time_size> value_type;
+ std::vector<value_type> data (5);
for (int i = 0; i < 5; ++i)
data[i].value_ = i + 1;
- test_list <typename testvalue_t::list_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_list <typename testvalue_t::list_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::list_node_> >::test_all(data);
-
+ test_list < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::list_base_hook_t
+ >::type
+ >::test_all(data);
+ test_list < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::list_member_hook_t
+ , &value_type::list_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
@@ -314,48 +351,64 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, false> testvalue_t;
- std::vector<testvalue_t> data (5);
+ typedef testvalue<VoidPointer, false> value_type;
+ std::vector<value_type> data (5);
for (int i = 0; i < 5; ++i)
data[i].value_ = i + 1;
- test_list <typename testvalue_t::list_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_list <typename testvalue_t::list_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::list_node_> >::test_all(data);
-
- test_list <typename testvalue_t::list_auto_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_list <typename testvalue_t::list_auto_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::list_auto_node_> >::test_all(data);
+ test_list < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::list_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_list < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::list_member_hook_t
+ , &value_type::list_node_
+ >
+ >::type
+ >::test_all(data);
+/*
+ test_list<stateful_value_traits
+ < value_type
+ , list_node_traits<VoidPointer>
+ , safe_link>
+ >::test_all(data);
+*/
+ test_list < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::list_auto_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_list < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::list_auto_member_hook_t
+ , &value_type::list_auto_node_
+ >
+ >::type
+ >::test_all(data);
+/*
+ test_list<stateful_value_traits
+ < value_type
+ , list_node_traits<VoidPointer>
+ , auto_unlink>
+ >::test_all(data);
+*/
return 0;
}
};
-//Explicit instantiations of non-counted classes
-//template class boost::intrusive::list<list_base_raw, false>;
-//template class boost::intrusive::list<list_member_raw, false>;
-//template class boost::intrusive::list<list_auto_base_raw, false>;
-//template class boost::intrusive::list<list_auto_member_raw, false>;
-//template class boost::intrusive::list<list_base_smart, false>;
-//template class boost::intrusive::list<list_member_smart, false>;
-//template class boost::intrusive::list<list_auto_base_smart, false>;
-//template class boost::intrusive::list<list_auto_member_smart, false>;
-
-//Explicit instantiation of counted classes
-//template class boost::intrusive::list<list_base_raw_t, true>;
-//template class boost::intrusive::list<list_member_raw_t, true>;
-//template class boost::intrusive::list<list_base_smart_t, true>;
-//template class boost::intrusive::list<list_member_smart_t, true>;
-
int main( int, char* [] )
{
test_main_template<void*, false>()();
- test_main_template<boost::intrusive::smart_ptr<void>, false>()();
+ test_main_template<smart_ptr<void>, false>()();
test_main_template<void*, true>()();
- test_main_template<boost::intrusive::smart_ptr<void>, true>()();
+ test_main_template<smart_ptr<void>, true>()();
+
return boost::report_errors();
}
#include <boost/intrusive/detail/config_end.hpp>
Modified: branches/bcbboost/libs/intrusive/test/multiset_test.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/multiset_test.cpp (original)
+++ branches/bcbboost/libs/intrusive/test/multiset_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,6 +10,7 @@
// See http://www.boost.org/libs/intrusive for documentation.
//
/////////////////////////////////////////////////////////////////////////////
+
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/set.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
@@ -22,7 +23,6 @@
#include "test_container.hpp"
using namespace boost::intrusive;
-
template<class ValueTraits>
struct test_multiset
{
@@ -34,15 +34,17 @@
static void test_find(std::vector<value_type>& values);
static void test_impl();
static void test_clone(std::vector<value_type>& values);
+ static void test_container_from_end(std::vector<value_type>& values);
};
template<class ValueTraits>
void test_multiset<ValueTraits>::test_all (std::vector<typename ValueTraits::value_type>& values)
{
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
{
multiset_type testset(values.begin(), values.end());
@@ -63,21 +65,24 @@
test_find(values);
test_impl();
test_clone(values);
+ test_container_from_end(values);
}
//test case due to an error in tree implementation:
template<class ValueTraits>
void test_multiset<ValueTraits>::test_impl()
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<testvalue_t> values (5);
+ typedef typename ValueTraits::value_type value_type;
+ std::vector<value_type> values (5);
for (int i = 0; i < 5; ++i)
values[i].value_ = i;
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
+
multiset_type testset;
for (int i = 0; i < 5; ++i)
testset.insert (values[i]);
@@ -94,12 +99,13 @@
template<class ValueTraits>
void test_multiset<ValueTraits>::test_sort(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
+
multiset_type testset1 (values.begin(), values.end());
{ int init_values [] = { 1, 2, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
@@ -108,9 +114,10 @@
BOOST_TEST (testset1.empty());
typedef multiset
- <ValueTraits
- ,even_odd
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ <value_type
+ , compare<even_odd>
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type2;
multiset_type2 testset2 (&values[0], &values[0] + 6);
{ int init_values [] = { 5, 3, 1, 4, 2, 2 };
@@ -124,11 +131,12 @@
template<class ValueTraits>
void test_multiset<ValueTraits>::test_insert(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
multiset_type testset;
@@ -147,6 +155,10 @@
i = testset.iterator_to (values[2]);
BOOST_TEST (&*i == &values[2]);
+
+ i = multiset_type::s_iterator_to (values[2]);
+ BOOST_TEST (&*i == &values[2]);
+
testset.erase(i);
{ int init_values [] = { 1, 3, 5 };
@@ -157,11 +169,12 @@
template<class ValueTraits>
void test_multiset<ValueTraits>::test_swap(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
multiset_type testset1 (&values[0], &values[0] + 2);
multiset_type testset2;
@@ -182,16 +195,17 @@
template<class ValueTraits>
void test_multiset<ValueTraits>::test_find(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
multiset_type testset (values.begin(), values.end());
typedef typename multiset_type::iterator iterator;
- testvalue_t cmp_val;
+ value_type cmp_val;
cmp_val.value_ = 2;
iterator i = testset.find (cmp_val);
BOOST_TEST (i->value_ == 2);
@@ -210,20 +224,37 @@
void test_multiset<ValueTraits>
::test_clone(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
+ typedef typename ValueTraits::value_type value_type;
typedef multiset
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> multiset_type;
+ multiset_type testmultiset1 (&values[0], &values[0] + values.size());
+ multiset_type testmultiset2;
- multiset_type testmultiset1 (&values[0], &values[0] + values.size());
- multiset_type testmultiset2;
+ testmultiset2.clone_from(testmultiset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
+ BOOST_TEST (testmultiset2 == testmultiset1);
+ testmultiset2.clear_and_dispose(test::delete_disposer<value_type>());
+ BOOST_TEST (testmultiset2.empty());
+}
- testmultiset2.clone_from(testmultiset1, test::new_cloner(), test::delete_disposer());
- BOOST_TEST (testmultiset2 == testmultiset1);
- testmultiset2.clear_and_dispose(test::delete_disposer());
- BOOST_TEST (testmultiset2.empty());
+template<class ValueTraits>
+void test_multiset<ValueTraits>
+ ::test_container_from_end(std::vector<typename ValueTraits::value_type>& values)
+{
+ typedef typename ValueTraits::value_type value_type;
+ typedef multiset
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
+ > multiset_type;
+
+ multiset_type testmultiset (&values[0], &values[0] + values.size());
+ BOOST_TEST (testmultiset == multiset_type::container_from_end_iterator(testmultiset.end()));
+ BOOST_TEST (testmultiset == multiset_type::container_from_end_iterator(testmultiset.cend()));
}
template<class VoidPointer, bool constant_time_size>
@@ -232,18 +263,25 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, constant_time_size> testvalue_t;
+ typedef testvalue<VoidPointer, constant_time_size> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, constant_time_size> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_multiset <typename testvalue_t::set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_multiset <typename testvalue_t::set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::set_node_> >::test_all(data);
-
+ test_multiset < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::set_base_hook_t
+ >::type
+ >::test_all(data);
+ test_multiset < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::set_member_hook_t
+ , &value_type::set_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
@@ -254,55 +292,73 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, false> testvalue_t;
+ typedef testvalue<VoidPointer, false> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, false> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_multiset <typename testvalue_t::set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_multiset <typename testvalue_t::set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::set_node_> >::test_all(data);
-
- test_multiset <typename testvalue_t::set_auto_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_multiset <typename testvalue_t::set_auto_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::set_auto_node_> >::test_all(data);
+ test_multiset < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::set_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_multiset < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::set_member_hook_t
+ , &value_type::set_node_
+ >
+ >::type
+ >::test_all(data);
+
+ test_multiset < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::set_auto_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_multiset < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::set_auto_member_hook_t
+ , &value_type::set_auto_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
-/*
+
//Explicit instantiations of non-counted classes
-template class multiset
- <set_base_raw, std::less<set_base_raw::value_type>, false>;
-template class multiset
- <set_member_raw, std::less<set_member_raw::value_type>, false>;
-template class multiset
- <set_auto_base_raw, std::less<set_auto_base_raw::value_type>, false>;
-template class multiset
- <set_auto_member_raw, std::less<set_auto_member_raw::value_type>, false>;
-template class multiset
- <set_base_smart, std::less<set_base_smart::value_type>, false>;
-template class multiset
- <set_member_smart, std::less<set_member_smart::value_type>, false>;
-template class multiset
- <set_auto_base_smart, std::less<set_auto_base_smart::value_type>, false>;
-template class multiset
- <set_auto_member_smart, std::less<set_auto_member_smart::value_type>, false>;
+//template class multiset
+// <set_base_raw, std::less<set_base_raw::value_type>, false>;
+//template class multiset
+// <set_member_raw, std::less<set_member_raw::value_type>, false>;
+//template class multiset
+// <set_auto_base_raw, std::less<set_auto_base_raw::value_type>, false>;
+//template class multiset
+// <set_auto_member_raw, std::less<set_auto_member_raw::value_type>, false>;
+//template class multiset
+// <set_base_smart, std::less<set_base_smart::value_type>, false>;
+//template class multiset
+// <set_member_smart, std::less<set_member_smart::value_type>, false>;
+//template class multiset
+// <set_auto_base_smart, std::less<set_auto_base_smart::value_type>, false>;
+//template class multiset
+// <set_auto_member_smart, std::less<set_auto_member_smart::value_type>, false>;
//Explicit instantiation of counted classes
-template class multiset
- <set_base_raw_t, std::less<set_base_raw_t::value_type>, true>;
-template class multiset
- <set_member_raw_t, std::less<set_member_raw_t::value_type>, true>;
-template class multiset
- <set_base_smart_t, std::less<set_base_smart_t::value_type>, true>;
-template class multiset
- <set_member_smart_t, std::less<set_member_smart_t::value_type>, true>;
-*/
+//template class multiset
+// <set_base_raw_t, std::less<set_base_raw_t::value_type>, true>;
+//template class multiset
+// <set_member_raw_t, std::less<set_member_raw_t::value_type>, true>;
+//template class multiset
+// <set_base_smart_t, std::less<set_base_smart_t::value_type>, true>;
+//template class multiset
+// <set_member_smart_t, std::less<set_member_smart_t::value_type>, true>;
+
int main( int, char* [] )
{
test_main_template<void*, false>()();
@@ -311,5 +367,3 @@
test_main_template<smart_ptr<void>, true>()();
return boost::report_errors();
}
-
-#include <boost/intrusive/detail/config_end.hpp>
Modified: branches/bcbboost/libs/intrusive/test/set_test.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/set_test.cpp (original)
+++ branches/bcbboost/libs/intrusive/test/set_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -34,15 +34,17 @@
static void test_find(std::vector<value_type>& values);
static void test_impl();
static void test_clone(std::vector<value_type>& values);
+ static void test_container_from_end(std::vector<value_type>& values);
};
template<class ValueTraits>
void test_set<ValueTraits>::test_all(std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
{
set_type testset(values.begin(), values.end());
@@ -63,21 +65,23 @@
test_find(values);
test_impl();
test_clone(values);
+ test_container_from_end(values);
}
//test case due to an error in tree implementation:
template<class ValueTraits>
void test_set<ValueTraits>::test_impl()
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<testvalue_t> values (5);
+ typedef typename ValueTraits::value_type value_type;
+ std::vector<value_type> values (5);
for (int i = 0; i < 5; ++i)
values[i].value_ = i;
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
set_type testset;
for (int i = 0; i < 5; ++i)
@@ -95,11 +99,11 @@
template<class ValueTraits>
void test_set<ValueTraits>::test_sort(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
set_type testset1 (values.begin(), values.end());
{ int init_values [] = { 1, 2, 3, 4, 5 };
@@ -108,10 +112,12 @@
testset1.clear();
BOOST_TEST (testset1.empty());
- typedef boost::intrusive::set
- <ValueTraits
- ,even_odd
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , compare<even_odd>
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type2;
set_type2 testset2 (&values[0], &values[0] + 6);
{ int init_values [] = { 5, 3, 1, 4, 2 };
@@ -120,15 +126,15 @@
BOOST_TEST (testset2.rbegin()->value_ == 5);
}
-//test: insert, const_iterator, const_reverse_iterator, erase, iterator_to:
+//test: insert, const_iterator, const_reverse_iterator, erase, s_iterator_to:
template<class ValueTraits>
void test_set<ValueTraits>::test_insert(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
set_type testset;
testset.insert(&values[0] + 2, &values[0] + 5);
@@ -149,6 +155,9 @@
i = testset.iterator_to (values[2]);
BOOST_TEST (&*i == &values[2]);
+ i = set_type::s_iterator_to(values[2]);
+ BOOST_TEST (&*i == &values[2]);
+
testset.erase (i);
{ int init_values [] = { 1, 3, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset.begin() ); }
@@ -158,11 +167,11 @@
template<class ValueTraits>
void test_set<ValueTraits>::test_swap(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
set_type testset1 (&values[0], &values[0] + 2);
set_type testset2;
@@ -185,16 +194,16 @@
template<class ValueTraits>
void test_set<ValueTraits>::test_find(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
set_type testset (values.begin(), values.end());
typedef typename set_type::iterator iterator;
- testvalue_t cmp_val;
+ value_type cmp_val;
cmp_val.value_ = 2;
iterator i = testset.find (cmp_val);
BOOST_TEST (i->value_ == 2);
@@ -213,20 +222,35 @@
void test_set<ValueTraits>
::test_clone(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::set
- <ValueTraits
- ,std::less<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> set_type;
- set_type testset1 (&values[0], &values[0] + values.size());
- set_type testset2;
+ set_type testset1 (&values[0], &values[0] + values.size());
+ set_type testset2;
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
- BOOST_TEST (testset2 == testset1);
- testset2.clear_and_dispose(test::delete_disposer());
- BOOST_TEST (testset2.empty());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
+ BOOST_TEST (testset2 == testset1);
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
+ BOOST_TEST (testset2.empty());
+}
+
+template<class ValueTraits>
+void test_set<ValueTraits>
+ ::test_container_from_end(std::vector<typename ValueTraits::value_type>& values)
+{
+ typedef typename ValueTraits::value_type value_type;
+ typedef set
+ < value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
+ > set_type;
+ set_type testset (&values[0], &values[0] + values.size());
+ BOOST_TEST (testset == set_type::container_from_end_iterator(testset.end()));
+ BOOST_TEST (testset == set_type::container_from_end_iterator(testset.cend()));
}
template<class VoidPointer, bool constant_time_size>
@@ -235,18 +259,25 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, constant_time_size> testvalue_t;
+ typedef testvalue<VoidPointer, constant_time_size> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, constant_time_size> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_set <typename testvalue_t::set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_set <typename testvalue_t::set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::set_node_> >::test_all(data);
-
+ test_set < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::set_base_hook_t
+ >::type
+ >::test_all(data);
+ test_set < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::set_member_hook_t
+ , &value_type::set_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
@@ -257,61 +288,53 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, false> testvalue_t;
+ typedef testvalue<VoidPointer, false> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, false> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_set <typename testvalue_t::set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
+ test_set < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::set_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_set < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::set_member_hook_t
+ , &value_type::set_node_
+ >
+ >::type
+ >::test_all(data);
+
+ test_set < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::set_auto_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_set < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::set_auto_member_hook_t
+ , &value_type::set_auto_node_
+ >
+ >::type
+ >::test_all(data);
- test_set <typename testvalue_t::set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::set_node_> >::test_all(data);
-
- test_set <typename testvalue_t::set_auto_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_set <typename testvalue_t::set_auto_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::set_auto_node_> >::test_all(data);
return 0;
}
};
-/*
-//Explicit instantiations of non-counted classes
-template class boost::intrusive::set
- <set_base_raw, std::less<set_base_raw::value_type>, false>;
-template class boost::intrusive::set
- <set_member_raw, std::less<set_member_raw::value_type>, false>;
-template class boost::intrusive::set
- <set_auto_base_raw, std::less<set_auto_base_raw::value_type>, false>;
-template class boost::intrusive::set
- <set_auto_member_raw, std::less<set_auto_member_raw::value_type>, false>;
-template class boost::intrusive::set
- <set_base_smart, std::less<set_base_smart::value_type>, false>;
-template class boost::intrusive::set
- <set_member_smart, std::less<set_member_smart::value_type>, false>;
-template class boost::intrusive::set
- <set_auto_base_smart, std::less<set_auto_base_smart::value_type>, false>;
-template class boost::intrusive::set
- <set_auto_member_smart, std::less<set_auto_member_smart::value_type>, false>;
-
-//Explicit instantiation of counted classes
-template class boost::intrusive::set
- <set_base_raw_t, std::less<set_base_raw_t::value_type>, true>;
-template class boost::intrusive::set
- <set_member_raw_t, std::less<set_member_raw_t::value_type>, true>;
-template class boost::intrusive::set
- <set_base_smart_t, std::less<set_base_smart_t::value_type>, true>;
-template class boost::intrusive::set
- <set_member_smart_t, std::less<set_member_smart_t::value_type>, true>;
-*/
+
int main( int, char* [] )
{
+
test_main_template<void*, false>()();
- test_main_template<boost::intrusive::smart_ptr<void>, false>()();
+ test_main_template<smart_ptr<void>, false>()();
test_main_template<void*, true>()();
- test_main_template<boost::intrusive::smart_ptr<void>, true>()();
+ test_main_template<smart_ptr<void>, true>()();
return boost::report_errors();
}
#include <boost/intrusive/detail/config_end.hpp>
Modified: branches/bcbboost/libs/intrusive/test/slist_test.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/slist_test.cpp (original)
+++ branches/bcbboost/libs/intrusive/test/slist_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -10,6 +10,7 @@
// See http://www.boost.org/libs/intrusive for documentation.
//
/////////////////////////////////////////////////////////////////////////////
+
#include <boost/intrusive/detail/config_begin.hpp>
#include <boost/intrusive/slist.hpp>
#include <boost/intrusive/detail/pointer_to_other.hpp>
@@ -36,15 +37,19 @@
static void test_swap(std::vector<value_type>& values);
static void test_slow_insert (std::vector<value_type>& values);
static void test_clone (std::vector<value_type>& values);
+ static void test_container_from_end(std::vector<value_type> &values);
};
template<class ValueTraits>
void test_slist<ValueTraits>
::test_all (std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
{
list_type list(values.begin(), values.end());
@@ -61,6 +66,7 @@
test_slow_insert (values);
test_swap(values);
test_clone(values);
+ test_container_from_end(values);
}
//test: push_front, pop_front, front, size, empty:
@@ -68,9 +74,12 @@
void test_slist<ValueTraits>
::test_front_back (std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
BOOST_TEST (testlist.empty());
@@ -96,10 +105,12 @@
void test_slist<ValueTraits>
::test_merge (std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist1, testlist2;
testlist1.push_front (values[0]);
@@ -117,10 +128,12 @@
void test_slist<ValueTraits>
::test_sort(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist (values.begin(), values.end());
@@ -136,15 +149,17 @@
TEST_INTRUSIVE_SEQUENCE( init_values, testlist.begin() ); }
}
-//test: assign, insert_after, const_iterator, erase_after, iterator_to, previous:
+//test: assign, insert_after, const_iterator, erase_after, s_iterator_to, previous:
template<class ValueTraits>
void test_slist<ValueTraits>
::test_insert(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
testlist.assign (&values[0] + 2, &values[0] + 5);
@@ -162,6 +177,8 @@
i = testlist.iterator_to (values[4]);
BOOST_TEST (&*i == &values[4]);
+ i = list_type::s_iterator_to (values[4]);
+ BOOST_TEST (&*i == &values[4]);
i = testlist.previous (i);
BOOST_TEST (&*i == &values[0]);
@@ -171,15 +188,17 @@
TEST_INTRUSIVE_SEQUENCE( init_values, const_testlist.begin() ); }
}
-//test: insert, const_iterator, erase, iterator_to:
+//test: insert, const_iterator, erase, siterator_to:
template<class ValueTraits>
void test_slist<ValueTraits>
::test_slow_insert (std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
testlist.push_front (values[4]);
@@ -199,6 +218,9 @@
i = testlist.iterator_to (values[4]);
BOOST_TEST (&*i == &values[4]);
+ i = list_type::s_iterator_to (values[4]);
+ BOOST_TEST (&*i == &values[4]);
+
i = testlist.erase (i);
BOOST_TEST (i == testlist.end());
@@ -214,10 +236,12 @@
void test_slist<ValueTraits>
::test_shift(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist;
@@ -254,10 +278,12 @@
void test_slist<ValueTraits>
::test_swap(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
{
list_type testlist1 (&values[0], &values[0] + 2);
@@ -306,37 +332,63 @@
void test_slist<ValueTraits>
::test_clone(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::slist
- <ValueTraits
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
> list_type;
list_type testlist1 (&values[0], &values[0] + values.size());
list_type testlist2;
- testlist2.clone_from(testlist1, test::new_cloner(), test::delete_disposer());
+ testlist2.clone_from(testlist1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
BOOST_TEST (testlist2 == testlist1);
- testlist2.clear_and_dispose(test::delete_disposer());
+ testlist2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testlist2.empty());
}
+template<class ValueTraits>
+void test_slist<ValueTraits>
+ ::test_container_from_end(std::vector<typename ValueTraits::value_type>& values)
+{
+ typedef typename ValueTraits::value_type value_type;
+ typedef slist
+ < value_type
+ , value_traits<ValueTraits>
+ , size_type<std::size_t>
+ , constant_time_size<value_type::constant_time_size>
+ > list_type;
+ list_type testlist1 (&values[0], &values[0] + values.size());
+ BOOST_TEST (testlist1 == list_type::container_from_end_iterator(testlist1.end()));
+ BOOST_TEST (testlist1 == list_type::container_from_end_iterator(testlist1.cend()));
+}
+
template<class VoidPointer, bool constant_time_size>
class test_main_template
{
public:
int operator()()
{
- typedef testvalue<VoidPointer, constant_time_size> testvalue_t;
- std::vector<testvalue_t> data (5);
+ typedef testvalue<VoidPointer, constant_time_size> value_type;
+ std::vector<value_type> data (5);
for (int i = 0; i < 5; ++i)
data[i].value_ = i + 1;
- test_slist <typename testvalue_t::slist_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_slist <typename testvalue_t::slist_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::slist_node_> >::test_all(data);
+ test_slist < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::slist_base_hook_t
+ >::type
+ >::test_all(data);
+ test_slist < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::slist_member_hook_t
+ , &value_type::slist_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
@@ -348,48 +400,50 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, false> testvalue_t;
- std::vector<testvalue_t> data (5);
+ typedef testvalue<VoidPointer, false> value_type;
+ std::vector<value_type> data (5);
for (int i = 0; i < 5; ++i)
data[i].value_ = i + 1;
- test_slist <typename testvalue_t::slist_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_slist <typename testvalue_t::slist_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::slist_node_> >::test_all(data);
-
- test_slist <typename testvalue_t::slist_auto_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_slist <typename testvalue_t::slist_auto_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::slist_auto_node_> >::test_all(data);
+ test_slist < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::slist_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_slist < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::slist_member_hook_t
+ , &value_type::slist_node_
+ >
+ >::type
+ >::test_all(data);
+
+ test_slist < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::slist_auto_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_slist < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::slist_auto_member_hook_t
+ , &value_type::slist_auto_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
-/*
-//Explicit instantiations of non-counted classes
-template class boost::intrusive::slist<slist_base_raw, false>;
-template class boost::intrusive::slist<slist_member_raw, false>;
-template class boost::intrusive::slist<slist_auto_base_raw, false>;
-template class boost::intrusive::slist<slist_auto_member_raw, false>;
-template class boost::intrusive::slist<slist_base_smart, false>;
-template class boost::intrusive::slist<slist_member_smart, false>;
-template class boost::intrusive::slist<slist_auto_base_smart, false>;
-template class boost::intrusive::slist<slist_auto_member_smart, false>;
-
-//Explicit instantiation of counted classes
-template class boost::intrusive::slist<slist_base_raw_t, true>;
-template class boost::intrusive::slist<slist_member_raw_t, true>;
-template class boost::intrusive::slist<slist_base_smart_t, true>;
-template class boost::intrusive::slist<slist_member_smart_t, true>;
-*/
+
int main(int, char* [])
{
test_main_template<void*, false>()();
- test_main_template<boost::intrusive::smart_ptr<void>, false>()();
+ test_main_template<smart_ptr<void>, false>()();
test_main_template<void*, true>()();
- test_main_template<boost::intrusive::smart_ptr<void>, true>()();
+ test_main_template<smart_ptr<void>, true>()();
return boost::report_errors();
}
#include <boost/intrusive/detail/config_end.hpp>
Modified: branches/bcbboost/libs/intrusive/test/smart_ptr.hpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/smart_ptr.hpp (original)
+++ branches/bcbboost/libs/intrusive/test/smart_ptr.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -106,123 +106,122 @@
public: //Public Functions
- /*!Constructor from raw pointer (allows "0" pointer conversion). Never throws.*/
+ //!Constructor from raw pointer (allows "0" pointer conversion). Never throws.
smart_ptr(pointer ptr = 0)
: m_ptr(ptr)
{}
- /*!Constructor from other pointer. Never throws.*/
-
+ //!Constructor from other pointer. Never throws.
template <class T>
smart_ptr(T *ptr)
: m_ptr(ptr)
{}
- /*!Constructor from other smart_ptr */
+ //!Constructor from other smart_ptr
smart_ptr(const smart_ptr& ptr)
: m_ptr(ptr.m_ptr)
{}
- /*!Constructor from other smart_ptr. If pointers of pointee types are
- convertible, offset_ptrs will be convertibles. Never throws.*/
+ //!Constructor from other smart_ptr. If pointers of pointee types are
+ //!convertible, offset_ptrs will be convertibles. Never throws.
template<class T2>
smart_ptr(const smart_ptr<T2> &ptr)
: m_ptr(ptr.m_ptr)
{}
- /*!Emulates static_cast operator. Never throws. */
+ //!Emulates static_cast operator. Never throws.
template<class Y>
smart_ptr(const smart_ptr<Y> & r, detail::static_cast_tag)
: m_ptr(static_cast<PointedType*>(r.get()))
{}
- /*!Emulates const_cast operator. Never throws.*/
+ //!Emulates const_cast operator. Never throws.
template<class Y>
smart_ptr(const smart_ptr<Y> & r, detail::const_cast_tag)
: m_ptr(const_cast<PointedType*>(r.get()))
{}
- /*!Emulates dynamic_cast operator. Never throws.*/
+ //!Emulates dynamic_cast operator. Never throws.
template<class Y>
smart_ptr(const smart_ptr<Y> & r, detail::dynamic_cast_tag)
: m_ptr(dynamic_cast<PointedType*>(r.get()))
{}
- /*!Emulates reinterpret_cast operator. Never throws.*/
+ //!Emulates reinterpret_cast operator. Never throws.
template<class Y>
smart_ptr(const smart_ptr<Y> & r, detail::reinterpret_cast_tag)
: m_ptr(reinterpret_cast<PointedType*>(r.get()))
{}
- /*!Obtains raw pointer from offset. Never throws.*/
+ //!Obtains raw pointer from offset. Never throws.
pointer get() const
{ return m_ptr; }
- /*!Pointer-like -> operator. It can return 0 pointer. Never throws.*/
+ //!Pointer-like -> operator. It can return 0 pointer. Never throws.
pointer operator->() const
{ return this->get(); }
- /*!Dereferencing operator, if it is a null smart_ptr behavior
- is undefined. Never throws.*/
+ //!Dereferencing operator, if it is a null smart_ptr behavior
+ //! is undefined. Never throws.
reference operator* () const
{ return *(this->get()); }
- /*!Indexing operator. Never throws.*/
+ //!Indexing operator. Never throws.
reference operator[](std::ptrdiff_t idx) const
{ return this->get()[idx]; }
- /*!Assignment from pointer (saves extra conversion). Never throws.*/
+ //!Assignment from pointer (saves extra conversion). Never throws.
smart_ptr& operator= (pointer from)
{ m_ptr = from; return *this; }
- /*!Assignment from other smart_ptr. Never throws.*/
+ //!Assignment from other smart_ptr. Never throws.
smart_ptr& operator= (const smart_ptr & pt)
{ m_ptr = pt.m_ptr; return *this; }
- /*!Assignment from related smart_ptr. If pointers of pointee types
- are assignable, offset_ptrs will be assignable. Never throws.*/
+ //!Assignment from related smart_ptr. If pointers of pointee types
+ //! are assignable, offset_ptrs will be assignable. Never throws.
template <class T2>
smart_ptr& operator= (const smart_ptr<T2> & pt)
{ m_ptr = pt.m_ptr; return *this; }
- /*!smart_ptr + std::ptrdiff_t. Never throws.*/
+ //!smart_ptr + std::ptrdiff_t. Never throws.
smart_ptr operator+ (std::ptrdiff_t offset) const
{ return smart_ptr(this->get()+offset); }
- /*!smart_ptr - std::ptrdiff_t. Never throws.*/
+ //!smart_ptr - std::ptrdiff_t. Never throws.
smart_ptr operator- (std::ptrdiff_t offset) const
{ return smart_ptr(this->get()-offset); }
- /*!smart_ptr += std::ptrdiff_t. Never throws.*/
+ //!smart_ptr += std::ptrdiff_t. Never throws.
smart_ptr &operator+= (std::ptrdiff_t offset)
{ m_ptr += offset; return *this; }
- /*!smart_ptr -= std::ptrdiff_t. Never throws.*/
+ //!smart_ptr -= std::ptrdiff_t. Never throws.
smart_ptr &operator-= (std::ptrdiff_t offset)
{ m_ptr -= offset; return *this; }
- /*!++smart_ptr. Never throws.*/
+ //!++smart_ptr. Never throws.
smart_ptr& operator++ (void)
{ ++m_ptr; return *this; }
- /*!smart_ptr++. Never throws.*/
+ //!smart_ptr++. Never throws.
smart_ptr operator++ (int)
{ smart_ptr temp(*this); ++*this; return temp; }
- /*!--smart_ptr. Never throws.*/
+ //!--smart_ptr. Never throws.
smart_ptr& operator-- (void)
{ --m_ptr; return *this; }
- /*!smart_ptr--. Never throws.*/
+ //!smart_ptr--. Never throws.
smart_ptr operator-- (int)
{ smart_ptr temp(*this); --*this; return temp; }
- /*!safe bool conversion operator. Never throws.*/
+ //!safe bool conversion operator. Never throws.
operator unspecified_bool_type() const
{ return this->get()? &self_t::unspecified_bool_type_func : 0; }
- /*!Not operator. Not needed in theory, but improves portability.
- Never throws.*/
+ //!Not operator. Not needed in theory, but improves portability.
+ //!Never throws.
bool operator! () const
{ return this->get() == 0; }
/*
@@ -235,65 +234,65 @@
*/
};
-/*!smart_ptr<T1> == smart_ptr<T2>. Never throws.*/
+//!smart_ptr<T1> == smart_ptr<T2>. Never throws.
template<class T1, class T2>
inline bool operator== (const smart_ptr<T1> &pt1,
const smart_ptr<T2> &pt2)
{ return pt1.get() == pt2.get(); }
-/*!smart_ptr<T1> != smart_ptr<T2>. Never throws.*/
+//!smart_ptr<T1> != smart_ptr<T2>. Never throws.
template<class T1, class T2>
inline bool operator!= (const smart_ptr<T1> &pt1,
const smart_ptr<T2> &pt2)
{ return pt1.get() != pt2.get(); }
-/*!smart_ptr<T1> < smart_ptr<T2>. Never throws.*/
+//!smart_ptr<T1> < smart_ptr<T2>. Never throws.
template<class T1, class T2>
inline bool operator< (const smart_ptr<T1> &pt1,
const smart_ptr<T2> &pt2)
{ return pt1.get() < pt2.get(); }
-/*!smart_ptr<T1> <= smart_ptr<T2>. Never throws.*/
+//!smart_ptr<T1> <= smart_ptr<T2>. Never throws.
template<class T1, class T2>
inline bool operator<= (const smart_ptr<T1> &pt1,
const smart_ptr<T2> &pt2)
{ return pt1.get() <= pt2.get(); }
-/*!smart_ptr<T1> > smart_ptr<T2>. Never throws.*/
+//!smart_ptr<T1> > smart_ptr<T2>. Never throws.
template<class T1, class T2>
inline bool operator> (const smart_ptr<T1> &pt1,
const smart_ptr<T2> &pt2)
{ return pt1.get() > pt2.get(); }
-/*!smart_ptr<T1> >= smart_ptr<T2>. Never throws.*/
+//!smart_ptr<T1> >= smart_ptr<T2>. Never throws.
template<class T1, class T2>
inline bool operator>= (const smart_ptr<T1> &pt1,
const smart_ptr<T2> &pt2)
{ return pt1.get() >= pt2.get(); }
-/*!operator<< */
+//!operator<<
template<class E, class T, class Y>
inline std::basic_ostream<E, T> & operator<<
(std::basic_ostream<E, T> & os, smart_ptr<Y> const & p)
{ return os << p.get(); }
-/*!operator>> */
+//!operator>>
template<class E, class T, class Y>
inline std::basic_istream<E, T> & operator>>
(std::basic_istream<E, T> & os, smart_ptr<Y> & p)
{ Y * tmp; return os >> tmp; p = tmp; }
-/*!std::ptrdiff_t + smart_ptr */
+//!std::ptrdiff_t + smart_ptr
template<class T>
inline smart_ptr<T> operator+(std::ptrdiff_t diff, const smart_ptr<T>& right)
{ return right + diff; }
-/*!smart_ptr - smart_ptr */
+//!smart_ptr - smart_ptr
template<class T, class T2>
inline std::ptrdiff_t operator- (const smart_ptr<T> &pt, const smart_ptr<T2> &pt2)
{ return pt.get()- pt2.get(); }
-/*!swap specialization */
+//!swap specialization
template<class T>
inline void swap (smart_ptr<T> &pt,
smart_ptr<T> &pt2)
@@ -303,13 +302,13 @@
pt2 = ptr;
}
-/*!get_pointer() enables boost::mem_fn to recognize smart_ptr.
- Never throws.*/
+//!detail::get_pointer() enables boost::mem_fn to recognize smart_ptr.
+//!Never throws.
template<class T>
inline T* get_pointer(const smart_ptr<T> & p)
{ return p.get(); }
-/*!Simulation of static_cast between pointers. Never throws.*/
+//!Simulation of static_cast between pointers. Never throws.
template<class T, class U>
inline smart_ptr<T>
static_pointer_cast(smart_ptr<U> const & r)
@@ -317,14 +316,14 @@
return smart_ptr<T>(r, detail::static_cast_tag());
}
-/*!Simulation of const_cast between pointers. Never throws.*/
+//!Simulation of const_cast between pointers. Never throws.
template<class T, class U>
inline smart_ptr<T>const_pointer_cast(smart_ptr<U> const & r)
{
return smart_ptr<T>(r, detail::const_cast_tag());
}
-/*!Simulation of dynamic_cast between pointers. Never throws.*/
+//!Simulation of dynamic_cast between pointers. Never throws.
template<class T, class U>
inline smart_ptr<T>
dynamic_pointer_cast(smart_ptr<U> const & r)
@@ -333,7 +332,7 @@
(r, detail::dynamic_cast_tag());
}
-/*!Simulation of reinterpret_cast between pointers. Never throws.*/
+//!Simulation of reinterpret_cast between pointers. Never throws.
template<class T, class U>
inline smart_ptr<T>
reinterpret_pointer_cast(smart_ptr<U> const & r)
Modified: branches/bcbboost/libs/intrusive/test/test_container.hpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/test_container.hpp (original)
+++ branches/bcbboost/libs/intrusive/test/test_container.hpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -71,8 +71,11 @@
BOOST_TEST( c.size() == 0 );
BOOST_TEST( c.empty() );
- c.insert( c.begin(), *d.begin() );
- c.insert( c.end(), *(++d.begin()) );
+ {
+ typename Data::iterator i = d.begin();
+ c.insert( c.begin(), *i );
+ c.insert( c.end(), *(++i) );
+ }
BOOST_TEST( c.size() == 2 );
BOOST_TEST( !c.empty() );
@@ -81,7 +84,11 @@
BOOST_TEST( c.size() == 1 );
- c.insert( c.begin(), *(++++d.begin()) );
+ {
+ typename Data::iterator i = d.begin();
+ ++++i;
+ c.insert( c.begin(), *(i) );
+ }
c.erase( c.begin(), c.end() );
@@ -121,8 +128,8 @@
BOOST_TEST( c.find(*di) != c.end() );
}
- typename Data::const_iterator da = d.begin();
- typename Data::const_iterator db = ++d.begin();
+ typename Data::const_iterator db = d.begin();
+ typename Data::const_iterator da = db++;
size_type old_size = c.size();
Deleted: branches/bcbboost/libs/intrusive/test/test_intrusive_associative_container.hpp
==============================================================================
Deleted: branches/bcbboost/libs/intrusive/test/test_intrusive_sequence_container.hpp
==============================================================================
Deleted: branches/bcbboost/libs/intrusive/test/test_intrusive_unordered_container.hpp
==============================================================================
Modified: branches/bcbboost/libs/intrusive/test/unordered_multiset_test.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/unordered_multiset_test.cpp (original)
+++ branches/bcbboost/libs/intrusive/test/unordered_multiset_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -44,15 +44,16 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_all (std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
{
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
typename unordered_multiset_type::bucket_type buckets [BucketSize];
- unordered_multiset_type testset(buckets, BucketSize);
+ unordered_multiset_type testset(bucket_traits(buckets, BucketSize));
testset.insert(values.begin(), values.end());
test::test_container(testset);
testset.clear();
@@ -78,18 +79,20 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_impl()
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<testvalue_t> values (5);
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
+ > unordered_multiset_type;
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
+
+ std::vector<value_type> values (5);
for (int i = 0; i < 5; ++i)
values[i].value_ = i;
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
- > unordered_multiset_type;
+
typename unordered_multiset_type::bucket_type buckets [BucketSize];
- unordered_multiset_type testset(buckets, BucketSize);
+ unordered_multiset_type testset(bucket_traits(buckets, BucketSize));
for (int i = 0; i < 5; ++i)
testset.insert (values[i]);
@@ -106,15 +109,16 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_sort(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
+
typename unordered_multiset_type::bucket_type buckets [BucketSize];
- unordered_multiset_type testset1(buckets, BucketSize, values.begin(), values.end());
+ unordered_multiset_type testset1(values.begin(), values.end(), bucket_traits(buckets, BucketSize));
{ int init_values [] = { 1, 2, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
@@ -126,16 +130,16 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_insert(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
+
typename unordered_multiset_type::bucket_type buckets [BucketSize];
- unordered_multiset_type testset(buckets, BucketSize);
- typedef typename unordered_multiset_type::value_type value_type;
+ unordered_multiset_type testset(bucket_traits(buckets, BucketSize));
testset.insert(&values[0] + 2, &values[0] + 5);
@@ -170,7 +174,7 @@
//Now with a single bucket
typename unordered_multiset_type::bucket_type single_bucket[1];
- unordered_multiset_type testset2(single_bucket, 1);
+ unordered_multiset_type testset2(bucket_traits(single_bucket, 1));
testset2.insert(&values[0], &values[0] + values.size());
BOOST_TEST (testset2.erase(5) == 1);
BOOST_TEST (testset2.erase(2) == 2);
@@ -184,18 +188,18 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_swap(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
- typename unordered_multiset_type::bucket_type buckets [BucketSize];
- unordered_multiset_type testset1(buckets, BucketSize, &values[0], &values[0] + 2);
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
+ typename unordered_multiset_type::bucket_type buckets [BucketSize];
typename unordered_multiset_type::bucket_type buckets2 [BucketSize];
- unordered_multiset_type testset2(buckets2, BucketSize);
+ unordered_multiset_type testset1(&values[0], &values[0] + 2, bucket_traits(buckets, BucketSize));
+ unordered_multiset_type testset2(bucket_traits(buckets2, BucketSize));
testset2.insert (&values[0] + 2, &values[0] + 6);
testset1.swap (testset2);
@@ -216,40 +220,41 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_rehash(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
typename unordered_multiset_type::bucket_type buckets1 [BucketSize];
- unordered_multiset_type testset1(buckets1, BucketSize, &values[0], &values[0] + 6);
+ typename unordered_multiset_type::bucket_type buckets2 [2];
+ typename unordered_multiset_type::bucket_type buckets3 [BucketSize*2];
+
+ unordered_multiset_type testset1(&values[0], &values[0] + 6, bucket_traits(buckets1, BucketSize));
BOOST_TEST (testset1.size() == 6);
{ int init_values [] = { 1, 2, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
- typename unordered_multiset_type::bucket_type buckets2 [2];
- testset1.rehash(buckets2, 2);
+ testset1.rehash(bucket_traits(buckets2, 2));
BOOST_TEST (testset1.size() == 6);
{ int init_values [] = { 4, 2, 2, 5, 3, 1 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
- typename unordered_multiset_type::bucket_type buckets3 [BucketSize*2];
- testset1.rehash(buckets3, BucketSize*2);
+ testset1.rehash(bucket_traits(buckets3, BucketSize*2));
BOOST_TEST (testset1.size() == 6);
{ int init_values [] = { 1, 2, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
//Now rehash reducing the buckets
- testset1.rehash(buckets3, 2);
+ testset1.rehash(bucket_traits(buckets3, 2));
BOOST_TEST (testset1.size() == 6);
{ int init_values [] = { 4, 2, 2, 5, 3, 1 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
//Now rehash increasing the buckets
- testset1.rehash(buckets3, BucketSize*2);
+ testset1.rehash(bucket_traits(buckets3, BucketSize*2));
BOOST_TEST (testset1.size() == 6);
{ int init_values [] = { 1, 2, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
@@ -259,19 +264,20 @@
template<class ValueTraits>
void test_unordered_multiset<ValueTraits>::test_find(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
+
typename unordered_multiset_type::bucket_type buckets[BucketSize];
- unordered_multiset_type testset(buckets, BucketSize, values.begin(), values.end());
+ unordered_multiset_type testset(values.begin(), values.end(), bucket_traits(buckets, BucketSize));
typedef typename unordered_multiset_type::iterator iterator;
- testvalue_t cmp_val;
+ value_type cmp_val;
cmp_val.value_ = 2;
iterator i = testset.find (cmp_val);
BOOST_TEST (i->value_ == 2);
@@ -291,61 +297,62 @@
void test_unordered_multiset<ValueTraits>
::test_clone(std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::unordered_multiset
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_multiset
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_multiset_type;
+ typedef typename unordered_multiset_type::bucket_traits bucket_traits;
{
//Test with equal bucket arrays
typename unordered_multiset_type::bucket_type buckets1 [BucketSize];
typename unordered_multiset_type::bucket_type buckets2 [BucketSize];
- unordered_multiset_type testset1 (buckets1, BucketSize, values.begin(), values.end());
- unordered_multiset_type testset2 (buckets2, BucketSize);
+ unordered_multiset_type testset1 (values.begin(), values.end(), bucket_traits(buckets1, BucketSize));
+ unordered_multiset_type testset2 (bucket_traits(buckets2, BucketSize));
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
//Ordering is not guarantee in the cloning so insert data in a set and test
std::multiset<typename ValueTraits::value_type>
src(testset1.begin(), testset1.end());
std::multiset<typename ValueTraits::value_type>
dst(testset2.begin(), testset2.end());
BOOST_TEST (src == dst);
- testset2.clear_and_dispose(test::delete_disposer());
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testset2.empty());
}
{
//Test with bigger source bucket arrays
typename unordered_multiset_type::bucket_type buckets1 [BucketSize*2];
typename unordered_multiset_type::bucket_type buckets2 [BucketSize];
- unordered_multiset_type testset1 (buckets1, BucketSize*2, values.begin(), values.end());
- unordered_multiset_type testset2 (buckets2, BucketSize);
+ unordered_multiset_type testset1 (values.begin(), values.end(), bucket_traits(buckets1, BucketSize*2));
+ unordered_multiset_type testset2 (bucket_traits(buckets2, BucketSize));
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
//Ordering is not guarantee in the cloning so insert data in a set and test
std::multiset<typename ValueTraits::value_type>
src(testset1.begin(), testset1.end());
std::multiset<typename ValueTraits::value_type>
dst(testset2.begin(), testset2.end());
BOOST_TEST (src == dst);
- testset2.clear_and_dispose(test::delete_disposer());
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testset2.empty());
}
{
//Test with smaller source bucket arrays
typename unordered_multiset_type::bucket_type buckets1 [BucketSize];
typename unordered_multiset_type::bucket_type buckets2 [BucketSize*2];
- unordered_multiset_type testset1 (buckets1, BucketSize, values.begin(), values.end());
- unordered_multiset_type testset2 (buckets2, BucketSize*2);
+ unordered_multiset_type testset1 (values.begin(), values.end(), bucket_traits(buckets1, BucketSize));
+ unordered_multiset_type testset2 (bucket_traits(buckets2, BucketSize*2));
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
//Ordering is not guarantee in the cloning so insert data in a set and test
std::multiset<typename ValueTraits::value_type>
src(testset1.begin(), testset1.end());
std::multiset<typename ValueTraits::value_type>
dst(testset2.begin(), testset2.end());
BOOST_TEST (src == dst);
- testset2.clear_and_dispose(test::delete_disposer());
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testset2.empty());
}
}
@@ -356,17 +363,26 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, constant_time_size> testvalue_t;
+ typedef testvalue<VoidPointer, constant_time_size> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, constant_time_size> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_unordered_multiset <typename testvalue_t::unordered_set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_unordered_multiset <typename testvalue_t::unordered_set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::unordered_set_node_> >::test_all(data);
+ test_unordered_multiset < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::unordered_set_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_unordered_multiset < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::unordered_set_member_hook_t
+ , &value_type::unordered_set_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
@@ -378,87 +394,51 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, false> testvalue_t;
+ typedef testvalue<VoidPointer, false> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, false> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_unordered_multiset <typename testvalue_t::unordered_set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_unordered_multiset <typename testvalue_t::unordered_set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::unordered_set_node_> >::test_all(data);
-
- test_unordered_multiset <typename testvalue_t::unordered_set_auto_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_unordered_multiset <typename testvalue_t::unordered_set_auto_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::unordered_set_auto_node_> >::test_all(data);
+ test_unordered_multiset < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::unordered_set_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_unordered_multiset < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::unordered_set_member_hook_t
+ , &value_type::unordered_set_node_
+ >
+ >::type
+ >::test_all(data);
+
+ test_unordered_multiset < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::unordered_set_auto_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_unordered_multiset < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::unordered_set_auto_member_hook_t
+ , &value_type::unordered_set_auto_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
-/*
-//Explicit instantiations of non-counted classes
-template class boost::intrusive::unordered_multiset
- < unordered_set_base_raw_t
- , boost::hash<unordered_set_base_raw_t::value_type>
- , std::equal_to<unordered_set_base_raw_t::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_member_raw_t
- , boost::hash<unordered_set_member_raw_t::value_type>
- , std::equal_to<unordered_set_member_raw_t::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_auto_base_raw
- , boost::hash<unordered_set_auto_base_raw::value_type>
- , std::equal_to<unordered_set_auto_base_raw::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_auto_member_raw
- , boost::hash<unordered_set_auto_member_raw::value_type>
- , std::equal_to<unordered_set_auto_member_raw::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_base_smart
- , boost::hash<unordered_set_base_smart::value_type>
- , std::equal_to<unordered_set_base_smart::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_member_smart
- , boost::hash<unordered_set_member_smart::value_type>
- , std::equal_to<unordered_set_member_smart::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_auto_base_smart
- , boost::hash<unordered_set_auto_base_smart::value_type>
- , std::equal_to<unordered_set_auto_base_smart::value_type>, false>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_auto_member_smart
- , boost::hash<unordered_set_auto_member_smart::value_type>
- , std::equal_to<unordered_set_auto_member_smart::value_type>, false>;
-
-//Explicit instantiation of counted classes
-template class boost::intrusive::unordered_multiset
- < unordered_set_base_raw_t
- , boost::hash<unordered_set_base_raw_t::value_type>
- , std::equal_to<unordered_set_base_raw_t::value_type>, true>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_member_raw_t
- , boost::hash<unordered_set_base_raw_t::value_type>
- , std::equal_to<unordered_set_member_raw_t::value_type>, true>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_base_smart_t
- , boost::hash<unordered_set_base_smart_t::value_type>
- , std::equal_to<unordered_set_base_smart_t::value_type>, true>;
-template class boost::intrusive::unordered_multiset
- < unordered_set_member_smart_t
- , boost::hash<unordered_set_member_smart_t::value_type>
- , std::equal_to<unordered_set_member_smart_t::value_type>, true>;
-*/
-
int main( int, char* [] )
{
test_main_template<void*, false>()();
- test_main_template<boost::intrusive::smart_ptr<void>, false>()();
+ test_main_template<smart_ptr<void>, false>()();
test_main_template<void*, true>()();
- test_main_template<boost::intrusive::smart_ptr<void>, true>()();
+ test_main_template<smart_ptr<void>, true>()();
return boost::report_errors();
}
Modified: branches/bcbboost/libs/intrusive/test/unordered_set_test.cpp
==============================================================================
--- branches/bcbboost/libs/intrusive/test/unordered_set_test.cpp (original)
+++ branches/bcbboost/libs/intrusive/test/unordered_set_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -43,15 +43,16 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_all(std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
{
typename unordered_set_type::bucket_type buckets [BucketSize];
- unordered_set_type testset(buckets, BucketSize);
+ unordered_set_type testset(bucket_traits(buckets, BucketSize));
testset.insert(values.begin(), values.end());
test::test_container(testset);
testset.clear();
@@ -77,19 +78,20 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_impl()
{
- typedef typename ValueTraits::value_type testvalue_t;
- std::vector<testvalue_t> values (5);
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
+ > unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
+
+ std::vector<value_type> values (5);
for (int i = 0; i < 5; ++i)
values[i].value_ = i;
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
- > unordered_set_type;
typename unordered_set_type::bucket_type buckets [BucketSize];
- unordered_set_type testset(buckets, BucketSize);
+ unordered_set_type testset(bucket_traits(buckets, BucketSize));
for (int i = 0; i < 5; ++i)
testset.insert (values[i]);
@@ -104,15 +106,16 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_sort(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
+
typename unordered_set_type::bucket_type buckets [BucketSize];
- unordered_set_type testset1(buckets, BucketSize, values.begin(), values.end());
+ unordered_set_type testset1(values.begin(), values.end(), bucket_traits(buckets, BucketSize));
BOOST_TEST (5 == std::distance(testset1.begin(), testset1.end()));
{ int init_values [] = { 1, 2, 3, 4, 5 };
@@ -126,15 +129,16 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_insert(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
+
typename unordered_set_type::bucket_type buckets [BucketSize];
- unordered_set_type testset(buckets, BucketSize);
+ unordered_set_type testset(bucket_traits(buckets, BucketSize));
testset.insert(&values[0] + 2, &values[0] + 5);
const unordered_set_type& const_testset = testset;
@@ -160,19 +164,18 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_swap(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
typename unordered_set_type::bucket_type buckets1 [BucketSize];
- unordered_set_type testset1(buckets1, BucketSize, &values[0], &values[0] + 2);
-
typename unordered_set_type::bucket_type buckets2 [BucketSize];
- unordered_set_type testset2(buckets2, BucketSize);
+ unordered_set_type testset1(&values[0], &values[0] + 2, bucket_traits(buckets1, BucketSize));
+ unordered_set_type testset2(bucket_traits(buckets2, BucketSize));
testset2.insert (&values[0] + 2, &values[0] + 6);
testset1.swap (testset2);
@@ -192,40 +195,41 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_rehash(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
typename unordered_set_type::bucket_type buckets1 [BucketSize];
- unordered_set_type testset1(buckets1, BucketSize, &values[0], &values[0] + 6);
+ typename unordered_set_type::bucket_type buckets2 [2];
+ typename unordered_set_type::bucket_type buckets3 [BucketSize*2];
+
+ unordered_set_type testset1(&values[0], &values[0] + 6, bucket_traits(buckets1, BucketSize));
BOOST_TEST (testset1.size() == 5);
{ int init_values [] = { 1, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
- typename unordered_set_type::bucket_type buckets2 [2];
- testset1.rehash(buckets2, 2);
+ testset1.rehash(bucket_traits(buckets2, 2));
BOOST_TEST (testset1.size() == 5);
{ int init_values [] = { 4, 2, 5, 3, 1 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
- typename unordered_set_type::bucket_type buckets3 [BucketSize*2];
- testset1.rehash(buckets3, BucketSize*2);
+ testset1.rehash(bucket_traits(buckets3, BucketSize*2));
BOOST_TEST (testset1.size() == 5);
{ int init_values [] = { 1, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
//Now rehash reducing the buckets
- testset1.rehash(buckets3, 2);
+ testset1.rehash(bucket_traits(buckets3, 2));
BOOST_TEST (testset1.size() == 5);
{ int init_values [] = { 4, 2, 5, 3, 1 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
//Now rehash increasing the buckets
- testset1.rehash(buckets3, BucketSize*2);
+ testset1.rehash(bucket_traits(buckets3, BucketSize*2));
BOOST_TEST (testset1.size() == 5);
{ int init_values [] = { 1, 2, 3, 4, 5 };
TEST_INTRUSIVE_SEQUENCE( init_values, testset1.begin() ); }
@@ -236,18 +240,19 @@
template<class ValueTraits>
void test_unordered_set<ValueTraits>::test_find(std::vector<typename ValueTraits::value_type>& values)
{
- typedef typename ValueTraits::value_type testvalue_t;
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
+
typename unordered_set_type::bucket_type buckets [BucketSize];
- unordered_set_type testset (buckets, BucketSize, values.begin(), values.end());
+ unordered_set_type testset (values.begin(), values.end(), bucket_traits(buckets, BucketSize));
typedef typename unordered_set_type::iterator iterator;
- testvalue_t cmp_val;
+ value_type cmp_val;
cmp_val.value_ = 2;
iterator i = testset.find (cmp_val);
BOOST_TEST (i->value_ == 2);
@@ -266,61 +271,62 @@
void test_unordered_set<ValueTraits>
::test_clone(std::vector<typename ValueTraits::value_type>& values)
{
- typedef boost::intrusive::unordered_set
- <ValueTraits
- ,boost::hash<typename ValueTraits::value_type>
- ,std::equal_to<typename ValueTraits::value_type>
- ,ValueTraits::value_type::constant_time_size, std::size_t
+ typedef typename ValueTraits::value_type value_type;
+ typedef unordered_set
+ <value_type
+ , value_traits<ValueTraits>
+ , constant_time_size<value_type::constant_time_size>
> unordered_set_type;
+ typedef typename unordered_set_type::bucket_traits bucket_traits;
{
//Test with equal bucket arrays
typename unordered_set_type::bucket_type buckets1 [BucketSize];
typename unordered_set_type::bucket_type buckets2 [BucketSize];
- unordered_set_type testset1 (buckets1, BucketSize, values.begin(), values.end());
- unordered_set_type testset2 (buckets2, BucketSize);
+ unordered_set_type testset1 (values.begin(), values.end(), bucket_traits(buckets1, BucketSize));
+ unordered_set_type testset2 (bucket_traits(buckets2, BucketSize));
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
//Ordering is not guarantee in the cloning so insert data in a set and test
std::set<typename ValueTraits::value_type>
src(testset1.begin(), testset1.end());
std::set<typename ValueTraits::value_type>
dst(testset2.begin(), testset2.end());
BOOST_TEST (src == dst );
- testset2.clear_and_dispose(test::delete_disposer());
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testset2.empty());
}
{
//Test with bigger source bucket arrays
typename unordered_set_type::bucket_type buckets1 [BucketSize*2];
typename unordered_set_type::bucket_type buckets2 [BucketSize];
- unordered_set_type testset1 (buckets1, BucketSize*2, values.begin(), values.end());
- unordered_set_type testset2 (buckets2, BucketSize);
+ unordered_set_type testset1 (values.begin(), values.end(), bucket_traits(buckets1, BucketSize*2));
+ unordered_set_type testset2 (bucket_traits(buckets2, BucketSize));
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
//Ordering is not guarantee in the cloning so insert data in a set and test
std::set<typename ValueTraits::value_type>
src(testset1.begin(), testset1.end());
std::set<typename ValueTraits::value_type>
dst(testset2.begin(), testset2.end());
BOOST_TEST (src == dst );
- testset2.clear_and_dispose(test::delete_disposer());
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testset2.empty());
}
{
//Test with smaller source bucket arrays
typename unordered_set_type::bucket_type buckets1 [BucketSize];
typename unordered_set_type::bucket_type buckets2 [BucketSize*2];
- unordered_set_type testset1 (buckets1, BucketSize, values.begin(), values.end());
- unordered_set_type testset2 (buckets2, BucketSize*2);
+ unordered_set_type testset1 (values.begin(), values.end(), bucket_traits(buckets1, BucketSize));
+ unordered_set_type testset2 (bucket_traits(buckets2, BucketSize*2));
- testset2.clone_from(testset1, test::new_cloner(), test::delete_disposer());
+ testset2.clone_from(testset1, test::new_cloner<value_type>(), test::delete_disposer<value_type>());
//Ordering is not guarantee in the cloning so insert data in a set and test
std::set<typename ValueTraits::value_type>
src(testset1.begin(), testset1.end());
std::set<typename ValueTraits::value_type>
dst(testset2.begin(), testset2.end());
BOOST_TEST (src == dst );
- testset2.clear_and_dispose(test::delete_disposer());
+ testset2.clear_and_dispose(test::delete_disposer<value_type>());
BOOST_TEST (testset2.empty());
}
}
@@ -331,17 +337,25 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, constant_time_size> testvalue_t;
+ typedef testvalue<VoidPointer, constant_time_size> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, constant_time_size> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_unordered_set <typename testvalue_t::unordered_set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_unordered_set <typename testvalue_t::unordered_set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::unordered_set_node_> >::test_all(data);
+ test_unordered_set < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::unordered_set_base_hook_t
+ >::type
+ >::test_all(data);
+ test_unordered_set < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::unordered_set_member_hook_t
+ , &value_type::unordered_set_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
@@ -353,84 +367,51 @@
public:
int operator()()
{
- typedef testvalue<VoidPointer, false> testvalue_t;
+ typedef testvalue<VoidPointer, false> value_type;
static const int random_init[6] = { 3, 2, 4, 1, 5, 2 };
std::vector<testvalue<VoidPointer, false> > data (6);
for (int i = 0; i < 6; ++i)
data[i].value_ = random_init[i];
- test_unordered_set <typename testvalue_t::unordered_set_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_unordered_set <typename testvalue_t::unordered_set_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::unordered_set_node_> >::test_all(data);
-
- test_unordered_set <typename testvalue_t::unordered_set_auto_base_hook_t::template
- value_traits<testvalue_t> >::test_all(data);
-
- test_unordered_set <typename testvalue_t::unordered_set_auto_member_hook_t::template
- value_traits<testvalue_t, &testvalue_t::unordered_set_auto_node_> >::test_all(data);
+ test_unordered_set < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::unordered_set_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_unordered_set < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::unordered_set_member_hook_t
+ , &value_type::unordered_set_node_
+ >
+ >::type
+ >::test_all(data);
+
+ test_unordered_set < typename detail::get_base_value_traits
+ < value_type
+ , typename value_type::unordered_set_auto_base_hook_t
+ >::type
+ >::test_all(data);
+
+ test_unordered_set < typename detail::get_member_value_traits
+ < value_type
+ , member_hook< value_type
+ , typename value_type::unordered_set_auto_member_hook_t
+ , &value_type::unordered_set_auto_node_
+ >
+ >::type
+ >::test_all(data);
return 0;
}
};
-/*
-template class boost::intrusive::unordered_set
- < unordered_set_base_raw_t
- , boost::hash<unordered_set_base_raw_t::value_type>
- , std::equal_to<unordered_set_base_raw_t::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_member_raw_t
- , boost::hash<unordered_set_member_raw_t::value_type>
- , std::equal_to<unordered_set_member_raw_t::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_auto_base_raw
- , boost::hash<unordered_set_auto_base_raw::value_type>
- , std::equal_to<unordered_set_auto_base_raw::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_auto_member_raw
- , boost::hash<unordered_set_auto_member_raw::value_type>
- , std::equal_to<unordered_set_auto_member_raw::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_base_smart
- , boost::hash<unordered_set_base_smart::value_type>
- , std::equal_to<unordered_set_base_smart::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_member_smart
- , boost::hash<unordered_set_member_smart::value_type>
- , std::equal_to<unordered_set_member_smart::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_auto_base_smart
- , boost::hash<unordered_set_auto_base_smart::value_type>
- , std::equal_to<unordered_set_auto_base_smart::value_type>, false>;
-template class boost::intrusive::unordered_set
- < unordered_set_auto_member_smart
- , boost::hash<unordered_set_auto_member_smart::value_type>
- , std::equal_to<unordered_set_auto_member_smart::value_type>, false>;
-
-//Explicit instantiation of counted classes
-template class boost::intrusive::unordered_set
- < unordered_set_base_raw_t
- , boost::hash<unordered_set_base_raw_t::value_type>
- , std::equal_to<unordered_set_base_raw_t::value_type>, true>;
-template class boost::intrusive::unordered_set
- < unordered_set_member_raw_t
- , boost::hash<unordered_set_base_raw_t::value_type>
- , std::equal_to<unordered_set_member_raw_t::value_type>, true>;
-template class boost::intrusive::unordered_set
- < unordered_set_base_smart_t
- , boost::hash<unordered_set_base_smart_t::value_type>
- , std::equal_to<unordered_set_base_smart_t::value_type>, true>;
-template class boost::intrusive::unordered_set
- < unordered_set_member_smart_t
- , boost::hash<unordered_set_member_smart_t::value_type>
- , std::equal_to<unordered_set_member_smart_t::value_type>, true>;
-*/
+
int main( int, char* [] )
{
test_main_template<void*, false>()();
- test_main_template<boost::intrusive::smart_ptr<void>, false>()();
+ test_main_template<smart_ptr<void>, false>()();
test_main_template<void*, true>()();
- test_main_template<boost::intrusive::smart_ptr<void>, true>()();
+ test_main_template<smart_ptr<void>, true>()();
return boost::report_errors();
}
#include <boost/intrusive/detail/config_end.hpp>
Modified: branches/bcbboost/libs/system/test/error_code_user_test.cpp
==============================================================================
--- branches/bcbboost/libs/system/test/error_code_user_test.cpp (original)
+++ branches/bcbboost/libs/system/test/error_code_user_test.cpp 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -73,23 +73,26 @@
namespace lib3
{
// lib3 has its own error_category:
- extern const boost::system::error_category & lib3_error_category;
+ const boost::system::error_category & get_lib3_error_category();
+ const boost::system::error_category & lib3_error_category = get_lib3_error_category();
enum error
{
boo_boo=123,
big_boo_boo
};
-
}
namespace system
{
template<> struct is_error_code_enum<boost::lib3::error>
{ static const bool value = true; };
+ }
- template<> inline error_code make_error_code(boost::lib3::error e)
- { return error_code(e,boost::lib3::lib3_error_category); }
+ namespace lib3
+ {
+ inline boost::system::error_code make_error_code(error e)
+ { return boost::system::error_code(e,lib3_error_category); }
}
}
@@ -125,12 +128,14 @@
if ( ev == big_boo_boo ) return std::string("big boo boo");
return std::string("unknown error");
}
- };
- const lib3_error_category_imp lib3_error_category_const;
+ };
- const boost::system::error_category & lib3_error_category
- = lib3_error_category_const;
+ const boost::system::error_category & get_lib3_error_category()
+ {
+ static const lib3_error_category_imp l3ecat;
+ return l3ecat;
+ }
}
}
@@ -147,7 +152,8 @@
namespace lib4
{
// lib4 has its own error_category:
- extern const boost::system::error_category & lib4_error_category;
+ const boost::system::error_category & get_lib4_error_category();
+ const boost::system::error_category & lib4_error_category = get_lib4_error_category();
extern const boost::system::error_code boo_boo;
extern const boost::system::error_code big_boo_boo;
@@ -183,10 +189,11 @@
}
};
- const lib4_error_category_imp lib4_error_category_const;
-
- const boost::system::error_category & lib4_error_category
- = lib4_error_category_const;
+ const boost::system::error_category & get_lib4_error_category()
+ {
+ static const lib4_error_category_imp l4ecat;
+ return l4ecat;
+ }
const boost::system::error_code boo_boo( 456, lib4_error_category );
const boost::system::error_code big_boo_boo( 789, lib4_error_category );
Modified: branches/bcbboost/more/formal_review_schedule.html
==============================================================================
--- branches/bcbboost/more/formal_review_schedule.html (original)
+++ branches/bcbboost/more/formal_review_schedule.html 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -88,7 +88,7 @@
<td><a href="http://svn.boost.org/svn/boost/sandbox/graph-v2">
Boost Sandbox</a></td>
<td>Jeremy Siek</td>
- <td>-</td>
+ <td>October 8, 2007 - October 12, 2007</td>
</tr>
<tr>
@@ -97,7 +97,7 @@
<td><a href="http://svn.boost.org/svn/boost/sandbox/graph-v2">
Boost Sandbox</a></td>
<td>Jeremy Siek</td>
- <td>-</td>
+ <td>October 15, 2007 - October 19, 2007</td>
</tr>
<tr>
@@ -136,6 +136,17 @@
<td>-</td>
</tr>
+ <tr>
+ <td>Thread-Safe Signals</td>
+ <td>Frank Hess</td>
+ <td><a href="http://www.boost-consulting.com/vault/index.php?&direction=0&order=&directory=thread_safe_signals">
+ Boost Sandbox Vault</a></td>
+ <td>Needed</td>
+ <td>-</td>
+ </tr>
+
+
+
</table>
<h2>Past Review Results and Milestones</h2>
Modified: branches/bcbboost/tools/jam/src/execunix.c
==============================================================================
--- branches/bcbboost/tools/jam/src/execunix.c (original)
+++ branches/bcbboost/tools/jam/src/execunix.c 2007-09-26 17:55:31 EDT (Wed, 26 Sep 2007)
@@ -62,6 +62,7 @@
static clock_t tps = 0;
static struct timeval tv;
+static int timeout = 0;
static int intr = 0;
static int cmdsrunning = 0;
@@ -355,6 +356,9 @@
void populate_file_descriptors(int *fmax, fd_set *fds)
{
int i, fd_max = 0;
+ struct tms buf;
+ clock_t current = times(&buf);
+ timeout = globs.timeout;
/* compute max read file descriptor for use in select */
FD_ZERO(fds);
@@ -375,9 +379,9 @@
}
if (globs.timeout && cmdtab[i].pid) {
- struct tms buf;
- clock_t current = times(&buf);
- if (globs.timeout <= (current-cmdtab[i].start_time)/tps) {
+ clock_t consumed = (current - cmdtab[i].start_time) / tps;
+ timeout = (globs.timeout - consumed) < timeout ? (globs.timeout - consumed) : timeout;
+ if (globs.timeout <= consumed) {
killpg(cmdtab[i].pid, SIGKILL);
cmdtab[i].exit_reason = EXIT_TIMEOUT;
}
@@ -414,7 +418,7 @@
if (0 < globs.timeout) {
/* force select to timeout so we can terminate expired processes */
- tv.tv_sec = globs.timeout;
+ tv.tv_sec = timeout;
tv.tv_usec = 0;
/* select will wait until: io on a descriptor, a signal, or we time out */
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