Clean-up: action-executor: typo and missing tab
[lttng-tools.git] / src / common / trigger.c
CommitLineData
a58c490f 1/*
ab5be9fa 2 * Copyright (C) 2017 Jérémie Galarneau <jeremie.galarneau@efficios.com>
a58c490f 3 *
ab5be9fa 4 * SPDX-License-Identifier: LGPL-2.1-only
a58c490f 5 *
a58c490f
JG
6 */
7
8#include <lttng/trigger/trigger-internal.h>
9#include <lttng/condition/condition-internal.h>
10#include <lttng/action/action-internal.h>
3da864a9 11#include <common/credentials.h>
9e620ea7
JG
12#include <common/payload.h>
13#include <common/payload-view.h>
a58c490f 14#include <common/error.h>
3da864a9 15#include <common/optional.h>
a58c490f
JG
16#include <assert.h>
17
18LTTNG_HIDDEN
19bool lttng_trigger_validate(struct lttng_trigger *trigger)
20{
21 bool valid;
22
23 if (!trigger) {
24 valid = false;
25 goto end;
26 }
27
28 valid = lttng_condition_validate(trigger->condition) &&
29 lttng_action_validate(trigger->action);
30end:
31 return valid;
32}
33
34struct lttng_trigger *lttng_trigger_create(
35 struct lttng_condition *condition,
36 struct lttng_action *action)
37{
38 struct lttng_trigger *trigger = NULL;
39
40 if (!condition || !action) {
41 goto end;
42 }
43
44 trigger = zmalloc(sizeof(struct lttng_trigger));
45 if (!trigger) {
46 goto end;
47 }
48
f01d28b4
JR
49 urcu_ref_init(&trigger->ref);
50
7ca172c1 51 lttng_condition_get(condition);
a58c490f 52 trigger->condition = condition;
7ca172c1
JR
53
54 lttng_action_get(action);
a58c490f 55 trigger->action = action;
3da864a9 56
a58c490f
JG
57end:
58 return trigger;
59}
60
7ca172c1
JR
61/*
62 * Note: the lack of reference counting 'get' on the condition object is normal.
63 * This API was exposed as such in 2.11. The client is not expected to call
64 * lttng_condition_destroy on the returned object.
65 */
a58c490f
JG
66struct lttng_condition *lttng_trigger_get_condition(
67 struct lttng_trigger *trigger)
68{
69 return trigger ? trigger->condition : NULL;
70}
71
9b63a4aa
JG
72LTTNG_HIDDEN
73const struct lttng_condition *lttng_trigger_get_const_condition(
74 const struct lttng_trigger *trigger)
75{
76 return trigger->condition;
77}
78
7ca172c1
JR
79
80/*
81 * Note: the lack of reference counting 'get' on the action object is normal.
82 * This API was exposed as such in 2.11. The client is not expected to call
83 * lttng_action_destroy on the returned object.
84 */
e2ba1c78 85struct lttng_action *lttng_trigger_get_action(
a58c490f
JG
86 struct lttng_trigger *trigger)
87{
88 return trigger ? trigger->action : NULL;
89}
90
9b63a4aa
JG
91LTTNG_HIDDEN
92const struct lttng_action *lttng_trigger_get_const_action(
93 const struct lttng_trigger *trigger)
94{
95 return trigger->action;
96}
97
f01d28b4 98static void trigger_destroy_ref(struct urcu_ref *ref)
a58c490f 99{
f01d28b4
JR
100 struct lttng_trigger *trigger =
101 container_of(ref, struct lttng_trigger, ref);
7ca172c1
JR
102 struct lttng_action *action = lttng_trigger_get_action(trigger);
103 struct lttng_condition *condition =
104 lttng_trigger_get_condition(trigger);
105
7ca172c1
JR
106 assert(action);
107 assert(condition);
108
109 /* Release ownership. */
110 lttng_action_put(action);
111 lttng_condition_put(condition);
112
a58c490f
JG
113 free(trigger);
114}
115
f01d28b4
JR
116void lttng_trigger_destroy(struct lttng_trigger *trigger)
117{
118 lttng_trigger_put(trigger);
119}
120
a58c490f 121LTTNG_HIDDEN
c0a66c84
JG
122ssize_t lttng_trigger_create_from_payload(
123 struct lttng_payload_view *src_view,
a58c490f
JG
124 struct lttng_trigger **trigger)
125{
126 ssize_t ret, offset = 0, condition_size, action_size;
127 struct lttng_condition *condition = NULL;
128 struct lttng_action *action = NULL;
129 const struct lttng_trigger_comm *trigger_comm;
a58c490f
JG
130
131 if (!src_view || !trigger) {
132 ret = -1;
133 goto end;
134 }
135
136 /* lttng_trigger_comm header */
c0a66c84 137 trigger_comm = (typeof(trigger_comm)) src_view->buffer.data;
a58c490f 138 offset += sizeof(*trigger_comm);
c0a66c84
JG
139 {
140 /* struct lttng_condition */
141 struct lttng_payload_view condition_view =
142 lttng_payload_view_from_view(
143 src_view, offset, -1);
144
145 condition_size = lttng_condition_create_from_payload(&condition_view,
146 &condition);
147 }
a58c490f 148
a58c490f
JG
149 if (condition_size < 0) {
150 ret = condition_size;
151 goto end;
152 }
c0a66c84 153
a58c490f 154 offset += condition_size;
c0a66c84
JG
155 {
156 /* struct lttng_action */
157 struct lttng_payload_view action_view =
158 lttng_payload_view_from_view(
159 src_view, offset, -1);
160
161 action_size = lttng_action_create_from_payload(&action_view, &action);
162 }
a58c490f 163
a58c490f
JG
164 if (action_size < 0) {
165 ret = action_size;
166 goto end;
167 }
168 offset += action_size;
169
170 /* Unexpected size of inner-elements; the buffer is corrupted. */
171 if ((ssize_t) trigger_comm->length != condition_size + action_size) {
172 ret = -1;
173 goto error;
174 }
175
176 *trigger = lttng_trigger_create(condition, action);
177 if (!*trigger) {
178 ret = -1;
179 goto error;
180 }
c0a66c84 181
7ca172c1
JR
182 /*
183 * The trigger object owns references to the action and condition
184 * objects.
185 */
186 lttng_condition_put(condition);
187 condition = NULL;
188
189 lttng_action_put(action);
190 action = NULL;
191
a58c490f 192 ret = offset;
7ca172c1 193
a58c490f
JG
194error:
195 lttng_condition_destroy(condition);
196 lttng_action_destroy(action);
7ca172c1 197end:
a58c490f
JG
198 return ret;
199}
200
201/*
a58c490f
JG
202 * Both elements are stored contiguously, see their "*_comm" structure
203 * for the detailed format.
204 */
205LTTNG_HIDDEN
3647288f 206int lttng_trigger_serialize(struct lttng_trigger *trigger,
c0a66c84 207 struct lttng_payload *payload)
a58c490f 208{
3647288f
JG
209 int ret;
210 size_t header_offset, size_before_payload;
c0a66c84 211 struct lttng_trigger_comm trigger_comm = {};
3647288f 212 struct lttng_trigger_comm *header;
a58c490f 213
c0a66c84
JG
214 header_offset = payload->buffer.size;
215 ret = lttng_dynamic_buffer_append(&payload->buffer, &trigger_comm,
3647288f
JG
216 sizeof(trigger_comm));
217 if (ret) {
a58c490f
JG
218 goto end;
219 }
220
c0a66c84
JG
221 size_before_payload = payload->buffer.size;
222 ret = lttng_condition_serialize(trigger->condition, payload);
3647288f 223 if (ret) {
a58c490f
JG
224 goto end;
225 }
a58c490f 226
c0a66c84 227 ret = lttng_action_serialize(trigger->action, payload);
3647288f 228 if (ret) {
a58c490f
JG
229 goto end;
230 }
a58c490f 231
3647288f 232 /* Update payload size. */
c0a66c84
JG
233 header = (typeof(header)) (payload->buffer.data + header_offset);
234 header->length = payload->buffer.size - size_before_payload;
a58c490f
JG
235end:
236 return ret;
237}
3da864a9 238
f01d28b4
JR
239LTTNG_HIDDEN
240void lttng_trigger_get(struct lttng_trigger *trigger)
241{
242 urcu_ref_get(&trigger->ref);
243}
244
245LTTNG_HIDDEN
246void lttng_trigger_put(struct lttng_trigger *trigger)
247{
248 if (!trigger) {
249 return;
250 }
251
252 urcu_ref_put(&trigger->ref , trigger_destroy_ref);
253}
254
3da864a9
JR
255LTTNG_HIDDEN
256const struct lttng_credentials *lttng_trigger_get_credentials(
257 const struct lttng_trigger *trigger)
258{
259 return LTTNG_OPTIONAL_GET_PTR(trigger->creds);
260}
261
262LTTNG_HIDDEN
263void lttng_trigger_set_credentials(
264 struct lttng_trigger *trigger,
265 const struct lttng_credentials *creds)
266{
267 assert(creds);
268 LTTNG_OPTIONAL_SET(&trigger->creds, *creds);
269}
This page took 0.07369 seconds and 4 git commands to generate.