[6879] Not apply casting time spell bonuses mods to creature (non-pets) casted spells...
[getmangos.git] / dep / include / zthread / BlockingQueue.h
blobac17347d1ccb0160c68d100826aa3f231565f5f2
1 /*
2 * Copyright (c) 2005, Eric Crahen
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is furnished
9 * to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included in all
12 * copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
18 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 #ifndef __ZTBLOCKINGQUEUE_H__
24 #define __ZTBLOCKINGQUEUE_H__
26 #include "zthread/Guard.h"
27 #include "zthread/Condition.h"
28 #include "zthread/Queue.h"
30 #include <deque>
32 namespace ZThread {
34 /**
35 * @class BlockingQueue
36 * @author Eric Crahen <http://www.code-foo.com>
37 * @date <2003-07-16T12:01:43-0400>
38 * @version 2.3.0
40 * Like a LockedQueue, a BlockingQueue is a Queue implementation that provides
41 * serialized access to the items added to it. It differs by causing threads
42 * accessing the next() methods to block until a value becomes available.
44 template <class T, class LockType, typename StorageType = std::deque<T> >
45 class BlockingQueue : public Queue<T>, public Lockable {
47 //! Serialize access
48 LockType _lock;
50 //! Signaled when empty
51 Condition _notEmpty;
53 //! Storage backing the queue
54 StorageType _queue;
56 //! Cancellation flag
57 volatile bool _canceled;
59 public:
61 //! Create a new BlockingQueue
62 BlockingQueue() : _notEmpty(_lock), _canceled(false) {}
64 //! Destroy this BlockingQueue
65 virtual ~BlockingQueue() { }
67 /**
68 * @see Queue::add(const T& item)
70 virtual void add(const T& item) {
72 Guard<LockType> g(_lock);
74 if(_canceled)
75 throw Cancellation_Exception();
77 _queue.push_back(item);
79 _notEmpty.signal();
83 /**
84 * @see Queue::add(const T& item, unsigned long timeout)
86 virtual bool add(T item, unsigned long timeout) {
88 try {
90 Guard<LockType> g(_lock, timeout);
92 if(_canceled)
93 throw Cancellation_Exception();
95 _queue.push_back(item);
97 _notEmpty.signal();
99 } catch(Timeout_Exception&) { return false; }
101 return true;
106 * Get a value from this Queue. The calling thread may block indefinitely.
108 * @return <em>T</em> next available value
110 * @exception Cancellation_Exception thrown if this Queue has been canceled.
112 * @exception Interrupted_Exception thrown if the calling thread is interrupted
113 * before a value becomes available.
115 * @pre The Queue should not have been canceled prior to the invocation of this function.
116 * @post The value returned will have been removed from the Queue.
118 * @see Queue::next()
120 virtual T next() {
122 Guard<LockType> g(_lock);
124 while(_queue.empty() && !_canceled)
125 _notEmpty.wait();
127 if( _queue.empty() )
128 throw Cancellation_Exception();
130 T item = _queue.front();
131 _queue.pop_front();
133 return item;
139 * Get a value from this Queue. The calling thread may block indefinitely.
141 * @param timeout maximum amount of time (milliseconds) this method may block
142 * the calling thread.
144 * @return <em>T</em> next available value
146 * @exception Cancellation_Exception thrown if this Queue has been canceled.
147 * @exception Timeout_Exception thrown if the timeout expires before a value
148 * can be retrieved.
149 * @exception Interrupted_Exception thrown if the calling thread is interrupted
150 * before a value becomes available.
152 * @pre The Queue should not have been canceled prior to the invocation of this function.
153 * @post The value returned will have been removed from the Queue.
155 * @see Queue::next(unsigned long timeout)
157 virtual T next(unsigned long timeout) {
159 Guard<LockType> g(_lock, timeout);
161 while(_queue.empty() && !_canceled) {
162 if(!_notEmpty.wait(timeout))
163 throw Timeout_Exception();
166 if(_queue.empty() )
167 throw Cancellation_Exception();
169 T item = _queue.front();
170 _queue.pop_front();
172 return item;
178 * @see Queue::cancel()
180 * @post If threads are blocked on one of the next() functions then
181 * they will be awakened with a Cancellation_Exception.
183 virtual void cancel() {
185 Guard<LockType> g(_lock);
187 _notEmpty.broadcast();
188 _canceled = true;
193 * @see Queue::isCanceled()
195 virtual bool isCanceled() {
197 // Faster check since the queue will not become un-canceled
198 if(_canceled)
199 return true;
201 Guard<LockType> g(_lock);
203 return _canceled;
208 * @see Queue::size()
210 virtual size_t size() {
212 Guard<LockType> g(_lock);
213 return _queue.size();
218 * @see Queue::size(unsigned long timeout)
220 virtual size_t size(unsigned long timeout) {
222 Guard<LockType> g(_lock, timeout);
223 return _queue.size();
227 public:
229 virtual void acquire() {
230 _lock.acquire();
233 virtual bool tryAcquire(unsigned long timeout) {
234 return _lock.tryAcquire(timeout);
237 virtual void release() {
238 _lock.release();
241 }; /* BlockingQueue */
243 } // namespace ZThread
245 #endif // __ZTBLOCKINGQUEUE_H__