actions: Make lttng_action reference countable
authorJérémie Galarneau <jeremie.galarneau@efficios.com>
Wed, 5 Feb 2020 23:13:07 +0000 (18:13 -0500)
committerJérémie Galarneau <jeremie.galarneau@efficios.com>
Fri, 12 Jun 2020 21:36:49 +0000 (17:36 -0400)
lttng_action objects will be shared with the action executor subsystem
which executes them asynchronously. This introduces an ambiguous
ownership since triggers could be unregistered while an action is
executing (or pending execution).

Also ease the object ownership management of the group action sub
actions. This allow clients to add multiple time the same action to an
action group without any problem.

The currently user-visible 'destroy' method simply calls the 'put'
method which preserves the expected behaviour for current users (both
internal and public) of the API.

Signed-off-by: Jérémie Galarneau <jeremie.galarneau@efficios.com>
Change-Id: I2d016a9b80e418d40c72db8e155c44e96852b33f

include/lttng/action/action-internal.h
src/common/actions/action.c

index 152b27eabbc38518c146ce15219b7153efdf0f2f..e4c3b7b09eedfc9f98a586a02a36bf0e8d18e89d 100644 (file)
@@ -16,6 +16,7 @@
 #include <common/sessiond-comm/payload.h>
 #include <stdbool.h>
 #include <sys/types.h>
 #include <common/sessiond-comm/payload.h>
 #include <stdbool.h>
 #include <sys/types.h>
+#include <urcu/ref.h>
 
 typedef bool (*action_validate_cb)(struct lttng_action *action);
 typedef void (*action_destroy_cb)(struct lttng_action *action);
 
 typedef bool (*action_validate_cb)(struct lttng_action *action);
 typedef void (*action_destroy_cb)(struct lttng_action *action);
@@ -28,6 +29,7 @@ typedef ssize_t (*action_create_from_payload_cb)(
                struct lttng_action **action);
 
 struct lttng_action {
                struct lttng_action **action);
 
 struct lttng_action {
+       struct urcu_ref ref;
        enum lttng_action_type type;
        action_validate_cb validate;
        action_serialize_cb serialize;
        enum lttng_action_type type;
        action_validate_cb validate;
        action_serialize_cb serialize;
@@ -67,4 +69,10 @@ LTTNG_HIDDEN
 bool lttng_action_is_equal(const struct lttng_action *a,
                const struct lttng_action *b);
 
 bool lttng_action_is_equal(const struct lttng_action *a,
                const struct lttng_action *b);
 
+LTTNG_HIDDEN
+void lttng_action_get(struct lttng_action *action);
+
+LTTNG_HIDDEN
+void lttng_action_put(struct lttng_action *action);
+
 #endif /* LTTNG_ACTION_INTERNAL_H */
 #endif /* LTTNG_ACTION_INTERNAL_H */
index 7325a532c8ae15078ee9cc82907a8906dadfd1ed..1a541ce469efc22381f198261a484b9df7ee4f26 100644 (file)
@@ -55,6 +55,7 @@ void lttng_action_init(
                action_equal_cb equal,
                action_destroy_cb destroy)
 {
                action_equal_cb equal,
                action_destroy_cb destroy)
 {
+       urcu_ref_init(&action->ref);
        action->type = type;
        action->validate = validate;
        action->serialize = serialize;
        action->type = type;
        action->validate = validate;
        action->serialize = serialize;
@@ -62,14 +63,35 @@ void lttng_action_init(
        action->destroy = destroy;
 }
 
        action->destroy = destroy;
 }
 
-void lttng_action_destroy(struct lttng_action *action)
+static
+void action_destroy_ref(struct urcu_ref *ref)
+{
+       struct lttng_action *action =
+                       container_of(ref, struct lttng_action, ref);
+
+       action->destroy(action);
+}
+
+LTTNG_HIDDEN
+void lttng_action_get(struct lttng_action *action)
+{
+       urcu_ref_get(&action->ref);
+}
+
+LTTNG_HIDDEN
+void lttng_action_put(struct lttng_action *action)
 {
        if (!action) {
                return;
        }
 
        assert(action->destroy);
 {
        if (!action) {
                return;
        }
 
        assert(action->destroy);
-       action->destroy(action);
+       urcu_ref_put(&action->ref, action_destroy_ref);
+}
+
+void lttng_action_destroy(struct lttng_action *action)
+{
+       lttng_action_put(action);
 }
 
 LTTNG_HIDDEN
 }
 
 LTTNG_HIDDEN
This page took 0.027554 seconds and 4 git commands to generate.