Fix: session rotation logging statement references snapshot
[lttng-tools.git] / src / bin / lttng-sessiond / kernel.c
CommitLineData
20fe2104
DG
1/*
2 * Copyright (C) 2011 - David Goulet <david.goulet@polymtl.ca>
3 *
d14d33bf
AM
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License, version 2 only,
6 * as published by the Free Software Foundation.
20fe2104
DG
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
d14d33bf
AM
13 * You should have received a copy of the GNU General Public License along
14 * with this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20fe2104
DG
16 */
17
6c1c0768 18#define _LGPL_SOURCE
7b395890 19#include <fcntl.h>
20fe2104
DG
20#include <stdlib.h>
21#include <stdio.h>
f34daff7 22#include <string.h>
8c0faa1d 23#include <unistd.h>
77c7c900 24#include <inttypes.h>
20fe2104 25
990570ed 26#include <common/common.h>
db758600 27#include <common/kernel-ctl/kernel-ctl.h>
c052142c 28#include <common/kernel-ctl/kernel-ioctl.h>
42224349 29#include <common/sessiond-comm/sessiond-comm.h>
1e307fab 30
2f77fc4b 31#include "consumer.h"
4771f025 32#include "kernel.h"
6dc3064a 33#include "kernel-consumer.h"
096102bd 34#include "kern-modules.h"
834978fd 35#include "utils.h"
5c408ad8 36#include "rotate.h"
20fe2104 37
e1f3997a
JD
38/*
39 * Key used to reference a channel between the sessiond and the consumer. This
40 * is only read and updated with the session_list lock held.
41 */
42static uint64_t next_kernel_channel_key;
43
410b78a0
FD
44#include <lttng/userspace-probe.h>
45#include <lttng/userspace-probe-internal.h>
d65106b1 46/*
050349bb 47 * Add context on a kernel channel.
df3c77c8
JG
48 *
49 * Assumes the ownership of ctx.
d65106b1
DG
50 */
51int kernel_add_channel_context(struct ltt_kernel_channel *chan,
645328ae 52 struct ltt_kernel_context *ctx)
d65106b1
DG
53{
54 int ret;
55
0525e9ae
DG
56 assert(chan);
57 assert(ctx);
58
d65106b1 59 DBG("Adding context to channel %s", chan->channel->name);
645328ae 60 ret = kernctl_add_context(chan->fd, &ctx->ctx);
d65106b1 61 if (ret < 0) {
32af2c95 62 switch (-ret) {
1ae5e83e
JD
63 case ENOSYS:
64 /* Exists but not available for this kernel */
65 ret = LTTNG_ERR_KERN_CONTEXT_UNAVAILABLE;
66 goto error;
67 case EEXIST:
b579acd9
DG
68 /* If EEXIST, we just ignore the error */
69 ret = 0;
1ae5e83e
JD
70 goto end;
71 default:
72 PERROR("add context ioctl");
73 ret = LTTNG_ERR_KERN_CONTEXT_FAIL;
74 goto error;
b579acd9 75 }
d65106b1 76 }
21ed98c1 77 ret = 0;
d65106b1 78
1ae5e83e 79end:
645328ae 80 cds_list_add_tail(&ctx->list, &chan->ctx_list);
ba985c3a 81 ctx->in_list = true;
df3c77c8 82 ctx = NULL;
d65106b1 83error:
df3c77c8
JG
84 if (ctx) {
85 trace_kernel_destroy_context(ctx);
86 }
d65106b1
DG
87 return ret;
88}
89
20fe2104 90/*
050349bb
DG
91 * Create a new kernel session, register it to the kernel tracer and add it to
92 * the session daemon session.
20fe2104 93 */
8c0faa1d 94int kernel_create_session(struct ltt_session *session, int tracer_fd)
20fe2104
DG
95{
96 int ret;
97 struct ltt_kernel_session *lks;
98
0525e9ae
DG
99 assert(session);
100
54012638 101 /* Allocate data structure */
dec56f6c 102 lks = trace_kernel_create_session();
20fe2104 103 if (lks == NULL) {
54012638 104 ret = -1;
20fe2104
DG
105 goto error;
106 }
107
54012638 108 /* Kernel tracer session creation */
20fe2104
DG
109 ret = kernctl_create_session(tracer_fd);
110 if (ret < 0) {
df0f840b 111 PERROR("ioctl kernel create session");
20fe2104
DG
112 goto error;
113 }
114
20fe2104 115 lks->fd = ret;
7b395890
DG
116 /* Prevent fd duplication after execlp() */
117 ret = fcntl(lks->fd, F_SETFD, FD_CLOEXEC);
118 if (ret < 0) {
df0f840b 119 PERROR("fcntl session fd");
7b395890
DG
120 }
121
53632229 122 lks->id = session->id;
3bd1e081 123 lks->consumer_fds_sent = 0;
8c0faa1d 124 session->kernel_session = lks;
8c0faa1d
DG
125
126 DBG("Kernel session created (fd: %d)", lks->fd);
20fe2104
DG
127
128 return 0;
129
130error:
5f62c685
DG
131 if (lks) {
132 trace_kernel_destroy_session(lks);
133 }
20fe2104
DG
134 return ret;
135}
136
137/*
050349bb
DG
138 * Create a kernel channel, register it to the kernel tracer and add it to the
139 * kernel session.
20fe2104 140 */
050349bb 141int kernel_create_channel(struct ltt_kernel_session *session,
fdd9eb17 142 struct lttng_channel *chan)
20fe2104
DG
143{
144 int ret;
145 struct ltt_kernel_channel *lkc;
20fe2104 146
0525e9ae
DG
147 assert(session);
148 assert(chan);
0525e9ae 149
54012638 150 /* Allocate kernel channel */
fdd9eb17 151 lkc = trace_kernel_create_channel(chan);
54012638 152 if (lkc == NULL) {
20fe2104
DG
153 goto error;
154 }
155
ecc48a90 156 DBG3("Kernel create channel %s with attr: %d, %" PRIu64 ", %" PRIu64 ", %u, %u, %d, %d",
fdd9eb17 157 chan->name, lkc->channel->attr.overwrite,
173af62f
DG
158 lkc->channel->attr.subbuf_size, lkc->channel->attr.num_subbuf,
159 lkc->channel->attr.switch_timer_interval, lkc->channel->attr.read_timer_interval,
ecc48a90 160 lkc->channel->attr.live_timer_interval, lkc->channel->attr.output);
173af62f 161
54012638 162 /* Kernel tracer channel creation */
f3ed775e 163 ret = kernctl_create_channel(session->fd, &lkc->channel->attr);
20fe2104 164 if (ret < 0) {
df0f840b 165 PERROR("ioctl kernel create channel");
20fe2104
DG
166 goto error;
167 }
168
54012638 169 /* Setup the channel fd */
20fe2104 170 lkc->fd = ret;
7b395890
DG
171 /* Prevent fd duplication after execlp() */
172 ret = fcntl(lkc->fd, F_SETFD, FD_CLOEXEC);
173 if (ret < 0) {
df0f840b 174 PERROR("fcntl session fd");
7b395890
DG
175 }
176
54012638 177 /* Add channel to session */
8c0faa1d
DG
178 cds_list_add(&lkc->list, &session->channel_list.head);
179 session->channel_count++;
fb5f35b6 180 lkc->session = session;
e1f3997a 181 lkc->key = ++next_kernel_channel_key;
20fe2104 182
e1f3997a
JD
183 DBG("Kernel channel %s created (fd: %d, key: %" PRIu64 ")",
184 lkc->channel->name, lkc->fd, lkc->key);
20fe2104
DG
185
186 return 0;
187
188error:
5f62c685
DG
189 if (lkc) {
190 free(lkc->channel);
191 free(lkc);
192 }
54012638 193 return -1;
20fe2104 194}
f34daff7 195
410b78a0
FD
196/*
197 * Compute the offset of the instrumentation byte in the binary based on the
198 * function probe location using the ELF lookup method.
199 *
200 * Returns 0 on success and set the offset out parameter to the offset of the
201 * elf symbol
202 * Returns -1 on error
203 */
204static
205int extract_userspace_probe_offset_function_elf(
87597c2c 206 const struct lttng_userspace_probe_location *probe_location,
410b78a0
FD
207 struct ltt_kernel_session *session, uint64_t *offset)
208{
209 int fd;
210 int ret = 0;
211 const char *symbol = NULL;
87597c2c 212 const struct lttng_userspace_probe_location_lookup_method *lookup = NULL;
410b78a0
FD
213 enum lttng_userspace_probe_location_lookup_method_type lookup_method_type;
214
410b78a0
FD
215 assert(lttng_userspace_probe_location_get_type(probe_location) ==
216 LTTNG_USERSPACE_PROBE_LOCATION_TYPE_FUNCTION);
217
218 lookup = lttng_userspace_probe_location_get_lookup_method(
219 probe_location);
220 if (!lookup) {
221 ret = -1;
222 goto end;
223 }
224
225 lookup_method_type =
226 lttng_userspace_probe_location_lookup_method_get_type(lookup);
227
228 assert(lookup_method_type ==
229 LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_FUNCTION_ELF);
230
231 symbol = lttng_userspace_probe_location_function_get_function_name(
232 probe_location);
233 if (!symbol) {
234 ret = -1;
235 goto end;
236 }
237
238 fd = lttng_userspace_probe_location_function_get_binary_fd(probe_location);
239 if (fd < 0) {
240 ret = -1;
241 goto end;
242 }
243
244 ret = run_as_extract_elf_symbol_offset(fd, symbol, session->uid,
245 session->gid, offset);
246 if (ret < 0) {
247 DBG("userspace probe offset calculation failed for "
248 "function %s", symbol);
249 goto end;
250 }
251
252 DBG("userspace probe elf offset for %s is 0x%jd", symbol, (intmax_t)(*offset));
253end:
254 return ret;
255}
256
257/*
258 * Compute the offsets of the instrumentation bytes in the binary based on the
259 * tracepoint probe location using the SDT lookup method. This function
260 * allocates the offsets buffer, the caller must free it.
261 *
262 * Returns 0 on success and set the offset out parameter to the offsets of the
263 * SDT tracepoint.
264 * Returns -1 on error.
265 */
266static
267int extract_userspace_probe_offset_tracepoint_sdt(
87597c2c 268 const struct lttng_userspace_probe_location *probe_location,
410b78a0
FD
269 struct ltt_kernel_session *session, uint64_t **offsets,
270 uint32_t *offsets_count)
271{
272 enum lttng_userspace_probe_location_lookup_method_type lookup_method_type;
87597c2c 273 const struct lttng_userspace_probe_location_lookup_method *lookup = NULL;
410b78a0
FD
274 const char *probe_name = NULL, *provider_name = NULL;
275 int ret = 0;
276 int fd, i;
277
278 assert(lttng_userspace_probe_location_get_type(probe_location) ==
279 LTTNG_USERSPACE_PROBE_LOCATION_TYPE_TRACEPOINT);
280
281 lookup = lttng_userspace_probe_location_get_lookup_method(probe_location);
282 if (!lookup) {
283 ret = -1;
284 goto end;
285 }
286
287 lookup_method_type =
288 lttng_userspace_probe_location_lookup_method_get_type(lookup);
289
290 assert(lookup_method_type ==
291 LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_TRACEPOINT_SDT);
292
293
294 probe_name = lttng_userspace_probe_location_tracepoint_get_probe_name(
295 probe_location);
296 if (!probe_name) {
297 ret = -1;
298 goto end;
299 }
300
301 provider_name = lttng_userspace_probe_location_tracepoint_get_provider_name(
302 probe_location);
303 if (!provider_name) {
304 ret = -1;
305 goto end;
306 }
307
308 fd = lttng_userspace_probe_location_tracepoint_get_binary_fd(probe_location);
309 if (fd < 0) {
310 ret = -1;
311 goto end;
312 }
313
314 ret = run_as_extract_sdt_probe_offsets(fd, provider_name, probe_name,
315 session->uid, session->gid, offsets, offsets_count);
316 if (ret < 0) {
317 DBG("userspace probe offset calculation failed for sdt "
318 "probe %s:%s", provider_name, probe_name);
319 goto end;
320 }
321
322 if (*offsets_count == 0) {
323 DBG("no userspace probe offset found");
324 goto end;
325 }
326
327 DBG("%u userspace probe SDT offsets found for %s:%s at:",
328 *offsets_count, provider_name, probe_name);
329 for (i = 0; i < *offsets_count; i++) {
330 DBG("\t0x%jd", (intmax_t)((*offsets)[i]));
331 }
332end:
333 return ret;
334}
335
336/*
337 * Extract the offsets of the instrumentation point for the different lookup
338 * methods.
339 */
340static
341int userspace_probe_add_callsites(struct lttng_event *ev,
342 struct ltt_kernel_session *session, int fd)
343{
87597c2c 344 const struct lttng_userspace_probe_location_lookup_method *lookup_method = NULL;
410b78a0 345 enum lttng_userspace_probe_location_lookup_method_type type;
87597c2c 346 const struct lttng_userspace_probe_location *location = NULL;
410b78a0
FD
347 int ret;
348
349 assert(ev);
350 assert(ev->type == LTTNG_EVENT_USERSPACE_PROBE);
351
352 location = lttng_event_get_userspace_probe_location(ev);
353 if (!location) {
354 ret = -1;
355 goto end;
356 }
357 lookup_method =
358 lttng_userspace_probe_location_get_lookup_method(location);
359 if (!lookup_method) {
360 ret = -1;
361 goto end;
362 }
363
364 type = lttng_userspace_probe_location_lookup_method_get_type(lookup_method);
365 switch (type) {
366 case LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_FUNCTION_ELF:
367 {
368 struct lttng_kernel_event_callsite callsite;
369 uint64_t offset;
370
371 ret = extract_userspace_probe_offset_function_elf(location, session, &offset);
372 if (ret) {
373 ret = LTTNG_ERR_PROBE_LOCATION_INVAL;
374 goto end;
375 }
376
377 callsite.u.uprobe.offset = offset;
378 ret = kernctl_add_callsite(fd, &callsite);
379 if (ret) {
380 WARN("Adding callsite to userspace probe "
381 "event %s failed.", ev->name);
382 ret = LTTNG_ERR_KERN_ENABLE_FAIL;
383 goto end;
384 }
385 break;
386 }
387 case LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_TRACEPOINT_SDT:
388 {
389 int i;
390 uint64_t *offsets = NULL;
391 uint32_t offsets_count;
392 struct lttng_kernel_event_callsite callsite;
393
394 /*
395 * This call allocates the offsets buffer. This buffer must be freed
396 * by the caller
397 */
398 ret = extract_userspace_probe_offset_tracepoint_sdt(location, session,
399 &offsets, &offsets_count);
400 if (ret) {
401 ret = LTTNG_ERR_PROBE_LOCATION_INVAL;
402 goto end;
403 }
404 for (i = 0; i < offsets_count; i++) {
405 callsite.u.uprobe.offset = offsets[i];
406 ret = kernctl_add_callsite(fd, &callsite);
407 if (ret) {
408 WARN("Adding callsite to userspace probe "
409 "event %s failed.", ev->name);
410 ret = LTTNG_ERR_KERN_ENABLE_FAIL;
411 free(offsets);
412 goto end;
413 }
414 }
415 free(offsets);
416 break;
417 }
418 default:
419 ret = LTTNG_ERR_PROBE_LOCATION_INVAL;
420 goto end;
421 }
422end:
423 return ret;
424}
425
f34daff7 426/*
050349bb
DG
427 * Create a kernel event, enable it to the kernel tracer and add it to the
428 * channel event list of the kernel session.
49d21f93 429 * We own filter_expression and filter.
f34daff7 430 */
050349bb 431int kernel_create_event(struct lttng_event *ev,
00a62084
MD
432 struct ltt_kernel_channel *channel,
433 char *filter_expression,
434 struct lttng_filter_bytecode *filter)
f34daff7 435{
71a3bb01
FD
436 int err, fd;
437 enum lttng_error_code ret;
f34daff7 438 struct ltt_kernel_event *event;
f34daff7 439
0525e9ae
DG
440 assert(ev);
441 assert(channel);
442
a969e101 443 /* We pass ownership of filter_expression and filter */
71a3bb01
FD
444 ret = trace_kernel_create_event(ev, filter_expression,
445 filter, &event);
446 if (ret != LTTNG_OK) {
f34daff7
DG
447 goto error;
448 }
449
71a3bb01
FD
450 fd = kernctl_create_event(channel->fd, event->event);
451 if (fd < 0) {
452 switch (-fd) {
bd29c13d 453 case EEXIST:
71a3bb01 454 ret = LTTNG_ERR_KERN_EVENT_EXIST;
bd29c13d
DG
455 break;
456 case ENOSYS:
457 WARN("Event type not implemented");
71a3bb01 458 ret = LTTNG_ERR_KERN_EVENT_ENOSYS;
bd29c13d 459 break;
8197a339
DG
460 case ENOENT:
461 WARN("Event %s not found!", ev->name);
71a3bb01 462 ret = LTTNG_ERR_KERN_ENABLE_FAIL;
8197a339 463 break;
bd29c13d 464 default:
71a3bb01 465 ret = LTTNG_ERR_KERN_ENABLE_FAIL;
d87bfb32
DG
466 PERROR("create event ioctl");
467 }
e953ef25 468 goto free_event;
8c0faa1d 469 }
f34daff7 470
d0ae4ea8 471 event->type = ev->type;
71a3bb01 472 event->fd = fd;
7b395890 473 /* Prevent fd duplication after execlp() */
71a3bb01
FD
474 err = fcntl(event->fd, F_SETFD, FD_CLOEXEC);
475 if (err < 0) {
df0f840b 476 PERROR("fcntl session fd");
7b395890
DG
477 }
478
00a62084 479 if (filter) {
71a3bb01
FD
480 err = kernctl_filter(event->fd, filter);
481 if (err < 0) {
482 switch (-err) {
483 case ENOMEM:
484 ret = LTTNG_ERR_FILTER_NOMEM;
485 break;
486 default:
487 ret = LTTNG_ERR_FILTER_INVAL;
488 break;
489 }
00a62084
MD
490 goto filter_error;
491 }
492 }
493
dcabc190
FD
494 if (ev->type == LTTNG_EVENT_USERSPACE_PROBE) {
495 ret = userspace_probe_add_callsites(ev, channel->session, event->fd);
496 if (ret) {
497 goto add_callsite_error;
498 }
499 }
500
71a3bb01
FD
501 err = kernctl_enable(event->fd);
502 if (err < 0) {
503 switch (-err) {
00a62084
MD
504 case EEXIST:
505 ret = LTTNG_ERR_KERN_EVENT_EXIST;
506 break;
507 default:
508 PERROR("enable kernel event");
71a3bb01 509 ret = LTTNG_ERR_KERN_ENABLE_FAIL;
00a62084
MD
510 break;
511 }
512 goto enable_error;
513 }
514
f3ed775e
DG
515 /* Add event to event list */
516 cds_list_add(&event->list, &channel->events_list.head);
cbbbb275
DG
517 channel->event_count++;
518
e953ef25
DG
519 DBG("Event %s created (fd: %d)", ev->name, event->fd);
520
521 return 0;
522
dcabc190 523add_callsite_error:
00a62084
MD
524enable_error:
525filter_error:
526 {
527 int closeret;
528
529 closeret = close(event->fd);
530 if (closeret) {
531 PERROR("close event fd");
532 }
533 }
e953ef25
DG
534free_event:
535 free(event);
536error:
d87bfb32 537 return ret;
e953ef25
DG
538}
539
26cc6b4e 540/*
050349bb 541 * Disable a kernel channel.
26cc6b4e
DG
542 */
543int kernel_disable_channel(struct ltt_kernel_channel *chan)
544{
545 int ret;
546
0525e9ae
DG
547 assert(chan);
548
26cc6b4e
DG
549 ret = kernctl_disable(chan->fd);
550 if (ret < 0) {
df0f840b 551 PERROR("disable chan ioctl");
26cc6b4e
DG
552 goto error;
553 }
554
555 chan->enabled = 0;
e1f3997a
JD
556 DBG("Kernel channel %s disabled (fd: %d, key: %" PRIu64 ")",
557 chan->channel->name, chan->fd, chan->key);
26cc6b4e
DG
558
559 return 0;
560
561error:
562 return ret;
563}
564
d36b8583 565/*
050349bb 566 * Enable a kernel channel.
d36b8583
DG
567 */
568int kernel_enable_channel(struct ltt_kernel_channel *chan)
569{
570 int ret;
571
0525e9ae
DG
572 assert(chan);
573
d36b8583 574 ret = kernctl_enable(chan->fd);
32af2c95 575 if (ret < 0 && ret != -EEXIST) {
df0f840b 576 PERROR("Enable kernel chan");
d36b8583
DG
577 goto error;
578 }
579
580 chan->enabled = 1;
e1f3997a
JD
581 DBG("Kernel channel %s enabled (fd: %d, key: %" PRIu64 ")",
582 chan->channel->name, chan->fd, chan->key);
d36b8583
DG
583
584 return 0;
585
586error:
587 return ret;
588}
589
19e70852 590/*
050349bb 591 * Enable a kernel event.
19e70852
DG
592 */
593int kernel_enable_event(struct ltt_kernel_event *event)
594{
595 int ret;
596
0525e9ae
DG
597 assert(event);
598
19e70852 599 ret = kernctl_enable(event->fd);
42224349 600 if (ret < 0) {
32af2c95 601 switch (-ret) {
42224349 602 case EEXIST:
f73fabfd 603 ret = LTTNG_ERR_KERN_EVENT_EXIST;
42224349
DG
604 break;
605 default:
606 PERROR("enable kernel event");
607 break;
608 }
19e70852
DG
609 goto error;
610 }
611
612 event->enabled = 1;
613 DBG("Kernel event %s enabled (fd: %d)", event->event->name, event->fd);
614
615 return 0;
616
617error:
d36b8583 618 return ret;
19e70852
DG
619}
620
e953ef25 621/*
050349bb 622 * Disable a kernel event.
e953ef25 623 */
19e70852 624int kernel_disable_event(struct ltt_kernel_event *event)
e953ef25
DG
625{
626 int ret;
19e70852 627
0525e9ae
DG
628 assert(event);
629
19e70852 630 ret = kernctl_disable(event->fd);
42224349 631 if (ret < 0) {
32af2c95 632 switch (-ret) {
42224349 633 case EEXIST:
f73fabfd 634 ret = LTTNG_ERR_KERN_EVENT_EXIST;
42224349
DG
635 break;
636 default:
637 PERROR("disable kernel event");
638 break;
639 }
19e70852 640 goto error;
e953ef25 641 }
f3ed775e 642
19e70852
DG
643 event->enabled = 0;
644 DBG("Kernel event %s disabled (fd: %d)", event->event->name, event->fd);
645
f34daff7
DG
646 return 0;
647
648error:
d36b8583 649 return ret;
f34daff7 650}
aaf26714 651
6e911cad 652
ccf10263
MD
653int kernel_track_pid(struct ltt_kernel_session *session, int pid)
654{
7c493d31
MD
655 int ret;
656
ccf10263
MD
657 DBG("Kernel track PID %d for session id %" PRIu64 ".",
658 pid, session->id);
7c493d31
MD
659 ret = kernctl_track_pid(session->fd, pid);
660 if (!ret) {
661 return LTTNG_OK;
662 }
32af2c95 663 switch (-ret) {
7c493d31
MD
664 case EINVAL:
665 return LTTNG_ERR_INVALID;
666 case ENOMEM:
667 return LTTNG_ERR_NOMEM;
668 case EEXIST:
669 return LTTNG_ERR_PID_TRACKED;
670 default:
671 return LTTNG_ERR_UNK;
672 }
ccf10263
MD
673}
674
675int kernel_untrack_pid(struct ltt_kernel_session *session, int pid)
676{
7c493d31
MD
677 int ret;
678
ccf10263
MD
679 DBG("Kernel untrack PID %d for session id %" PRIu64 ".",
680 pid, session->id);
7c493d31
MD
681 ret = kernctl_untrack_pid(session->fd, pid);
682 if (!ret) {
683 return LTTNG_OK;
684 }
32af2c95 685 switch (-ret) {
7c493d31
MD
686 case EINVAL:
687 return LTTNG_ERR_INVALID;
688 case ENOMEM:
689 return LTTNG_ERR_NOMEM;
690 case ENOENT:
691 return LTTNG_ERR_PID_NOT_TRACKED;
692 default:
693 return LTTNG_ERR_UNK;
694 }
ccf10263
MD
695}
696
a5dfbb9d
MD
697ssize_t kernel_list_tracker_pids(struct ltt_kernel_session *session,
698 int **_pids)
699{
700 int fd, ret;
701 int pid;
702 ssize_t nbmem, count = 0;
703 FILE *fp;
704 int *pids;
705
706 fd = kernctl_list_tracker_pids(session->fd);
707 if (fd < 0) {
708 PERROR("kernel tracker pids list");
709 goto error;
710 }
711
712 fp = fdopen(fd, "r");
713 if (fp == NULL) {
714 PERROR("kernel tracker pids list fdopen");
715 goto error_fp;
716 }
717
718 nbmem = KERNEL_TRACKER_PIDS_INIT_LIST_SIZE;
719 pids = zmalloc(sizeof(*pids) * nbmem);
720 if (pids == NULL) {
721 PERROR("alloc list pids");
722 count = -ENOMEM;
723 goto end;
724 }
725
726 while (fscanf(fp, "process { pid = %u; };\n", &pid) == 1) {
727 if (count >= nbmem) {
728 int *new_pids;
729 size_t new_nbmem;
730
731 new_nbmem = nbmem << 1;
732 DBG("Reallocating pids list from %zu to %zu entries",
733 nbmem, new_nbmem);
734 new_pids = realloc(pids, new_nbmem * sizeof(*new_pids));
735 if (new_pids == NULL) {
736 PERROR("realloc list events");
737 free(pids);
738 count = -ENOMEM;
739 goto end;
740 }
741 /* Zero the new memory */
742 memset(new_pids + nbmem, 0,
743 (new_nbmem - nbmem) * sizeof(*new_pids));
744 nbmem = new_nbmem;
745 pids = new_pids;
746 }
747 pids[count++] = pid;
748 }
749
750 *_pids = pids;
751 DBG("Kernel list tracker pids done (%zd pids)", count);
752end:
753 ret = fclose(fp); /* closes both fp and fd */
754 if (ret) {
755 PERROR("fclose");
756 }
757 return count;
758
759error_fp:
760 ret = close(fd);
761 if (ret) {
762 PERROR("close");
763 }
764error:
765 return -1;
766}
767
aaf26714 768/*
050349bb
DG
769 * Create kernel metadata, open from the kernel tracer and add it to the
770 * kernel session.
aaf26714 771 */
a4b92340 772int kernel_open_metadata(struct ltt_kernel_session *session)
aaf26714
DG
773{
774 int ret;
74024a21 775 struct ltt_kernel_metadata *lkm = NULL;
aaf26714 776
0525e9ae
DG
777 assert(session);
778
54012638 779 /* Allocate kernel metadata */
a4b92340 780 lkm = trace_kernel_create_metadata();
54012638 781 if (lkm == NULL) {
aaf26714
DG
782 goto error;
783 }
784
54012638 785 /* Kernel tracer metadata creation */
f3ed775e 786 ret = kernctl_open_metadata(session->fd, &lkm->conf->attr);
aaf26714 787 if (ret < 0) {
74024a21 788 goto error_open;
aaf26714
DG
789 }
790
8c0faa1d 791 lkm->fd = ret;
d40f0359 792 lkm->key = ++next_kernel_channel_key;
7b395890
DG
793 /* Prevent fd duplication after execlp() */
794 ret = fcntl(lkm->fd, F_SETFD, FD_CLOEXEC);
795 if (ret < 0) {
df0f840b 796 PERROR("fcntl session fd");
7b395890
DG
797 }
798
aaf26714 799 session->metadata = lkm;
8c0faa1d 800
00e2e675 801 DBG("Kernel metadata opened (fd: %d)", lkm->fd);
8c0faa1d
DG
802
803 return 0;
804
74024a21
DG
805error_open:
806 trace_kernel_destroy_metadata(lkm);
8c0faa1d 807error:
54012638 808 return -1;
8c0faa1d
DG
809}
810
811/*
050349bb 812 * Start tracing session.
8c0faa1d
DG
813 */
814int kernel_start_session(struct ltt_kernel_session *session)
815{
816 int ret;
817
0525e9ae
DG
818 assert(session);
819
8c0faa1d
DG
820 ret = kernctl_start_session(session->fd);
821 if (ret < 0) {
df0f840b 822 PERROR("ioctl start session");
8c0faa1d
DG
823 goto error;
824 }
825
826 DBG("Kernel session started");
827
828 return 0;
829
830error:
831 return ret;
832}
833
f3ed775e 834/*
050349bb 835 * Make a kernel wait to make sure in-flight probe have completed.
f3ed775e
DG
836 */
837void kernel_wait_quiescent(int fd)
838{
839 int ret;
840
841 DBG("Kernel quiescent wait on %d", fd);
842
843 ret = kernctl_wait_quiescent(fd);
844 if (ret < 0) {
df0f840b 845 PERROR("wait quiescent ioctl");
f3ed775e
DG
846 ERR("Kernel quiescent wait failed");
847 }
848}
849
850/*
f3ed775e
DG
851 * Force flush buffer of metadata.
852 */
853int kernel_metadata_flush_buffer(int fd)
854{
855 int ret;
856
169d2cb7
DG
857 DBG("Kernel flushing metadata buffer on fd %d", fd);
858
f3ed775e
DG
859 ret = kernctl_buffer_flush(fd);
860 if (ret < 0) {
00e2e675 861 ERR("Fail to flush metadata buffers %d (ret: %d)", fd, ret);
f3ed775e
DG
862 }
863
864 return 0;
865}
866
867/*
050349bb 868 * Force flush buffer for channel.
f3ed775e
DG
869 */
870int kernel_flush_buffer(struct ltt_kernel_channel *channel)
871{
872 int ret;
873 struct ltt_kernel_stream *stream;
874
0525e9ae
DG
875 assert(channel);
876
f3ed775e
DG
877 DBG("Flush buffer for channel %s", channel->channel->name);
878
879 cds_list_for_each_entry(stream, &channel->stream_list.head, list) {
880 DBG("Flushing channel stream %d", stream->fd);
881 ret = kernctl_buffer_flush(stream->fd);
882 if (ret < 0) {
df0f840b 883 PERROR("ioctl");
f3ed775e
DG
884 ERR("Fail to flush buffer for stream %d (ret: %d)",
885 stream->fd, ret);
886 }
887 }
888
889 return 0;
890}
891
8c0faa1d 892/*
050349bb 893 * Stop tracing session.
8c0faa1d
DG
894 */
895int kernel_stop_session(struct ltt_kernel_session *session)
896{
897 int ret;
898
0525e9ae
DG
899 assert(session);
900
8c0faa1d
DG
901 ret = kernctl_stop_session(session->fd);
902 if (ret < 0) {
903 goto error;
904 }
905
906 DBG("Kernel session stopped");
907
908 return 0;
909
910error:
911 return ret;
912}
913
914/*
050349bb
DG
915 * Open stream of channel, register it to the kernel tracer and add it
916 * to the stream list of the channel.
8c0faa1d 917 *
1cfb4b98
MD
918 * Note: given that the streams may appear in random order wrt CPU
919 * number (e.g. cpu hotplug), the index value of the stream number in
920 * the stream name is not necessarily linked to the CPU number.
921 *
050349bb 922 * Return the number of created stream. Else, a negative value.
8c0faa1d 923 */
f3ed775e 924int kernel_open_channel_stream(struct ltt_kernel_channel *channel)
8c0faa1d 925{
1cfb4b98 926 int ret;
8c0faa1d
DG
927 struct ltt_kernel_stream *lks;
928
0525e9ae
DG
929 assert(channel);
930
5a47c6a2 931 while ((ret = kernctl_create_stream(channel->fd)) >= 0) {
1cfb4b98
MD
932 lks = trace_kernel_create_stream(channel->channel->name,
933 channel->stream_count);
8c0faa1d 934 if (lks == NULL) {
799e2c4f
MD
935 ret = close(ret);
936 if (ret) {
937 PERROR("close");
938 }
8c0faa1d
DG
939 goto error;
940 }
941
942 lks->fd = ret;
7b395890
DG
943 /* Prevent fd duplication after execlp() */
944 ret = fcntl(lks->fd, F_SETFD, FD_CLOEXEC);
945 if (ret < 0) {
df0f840b 946 PERROR("fcntl session fd");
7b395890
DG
947 }
948
1624d5b7
JD
949 lks->tracefile_size = channel->channel->attr.tracefile_size;
950 lks->tracefile_count = channel->channel->attr.tracefile_count;
951
1cfb4b98 952 /* Add stream to channel stream list */
8c0faa1d
DG
953 cds_list_add(&lks->list, &channel->stream_list.head);
954 channel->stream_count++;
8c0faa1d 955
00e2e675
DG
956 DBG("Kernel stream %s created (fd: %d, state: %d)", lks->name, lks->fd,
957 lks->state);
54012638 958 }
8c0faa1d
DG
959
960 return channel->stream_count;
961
962error:
54012638 963 return -1;
8c0faa1d
DG
964}
965
966/*
050349bb 967 * Open the metadata stream and set it to the kernel session.
8c0faa1d 968 */
f3ed775e 969int kernel_open_metadata_stream(struct ltt_kernel_session *session)
8c0faa1d
DG
970{
971 int ret;
972
0525e9ae
DG
973 assert(session);
974
8c0faa1d
DG
975 ret = kernctl_create_stream(session->metadata->fd);
976 if (ret < 0) {
df0f840b 977 PERROR("kernel create metadata stream");
8c0faa1d
DG
978 goto error;
979 }
980
981 DBG("Kernel metadata stream created (fd: %d)", ret);
982 session->metadata_stream_fd = ret;
7b395890
DG
983 /* Prevent fd duplication after execlp() */
984 ret = fcntl(session->metadata_stream_fd, F_SETFD, FD_CLOEXEC);
985 if (ret < 0) {
df0f840b 986 PERROR("fcntl session fd");
7b395890 987 }
aaf26714
DG
988
989 return 0;
990
991error:
54012638 992 return -1;
aaf26714 993}
2ef84c95
DG
994
995/*
9f19cc17 996 * Get the event list from the kernel tracer and return the number of elements.
2ef84c95 997 */
9f19cc17 998ssize_t kernel_list_events(int tracer_fd, struct lttng_event **events)
2ef84c95 999{
53efb85a 1000 int fd, ret;
9f19cc17
DG
1001 char *event;
1002 size_t nbmem, count = 0;
2ef84c95 1003 FILE *fp;
9f19cc17 1004 struct lttng_event *elist;
2ef84c95 1005
0525e9ae
DG
1006 assert(events);
1007
2ef84c95
DG
1008 fd = kernctl_tracepoint_list(tracer_fd);
1009 if (fd < 0) {
df0f840b 1010 PERROR("kernel tracepoint list");
2ef84c95
DG
1011 goto error;
1012 }
1013
1014 fp = fdopen(fd, "r");
1015 if (fp == NULL) {
df0f840b 1016 PERROR("kernel tracepoint list fdopen");
61b73b12 1017 goto error_fp;
2ef84c95
DG
1018 }
1019
1020 /*
1021 * Init memory size counter
1022 * See kernel-ctl.h for explanation of this value
1023 */
6725fe19 1024 nbmem = KERNEL_EVENT_INIT_LIST_SIZE;
ba7f0ae5 1025 elist = zmalloc(sizeof(struct lttng_event) * nbmem);
3b870559
MD
1026 if (elist == NULL) {
1027 PERROR("alloc list events");
1028 count = -ENOMEM;
1029 goto end;
1030 }
2ef84c95 1031
53efb85a 1032 while (fscanf(fp, "event { name = %m[^;]; };\n", &event) == 1) {
6725fe19 1033 if (count >= nbmem) {
3b870559 1034 struct lttng_event *new_elist;
53efb85a 1035 size_t new_nbmem;
3b870559 1036
53efb85a
MD
1037 new_nbmem = nbmem << 1;
1038 DBG("Reallocating event list from %zu to %zu bytes",
1039 nbmem, new_nbmem);
1040 new_elist = realloc(elist, new_nbmem * sizeof(struct lttng_event));
3b870559 1041 if (new_elist == NULL) {
df0f840b 1042 PERROR("realloc list events");
3b870559
MD
1043 free(event);
1044 free(elist);
61b73b12
MD
1045 count = -ENOMEM;
1046 goto end;
2ef84c95 1047 }
53efb85a
MD
1048 /* Zero the new memory */
1049 memset(new_elist + nbmem, 0,
1050 (new_nbmem - nbmem) * sizeof(struct lttng_event));
1051 nbmem = new_nbmem;
3b870559 1052 elist = new_elist;
2ef84c95 1053 }
99497cd0
MD
1054 strncpy(elist[count].name, event, LTTNG_SYMBOL_NAME_LEN);
1055 elist[count].name[LTTNG_SYMBOL_NAME_LEN - 1] = '\0';
67b9d018 1056 elist[count].enabled = -1;
9f19cc17 1057 count++;
3b870559 1058 free(event);
2ef84c95
DG
1059 }
1060
9f19cc17 1061 *events = elist;
ced2f820 1062 DBG("Kernel list events done (%zu events)", count);
61b73b12 1063end:
799e2c4f
MD
1064 ret = fclose(fp); /* closes both fp and fd */
1065 if (ret) {
1066 PERROR("fclose");
1067 }
9f19cc17 1068 return count;
2ef84c95 1069
61b73b12 1070error_fp:
799e2c4f
MD
1071 ret = close(fd);
1072 if (ret) {
1073 PERROR("close");
1074 }
2ef84c95
DG
1075error:
1076 return -1;
1077}
096102bd
DG
1078
1079/*
1080 * Get kernel version and validate it.
1081 */
88076e89
JD
1082int kernel_validate_version(int tracer_fd,
1083 struct lttng_kernel_tracer_version *version,
1084 struct lttng_kernel_tracer_abi_version *abi_version)
096102bd
DG
1085{
1086 int ret;
096102bd 1087
88076e89 1088 ret = kernctl_tracer_version(tracer_fd, version);
096102bd 1089 if (ret < 0) {
521dd134 1090 ERR("Failed to retrieve the lttng-modules version");
096102bd
DG
1091 goto error;
1092 }
1093
1094 /* Validate version */
88076e89 1095 if (version->major != VERSION_MAJOR) {
c052142c 1096 ERR("Kernel tracer major version (%d) is not compatible with lttng-tools major version (%d)",
88076e89 1097 version->major, VERSION_MAJOR);
096102bd 1098 goto error_version;
096102bd 1099 }
88076e89 1100 ret = kernctl_tracer_abi_version(tracer_fd, abi_version);
c052142c 1101 if (ret < 0) {
521dd134 1102 ERR("Failed to retrieve lttng-modules ABI version");
c052142c
MD
1103 goto error;
1104 }
88076e89 1105 if (abi_version->major != LTTNG_MODULES_ABI_MAJOR_VERSION) {
521dd134 1106 ERR("Kernel tracer ABI version (%d.%d) does not match the expected ABI major version (%d.*)",
88076e89 1107 abi_version->major, abi_version->minor,
c052142c
MD
1108 LTTNG_MODULES_ABI_MAJOR_VERSION);
1109 goto error;
1110 }
1111 DBG2("Kernel tracer version validated (%d.%d, ABI %d.%d)",
88076e89
JD
1112 version->major, version->minor,
1113 abi_version->major, abi_version->minor);
096102bd
DG
1114 return 0;
1115
1116error_version:
096102bd
DG
1117 ret = -1;
1118
1119error:
521dd134 1120 ERR("Kernel tracer version check failed; kernel tracing will not be available");
096102bd
DG
1121 return ret;
1122}
335a95b7
MD
1123
1124/*
1125 * Kernel work-arounds called at the start of sessiond main().
1126 */
1127int init_kernel_workarounds(void)
1128{
8936c33a 1129 int ret;
335a95b7
MD
1130 FILE *fp;
1131
1132 /*
1133 * boot_id needs to be read once before being used concurrently
1134 * to deal with a Linux kernel race. A fix is proposed for
1135 * upstream, but the work-around is needed for older kernels.
1136 */
1137 fp = fopen("/proc/sys/kernel/random/boot_id", "r");
1138 if (!fp) {
1139 goto end_boot_id;
1140 }
1141 while (!feof(fp)) {
1142 char buf[37] = "";
1143
8936c33a
DG
1144 ret = fread(buf, 1, sizeof(buf), fp);
1145 if (ret < 0) {
1146 /* Ignore error, we don't really care */
1147 }
335a95b7 1148 }
799e2c4f
MD
1149 ret = fclose(fp);
1150 if (ret) {
1151 PERROR("fclose");
1152 }
335a95b7 1153end_boot_id:
335a95b7
MD
1154 return 0;
1155}
2f77fc4b
DG
1156
1157/*
1158 * Complete teardown of a kernel session.
1159 */
1160void kernel_destroy_session(struct ltt_kernel_session *ksess)
1161{
1162 if (ksess == NULL) {
1163 DBG3("No kernel session when tearing down session");
1164 return;
1165 }
1166
1167 DBG("Tearing down kernel session");
1168
07b86b52 1169 /*
15dc512a
DG
1170 * Destroy channels on the consumer if at least one FD has been sent and we
1171 * are in no output mode because the streams are in *no* monitor mode so we
1172 * have to send a command to clean them up or else they leaked.
07b86b52 1173 */
15dc512a 1174 if (!ksess->output_traces && ksess->consumer_fds_sent) {
07b86b52
JD
1175 int ret;
1176 struct consumer_socket *socket;
1177 struct lttng_ht_iter iter;
1178
1179 /* For each consumer socket. */
d069d577 1180 rcu_read_lock();
07b86b52
JD
1181 cds_lfht_for_each_entry(ksess->consumer->socks->ht, &iter.iter,
1182 socket, node.node) {
1183 struct ltt_kernel_channel *chan;
1184
1185 /* For each channel, ask the consumer to destroy it. */
1186 cds_list_for_each_entry(chan, &ksess->channel_list.head, list) {
1187 ret = kernel_consumer_destroy_channel(socket, chan);
1188 if (ret < 0) {
1189 /* Consumer is probably dead. Use next socket. */
1190 continue;
1191 }
1192 }
1193 }
d069d577 1194 rcu_read_unlock();
07b86b52
JD
1195 }
1196
2f77fc4b
DG
1197 /* Close any relayd session */
1198 consumer_output_send_destroy_relayd(ksess->consumer);
1199
1200 trace_kernel_destroy_session(ksess);
1201}
fb5f35b6
DG
1202
1203/*
1204 * Destroy a kernel channel object. It does not do anything on the tracer side.
1205 */
1206void kernel_destroy_channel(struct ltt_kernel_channel *kchan)
1207{
1208 struct ltt_kernel_session *ksess = NULL;
1209
1210 assert(kchan);
1211 assert(kchan->channel);
1212
1213 DBG3("Kernel destroy channel %s", kchan->channel->name);
1214
1215 /* Update channel count of associated session. */
1216 if (kchan->session) {
1217 /* Keep pointer reference so we can update it after the destroy. */
1218 ksess = kchan->session;
1219 }
1220
1221 trace_kernel_destroy_channel(kchan);
1222
1223 /*
1224 * At this point the kernel channel is not visible anymore. This is safe
1225 * since in order to work on a visible kernel session, the tracing session
1226 * lock (ltt_session.lock) MUST be acquired.
1227 */
1228 if (ksess) {
1229 ksess->channel_count--;
1230 }
1231}
6dc3064a
DG
1232
1233/*
1234 * Take a snapshot for a given kernel session.
1235 *
2a06df8d 1236 * Return 0 on success or else return a LTTNG_ERR code.
6dc3064a
DG
1237 */
1238int kernel_snapshot_record(struct ltt_kernel_session *ksess,
d07ceecd
MD
1239 struct snapshot_output *output, int wait,
1240 uint64_t nb_packets_per_stream)
6dc3064a 1241{
2a06df8d 1242 int err, ret, saved_metadata_fd;
6dc3064a
DG
1243 struct consumer_socket *socket;
1244 struct lttng_ht_iter iter;
1245 struct ltt_kernel_metadata *saved_metadata;
e098433c
JG
1246 struct ltt_session *session;
1247 uint64_t trace_archive_id;
6dc3064a
DG
1248
1249 assert(ksess);
1250 assert(ksess->consumer);
1251 assert(output);
1252
1253 DBG("Kernel snapshot record started");
1254
e098433c
JG
1255 session = session_find_by_id(ksess->id);
1256 assert(session);
1257 assert(pthread_mutex_trylock(&session->lock));
1258 assert(session_trylock_list());
1259 trace_archive_id = session->current_archive_id;
1260
6dc3064a
DG
1261 /* Save current metadata since the following calls will change it. */
1262 saved_metadata = ksess->metadata;
1263 saved_metadata_fd = ksess->metadata_stream_fd;
1264
1265 rcu_read_lock();
1266
1267 ret = kernel_open_metadata(ksess);
1268 if (ret < 0) {
1269 ret = LTTNG_ERR_KERN_META_FAIL;
1270 goto error;
1271 }
1272
1273 ret = kernel_open_metadata_stream(ksess);
1274 if (ret < 0) {
1275 ret = LTTNG_ERR_KERN_META_FAIL;
1276 goto error_open_stream;
1277 }
1278
1279 /* Send metadata to consumer and snapshot everything. */
1280 cds_lfht_for_each_entry(ksess->consumer->socks->ht, &iter.iter,
1281 socket, node.node) {
1282 struct consumer_output *saved_output;
1283 struct ltt_kernel_channel *chan;
6dc3064a
DG
1284
1285 /*
1286 * Temporarly switch consumer output for our snapshot output. As long
1287 * as the session lock is taken, this is safe.
1288 */
1289 saved_output = ksess->consumer;
1290 ksess->consumer = output->consumer;
1291
1292 pthread_mutex_lock(socket->lock);
1293 /* This stream must not be monitored by the consumer. */
07b86b52 1294 ret = kernel_consumer_add_metadata(socket, ksess, 0);
6dc3064a 1295 pthread_mutex_unlock(socket->lock);
07b86b52 1296 /* Put back the saved consumer output into the session. */
6dc3064a
DG
1297 ksess->consumer = saved_output;
1298 if (ret < 0) {
1299 ret = LTTNG_ERR_KERN_CONSUMER_FAIL;
1300 goto error_consumer;
1301 }
1302
1303 /* For each channel, ask the consumer to snapshot it. */
1304 cds_list_for_each_entry(chan, &ksess->channel_list.head, list) {
0a28e553 1305 ret = consumer_snapshot_channel(socket, chan->key, output, 0,
5c786ded
JD
1306 ksess->uid, ksess->gid,
1307 DEFAULT_KERNEL_TRACE_DIR, wait,
e098433c
JG
1308 nb_packets_per_stream,
1309 trace_archive_id);
6dc3064a
DG
1310 if (ret < 0) {
1311 ret = LTTNG_ERR_KERN_CONSUMER_FAIL;
2a06df8d
DG
1312 (void) kernel_consumer_destroy_metadata(socket,
1313 ksess->metadata);
6dc3064a
DG
1314 goto error_consumer;
1315 }
1316 }
1317
1318 /* Snapshot metadata, */
d40f0359 1319 ret = consumer_snapshot_channel(socket, ksess->metadata->key, output,
5c786ded 1320 1, ksess->uid, ksess->gid,
e098433c
JG
1321 DEFAULT_KERNEL_TRACE_DIR, wait, 0,
1322 trace_archive_id);
6dc3064a
DG
1323 if (ret < 0) {
1324 ret = LTTNG_ERR_KERN_CONSUMER_FAIL;
1325 goto error_consumer;
1326 }
07b86b52
JD
1327
1328 /*
1329 * The metadata snapshot is done, ask the consumer to destroy it since
1330 * it's not monitored on the consumer side.
1331 */
1332 (void) kernel_consumer_destroy_metadata(socket, ksess->metadata);
6dc3064a
DG
1333 }
1334
fac41e72
DG
1335 ret = LTTNG_OK;
1336
6dc3064a
DG
1337error_consumer:
1338 /* Close newly opened metadata stream. It's now on the consumer side. */
2a06df8d
DG
1339 err = close(ksess->metadata_stream_fd);
1340 if (err < 0) {
6dc3064a
DG
1341 PERROR("close snapshot kernel");
1342 }
1343
1344error_open_stream:
1345 trace_kernel_destroy_metadata(ksess->metadata);
1346error:
1347 /* Restore metadata state.*/
1348 ksess->metadata = saved_metadata;
1349 ksess->metadata_stream_fd = saved_metadata_fd;
1350
1351 rcu_read_unlock();
1352 return ret;
1353}
834978fd
DG
1354
1355/*
1356 * Get the syscall mask array from the kernel tracer.
1357 *
1358 * Return 0 on success else a negative value. In both case, syscall_mask should
1359 * be freed.
1360 */
1361int kernel_syscall_mask(int chan_fd, char **syscall_mask, uint32_t *nr_bits)
1362{
1363 assert(syscall_mask);
1364 assert(nr_bits);
1365
1366 return kernctl_syscall_mask(chan_fd, syscall_mask, nr_bits);
1367}
6e21424e
JR
1368
1369/*
1370 * Check for the support of the RING_BUFFER_SNAPSHOT_SAMPLE_POSITIONS via abi
1371 * version number.
1372 *
1373 * Return 1 on success, 0 when feature is not supported, negative value in case
1374 * of errors.
1375 */
1376int kernel_supports_ring_buffer_snapshot_sample_positions(int tracer_fd)
1377{
1378 int ret = 0; // Not supported by default
1379 struct lttng_kernel_tracer_abi_version abi;
1380
1381 ret = kernctl_tracer_abi_version(tracer_fd, &abi);
1382 if (ret < 0) {
1383 ERR("Failed to retrieve lttng-modules ABI version");
1384 goto error;
1385 }
1386
1387 /*
1388 * RING_BUFFER_SNAPSHOT_SAMPLE_POSITIONS was introduced in 2.3
1389 */
1390 if (abi.major >= 2 && abi.minor >= 3) {
1391 /* Supported */
1392 ret = 1;
1393 } else {
1394 /* Not supported */
1395 ret = 0;
1396 }
1397error:
1398 return ret;
1399}
5c408ad8
JD
1400
1401/*
1402 * Rotate a kernel session.
1403 *
1404 * Return 0 on success or else return a LTTNG_ERR code.
1405 */
1406int kernel_rotate_session(struct ltt_session *session)
1407{
1408 int ret;
1409 struct consumer_socket *socket;
1410 struct lttng_ht_iter iter;
1411 struct ltt_kernel_session *ksess = session->kernel_session;
1412
1413 assert(ksess);
1414 assert(ksess->consumer);
1415
1416 DBG("Rotate kernel session %s started (session %" PRIu64 ")",
1417 session->name, session->id);
1418
1419 rcu_read_lock();
1420
1421 /*
1422 * Note that this loop will end after one iteration given that there is
1423 * only one kernel consumer.
1424 */
1425 cds_lfht_for_each_entry(ksess->consumer->socks->ht, &iter.iter,
1426 socket, node.node) {
1427 struct ltt_kernel_channel *chan;
1428
5c408ad8
JD
1429 /* For each channel, ask the consumer to rotate it. */
1430 cds_list_for_each_entry(chan, &ksess->channel_list.head, list) {
92816cc3
JG
1431 DBG("Rotate kernel channel %" PRIu64 ", session %s",
1432 chan->key, session->name);
5c408ad8
JD
1433 ret = consumer_rotate_channel(socket, chan->key,
1434 ksess->uid, ksess->gid, ksess->consumer,
1435 ksess->consumer->subdir,
1436 /* is_metadata_channel */ false,
92816cc3 1437 session->current_archive_id);
5c408ad8
JD
1438 if (ret < 0) {
1439 ret = LTTNG_ERR_KERN_CONSUMER_FAIL;
1440 goto error;
1441 }
1442 }
1443
1444 /*
1445 * Rotate the metadata channel.
1446 */
22a1b931 1447 ret = consumer_rotate_channel(socket, ksess->metadata->key,
5c408ad8
JD
1448 ksess->uid, ksess->gid, ksess->consumer,
1449 ksess->consumer->subdir,
1450 /* is_metadata_channel */ true,
92816cc3 1451 session->current_archive_id);
5c408ad8
JD
1452 if (ret < 0) {
1453 ret = LTTNG_ERR_KERN_CONSUMER_FAIL;
1454 goto error;
1455 }
1456 }
1457
1458 ret = LTTNG_OK;
1459
1460error:
1461 rcu_read_unlock();
1462 return ret;
1463}
This page took 0.144451 seconds and 5 git commands to generate.