common: compile libcommon as C++
[lttng-tools.git] / src / common / actions / rotate-session.cpp
CommitLineData
bfb2ec6a
SM
1/*
2 * Copyright (C) 2019 Simon Marchi <simon.marchi@efficios.com>
3 *
4 * SPDX-License-Identifier: LGPL-2.1-only
5 *
6 */
7
bfb2ec6a
SM
8#include <common/error.h>
9#include <common/macros.h>
6a751b95 10#include <common/mi-lttng.h>
bfb2ec6a 11#include <lttng/action/action-internal.h>
7f4d5b07
JR
12#include <lttng/action/rate-policy-internal.h>
13#include <lttng/action/rate-policy.h>
bfb2ec6a
SM
14#include <lttng/action/rotate-session-internal.h>
15#include <lttng/action/rotate-session.h>
16
17#define IS_ROTATE_SESSION_ACTION(action) \
17182cfd 18 (lttng_action_get_type(action) == LTTNG_ACTION_TYPE_ROTATE_SESSION)
bfb2ec6a
SM
19
20struct lttng_action_rotate_session {
21 struct lttng_action parent;
22
23 /* Owned by this. */
24 char *session_name;
7f4d5b07 25 struct lttng_rate_policy *policy;
bfb2ec6a
SM
26};
27
28struct lttng_action_rotate_session_comm {
29 /* Includes the trailing \0. */
30 uint32_t session_name_len;
31
32 /*
33 * Variable data:
34 *
35 * - session name (null terminated)
c2c58434 36 * - policy
bfb2ec6a
SM
37 */
38 char data[];
39} LTTNG_PACKED;
40
7f4d5b07
JR
41static const struct lttng_rate_policy *
42lttng_action_rotate_session_internal_get_rate_policy(
2d57482c
JR
43 const struct lttng_action *action);
44
bfb2ec6a
SM
45static struct lttng_action_rotate_session *action_rotate_session_from_action(
46 struct lttng_action *action)
47{
a0377dfe 48 LTTNG_ASSERT(action);
bfb2ec6a
SM
49
50 return container_of(action, struct lttng_action_rotate_session, parent);
51}
52
53static const struct lttng_action_rotate_session *
54action_rotate_session_from_action_const(const struct lttng_action *action)
55{
a0377dfe 56 LTTNG_ASSERT(action);
bfb2ec6a
SM
57
58 return container_of(action, struct lttng_action_rotate_session, parent);
59}
60
61static bool lttng_action_rotate_session_validate(struct lttng_action *action)
62{
63 bool valid;
64 struct lttng_action_rotate_session *action_rotate_session;
65
66 if (!action) {
67 valid = false;
68 goto end;
69 }
70
71 action_rotate_session = action_rotate_session_from_action(action);
72
73 /* A non-empty session name is mandatory. */
74 if (!action_rotate_session->session_name ||
75 strlen(action_rotate_session->session_name) == 0) {
76 valid = false;
77 goto end;
78 }
79
80 valid = true;
81end:
82 return valid;
83}
84
85static bool lttng_action_rotate_session_is_equal(
86 const struct lttng_action *_a, const struct lttng_action *_b)
87{
88 bool is_equal = false;
89 const struct lttng_action_rotate_session *a, *b;
90
91 a = action_rotate_session_from_action_const(_a);
92 b = action_rotate_session_from_action_const(_b);
93
94 /* Action is not valid if this is not true. */
a0377dfe
FD
95 LTTNG_ASSERT(a->session_name);
96 LTTNG_ASSERT(b->session_name);
bfb2ec6a
SM
97 if (strcmp(a->session_name, b->session_name)) {
98 goto end;
99 }
100
7f4d5b07 101 is_equal = lttng_rate_policy_is_equal(a->policy, b->policy);
bfb2ec6a
SM
102end:
103 return is_equal;
104}
105static int lttng_action_rotate_session_serialize(
c0a66c84 106 struct lttng_action *action, struct lttng_payload *payload)
bfb2ec6a
SM
107{
108 struct lttng_action_rotate_session *action_rotate_session;
109 struct lttng_action_rotate_session_comm comm;
110 size_t session_name_len;
111 int ret;
112
a0377dfe
FD
113 LTTNG_ASSERT(action);
114 LTTNG_ASSERT(payload);
bfb2ec6a
SM
115
116 action_rotate_session = action_rotate_session_from_action(action);
117
a0377dfe 118 LTTNG_ASSERT(action_rotate_session->session_name);
bfb2ec6a
SM
119
120 DBG("Serializing rotate session action: session-name: %s",
121 action_rotate_session->session_name);
122
123 session_name_len = strlen(action_rotate_session->session_name) + 1;
124 comm.session_name_len = session_name_len;
125
c0a66c84
JG
126 ret = lttng_dynamic_buffer_append(
127 &payload->buffer, &comm, sizeof(comm));
bfb2ec6a
SM
128 if (ret) {
129 ret = -1;
130 goto end;
131 }
132
c0a66c84 133 ret = lttng_dynamic_buffer_append(&payload->buffer,
bfb2ec6a
SM
134 action_rotate_session->session_name, session_name_len);
135 if (ret) {
136 ret = -1;
137 goto end;
138 }
139
7f4d5b07 140 ret = lttng_rate_policy_serialize(
c2c58434
JR
141 action_rotate_session->policy, payload);
142 if (ret) {
143 ret = -1;
144 goto end;
145 }
bfb2ec6a
SM
146end:
147 return ret;
148}
149
150static void lttng_action_rotate_session_destroy(struct lttng_action *action)
151{
152 struct lttng_action_rotate_session *action_rotate_session;
153
154 if (!action) {
155 goto end;
156 }
157
158 action_rotate_session = action_rotate_session_from_action(action);
159
7f4d5b07 160 lttng_rate_policy_destroy(action_rotate_session->policy);
bfb2ec6a
SM
161 free(action_rotate_session->session_name);
162 free(action_rotate_session);
163
164end:
165 return;
166}
167
c0a66c84
JG
168ssize_t lttng_action_rotate_session_create_from_payload(
169 struct lttng_payload_view *view,
bfb2ec6a
SM
170 struct lttng_action **p_action)
171{
c2c58434 172 ssize_t consumed_len, ret;
bfb2ec6a
SM
173 const struct lttng_action_rotate_session_comm *comm;
174 const char *session_name;
175 struct lttng_action *action;
176 enum lttng_action_status status;
7f4d5b07 177 struct lttng_rate_policy *policy = NULL;
bfb2ec6a
SM
178
179 action = lttng_action_rotate_session_create();
180 if (!action) {
181 consumed_len = -1;
182 goto end;
183 }
184
c0a66c84 185 comm = (typeof(comm)) view->buffer.data;
bfb2ec6a
SM
186 session_name = (const char *) &comm->data;
187
188 if (!lttng_buffer_view_contains_string(
c0a66c84 189 &view->buffer, session_name, comm->session_name_len)) {
bfb2ec6a
SM
190 consumed_len = -1;
191 goto end;
192 }
c2c58434
JR
193 consumed_len = sizeof(*comm) + comm->session_name_len;
194
7f4d5b07 195 /* Rate policy. */
c2c58434
JR
196 {
197 struct lttng_payload_view policy_view =
198 lttng_payload_view_from_view(
199 view, consumed_len, -1);
7f4d5b07 200 ret = lttng_rate_policy_create_from_payload(
c2c58434
JR
201 &policy_view, &policy);
202 if (ret < 0) {
203 consumed_len = -1;
204 goto end;
205 }
206 consumed_len += ret;
207 }
bfb2ec6a
SM
208
209 status = lttng_action_rotate_session_set_session_name(
210 action, session_name);
211 if (status != LTTNG_ACTION_STATUS_OK) {
212 consumed_len = -1;
213 goto end;
214 }
215
a0377dfe 216 LTTNG_ASSERT(policy);
7f4d5b07 217 status = lttng_action_rotate_session_set_rate_policy(action, policy);
c2c58434
JR
218 if (status != LTTNG_ACTION_STATUS_OK) {
219 consumed_len = -1;
220 goto end;
221 }
222
bfb2ec6a
SM
223 *p_action = action;
224 action = NULL;
225
226end:
7f4d5b07 227 lttng_rate_policy_destroy(policy);
bfb2ec6a
SM
228 lttng_action_rotate_session_destroy(action);
229
230 return consumed_len;
231}
232
6a751b95
JR
233static enum lttng_error_code lttng_action_rotate_session_mi_serialize(
234 const struct lttng_action *action, struct mi_writer *writer)
235{
236 int ret;
237 enum lttng_error_code ret_code;
238 enum lttng_action_status status;
239 const char *session_name = NULL;
240 const struct lttng_rate_policy *policy = NULL;
241
a0377dfe
FD
242 LTTNG_ASSERT(action);
243 LTTNG_ASSERT(IS_ROTATE_SESSION_ACTION(action));
6a751b95
JR
244
245 status = lttng_action_rotate_session_get_session_name(
246 action, &session_name);
a0377dfe
FD
247 LTTNG_ASSERT(status == LTTNG_ACTION_STATUS_OK);
248 LTTNG_ASSERT(session_name != NULL);
6a751b95
JR
249
250 status = lttng_action_notify_get_rate_policy(action, &policy);
a0377dfe
FD
251 LTTNG_ASSERT(status == LTTNG_ACTION_STATUS_OK);
252 LTTNG_ASSERT(policy != NULL);
6a751b95
JR
253
254 /* Open action rotate session element. */
255 ret = mi_lttng_writer_open_element(
256 writer, mi_lttng_element_action_rotate_session);
257 if (ret) {
258 goto mi_error;
259 }
260
261 /* Session name. */
262 ret = mi_lttng_writer_write_element_string(
263 writer, mi_lttng_element_session_name, session_name);
264 if (ret) {
265 goto mi_error;
266 }
267
268 /* Rate policy. */
269 ret_code = lttng_rate_policy_mi_serialize(policy, writer);
270 if (ret_code != LTTNG_OK) {
271 goto end;
272 }
273
274 /* Close action rotate session element. */
275 ret = mi_lttng_writer_close_element(writer);
276 if (ret) {
277 goto mi_error;
278 }
279
280 ret_code = LTTNG_OK;
281 goto end;
282
283mi_error:
284 ret_code = LTTNG_ERR_MI_IO_FAIL;
285end:
286 return ret_code;
287}
288
bfb2ec6a
SM
289struct lttng_action *lttng_action_rotate_session_create(void)
290{
c2c58434 291 struct lttng_action *action = NULL;
7f4d5b07 292 struct lttng_rate_policy *policy = NULL;
c2c58434
JR
293 enum lttng_action_status status;
294
7f4d5b07
JR
295 /* Create a every N = 1 rate policy. */
296 policy = lttng_rate_policy_every_n_create(1);
c2c58434
JR
297 if (!policy) {
298 goto end;
299 }
bfb2ec6a 300
a6bc4ca9 301 action = (lttng_action *) zmalloc(sizeof(struct lttng_action_rotate_session));
bfb2ec6a
SM
302 if (!action) {
303 goto end;
304 }
305
306 lttng_action_init(action, LTTNG_ACTION_TYPE_ROTATE_SESSION,
307 lttng_action_rotate_session_validate,
308 lttng_action_rotate_session_serialize,
309 lttng_action_rotate_session_is_equal,
2d57482c 310 lttng_action_rotate_session_destroy,
588c4b0d 311 lttng_action_rotate_session_internal_get_rate_policy,
6a751b95
JR
312 lttng_action_generic_add_error_query_results,
313 lttng_action_rotate_session_mi_serialize);
bfb2ec6a 314
7f4d5b07 315 status = lttng_action_rotate_session_set_rate_policy(action, policy);
c2c58434
JR
316 if (status != LTTNG_ACTION_STATUS_OK) {
317 free(action);
318 action = NULL;
319 goto end;
320 }
321
bfb2ec6a 322end:
7f4d5b07 323 lttng_rate_policy_destroy(policy);
bfb2ec6a
SM
324 return action;
325}
326
327enum lttng_action_status lttng_action_rotate_session_set_session_name(
328 struct lttng_action *action, const char *session_name)
329{
330 struct lttng_action_rotate_session *action_rotate_session;
331 enum lttng_action_status status;
332
333 if (!action || !IS_ROTATE_SESSION_ACTION(action) || !session_name ||
334 strlen(session_name) == 0) {
335 status = LTTNG_ACTION_STATUS_INVALID;
336 goto end;
337 }
338
339 action_rotate_session = action_rotate_session_from_action(action);
340
341 free(action_rotate_session->session_name);
342
343 action_rotate_session->session_name = strdup(session_name);
344 if (!action_rotate_session->session_name) {
345 status = LTTNG_ACTION_STATUS_ERROR;
346 goto end;
347 }
348
349 status = LTTNG_ACTION_STATUS_OK;
350end:
351 return status;
352}
353
354enum lttng_action_status lttng_action_rotate_session_get_session_name(
355 const struct lttng_action *action, const char **session_name)
356{
357 const struct lttng_action_rotate_session *action_rotate_session;
358 enum lttng_action_status status;
359
360 if (!action || !IS_ROTATE_SESSION_ACTION(action) || !session_name) {
361 status = LTTNG_ACTION_STATUS_INVALID;
362 goto end;
363 }
364
365 action_rotate_session = action_rotate_session_from_action_const(action);
366
367 *session_name = action_rotate_session->session_name;
368
369 status = LTTNG_ACTION_STATUS_OK;
370end:
371 return status;
372}
c2c58434 373
7f4d5b07 374enum lttng_action_status lttng_action_rotate_session_set_rate_policy(
c2c58434 375 struct lttng_action *action,
7f4d5b07 376 const struct lttng_rate_policy *policy)
c2c58434
JR
377{
378 enum lttng_action_status status;
379 struct lttng_action_rotate_session *rotate_session_action;
7f4d5b07 380 struct lttng_rate_policy *copy = NULL;
c2c58434
JR
381
382 if (!action || !policy || !IS_ROTATE_SESSION_ACTION(action)) {
383 status = LTTNG_ACTION_STATUS_INVALID;
384 goto end;
385 }
386
7f4d5b07 387 copy = lttng_rate_policy_copy(policy);
c2c58434
JR
388 if (!copy) {
389 status = LTTNG_ACTION_STATUS_ERROR;
390 goto end;
391 }
392
393 rotate_session_action = action_rotate_session_from_action(action);
394
7f4d5b07
JR
395 /* Free the previous rate policy .*/
396 lttng_rate_policy_destroy(rotate_session_action->policy);
c2c58434
JR
397
398 /* Assign the policy. */
399 rotate_session_action->policy = copy;
400 status = LTTNG_ACTION_STATUS_OK;
401 copy = NULL;
402
403end:
7f4d5b07 404 lttng_rate_policy_destroy(copy);
c2c58434
JR
405 return status;
406}
407
7f4d5b07 408enum lttng_action_status lttng_action_rotate_session_get_rate_policy(
c2c58434 409 const struct lttng_action *action,
7f4d5b07 410 const struct lttng_rate_policy **policy)
c2c58434
JR
411{
412 enum lttng_action_status status;
413 const struct lttng_action_rotate_session *rotate_session_action;
414
415 if (!action || !policy || !IS_ROTATE_SESSION_ACTION(action)) {
416 status = LTTNG_ACTION_STATUS_INVALID;
417 goto end;
418 }
419
420 rotate_session_action = action_rotate_session_from_action_const(action);
421
422 *policy = rotate_session_action->policy;
423 status = LTTNG_ACTION_STATUS_OK;
424end:
425 return status;
426}
2d57482c 427
7f4d5b07
JR
428static const struct lttng_rate_policy *
429lttng_action_rotate_session_internal_get_rate_policy(
2d57482c
JR
430 const struct lttng_action *action)
431{
432 const struct lttng_action_rotate_session *_action;
433 _action = action_rotate_session_from_action_const(action);
434
435 return _action->policy;
436}
This page took 0.048584 seconds and 4 git commands to generate.