Fixed bug in RCU batch_retire()
[libcds.git] / cds / urcu / details / gpi.h
index f4eee83eea2256619b77a0a802ba60cd96ad833b..23c105e18b938f3b37bdf3b8542676a6a2924898 100644 (file)
@@ -1,12 +1,11 @@
 //$$CDS-header$$
 
-#ifndef _CDS_URCU_DETAILS_GPI_H
-#define _CDS_URCU_DETAILS_GPI_H
+#ifndef CDSLIB_URCU_DETAILS_GPI_H
+#define CDSLIB_URCU_DETAILS_GPI_H
 
 #include <mutex>
 #include <cds/urcu/details/gp.h>
 #include <cds/algo/backoff_strategy.h>
-#include <cds/lock/scoped_lock.h>
 
 namespace cds { namespace urcu {
 
@@ -131,16 +130,27 @@ namespace cds { namespace urcu {
             }
         }
 
+        /// Retires the pointer chain until \p Func returns \p nullptr retired pointer
+        template <typename Func>
+        void batch_retire( Func e )
+        {
+            retired_ptr p{ e() };
+            if ( p.m_p ) {
+                synchronize();
+                while ( p.m_p ) {
+                    retired_ptr pr( p );
+                    p = e();
+                    pr.free();
+                }
+            }
+        }
+
         /// Waits to finish a grace period
         void synchronize()
         {
-            atomics::atomic_thread_fence( atomics::memory_order_acquire );
-            {
-                cds::lock::scoped_lock<lock_type> sl( m_Lock );
-                flip_and_wait();
-                flip_and_wait();
-            }
-            atomics::atomic_thread_fence( atomics::memory_order_release );
+            std::unique_lock<lock_type> sl( m_Lock );
+            flip_and_wait();
+            flip_and_wait();
         }
 
         //@cond
@@ -154,4 +164,4 @@ namespace cds { namespace urcu {
 
 }} // namespace cds::urcu
 
-#endif // #ifndef _CDS_URCU_DETAILS_GPI_H
+#endif // #ifndef CDSLIB_URCU_DETAILS_GPI_H