Added simplified form of urcu::batch_retire function
[libcds.git] / cds / urcu / details / gpt.h
index 30bb1ebb0eaceff60ec99cac5361b4ad3d1420df..1f5941481f91156ec8a09ba4f54846dce0971482 100644 (file)
@@ -108,7 +108,7 @@ namespace cds { namespace urcu {
         }
 
         // Return: true - synchronize has been called, false - otherwise
-        bool push_buffer( epoch_retired_ptr& p )
+        bool push_buffer( epoch_retired_ptr&& p )
         {
             bool bPushed = m_Buffer.push( p );
             if ( !bPushed || m_Buffer.size() >= capacity() ) {
@@ -168,10 +168,8 @@ namespace cds { namespace urcu {
         */
         virtual void retire_ptr( retired_ptr& p )
         {
-            if ( p.m_p ) {
-                epoch_retired_ptr ep( p, m_nCurEpoch.load( atomics::memory_order_acquire ) );
-                push_buffer( ep );
-            }
+            if ( p.m_p )
+                push_buffer( epoch_retired_ptr( p, m_nCurEpoch.load( atomics::memory_order_acquire )));
         }
 
         /// Retires the pointer chain [\p itFirst, \p itLast)
@@ -180,12 +178,21 @@ namespace cds { namespace urcu {
         {
             uint64_t nEpoch = m_nCurEpoch.load( atomics::memory_order_relaxed );
             while ( itFirst != itLast ) {
-                epoch_retired_ptr p( *itFirst, nEpoch );
+                push_buffer( epoch_retired_ptr( *itFirst, nEpoch ));
                 ++itFirst;
-                push_buffer( p );
             }
         }
 
+        /// Retires the pointer chain until \p Func returns \p nullptr retired pointer
+        template <typename Func>
+        void batch_retire( Func e )
+        {
+            uint64_t nEpoch = m_nCurEpoch.load( atomics::memory_order_relaxed );
+            for ( retired_ptr p{ e() }; p.m_p; p = e() )
+                push_buffer( epoch_retired_ptr( p, nEpoch ));
+        }
+
+
         /// Waits to finish a grace period and calls disposing thread
         void synchronize()
         {