4 #if __GNUC__ == 4 && __GNUC_MINOR__ == 4
5 # include <cstdatomic> // <atomic> is named <cstdatomic> in gcc 4.4
7 template<typename _Tp> // fix missing definition in gcc 4.4
9 atomic<_Tp*>::store(_Tp* __v, memory_order __m) volatile
10 { atomic_address::store(__v, __m); }
16 #define SYNC_QUEUE_BUFSIZE 16
23 head_node = tail_node = new node();
24 head.store(head_node->values);
25 tail.store(tail_node->values);
40 return head.load() == tail.load();
43 // size() is not not thread-safe
47 if (head_node == tail_node) {
48 count = tail.load() - head.load();
51 (head_node->values + (SYNC_QUEUE_BUFSIZE - 1)) - head.load();
52 for (node* n = head_node->next; n != tail_node; n = n->next)
53 count += SYNC_QUEUE_BUFSIZE;
54 count += tail.load() - tail_node->values;
59 bool push(const T& val)
61 T* old_tail = tail.load();
63 if (old_tail == tail_node->values + (SYNC_QUEUE_BUFSIZE - 1)) {
64 tail_node->next = new node();
65 tail_node = tail_node->next;
66 new_tail = tail_node->values;
68 new_tail = old_tail + 1;
72 return (old_tail == head.load());
77 T* old_head = head.load();
78 if (old_head == tail.load()) // empty?
82 if (old_head == head_node->values + (SYNC_QUEUE_BUFSIZE - 1)) {
83 node* old_head_node = head_node;
84 head_node = head_node->next;
86 new_head = head_node->values;
88 new_head = old_head + 1;
97 node(): next(NULL) { }
98 T values[SYNC_QUEUE_BUFSIZE];
104 std::atomic<T*> head;
105 std::atomic<T*> tail;
108 #endif // !SYNC_QUEUE_H