1 | // Copyright (C) 2010 Vicente Botet |
---|---|
2 | // |
3 | // Distributed under the Boost Software License, Version 1.0. (See accompanying |
4 | // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) |
5 | |
6 | #define BOOST_THREAD_VERSION 2 |
7 | |
8 | #include <boost/thread/thread.hpp> |
9 | #include <boost/thread/condition.hpp> |
10 | #include <boost/thread/recursive_mutex.hpp> |
11 | #include <list> |
12 | #include <iostream> |
13 | |
14 | #if defined BOOST_THREAD_USES_CHRONO |
15 | |
16 | using namespace std; |
17 | |
18 | boost::recursive_mutex theMutex; |
19 | |
20 | typedef std::list<boost::condition*> Conditions; |
21 | Conditions theConditions; |
22 | |
23 | void ThreadFuncWaiter() |
24 | { |
25 | boost::condition con1; |
26 | //for(; ; ) |
27 | for (int j = 0; j < 10; j++) |
28 | { |
29 | { |
30 | boost::unique_lock<boost::recursive_mutex> lockMtx(theMutex); |
31 | theConditions.push_back(x: &con1); |
32 | |
33 | cout << "Added "<< boost::this_thread::get_id() << " "<< &con1 << endl; |
34 | if (con1.timed_wait(m&: lockMtx, wait_duration: boost::posix_time::time_duration(0, 0, 50))) |
35 | { |
36 | cout << "Woke Up "<< boost::this_thread::get_id() << " "<< &con1 << endl; |
37 | } |
38 | else |
39 | { |
40 | cout << "*****Timed Out "<< boost::this_thread::get_id() << " "<< &con1 << endl; |
41 | exit(status: 13); |
42 | } |
43 | |
44 | theConditions.remove(value: &con1); |
45 | cout << "Removed "<< boost::this_thread::get_id() << " "<< &con1 << endl; |
46 | cout << "Waiter "<< j << endl; |
47 | |
48 | } |
49 | //Sleep(2000); |
50 | boost::this_thread::sleep_for(d: boost::chrono::milliseconds(200)); |
51 | } |
52 | } |
53 | |
54 | void ThreadFuncNotifier() |
55 | { |
56 | for (int j = 0; j < 70; j++) |
57 | { |
58 | { |
59 | boost::unique_lock<boost::recursive_mutex> lockMtx(theMutex); |
60 | cout << "<Notifier "<< j << endl; |
61 | |
62 | unsigned int i = 0; |
63 | for (Conditions::iterator it = theConditions.begin(); it != theConditions.end() && i < 2; ++it) |
64 | { |
65 | (*it)->notify_one(); |
66 | //WORKAROUND_ lockMtx.unlock(); |
67 | //WORKAROUND_ boost::this_thread::sleep_for(boost::chrono::milliseconds(50)); |
68 | cout << "Notified One "<< theConditions.size() << " "<< (*it) << endl; |
69 | ++i; |
70 | //WORKAROUND_ lockMtx.lock(); |
71 | } |
72 | |
73 | cout << "Notifier> "<< j << endl; |
74 | } |
75 | boost::this_thread::sleep_for(d: boost::chrono::milliseconds(50)); |
76 | } |
77 | } |
78 | |
79 | int main() |
80 | { |
81 | boost::thread_group tg; |
82 | for (int i = 0; i < 12; ++i) |
83 | { |
84 | tg.create_thread(threadfunc: ThreadFuncWaiter); |
85 | } |
86 | |
87 | tg.create_thread(threadfunc: ThreadFuncNotifier); |
88 | |
89 | tg.join_all(); |
90 | |
91 | return 0; |
92 | } |
93 | |
94 | |
95 | #else |
96 | #error "Test not applicable: BOOST_THREAD_USES_CHRONO not defined for this platform as not supported" |
97 | #endif |
98 |