-/*
- * Copyright (C) 2013 Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- */
+// SPDX-FileCopyrightText: 2013 Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
+//
+// SPDX-License-Identifier: LGPL-2.1-or-later
#include <unistd.h>
#include <stdlib.h>
#include <stdint.h>
#include <inttypes.h>
-#define RCU_MB /* Memory barrier RCU flavor */
-#include <urcu.h>
+#include <urcu/urcu-mb.h> /* Memory barrier RCU flavor */
#include <urcu/rculist.h> /* List example */
#include <urcu/compiler.h> /* For CAA_ARRAY_SIZE */
{
struct mynode *node;
- node = calloc(sizeof(*node), 1);
+ node = calloc(1, sizeof(*node));
if (!node)
return -1;
node->value = v;
free(node);
}
-int main(int argc, char **argv)
+int main(void)
{
uint64_t values[] = { 42, 36, 24, };
unsigned int i;
* Each thread need using RCU read-side need to be explicitly
* registered.
*/
- rcu_register_thread();
+ urcu_mb_register_thread();
/*
* Adding nodes to the linked-list. Safe against concurrent
* with rcu_read_lock() and rcu_read_unlock(). They can be
* nested. Those are no-ops for the QSBR flavor.
*/
- rcu_read_lock();
+ urcu_mb_read_lock();
/*
* RCU traversal of the linked list.
cds_list_for_each_entry_rcu(node, &mylist, node) {
printf("Value: %" PRIu64 "\n", node->value);
}
- rcu_read_unlock();
+ urcu_mb_read_unlock();
/*
* Removing nodes from linked list. Safe against concurrent RCU
* call_rcu() can be called from RCU read-side critical
* sections.
*/
- call_rcu(&node->rcu_head, rcu_free_node);
+ urcu_mb_call_rcu(&node->rcu_head, rcu_free_node);
}
+ /*
+ * We can also wait for a quiescent state by calling
+ * synchronize_rcu() rather than using call_rcu(). It is usually
+ * a slower approach than call_rcu(), because the latter can
+ * batch work. Moreover, call_rcu() can be called from a RCU
+ * read-side critical section, but synchronize_rcu() should not.
+ */
+ urcu_mb_synchronize_rcu();
+
sleep(1);
/*
* before program exits, or in library destructors, is a good
* practice.
*/
- rcu_barrier();
+ urcu_mb_barrier();
end:
- rcu_unregister_thread();
+ urcu_mb_unregister_thread();
return ret;
}