1 #ifndef BOOST_THREAD_DETAIL_THREAD_GROUP_HPP 2 #define BOOST_THREAD_DETAIL_THREAD_GROUP_HPP 3 // Distributed under the Boost Software License, Version 1.0. (See 4 // accompanying file LICENSE_1_0.txt or copy at 5 // http://www.boost.org/LICENSE_1_0.txt) 6 // (C) Copyright 2007-9 Anthony Williams 7 8 #include <list> 9 #include <boost/thread/shared_mutex.hpp> 10 #include <boost/thread/mutex.hpp> 11 #include <boost/thread/lock_guard.hpp> 12 13 #include <boost/config/abi_prefix.hpp> 14 15 #ifdef BOOST_MSVC 16 #pragma warning(push) 17 #pragma warning(disable:4251) 18 #endif 19 20 namespace boost 21 { 22 class thread_group 23 { 24 private: 25 thread_group(thread_group const&); 26 thread_group& operator=(thread_group const&); 27 public: thread_group()28 thread_group() {} ~thread_group()29 ~thread_group() 30 { 31 for(std::list<thread*>::iterator it=threads.begin(),end=threads.end(); 32 it!=end; 33 ++it) 34 { 35 delete *it; 36 } 37 } 38 is_this_thread_in()39 bool is_this_thread_in() 40 { 41 thread::id id = this_thread::get_id(); 42 boost::shared_lock<shared_mutex> guard(m); 43 for(std::list<thread*>::iterator it=threads.begin(),end=threads.end(); 44 it!=end; 45 ++it) 46 { 47 if ((*it)->get_id() == id) 48 return true; 49 } 50 return false; 51 } 52 is_thread_in(thread * thrd)53 bool is_thread_in(thread* thrd) 54 { 55 if(thrd) 56 { 57 thread::id id = thrd->get_id(); 58 boost::shared_lock<shared_mutex> guard(m); 59 for(std::list<thread*>::iterator it=threads.begin(),end=threads.end(); 60 it!=end; 61 ++it) 62 { 63 if ((*it)->get_id() == id) 64 return true; 65 } 66 return false; 67 } 68 else 69 { 70 return false; 71 } 72 } 73 74 template<typename F> create_thread(F threadfunc)75 thread* create_thread(F threadfunc) 76 { 77 boost::lock_guard<shared_mutex> guard(m); 78 std::auto_ptr<thread> new_thread(new thread(threadfunc)); 79 threads.push_back(new_thread.get()); 80 return new_thread.release(); 81 } 82 add_thread(thread * thrd)83 void add_thread(thread* thrd) 84 { 85 if(thrd) 86 { 87 BOOST_THREAD_ASSERT_PRECONDITION( ! is_thread_in(thrd) , 88 thread_resource_error(static_cast<int>(system::errc::resource_deadlock_would_occur), "boost::thread_group: trying to add a duplicated thread") 89 ); 90 91 boost::lock_guard<shared_mutex> guard(m); 92 threads.push_back(thrd); 93 } 94 } 95 remove_thread(thread * thrd)96 void remove_thread(thread* thrd) 97 { 98 boost::lock_guard<shared_mutex> guard(m); 99 std::list<thread*>::iterator const it=std::find(threads.begin(),threads.end(),thrd); 100 if(it!=threads.end()) 101 { 102 threads.erase(it); 103 } 104 } 105 join_all()106 void join_all() 107 { 108 BOOST_THREAD_ASSERT_PRECONDITION( ! is_this_thread_in() , 109 thread_resource_error(static_cast<int>(system::errc::resource_deadlock_would_occur), "boost::thread_group: trying joining itself") 110 ); 111 boost::shared_lock<shared_mutex> guard(m); 112 113 for(std::list<thread*>::iterator it=threads.begin(),end=threads.end(); 114 it!=end; 115 ++it) 116 { 117 if ((*it)->joinable()) 118 (*it)->join(); 119 } 120 } 121 122 #if defined BOOST_THREAD_PROVIDES_INTERRUPTIONS interrupt_all()123 void interrupt_all() 124 { 125 boost::shared_lock<shared_mutex> guard(m); 126 127 for(std::list<thread*>::iterator it=threads.begin(),end=threads.end(); 128 it!=end; 129 ++it) 130 { 131 (*it)->interrupt(); 132 } 133 } 134 #endif 135 size() const136 size_t size() const 137 { 138 boost::shared_lock<shared_mutex> guard(m); 139 return threads.size(); 140 } 141 142 private: 143 std::list<thread*> threads; 144 mutable shared_mutex m; 145 }; 146 } 147 148 #ifdef BOOST_MSVC 149 #pragma warning(pop) 150 #endif 151 152 #include <boost/config/abi_suffix.hpp> 153 154 #endif 155