MSQueue, MoirQueue refactoring done (issues #1, #2, #3)
[libcds.git] / tests / unit / queue / intrusive_queue_type.h
1 //$$CDS-header$$
2
3 #ifndef __CDSUNIT_INTRUSIVE_QUEUE_TYPES_H
4 #define __CDSUNIT_INTRUSIVE_QUEUE_TYPES_H
5
6 #include <cds/intrusive/msqueue.h>
7 #include <cds/intrusive/moir_queue.h>
8 #include <cds/intrusive/optimistic_queue.h>
9 #include <cds/intrusive/tsigas_cycle_queue.h>
10 #include <cds/intrusive/vyukov_mpmc_cycle_queue.h>
11 #include <cds/intrusive/basket_queue.h>
12 #include <cds/intrusive/fcqueue.h>
13 #include <cds/intrusive/segmented_queue.h>
14
15 #include <cds/gc/hp.h>
16 #include <cds/gc/hrc.h> //TODO: remove this line!
17 #include <cds/gc/dhp.h>
18
19 #include <boost/intrusive/slist.hpp>
20
21 #include "print_segmentedqueue_stat.h"
22
23 namespace queue {
24
25     namespace details {
26         struct empty_stat {};
27
28         template <typename T, typename Lock=std::mutex>
29         class BoostSList
30         {
31             typedef boost::intrusive::slist< T, boost::intrusive::cache_last<true> >    slist_type;
32             typedef Lock lock_type;
33             typedef std::lock_guard<lock_type> lock_guard;
34
35             slist_type  m_List;
36             mutable lock_type m_Lock;
37         public:
38             typedef T value_type;
39
40         public:
41             bool push( value_type& v )
42             {
43                 lock_guard l( m_Lock );
44                 m_List.push_back( v );
45                 return true;
46             }
47
48             bool enqueue( value_type& v )
49             {
50                 return push( v );
51             }
52
53             value_type * pop()
54             {
55                 lock_guard l( m_Lock );
56                 if ( m_List.empty() )
57                     return nullptr;
58                 value_type& v = m_List.front();
59                 m_List.pop_front();
60                 return &v;
61             }
62             value_type * deque()
63             {
64                 return pop();
65             }
66
67             bool empty() const
68             {
69                 lock_guard l( m_Lock );
70                 return m_List.empty();
71             }
72
73             size_t size() const
74             {
75                 lock_guard l( m_Lock );
76                 return m_List.size();
77             }
78
79             empty_stat statistics() const
80             {
81                 return empty_stat();
82             }
83         };
84     }
85
86     template <typename T>
87     struct Types {
88
89         // MSQueue, MoirQueue
90         struct traits_MSQueue_HP : public cds::intrusive::msqueue::traits
91         {
92             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::HP > > hook;
93         };
94         typedef cds::intrusive::MSQueue< cds::gc::HP, T, traits_MSQueue_HP > MSQueue_HP;
95         typedef cds::intrusive::MoirQueue< cds::gc::HP, T, traits_MSQueue_HP > MoirQueue_HP;
96
97         struct traits_MSQueue_HP_seqcst : public cds::intrusive::msqueue::traits
98         {
99             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::HP > > hook;
100             typedef cds::opt::v::sequential_consistent memory_model;
101         };
102         typedef cds::intrusive::MSQueue< cds::gc::HP, T, traits_MSQueue_HP_seqcst > MSQueue_HP_seqcst;
103         typedef cds::intrusive::MoirQueue< cds::gc::HP, T, traits_MSQueue_HP_seqcst > MoirQueue_HP_seqcst;
104
105         struct traits_MSQueue_DHP : public cds::intrusive::msqueue::traits
106         {
107             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::DHP > > hook;
108         };
109         typedef cds::intrusive::MSQueue< cds::gc::DHP, T, traits_MSQueue_DHP > MSQueue_DHP;
110         typedef cds::intrusive::MoirQueue< cds::gc::DHP, T, traits_MSQueue_DHP > MoirQueue_DHP;
111
112         struct traits_MSQueue_DHP_seqcst : public cds::intrusive::msqueue::traits
113         {
114             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::DHP > > hook;
115             typedef cds::opt::v::sequential_consistent memory_model;
116         };
117         typedef cds::intrusive::MSQueue< cds::gc::DHP, T, traits_MSQueue_DHP_seqcst > MSQueue_DHP_seqcst;
118         typedef cds::intrusive::MoirQueue< cds::gc::DHP, T, traits_MSQueue_DHP_seqcst > MoirQueue_DHP_seqcst;
119
120         // MSQueue + item counter
121         struct traits_MSQueue_HP_ic : public cds::intrusive::msqueue::traits
122         {
123             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::HP > > hook;
124             typedef cds::atomicity::item_counter item_counter;
125         };
126         typedef cds::intrusive::MSQueue< cds::gc::HP, T, traits_MSQueue_HP_ic > MSQueue_HP_ic;
127         typedef cds::intrusive::MoirQueue< cds::gc::HP, T, traits_MSQueue_HP_ic > MoirQueue_HP_ic;
128
129         struct traits_MSQueue_DHP_ic : public cds::intrusive::msqueue::traits
130         {
131             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::DHP > > hook;
132             typedef cds::atomicity::item_counter item_counter;
133         };
134         typedef cds::intrusive::MSQueue< cds::gc::DHP, T, traits_MSQueue_DHP_ic > MSQueue_DHP_ic;
135         typedef cds::intrusive::MoirQueue< cds::gc::DHP, T, traits_MSQueue_DHP_ic > MoirQueue_DHP_ic;
136
137         // MSQueue + stat
138         struct traits_MSQueue_HP_stat : public cds::intrusive::msqueue::traits
139         {
140             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::HP > > hook;
141             typedef cds::intrusive::msqueue::stat<> stat;
142         };
143         typedef cds::intrusive::MSQueue< cds::gc::HP, T, traits_MSQueue_HP_stat > MSQueue_HP_stat;
144         typedef cds::intrusive::MoirQueue< cds::gc::HP, T, traits_MSQueue_HP_stat > MoirQueue_HP_stat;
145
146         struct traits_MSQueue_DHP_stat : public cds::intrusive::msqueue::traits
147         {
148             typedef cds::intrusive::msqueue::base_hook< cds::opt::gc< cds::gc::DHP > > hook;
149             typedef cds::intrusive::msqueue::stat<> stat;
150         };
151         typedef cds::intrusive::MSQueue< cds::gc::DHP, T, traits_MSQueue_DHP_stat > MSQueue_DHP_stat;
152         typedef cds::intrusive::MoirQueue< cds::gc::DHP, T, traits_MSQueue_DHP_stat > MoirQueue_DHP_stat;
153
154
155         // OptimisticQueue
156         typedef cds::intrusive::OptimisticQueue< cds::gc::HP, T
157             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
158         >   OptimisticQueue_HP;
159
160         typedef cds::intrusive::OptimisticQueue< cds::gc::HP, T
161             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
162             ,cds::opt::memory_model< cds::opt::v::sequential_consistent >
163         >   OptimisticQueue_HP_seqcst;
164
165         typedef cds::intrusive::OptimisticQueue< cds::gc::PTB, T
166             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
167         >   OptimisticQueue_PTB;
168
169         typedef cds::intrusive::OptimisticQueue< cds::gc::PTB, T
170             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
171             ,cds::opt::memory_model< cds::opt::v::sequential_consistent >
172         >   OptimisticQueue_PTB_seqcst;
173
174
175         // OptimisticQueue + item counter
176         typedef cds::intrusive::OptimisticQueue< cds::gc::HP, T
177             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
178             ,cds::opt::item_counter< cds::atomicity::item_counter >
179         >   OptimisticQueue_HP_ic;
180
181         typedef cds::intrusive::OptimisticQueue< cds::gc::PTB, T
182             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
183             ,cds::opt::item_counter< cds::atomicity::item_counter >
184         >   OptimisticQueue_PTB_ic;
185
186         // OptimisticQueue + stat
187         typedef cds::intrusive::OptimisticQueue< cds::gc::HP, T
188             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
189             ,cds::opt::stat< cds::intrusive::queue_stat<> >
190         >   OptimisticQueue_HP_stat;
191
192         typedef cds::intrusive::OptimisticQueue< cds::gc::PTB, T
193             ,cds::intrusive::opt::hook< cds::intrusive::optimistic_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
194             ,cds::opt::stat< cds::intrusive::queue_stat<> >
195         >   OptimisticQueue_PTB_stat;
196
197         // TsigasCycleQueue
198         class TsigasCycleQueue_dyn
199             : public cds::intrusive::TsigasCycleQueue< T
200                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
201             >
202         {
203             typedef cds::intrusive::TsigasCycleQueue< T
204                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
205             > base_class;
206         public:
207             TsigasCycleQueue_dyn()
208                 : base_class( 1024 * 64 )
209             {}
210
211             TsigasCycleQueue_dyn( size_t nCapacity )
212                 : base_class( nCapacity )
213             {}
214
215             cds::opt::none statistics() const
216             {
217                 return cds::opt::none();
218             }
219         };
220
221         class TsigasCycleQueue_dyn_ic
222             : public cds::intrusive::TsigasCycleQueue< T
223                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
224                 ,cds::opt::item_counter< cds::atomicity::item_counter >
225             >
226         {
227             typedef cds::intrusive::TsigasCycleQueue< T
228                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
229                 ,cds::opt::item_counter< cds::atomicity::item_counter >
230             > base_class;
231         public:
232             TsigasCycleQueue_dyn_ic()
233                 : base_class( 1024 * 64 )
234             {}
235             TsigasCycleQueue_dyn_ic( size_t nCapacity )
236                 : base_class( nCapacity )
237             {}
238
239             cds::opt::none statistics() const
240             {
241                 return cds::opt::none();
242             }
243         };
244
245         // VyukovMPMCCycleQueue
246         class VyukovMPMCCycleQueue_dyn
247             : public cds::intrusive::VyukovMPMCCycleQueue< T
248                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
249             >
250         {
251             typedef cds::intrusive::VyukovMPMCCycleQueue< T
252                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
253             > base_class;
254         public:
255             VyukovMPMCCycleQueue_dyn()
256                 : base_class( 1024 * 64 )
257             {}
258             VyukovMPMCCycleQueue_dyn( size_t nCapacity )
259                 : base_class( nCapacity )
260             {}
261
262             cds::opt::none statistics() const
263             {
264                 return cds::opt::none();
265             }
266         };
267
268         class VyukovMPMCCycleQueue_dyn_ic
269             : public cds::intrusive::VyukovMPMCCycleQueue< T
270                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
271                 ,cds::opt::item_counter< cds::atomicity::item_counter >
272             >
273         {
274             typedef cds::intrusive::VyukovMPMCCycleQueue< T
275                 ,cds::opt::buffer< cds::opt::v::dynamic_buffer< int > >
276                 ,cds::opt::item_counter< cds::atomicity::item_counter >
277             > base_class;
278         public:
279             VyukovMPMCCycleQueue_dyn_ic()
280                 : base_class( 1024 * 64 )
281             {}
282             VyukovMPMCCycleQueue_dyn_ic( size_t nCapacity )
283                 : base_class( nCapacity )
284             {}
285
286             cds::opt::none statistics() const
287             {
288                 return cds::opt::none();
289             }
290         };
291
292         // BasketQueue
293         typedef cds::intrusive::BasketQueue< cds::gc::HP, T
294             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
295         >   BasketQueue_HP;
296
297         typedef cds::intrusive::BasketQueue<cds::gc::HP, T
298             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
299             ,cds::opt::memory_model< cds::opt::v::sequential_consistent >
300         >   BasketQueue_HP_seqcst;
301
302         typedef cds::intrusive::BasketQueue< cds::gc::HRC, T
303             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HRC > > >
304         >   BasketQueue_HRC;
305
306         typedef cds::intrusive::BasketQueue< cds::gc::HRC, T
307             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HRC > > >
308             ,cds::opt::memory_model< cds::opt::v::sequential_consistent >
309         >   BasketQueue_HRC_seqcst;
310
311         typedef cds::intrusive::BasketQueue< cds::gc::PTB, T
312             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
313         >   BasketQueue_PTB;
314
315         typedef cds::intrusive::BasketQueue< cds::gc::PTB, T
316             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
317             ,cds::opt::memory_model< cds::opt::v::sequential_consistent >
318         >   BasketQueue_PTB_seqcst;
319
320         // BasketQueue + item counter
321         typedef cds::intrusive::BasketQueue< cds::gc::HP, T
322             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
323             ,cds::opt::item_counter< cds::atomicity::item_counter >
324         >   BasketQueue_HP_ic;
325
326         typedef cds::intrusive::BasketQueue< cds::gc::HRC, T
327             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HRC > > >
328             ,cds::opt::item_counter< cds::atomicity::item_counter >
329         >   BasketQueue_HRC_ic;
330
331         typedef cds::intrusive::BasketQueue< cds::gc::PTB, T
332             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
333             ,cds::opt::item_counter< cds::atomicity::item_counter >
334         >   BasketQueue_PTB_ic;
335
336         // BasketQueue + stat
337         typedef cds::intrusive::BasketQueue< cds::gc::HP, T
338             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HP > > >
339             ,cds::opt::stat< cds::intrusive::queue_stat<> >
340         >   BasketQueue_HP_stat;
341
342         typedef cds::intrusive::BasketQueue< cds::gc::HRC, T
343             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::HRC > > >
344             ,cds::opt::stat< cds::intrusive::queue_stat<> >
345         >   BasketQueue_HRC_stat;
346
347         typedef cds::intrusive::BasketQueue< cds::gc::PTB, T
348             ,cds::intrusive::opt::hook< cds::intrusive::basket_queue::base_hook< cds::opt::gc< cds::gc::PTB > > >
349             ,cds::opt::stat< cds::intrusive::queue_stat<> >
350         >   BasketQueue_PTB_stat;
351
352         // FCQueue
353         class traits_FCQueue_delay2:
354             public cds::intrusive::fcqueue::make_traits<
355                 cds::opt::back_off< cds::backoff::delay_of<2> >
356             >::type
357         {};
358         class traits_FCQueue_delay2_elimination:
359             public cds::intrusive::fcqueue::make_traits<
360                 cds::opt::back_off< cds::backoff::delay_of<2> >
361                 ,cds::opt::enable_elimination< true >
362             >::type
363         {};
364         class traits_FCQueue_delay2_elimination_stat:
365             public cds::intrusive::fcqueue::make_traits<
366                 cds::opt::back_off< cds::backoff::delay_of<2> >
367                 ,cds::opt::stat< cds::intrusive::fcqueue::stat<> >
368                 ,cds::opt::enable_elimination< true >
369             >::type
370         {};
371         class traits_FCQueue_expbackoff_elimination:
372             public cds::intrusive::fcqueue::make_traits<
373                 cds::opt::enable_elimination< true >
374                 ,cds::opt::elimination_backoff< cds::backoff::Default >
375             >::type
376         {};
377         class traits_FCQueue_expbackoff_elimination_stat:
378             public cds::intrusive::fcqueue::make_traits<
379                 cds::opt::enable_elimination< true >
380                 ,cds::opt::stat< cds::intrusive::fcqueue::stat<> >
381                 ,cds::opt::elimination_backoff< cds::backoff::Default >
382             >::type
383         {};
384
385         typedef cds::intrusive::FCQueue< T, boost::intrusive::list<T>, traits_FCQueue_delay2 > FCQueue_list_delay2;
386         typedef cds::intrusive::FCQueue< T, boost::intrusive::list<T>, traits_FCQueue_delay2_elimination > FCQueue_list_delay2_elimination;
387         typedef cds::intrusive::FCQueue< T, boost::intrusive::list<T>, traits_FCQueue_delay2_elimination_stat > FCQueue_list_delay2_elimination_stat;
388         typedef cds::intrusive::FCQueue< T, boost::intrusive::list<T>, traits_FCQueue_expbackoff_elimination > FCQueue_list_expbackoff_elimination;
389         typedef cds::intrusive::FCQueue< T, boost::intrusive::list<T>, traits_FCQueue_expbackoff_elimination_stat > FCQueue_list_expbackoff_elimination_stat;
390
391         // SegmentedQueue
392         class traits_SegmentedQueue_spin_stat:
393             public cds::intrusive::segmented_queue::make_traits<
394                 cds::opt::stat< cds::intrusive::segmented_queue::stat<> >
395             >::type
396         {};
397         class traits_SegmentedQueue_mutex_stat:
398             public cds::intrusive::segmented_queue::make_traits<
399                 cds::opt::stat< cds::intrusive::segmented_queue::stat<> >
400                 ,cds::opt::lock_type< std::mutex >
401             >::type
402         {};
403         class traits_SegmentedQueue_mutex:
404             public cds::intrusive::segmented_queue::make_traits<
405                 cds::opt::lock_type< std::mutex >
406             >::type
407         {};
408
409         typedef cds::intrusive::SegmentedQueue< cds::gc::HP, T >  SegmentedQueue_HP_spin;
410         typedef cds::intrusive::SegmentedQueue< cds::gc::HP, T, traits_SegmentedQueue_spin_stat >  SegmentedQueue_HP_spin_stat;
411         typedef cds::intrusive::SegmentedQueue< cds::gc::HP, T, traits_SegmentedQueue_mutex >  SegmentedQueue_HP_mutex;
412         typedef cds::intrusive::SegmentedQueue< cds::gc::HP, T, traits_SegmentedQueue_mutex_stat >  SegmentedQueue_HP_mutex_stat;
413
414         typedef cds::intrusive::SegmentedQueue< cds::gc::PTB, T >  SegmentedQueue_PTB_spin;
415         typedef cds::intrusive::SegmentedQueue< cds::gc::PTB, T, traits_SegmentedQueue_spin_stat >  SegmentedQueue_PTB_spin_stat;
416         typedef cds::intrusive::SegmentedQueue< cds::gc::PTB, T, traits_SegmentedQueue_mutex >  SegmentedQueue_PTB_mutex;
417         typedef cds::intrusive::SegmentedQueue< cds::gc::PTB, T, traits_SegmentedQueue_mutex_stat >  SegmentedQueue_PTB_mutex_stat;
418
419         // Boost SList
420         typedef details::BoostSList< T, std::mutex >    BoostSList_mutex;
421         typedef details::BoostSList< T, cds::lock::Spin >   BoostSList_spin;
422     };
423 }
424
425
426 // *********************************************
427 // Queue statistics
428 namespace std {
429
430     // cds::intrusive::queue_stat
431     template <typename Counter>
432     static inline std::ostream& operator <<(std::ostream& o, cds::intrusive::queue_stat<Counter> const& s)
433     {
434         return o
435             << "\tStatistics:\n"
436             << "\t\t     Enqueue count: " << s.m_EnqueueCount.get() << "\n"
437             << "\t\t      Enqueue race: " << s.m_EnqueueRace.get() << "\n"
438             << "\t\t     Dequeue count: " << s.m_DequeueCount.get() << "\n"
439             << "\t\t      Dequeue race: " << s.m_DequeueRace.get() << "\n"
440             << "\t\tAdvance tail error: " << s.m_AdvanceTailError.get() << "\n"
441             << "\t\t          Bad tail: " << s.m_BadTail.get() << "\n";
442     }
443     static inline std::ostream& operator <<(std::ostream& o, cds::intrusive::queue_dummy_stat const& s)
444     {
445         return o;
446     }
447
448
449     template <typename Counter>
450     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::msqueue::stat<Counter> const& s )
451     {
452         return o
453             << "\tStatistics:\n"
454             << "\t\t     Enqueue count: " << s.m_EnqueueCount.get() << "\n"
455             << "\t\t      Enqueue race: " << s.m_EnqueueRace.get()  << "\n"
456             << "\t\t     Dequeue count: " << s.m_DequeueCount.get() << "\n"
457             << "\t\t      Dequeue race: " << s.m_DequeueRace.get()  << "\n"
458             << "\t\tAdvance tail error: " << s.m_AdvanceTailError.get() << "\n"
459             << "\t\t          Bad tail: " << s.m_BadTail.get() << "\n";
460     }
461
462     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::msqueue::empty_stat const& s )
463     {
464         return o;
465     }
466
467     static inline std::ostream& operator <<( std::ostream& o, cds::opt::none )
468     {
469         return o;
470     }
471
472     // cds::intrusive::optimistic_queue::stat
473     template <typename Counter>
474     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::optimistic_queue::stat<Counter> const& s )
475     {
476         return o
477             << static_cast<cds::intrusive::queue_stat<Counter> const&>( s )
478             << "\t\t"
479             << "\t\t    fix list call: " << s.m_FixListCount.get() << "\n";
480     }
481
482     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::optimistic_queue::dummy_stat const& s )
483     {
484         return o;
485     }
486
487     // cds::intrusive::basket_queue::stat
488     template <typename Counter>
489     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::basket_queue::stat<Counter> const& s )
490     {
491         return o
492             << static_cast<cds::intrusive::queue_stat<Counter> const&>( s )
493             << "\t\tTry Add basket count: " << s.m_TryAddBasket.get() << "\n"
494             << "\t\t    Add basket count: " << s.m_AddBasketCount.get() << "\n";
495     }
496
497     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::basket_queue::dummy_stat const& s )
498     {
499         return o;
500     }
501
502     // cds::intrusive::fcqueue::stat
503     template <typename Counter>
504     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::fcqueue::stat<Counter> const& s )
505     {
506             return o << "\tStatistics:\n"
507                 << "\t                    Push: " << s.m_nEnqueue.get()           << "\n"
508                 << "\t                     Pop: " << s.m_nDequeue.get()           << "\n"
509                 << "\t               FailedPop: " << s.m_nFailedDeq.get()         << "\n"
510                 << "\t  Collided push/pop pair: " << s.m_nCollided.get()          << "\n"
511                 << "\tFlat combining statistics:\n"
512                 << "\t        Combining factor: " << s.combining_factor()         << "\n"
513                 << "\t         Operation count: " << s.m_nOperationCount.get()    << "\n"
514                 << "\t      Combine call count: " << s.m_nCombiningCount.get()    << "\n"
515                 << "\t        Compact pub-list: " << s.m_nCompactPublicationList.get() << "\n"
516                 << "\t   Deactivate pub-record: " << s.m_nDeactivatePubRecord.get()    << "\n"
517                 << "\t     Activate pub-record: " << s.m_nActivatePubRecord.get() << "\n"
518                 << "\t       Create pub-record: " << s.m_nPubRecordCreated.get()  << "\n"
519                 << "\t       Delete pub-record: " << s.m_nPubRecordDeteted.get()  << "\n"
520                 << "\t      Acquire pub-record: " << s.m_nAcquirePubRecCount.get()<< "\n"
521                 << "\t      Release pub-record: " << s.m_nReleasePubRecCount.get()<< "\n";
522     }
523
524     static inline std::ostream& operator <<( std::ostream& o, cds::intrusive::fcqueue::empty_stat const& s )
525     {
526         return o;
527     }
528
529     static inline std::ostream& operator <<( std::ostream& o, queue::details::empty_stat const& s )
530     {
531         return o;
532     }
533
534 } // namespace std
535
536 #endif // #ifndef __CDSUNIT_INTRUSIVE_QUEUE_TYPES_H