#ifndef fifo_h
#define fifo_h
-#include <list>
-#include "lock.h"
+#include "types.h"
// blocks enq() and deq() when queue is FULL or EMPTY
template<class T>
class fifo {
- public:
- fifo(size_t limit=0) : max_(limit) {}
- bool enq(T, bool blocking=true);
- void deq(T *);
- bool size() {
+ public:
+ fifo(size_t limit=0) : max_(limit) {}
+ bool enq(T, bool blocking=true);
+ void deq(T *);
+ bool size() {
lock ml(m_);
return q_.size();
}
- private:
- std::list<T> q_;
+ private:
+ list<T> q_;
mutex m_;
cond non_empty_c_; // q went non-empty
- cond has_space_c_; // q is not longer overfull
- size_t max_; // maximum capacity of the queue, block enq threads if exceeds this limit
+ cond has_space_c_; // q is not longer overfull
+ size_t max_; // maximum capacity of the queue, block enq threads if exceeds this limit
};
template<class T> bool
fifo<T>::enq(T e, bool blocking)
{
lock ml(m_);
- while (max_ && q_.size() >= max_) {
- if (!blocking)
- return false;
+ while (max_ && q_.size() >= max_) {
+ if (!blocking)
+ return false;
has_space_c_.wait(ml);
- }
+ }
q_.push_back(e);
non_empty_c_.notify_one();
- return true;
+ return true;
}
template<class T> void
fifo<T>::deq(T *e)
{
- lock ml(m_);
- while(q_.empty())
+ lock ml(m_);
+ while(q_.empty())
non_empty_c_.wait(ml);
*e = q_.front();
q_.pop_front();