Add the GMT offset in the rotated chunk path
[lttng-tools.git] / src / common / session-consumed-size.c
CommitLineData
e8360425
JD
1/*
2 * Copyright (C) 2017 - Jérémie Galarneau <jeremie.galarneau@efficios.com>
3 *
4 * This library is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU Lesser General Public License, version 2.1 only,
6 * as published by the Free Software Foundation.
7 *
8 * This library is distributed in the hope that it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
11 * for more details.
12 *
13 * You should have received a copy of the GNU Lesser General Public License
14 * along with this library; if not, write to the Free Software Foundation,
15 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
16 */
17
18#include <lttng/condition/condition-internal.h>
19#include <lttng/condition/session-consumed-size-internal.h>
20#include <common/macros.h>
21#include <common/error.h>
22#include <assert.h>
23#include <math.h>
24#include <float.h>
25#include <time.h>
26
27#define IS_CONSUMED_SIZE_CONDITION(condition) ( \
28 lttng_condition_get_type(condition) == LTTNG_CONDITION_TYPE_SESSION_CONSUMED_SIZE \
29 )
30
31#define IS_CONSUMED_SIZE_EVALUATION(evaluation) ( \
32 lttng_evaluation_get_type(evaluation) == LTTNG_CONDITION_TYPE_SESSION_CONSUMED_SIZE \
33 )
34
35static
36void lttng_condition_session_consumed_size_destroy(struct lttng_condition *condition)
37{
38 struct lttng_condition_session_consumed_size *consumed_size;
39
40 consumed_size = container_of(condition,
41 struct lttng_condition_session_consumed_size, parent);
42
43 free(consumed_size->session_name);
44 free(consumed_size);
45}
46
47static
48bool lttng_condition_session_consumed_size_validate(
49 const struct lttng_condition *condition)
50{
51 bool valid = false;
52 struct lttng_condition_session_consumed_size *consumed;
53
54 if (!condition) {
55 goto end;
56 }
57
58 consumed = container_of(condition, struct lttng_condition_session_consumed_size,
59 parent);
60 if (!consumed->session_name) {
61 ERR("Invalid buffer condition: a target session name must be set.");
62 goto end;
63 }
64 if (!consumed->consumed_threshold_bytes.set) {
65 ERR("Invalid session condition: a threshold must be set.");
66 goto end;
67 }
68
69 valid = true;
70end:
71 return valid;
72}
73
74static
75ssize_t lttng_condition_session_consumed_size_serialize(
76 const struct lttng_condition *condition, char *buf)
77{
78 struct lttng_condition_session_consumed_size *consumed;
79 ssize_t ret, size;
80 size_t session_name_len;
81
82 if (!condition || !IS_CONSUMED_SIZE_CONDITION(condition)) {
83 ret = -1;
84 goto end;
85 }
86
87 DBG("Serializing session consumed condition");
88 consumed = container_of(condition, struct lttng_condition_session_consumed_size,
89 parent);
90 size = sizeof(struct lttng_condition_session_consumed_size_comm);
91 session_name_len = strlen(consumed->session_name) + 1;
92 if (session_name_len > LTTNG_NAME_MAX) {
93 ret = -1;
94 goto end;
95 }
96 size += session_name_len;
97 if (buf) {
98 struct lttng_condition_session_consumed_size_comm consumed_comm = {
99 .consumed_threshold_bytes = consumed->consumed_threshold_bytes.value,
100 .session_name_len = session_name_len,
101 };
102
103 memcpy(buf, &consumed_comm, sizeof(consumed_comm));
104 buf += sizeof(consumed_comm);
105 memcpy(buf, consumed->session_name, session_name_len);
106 buf += session_name_len;
107 }
108 ret = size;
109end:
110 return ret;
111}
112
113static
114bool lttng_condition_session_consumed_size_is_equal(const struct lttng_condition *_a,
115 const struct lttng_condition *_b)
116{
117 bool is_equal = false;
118 struct lttng_condition_session_consumed_size *a, *b;
119
120 a = container_of(_a, struct lttng_condition_session_consumed_size, parent);
121 b = container_of(_b, struct lttng_condition_session_consumed_size, parent);
122
123 if (a->consumed_threshold_bytes.set && b->consumed_threshold_bytes.set) {
124 uint64_t a_value, b_value;
125
126 a_value = a->consumed_threshold_bytes.value;
127 b_value = b->consumed_threshold_bytes.value;
128 if (a_value != b_value) {
129 goto end;
130 }
131 }
132
133 if ((a->session_name && !b->session_name) ||
134 (!a->session_name && b->session_name)) {
135 goto end;
136 }
137
138 is_equal = true;
139end:
140 return is_equal;
141}
142
143struct lttng_condition *lttng_condition_session_consumed_size_create(void)
144{
145 struct lttng_condition_session_consumed_size *condition;
146
147 condition = zmalloc(sizeof(struct lttng_condition_session_consumed_size));
148 if (!condition) {
149 return NULL;
150 }
151
152 lttng_condition_init(&condition->parent, LTTNG_CONDITION_TYPE_SESSION_CONSUMED_SIZE);
153 condition->parent.validate = lttng_condition_session_consumed_size_validate;
154 condition->parent.serialize = lttng_condition_session_consumed_size_serialize;
155 condition->parent.equal = lttng_condition_session_consumed_size_is_equal;
156 condition->parent.destroy = lttng_condition_session_consumed_size_destroy;
157 return &condition->parent;
158}
159
160static
161ssize_t init_condition_from_buffer(struct lttng_condition *condition,
162 const struct lttng_buffer_view *src_view)
163{
164 ssize_t ret, condition_size;
165 enum lttng_condition_status status;
166 const struct lttng_condition_session_consumed_size_comm *condition_comm;
167 const char *session_name;
168 struct lttng_buffer_view names_view;
169
170 if (src_view->size < sizeof(*condition_comm)) {
171 ERR("Failed to initialize from malformed condition buffer: buffer too short to contain header");
172 ret = -1;
173 goto end;
174 }
175
176 condition_comm = (const struct lttng_condition_session_consumed_size_comm *) src_view->data;
177 names_view = lttng_buffer_view_from_view(src_view,
178 sizeof(*condition_comm), -1);
179
180 if (condition_comm->session_name_len > LTTNG_NAME_MAX) {
181 ERR("Failed to initialize from malformed condition buffer: name exceeds LTTNG_MAX_NAME");
182 ret = -1;
183 goto end;
184 }
185
186 if (names_view.size < condition_comm->session_name_len) {
187 ERR("Failed to initialize from malformed condition buffer: buffer too short to contain element names");
188 ret = -1;
189 goto end;
190 }
191
192 status = lttng_condition_session_consumed_size_set_threshold(condition,
193 condition_comm->consumed_threshold_bytes);
194 if (status != LTTNG_CONDITION_STATUS_OK) {
195 ERR("Failed to initialize session consumed condition threshold");
196 ret = -1;
197 goto end;
198 }
199
200 session_name = names_view.data;
201 if (*(session_name + condition_comm->session_name_len - 1) != '\0') {
202 ERR("Malformed session name encountered in condition buffer");
203 ret = -1;
204 goto end;
205 }
206
207 status = lttng_condition_session_consumed_size_set_session_name(condition,
208 session_name);
209 if (status != LTTNG_CONDITION_STATUS_OK) {
210 ERR("Failed to set buffer consumed session name");
211 ret = -1;
212 goto end;
213 }
214
215 if (!lttng_condition_validate(condition)) {
216 ret = -1;
217 goto end;
218 }
219
220 condition_size = sizeof(*condition_comm) +
221 (ssize_t) condition_comm->session_name_len;
222 ret = condition_size;
223end:
224 return ret;
225}
226
227LTTNG_HIDDEN
228ssize_t lttng_condition_session_consumed_size_create_from_buffer(
229 const struct lttng_buffer_view *view,
230 struct lttng_condition **_condition)
231{
232 ssize_t ret;
233 struct lttng_condition *condition =
234 lttng_condition_session_consumed_size_create();
235
236 if (!_condition || !condition) {
237 ret = -1;
238 goto error;
239 }
240
241 ret = init_condition_from_buffer(condition, view);
242 if (ret < 0) {
243 goto error;
244 }
245
246 *_condition = condition;
247 return ret;
248error:
249 lttng_condition_destroy(condition);
250 return ret;
251}
252
253static
254struct lttng_evaluation *create_evaluation_from_buffer(
255 enum lttng_condition_type type,
256 const struct lttng_buffer_view *view)
257{
258 const struct lttng_evaluation_session_consumed_size_comm *comm =
259 (const struct lttng_evaluation_session_consumed_size_comm *) view->data;
260 struct lttng_evaluation *evaluation = NULL;
261
262 if (view->size < sizeof(*comm)) {
263 goto end;
264 }
265
266 evaluation = lttng_evaluation_session_consumed_size_create(type,
267 comm->session_consumed);
268end:
269 return evaluation;
270}
271
272LTTNG_HIDDEN
273ssize_t lttng_evaluation_session_consumed_size_create_from_buffer(
274 const struct lttng_buffer_view *view,
275 struct lttng_evaluation **_evaluation)
276{
277 ssize_t ret;
278 struct lttng_evaluation *evaluation = NULL;
279
280 if (!_evaluation) {
281 ret = -1;
282 goto error;
283 }
284
285 evaluation = create_evaluation_from_buffer(
286 LTTNG_CONDITION_TYPE_SESSION_CONSUMED_SIZE, view);
287 if (!evaluation) {
288 ret = -1;
289 goto error;
290 }
291
292 *_evaluation = evaluation;
293 ret = sizeof(struct lttng_evaluation_session_consumed_size_comm);
294 return ret;
295error:
296 lttng_evaluation_destroy(evaluation);
297 return ret;
298}
299
300enum lttng_condition_status
301lttng_condition_session_consumed_size_get_threshold(
302 const struct lttng_condition *condition,
303 uint64_t *consumed_threshold_bytes)
304{
305 struct lttng_condition_session_consumed_size *consumed;
306 enum lttng_condition_status status = LTTNG_CONDITION_STATUS_OK;
307
308 if (!condition || !IS_CONSUMED_SIZE_CONDITION(condition) || !consumed_threshold_bytes) {
309 status = LTTNG_CONDITION_STATUS_INVALID;
310 goto end;
311 }
312
313 consumed = container_of(condition, struct lttng_condition_session_consumed_size,
314 parent);
315 if (!consumed->consumed_threshold_bytes.set) {
316 status = LTTNG_CONDITION_STATUS_UNSET;
317 goto end;
318 }
319 *consumed_threshold_bytes = consumed->consumed_threshold_bytes.value;
320end:
321 return status;
322}
323
324enum lttng_condition_status
325lttng_condition_session_consumed_size_set_threshold(
326 struct lttng_condition *condition, uint64_t consumed_threshold_bytes)
327{
328 struct lttng_condition_session_consumed_size *consumed;
329 enum lttng_condition_status status = LTTNG_CONDITION_STATUS_OK;
330
331 if (!condition || !IS_CONSUMED_SIZE_CONDITION(condition)) {
332 status = LTTNG_CONDITION_STATUS_INVALID;
333 goto end;
334 }
335
336 consumed = container_of(condition, struct lttng_condition_session_consumed_size,
337 parent);
338 consumed->consumed_threshold_bytes.set = true;
339 consumed->consumed_threshold_bytes.value = consumed_threshold_bytes;
340end:
341 return status;
342}
343
344enum lttng_condition_status
345lttng_condition_session_consumed_size_get_session_name(
346 const struct lttng_condition *condition,
347 const char **session_name)
348{
349 struct lttng_condition_session_consumed_size *consumed;
350 enum lttng_condition_status status = LTTNG_CONDITION_STATUS_OK;
351
352 if (!condition || !IS_CONSUMED_SIZE_CONDITION(condition) || !session_name) {
353 status = LTTNG_CONDITION_STATUS_INVALID;
354 goto end;
355 }
356
357 consumed = container_of(condition, struct lttng_condition_session_consumed_size,
358 parent);
359 if (!consumed->session_name) {
360 status = LTTNG_CONDITION_STATUS_UNSET;
361 goto end;
362 }
363 *session_name = consumed->session_name;
364end:
365 return status;
366}
367
368enum lttng_condition_status
369lttng_condition_session_consumed_size_set_session_name(
370 struct lttng_condition *condition, const char *session_name)
371{
372 char *session_name_copy;
373 struct lttng_condition_session_consumed_size *consumed;
374 enum lttng_condition_status status = LTTNG_CONDITION_STATUS_OK;
375
376 if (!condition || !IS_CONSUMED_SIZE_CONDITION(condition) ||
377 !session_name || strlen(session_name) == 0) {
378 status = LTTNG_CONDITION_STATUS_INVALID;
379 goto end;
380 }
381
382 consumed = container_of(condition, struct lttng_condition_session_consumed_size,
383 parent);
384 session_name_copy = strdup(session_name);
385 if (!session_name_copy) {
386 status = LTTNG_CONDITION_STATUS_ERROR;
387 goto end;
388 }
389
390 if (consumed->session_name) {
391 free(consumed->session_name);
392 }
393 consumed->session_name = session_name_copy;
394end:
395 return status;
396}
397
398static
399ssize_t lttng_evaluation_session_consumed_size_serialize(
400 struct lttng_evaluation *evaluation, char *buf)
401{
402 ssize_t ret;
403 struct lttng_evaluation_session_consumed_size *consumed;
404
405 consumed = container_of(evaluation, struct lttng_evaluation_session_consumed_size,
406 parent);
407 if (buf) {
408 struct lttng_evaluation_session_consumed_size_comm comm = {
409 .session_consumed = consumed->session_consumed,
410 };
411
412 memcpy(buf, &comm, sizeof(comm));
413 }
414
415 ret = sizeof(struct lttng_evaluation_session_consumed_size_comm);
416 return ret;
417}
418
419static
420void lttng_evaluation_session_consumed_size_destroy(
421 struct lttng_evaluation *evaluation)
422{
423 struct lttng_evaluation_session_consumed_size *consumed;
424
425 consumed = container_of(evaluation, struct lttng_evaluation_session_consumed_size,
426 parent);
427 free(consumed);
428}
429
430LTTNG_HIDDEN
431struct lttng_evaluation *lttng_evaluation_session_consumed_size_create(
432 enum lttng_condition_type type, uint64_t consumed)
433{
434 struct lttng_evaluation_session_consumed_size *consumed_eval;
435
436 consumed_eval = zmalloc(sizeof(struct lttng_evaluation_session_consumed_size));
437 if (!consumed_eval) {
438 goto end;
439 }
440
441 consumed_eval->parent.type = type;
442 consumed_eval->session_consumed = consumed;
443 consumed_eval->parent.serialize = lttng_evaluation_session_consumed_size_serialize;
444 consumed_eval->parent.destroy = lttng_evaluation_session_consumed_size_destroy;
445end:
446 return &consumed_eval->parent;
447}
448
449enum lttng_evaluation_status
450lttng_evaluation_session_consumed_size_get_consumed_size(
451 const struct lttng_evaluation *evaluation,
452 uint64_t *session_consumed)
453{
454 struct lttng_evaluation_session_consumed_size *consumed;
455 enum lttng_evaluation_status status = LTTNG_EVALUATION_STATUS_OK;
456
457 if (!evaluation || !IS_CONSUMED_SIZE_EVALUATION(evaluation) ||
458 !session_consumed) {
459 status = LTTNG_EVALUATION_STATUS_INVALID;
460 goto end;
461 }
462
463 consumed = container_of(evaluation, struct lttng_evaluation_session_consumed_size,
464 parent);
465 *session_consumed = consumed->session_consumed;
466end:
467 return status;
468}
This page took 0.04119 seconds and 5 git commands to generate.