Split and remove lttng-share header file
[lttng-tools.git] / src / bin / lttng-sessiond / ust-app.c
CommitLineData
91d76f53
DG
1/*
2 * Copyright (C) 2011 - David Goulet <david.goulet@polymtl.ca>
3 *
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License
82a3637f
DG
6 * as published by the Free Software Foundation; only version 2
7 * of the License.
91d76f53
DG
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17 */
18
19#define _GNU_SOURCE
20#include <errno.h>
21#include <pthread.h>
22#include <stdio.h>
23#include <stdlib.h>
099e26bd 24#include <string.h>
aba8e916
DG
25#include <sys/stat.h>
26#include <sys/types.h>
099e26bd 27#include <unistd.h>
0df502fd 28#include <urcu/compiler.h>
bec39940 29
10a8a223 30#include <common/lttngerr.h>
990570ed 31#include <common/common.h>
1e307fab 32
56fff090 33#include "ust-app.h"
48842b30 34#include "ust-consumer.h"
d80a6244
DG
35#include "ust-ctl.h"
36
55cc08a6
DG
37/*
38 * Delete ust context safely. RCU read lock must be held before calling
39 * this function.
40 */
41static
42void delete_ust_app_ctx(int sock, struct ust_app_ctx *ua_ctx)
43{
44 if (ua_ctx->obj) {
45 ustctl_release_object(sock, ua_ctx->obj);
46 free(ua_ctx->obj);
47 }
48 free(ua_ctx);
49}
50
d80a6244
DG
51/*
52 * Delete ust app event safely. RCU read lock must be held before calling
53 * this function.
54 */
8b366481
DG
55static
56void delete_ust_app_event(int sock, struct ust_app_event *ua_event)
d80a6244 57{
55cc08a6 58 int ret;
bec39940 59 struct lttng_ht_iter iter;
55cc08a6
DG
60 struct ust_app_ctx *ua_ctx;
61
fc34caaa 62 /* Destroy each context of event */
bec39940
DG
63 cds_lfht_for_each_entry(ua_event->ctx->ht, &iter.iter, ua_ctx,
64 node.node) {
65 ret = lttng_ht_del(ua_event->ctx, &iter);
55cc08a6
DG
66 assert(!ret);
67 delete_ust_app_ctx(sock, ua_ctx);
68 }
bec39940 69 lttng_ht_destroy(ua_event->ctx);
d80a6244 70
edb67388
DG
71 if (ua_event->obj != NULL) {
72 ustctl_release_object(sock, ua_event->obj);
73 free(ua_event->obj);
74 }
d80a6244
DG
75 free(ua_event);
76}
77
78/*
79 * Delete ust app stream safely. RCU read lock must be held before calling
80 * this function.
81 */
8b366481
DG
82static
83void delete_ust_app_stream(int sock, struct ltt_ust_stream *stream)
d80a6244 84{
8b366481
DG
85 if (stream->obj) {
86 ustctl_release_object(sock, stream->obj);
87 free(stream->obj);
88 }
84cd17c6 89 free(stream);
d80a6244
DG
90}
91
92/*
93 * Delete ust app channel safely. RCU read lock must be held before calling
94 * this function.
95 */
8b366481
DG
96static
97void delete_ust_app_channel(int sock, struct ust_app_channel *ua_chan)
d80a6244
DG
98{
99 int ret;
bec39940 100 struct lttng_ht_iter iter;
d80a6244 101 struct ust_app_event *ua_event;
55cc08a6 102 struct ust_app_ctx *ua_ctx;
d80a6244
DG
103 struct ltt_ust_stream *stream, *stmp;
104
55cc08a6 105 /* Wipe stream */
d80a6244 106 cds_list_for_each_entry_safe(stream, stmp, &ua_chan->streams.head, list) {
84cd17c6 107 cds_list_del(&stream->list);
d80a6244
DG
108 delete_ust_app_stream(sock, stream);
109 }
110
55cc08a6 111 /* Wipe context */
bec39940
DG
112 cds_lfht_for_each_entry(ua_chan->ctx->ht, &iter.iter, ua_ctx, node.node) {
113 ret = lttng_ht_del(ua_chan->ctx, &iter);
55cc08a6
DG
114 assert(!ret);
115 delete_ust_app_ctx(sock, ua_ctx);
116 }
bec39940 117 lttng_ht_destroy(ua_chan->ctx);
d80a6244 118
55cc08a6 119 /* Wipe events */
bec39940
DG
120 cds_lfht_for_each_entry(ua_chan->events->ht, &iter.iter, ua_event,
121 node.node) {
122 ret = lttng_ht_del(ua_chan->events, &iter);
525b0740 123 assert(!ret);
d80a6244
DG
124 delete_ust_app_event(sock, ua_event);
125 }
bec39940 126 lttng_ht_destroy(ua_chan->events);
edb67388
DG
127
128 if (ua_chan->obj != NULL) {
129 ustctl_release_object(sock, ua_chan->obj);
130 free(ua_chan->obj);
131 }
84cd17c6 132 free(ua_chan);
d80a6244
DG
133}
134
135/*
136 * Delete ust app session safely. RCU read lock must be held before calling
137 * this function.
138 */
8b366481
DG
139static
140void delete_ust_app_session(int sock, struct ust_app_session *ua_sess)
d80a6244
DG
141{
142 int ret;
bec39940 143 struct lttng_ht_iter iter;
d80a6244
DG
144 struct ust_app_channel *ua_chan;
145
146 if (ua_sess->metadata) {
8b366481
DG
147 if (ua_sess->metadata->stream_obj) {
148 ustctl_release_object(sock, ua_sess->metadata->stream_obj);
149 free(ua_sess->metadata->stream_obj);
150 }
151 if (ua_sess->metadata->obj) {
152 ustctl_release_object(sock, ua_sess->metadata->obj);
153 free(ua_sess->metadata->obj);
154 }
d80a6244
DG
155 }
156
bec39940
DG
157 cds_lfht_for_each_entry(ua_sess->channels->ht, &iter.iter, ua_chan,
158 node.node) {
159 ret = lttng_ht_del(ua_sess->channels, &iter);
525b0740 160 assert(!ret);
d80a6244
DG
161 delete_ust_app_channel(sock, ua_chan);
162 }
bec39940 163 lttng_ht_destroy(ua_sess->channels);
d80a6244 164
aee6bafd
MD
165 if (ua_sess->handle != -1) {
166 ustctl_release_handle(sock, ua_sess->handle);
167 }
8b366481 168 free(ua_sess);
d80a6244 169}
91d76f53
DG
170
171/*
284d8f55
DG
172 * Delete a traceable application structure from the global list. Never call
173 * this function outside of a call_rcu call.
91d76f53 174 */
8b366481
DG
175static
176void delete_ust_app(struct ust_app *app)
91d76f53 177{
8b366481 178 int ret, sock;
bec39940 179 struct lttng_ht_iter iter;
284d8f55 180 struct ust_app_session *ua_sess;
44d3bd01 181
f6a9efaa 182 rcu_read_lock();
44d3bd01 183
d80a6244 184 /* Delete ust app sessions info */
6414a713
MD
185 sock = app->key.sock;
186 app->key.sock = -1;
d80a6244 187
8b366481 188 /* Wipe sessions */
bec39940
DG
189 cds_lfht_for_each_entry(app->sessions->ht, &iter.iter, ua_sess,
190 node.node) {
191 ret = lttng_ht_del(app->sessions, &iter);
525b0740 192 assert(!ret);
284d8f55 193 delete_ust_app_session(app->key.sock, ua_sess);
d80a6244 194 }
bec39940 195 lttng_ht_destroy(app->sessions);
d80a6244 196
6414a713 197 /*
bec39940
DG
198 * Wait until we have removed the key from the sock hash table before
199 * closing this socket, otherwise an application could re-use the socket ID
200 * and race with the teardown, using the same hash table entry.
6414a713
MD
201 */
202 close(sock);
d80a6244 203
284d8f55
DG
204 DBG2("UST app pid %d deleted", app->key.pid);
205 free(app);
bec39940 206
f6a9efaa 207 rcu_read_unlock();
099e26bd
DG
208}
209
210/*
f6a9efaa 211 * URCU intermediate call to delete an UST app.
099e26bd 212 */
8b366481
DG
213static
214void delete_ust_app_rcu(struct rcu_head *head)
099e26bd 215{
bec39940
DG
216 struct lttng_ht_node_ulong *node =
217 caa_container_of(head, struct lttng_ht_node_ulong, head);
f6a9efaa
DG
218 struct ust_app *app =
219 caa_container_of(node, struct ust_app, node);
220
bec39940 221 DBG3("Call RCU deleting app PID %d", app->key.pid);
f6a9efaa 222 delete_ust_app(app);
099e26bd
DG
223}
224
8b366481
DG
225/*
226 * Alloc new UST app session.
227 */
228static
229struct ust_app_session *alloc_ust_app_session(void)
230{
231 struct ust_app_session *ua_sess;
232
233 /* Init most of the default value by allocating and zeroing */
234 ua_sess = zmalloc(sizeof(struct ust_app_session));
235 if (ua_sess == NULL) {
236 PERROR("malloc");
237 goto error;
238 }
239
240 ua_sess->handle = -1;
bec39940 241 ua_sess->channels = lttng_ht_new(0, LTTNG_HT_TYPE_STRING);
8b366481
DG
242
243 return ua_sess;
244
245error:
246 return NULL;
247}
248
249/*
250 * Alloc new UST app channel.
251 */
252static
253struct ust_app_channel *alloc_ust_app_channel(char *name,
254 struct lttng_ust_channel *attr)
255{
256 struct ust_app_channel *ua_chan;
257
258 /* Init most of the default value by allocating and zeroing */
259 ua_chan = zmalloc(sizeof(struct ust_app_channel));
260 if (ua_chan == NULL) {
261 PERROR("malloc");
262 goto error;
263 }
264
265 /* Setup channel name */
266 strncpy(ua_chan->name, name, sizeof(ua_chan->name));
267 ua_chan->name[sizeof(ua_chan->name) - 1] = '\0';
268
269 ua_chan->enabled = 1;
270 ua_chan->handle = -1;
bec39940
DG
271 ua_chan->ctx = lttng_ht_new(0, LTTNG_HT_TYPE_ULONG);
272 ua_chan->events = lttng_ht_new(0, LTTNG_HT_TYPE_STRING);
273 lttng_ht_node_init_str(&ua_chan->node, ua_chan->name);
8b366481
DG
274
275 CDS_INIT_LIST_HEAD(&ua_chan->streams.head);
276
277 /* Copy attributes */
278 if (attr) {
279 memcpy(&ua_chan->attr, attr, sizeof(ua_chan->attr));
280 }
281
282 DBG3("UST app channel %s allocated", ua_chan->name);
283
284 return ua_chan;
285
286error:
287 return NULL;
288}
289
290/*
291 * Alloc new UST app event.
292 */
293static
294struct ust_app_event *alloc_ust_app_event(char *name,
295 struct lttng_ust_event *attr)
296{
297 struct ust_app_event *ua_event;
298
299 /* Init most of the default value by allocating and zeroing */
300 ua_event = zmalloc(sizeof(struct ust_app_event));
301 if (ua_event == NULL) {
302 PERROR("malloc");
303 goto error;
304 }
305
306 ua_event->enabled = 1;
307 strncpy(ua_event->name, name, sizeof(ua_event->name));
308 ua_event->name[sizeof(ua_event->name) - 1] = '\0';
bec39940
DG
309 ua_event->ctx = lttng_ht_new(0, LTTNG_HT_TYPE_ULONG);
310 lttng_ht_node_init_str(&ua_event->node, ua_event->name);
8b366481
DG
311
312 /* Copy attributes */
313 if (attr) {
314 memcpy(&ua_event->attr, attr, sizeof(ua_event->attr));
315 }
316
317 DBG3("UST app event %s allocated", ua_event->name);
318
319 return ua_event;
320
321error:
322 return NULL;
323}
324
325/*
326 * Alloc new UST app context.
327 */
328static
329struct ust_app_ctx *alloc_ust_app_ctx(struct lttng_ust_context *uctx)
330{
331 struct ust_app_ctx *ua_ctx;
332
333 ua_ctx = zmalloc(sizeof(struct ust_app_ctx));
334 if (ua_ctx == NULL) {
335 goto error;
336 }
337
338 if (uctx) {
339 memcpy(&ua_ctx->ctx, uctx, sizeof(ua_ctx->ctx));
340 }
341
342 DBG3("UST app context %d allocated", ua_ctx->ctx.ctx);
343
344error:
345 return ua_ctx;
346}
347
099e26bd 348/*
421cb601
DG
349 * Find an ust_app using the sock and return it. RCU read side lock must be
350 * held before calling this helper function.
099e26bd 351 */
8b366481
DG
352static
353struct ust_app *find_app_by_sock(int sock)
099e26bd 354{
bec39940 355 struct lttng_ht_node_ulong *node;
f6a9efaa 356 struct ust_app_key *key;
bec39940 357 struct lttng_ht_iter iter;
f6a9efaa 358
bec39940
DG
359 lttng_ht_lookup(ust_app_sock_key_map, (void *)((unsigned long) sock),
360 &iter);
361 node = lttng_ht_iter_get_node_ulong(&iter);
f6a9efaa
DG
362 if (node == NULL) {
363 DBG2("UST app find by sock %d key not found", sock);
f6a9efaa
DG
364 goto error;
365 }
f6a9efaa
DG
366 key = caa_container_of(node, struct ust_app_key, node);
367
bec39940
DG
368 lttng_ht_lookup(ust_app_ht, (void *)((unsigned long) key->pid), &iter);
369 node = lttng_ht_iter_get_node_ulong(&iter);
f6a9efaa
DG
370 if (node == NULL) {
371 DBG2("UST app find by sock %d not found", sock);
f6a9efaa
DG
372 goto error;
373 }
f6a9efaa
DG
374 return caa_container_of(node, struct ust_app, node);
375
376error:
377 return NULL;
099e26bd
DG
378}
379
55cc08a6
DG
380/*
381 * Create the channel context on the tracer.
382 */
383static
384int create_ust_channel_context(struct ust_app_channel *ua_chan,
385 struct ust_app_ctx *ua_ctx, struct ust_app *app)
386{
387 int ret;
388
389 ret = ustctl_add_context(app->key.sock, &ua_ctx->ctx,
390 ua_chan->obj, &ua_ctx->obj);
391 if (ret < 0) {
392 goto error;
393 }
394
395 ua_ctx->handle = ua_ctx->obj->handle;
396
397 DBG2("UST app context added to channel %s successfully", ua_chan->name);
398
399error:
400 return ret;
401}
402
403/*
404 * Create the event context on the tracer.
405 */
406static
407int create_ust_event_context(struct ust_app_event *ua_event,
408 struct ust_app_ctx *ua_ctx, struct ust_app *app)
409{
410 int ret;
411
412 ret = ustctl_add_context(app->key.sock, &ua_ctx->ctx,
413 ua_event->obj, &ua_ctx->obj);
414 if (ret < 0) {
415 goto error;
416 }
417
418 ua_ctx->handle = ua_ctx->obj->handle;
419
420 DBG2("UST app context added to event %s successfully", ua_event->name);
421
422error:
423 return ret;
424}
425
9730260e
DG
426/*
427 * Disable the specified event on to UST tracer for the UST session.
428 */
429static int disable_ust_event(struct ust_app *app,
430 struct ust_app_session *ua_sess, struct ust_app_event *ua_event)
431{
432 int ret;
433
434 ret = ustctl_disable(app->key.sock, ua_event->obj);
435 if (ret < 0) {
436 ERR("UST app event %s disable failed for app (pid: %d) "
437 "and session handle %d with ret %d",
438 ua_event->attr.name, app->key.pid, ua_sess->handle, ret);
439 goto error;
440 }
441
442 DBG2("UST app event %s disabled successfully for app (pid: %d)",
443 ua_event->attr.name, app->key.pid);
444
445error:
446 return ret;
447}
448
78f0bacd
DG
449/*
450 * Disable the specified channel on to UST tracer for the UST session.
451 */
452static int disable_ust_channel(struct ust_app *app,
453 struct ust_app_session *ua_sess, struct ust_app_channel *ua_chan)
454{
455 int ret;
456
457 ret = ustctl_disable(app->key.sock, ua_chan->obj);
458 if (ret < 0) {
459 ERR("UST app channel %s disable failed for app (pid: %d) "
460 "and session handle %d with ret %d",
461 ua_chan->name, app->key.pid, ua_sess->handle, ret);
462 goto error;
463 }
464
78f0bacd
DG
465 DBG2("UST app channel %s disabled successfully for app (pid: %d)",
466 ua_chan->name, app->key.pid);
467
468error:
469 return ret;
470}
471
472/*
473 * Enable the specified channel on to UST tracer for the UST session.
474 */
475static int enable_ust_channel(struct ust_app *app,
476 struct ust_app_session *ua_sess, struct ust_app_channel *ua_chan)
477{
478 int ret;
479
480 ret = ustctl_enable(app->key.sock, ua_chan->obj);
481 if (ret < 0) {
482 ERR("UST app channel %s enable failed for app (pid: %d) "
483 "and session handle %d with ret %d",
484 ua_chan->name, app->key.pid, ua_sess->handle, ret);
485 goto error;
486 }
487
488 ua_chan->enabled = 1;
489
490 DBG2("UST app channel %s enabled successfully for app (pid: %d)",
491 ua_chan->name, app->key.pid);
492
493error:
494 return ret;
495}
496
edb67388
DG
497/*
498 * Enable the specified event on to UST tracer for the UST session.
499 */
500static int enable_ust_event(struct ust_app *app,
501 struct ust_app_session *ua_sess, struct ust_app_event *ua_event)
502{
503 int ret;
504
505 ret = ustctl_enable(app->key.sock, ua_event->obj);
506 if (ret < 0) {
507 ERR("UST app event %s enable failed for app (pid: %d) "
508 "and session handle %d with ret %d",
509 ua_event->attr.name, app->key.pid, ua_sess->handle, ret);
510 goto error;
511 }
512
513 DBG2("UST app event %s enabled successfully for app (pid: %d)",
514 ua_event->attr.name, app->key.pid);
515
516error:
517 return ret;
518}
519
099e26bd 520/*
5b4a0ec0 521 * Open metadata onto the UST tracer for a UST session.
0177d773 522 */
5b4a0ec0
DG
523static int open_ust_metadata(struct ust_app *app,
524 struct ust_app_session *ua_sess)
0177d773 525{
5b4a0ec0
DG
526 int ret;
527 struct lttng_ust_channel_attr uattr;
0177d773 528
5b4a0ec0
DG
529 uattr.overwrite = ua_sess->metadata->attr.overwrite;
530 uattr.subbuf_size = ua_sess->metadata->attr.subbuf_size;
531 uattr.num_subbuf = ua_sess->metadata->attr.num_subbuf;
532 uattr.switch_timer_interval =
533 ua_sess->metadata->attr.switch_timer_interval;
534 uattr.read_timer_interval =
535 ua_sess->metadata->attr.read_timer_interval;
536 uattr.output = ua_sess->metadata->attr.output;
537
538 /* UST tracer metadata creation */
539 ret = ustctl_open_metadata(app->key.sock, ua_sess->handle, &uattr,
540 &ua_sess->metadata->obj);
541 if (ret < 0) {
fc34caaa
DG
542 ERR("UST app open metadata failed for app pid:%d with ret %d",
543 app->key.pid, ret);
f6a9efaa 544 goto error;
0177d773 545 }
f6a9efaa 546
6d3686da
DG
547 ua_sess->metadata->handle = ua_sess->metadata->obj->handle;
548
f6a9efaa 549error:
5b4a0ec0 550 return ret;
91d76f53
DG
551}
552
553/*
5b4a0ec0 554 * Create stream onto the UST tracer for a UST session.
91d76f53 555 */
5b4a0ec0
DG
556static int create_ust_stream(struct ust_app *app,
557 struct ust_app_session *ua_sess)
91d76f53 558{
5b4a0ec0 559 int ret;
421cb601 560
5b4a0ec0
DG
561 ret = ustctl_create_stream(app->key.sock, ua_sess->metadata->obj,
562 &ua_sess->metadata->stream_obj);
563 if (ret < 0) {
564 ERR("UST create metadata stream failed");
421cb601 565 goto error;
91d76f53 566 }
421cb601 567
421cb601 568error:
5b4a0ec0 569 return ret;
91d76f53
DG
570}
571
b551a063 572/*
5b4a0ec0 573 * Create the specified channel onto the UST tracer for a UST session.
b551a063 574 */
5b4a0ec0
DG
575static int create_ust_channel(struct ust_app *app,
576 struct ust_app_session *ua_sess, struct ust_app_channel *ua_chan)
b551a063 577{
5b4a0ec0 578 int ret;
b551a063 579
5b4a0ec0
DG
580 /* TODO: remove cast and use lttng-ust-abi.h */
581 ret = ustctl_create_channel(app->key.sock, ua_sess->handle,
582 (struct lttng_ust_channel_attr *)&ua_chan->attr, &ua_chan->obj);
583 if (ret < 0) {
58f3ca76 584 ERR("Creating channel %s for app (pid: %d, sock: %d) "
5b4a0ec0
DG
585 "and session handle %d with ret %d",
586 ua_chan->name, app->key.pid, app->key.sock,
587 ua_sess->handle, ret);
b551a063
DG
588 goto error;
589 }
590
5b4a0ec0 591 ua_chan->handle = ua_chan->obj->handle;
b551a063 592
5b4a0ec0
DG
593 DBG2("UST app channel %s created successfully for pid:%d and sock:%d",
594 ua_chan->name, app->key.pid, app->key.sock);
b551a063 595
8535a6d9
DG
596 /* If channel is not enabled, disable it on the tracer */
597 if (!ua_chan->enabled) {
598 ret = disable_ust_channel(app, ua_sess, ua_chan);
599 if (ret < 0) {
600 goto error;
601 }
602 }
603
b551a063
DG
604error:
605 return ret;
606}
607
91d76f53 608/*
5b4a0ec0 609 * Create the specified event onto the UST tracer for a UST session.
91d76f53 610 */
edb67388
DG
611static
612int create_ust_event(struct ust_app *app, struct ust_app_session *ua_sess,
613 struct ust_app_channel *ua_chan, struct ust_app_event *ua_event)
91d76f53 614{
5b4a0ec0 615 int ret = 0;
284d8f55 616
5b4a0ec0
DG
617 /* Create UST event on tracer */
618 ret = ustctl_create_event(app->key.sock, &ua_event->attr, ua_chan->obj,
619 &ua_event->obj);
620 if (ret < 0) {
fc34caaa
DG
621 if (ret == -EEXIST) {
622 ret = 0;
623 goto error;
624 }
5b4a0ec0
DG
625 ERR("Error ustctl create event %s for app pid: %d with ret %d",
626 ua_event->attr.name, app->key.pid, ret);
627 goto error;
91d76f53 628 }
f6a9efaa 629
5b4a0ec0 630 ua_event->handle = ua_event->obj->handle;
284d8f55 631
5b4a0ec0
DG
632 DBG2("UST app event %s created successfully for pid:%d",
633 ua_event->attr.name, app->key.pid);
f6a9efaa 634
8535a6d9 635 /* If event not enabled, disable it on the tracer */
fc34caaa 636 if (ua_event->enabled == 0) {
8535a6d9
DG
637 ret = disable_ust_event(app, ua_sess, ua_event);
638 if (ret < 0) {
fc34caaa
DG
639 /*
640 * If we hit an EPERM, something is wrong with our disable call. If
641 * we get an EEXIST, there is a problem on the tracer side since we
642 * just created it.
643 */
644 switch (ret) {
645 case -EPERM:
646 /* Code flow problem */
647 assert(0);
648 case -EEXIST:
649 /* It's OK for our use case. */
650 ret = 0;
651 break;
652 default:
653 break;
654 }
8535a6d9
DG
655 goto error;
656 }
657 }
658
5b4a0ec0
DG
659error:
660 return ret;
91d76f53 661}
48842b30 662
5b4a0ec0
DG
663/*
664 * Copy data between an UST app event and a LTT event.
665 */
421cb601 666static void shadow_copy_event(struct ust_app_event *ua_event,
48842b30
DG
667 struct ltt_ust_event *uevent)
668{
bec39940 669 struct lttng_ht_iter iter;
55cc08a6
DG
670 struct ltt_ust_context *uctx;
671 struct ust_app_ctx *ua_ctx;
672
48842b30
DG
673 strncpy(ua_event->name, uevent->attr.name, sizeof(ua_event->name));
674 ua_event->name[sizeof(ua_event->name) - 1] = '\0';
675
fc34caaa
DG
676 ua_event->enabled = uevent->enabled;
677
5b4a0ec0
DG
678 /* Copy event attributes */
679 memcpy(&ua_event->attr, &uevent->attr, sizeof(ua_event->attr));
680
bec39940 681 cds_lfht_for_each_entry(uevent->ctx->ht, &iter.iter, uctx, node.node) {
55cc08a6
DG
682 ua_ctx = alloc_ust_app_ctx(&uctx->ctx);
683 if (ua_ctx == NULL) {
fc34caaa
DG
684 /* malloc() failed. We should simply stop */
685 return;
55cc08a6 686 }
fc34caaa 687
bec39940
DG
688 lttng_ht_node_init_ulong(&ua_ctx->node,
689 (unsigned long) ua_ctx->ctx.ctx);
690 lttng_ht_add_unique_ulong(ua_event->ctx, &ua_ctx->node);
55cc08a6 691 }
48842b30
DG
692}
693
5b4a0ec0
DG
694/*
695 * Copy data between an UST app channel and a LTT channel.
696 */
421cb601 697static void shadow_copy_channel(struct ust_app_channel *ua_chan,
48842b30
DG
698 struct ltt_ust_channel *uchan)
699{
bec39940
DG
700 struct lttng_ht_iter iter;
701 struct lttng_ht_node_str *ua_event_node;
48842b30 702 struct ltt_ust_event *uevent;
55cc08a6 703 struct ltt_ust_context *uctx;
48842b30 704 struct ust_app_event *ua_event;
55cc08a6 705 struct ust_app_ctx *ua_ctx;
48842b30 706
fc34caaa 707 DBG2("UST app shadow copy of channel %s started", ua_chan->name);
48842b30
DG
708
709 strncpy(ua_chan->name, uchan->name, sizeof(ua_chan->name));
710 ua_chan->name[sizeof(ua_chan->name) - 1] = '\0';
5b4a0ec0
DG
711 /* Copy event attributes */
712 memcpy(&ua_chan->attr, &uchan->attr, sizeof(ua_chan->attr));
48842b30 713
fc34caaa
DG
714 ua_chan->enabled = uchan->enabled;
715
bec39940 716 cds_lfht_for_each_entry(uchan->ctx->ht, &iter.iter, uctx, node.node) {
55cc08a6
DG
717 ua_ctx = alloc_ust_app_ctx(&uctx->ctx);
718 if (ua_ctx == NULL) {
719 continue;
720 }
bec39940
DG
721 lttng_ht_node_init_ulong(&ua_ctx->node,
722 (unsigned long) ua_ctx->ctx.ctx);
723 lttng_ht_add_unique_ulong(ua_chan->ctx, &ua_ctx->node);
55cc08a6 724 }
48842b30 725
421cb601 726 /* Copy all events from ltt ust channel to ust app channel */
bec39940
DG
727 cds_lfht_for_each_entry(uchan->events->ht, &iter.iter, uevent, node.node) {
728 struct lttng_ht_iter uiter;
ba767faf 729
bec39940
DG
730 lttng_ht_lookup(ua_chan->events, (void *) uevent->attr.name, &uiter);
731 ua_event_node = lttng_ht_iter_get_node_str(&uiter);
48842b30 732 if (ua_event_node == NULL) {
421cb601 733 DBG2("UST event %s not found on shadow copy channel",
48842b30 734 uevent->attr.name);
284d8f55 735 ua_event = alloc_ust_app_event(uevent->attr.name, &uevent->attr);
48842b30 736 if (ua_event == NULL) {
5b4a0ec0 737 continue;
48842b30 738 }
421cb601 739 shadow_copy_event(ua_event, uevent);
bec39940 740 lttng_ht_add_unique_str(ua_chan->events, &ua_event->node);
48842b30 741 }
48842b30
DG
742 }
743
fc34caaa 744 DBG3("UST app shadow copy of channel %s done", ua_chan->name);
48842b30
DG
745}
746
5b4a0ec0
DG
747/*
748 * Copy data between a UST app session and a regular LTT session.
749 */
421cb601 750static void shadow_copy_session(struct ust_app_session *ua_sess,
bec39940 751 struct ltt_ust_session *usess, struct ust_app *app)
48842b30 752{
bec39940
DG
753 struct lttng_ht_node_str *ua_chan_node;
754 struct lttng_ht_iter iter;
48842b30
DG
755 struct ltt_ust_channel *uchan;
756 struct ust_app_channel *ua_chan;
477d7741
MD
757 time_t rawtime;
758 struct tm *timeinfo;
759 char datetime[16];
760 int ret;
761
762 /* Get date and time for unique app path */
763 time(&rawtime);
764 timeinfo = localtime(&rawtime);
765 strftime(datetime, sizeof(datetime), "%Y%m%d-%H%M%S", timeinfo);
48842b30 766
421cb601 767 DBG2("Shadow copy of session handle %d", ua_sess->handle);
48842b30 768
a991f516 769 ua_sess->id = usess->id;
6df2e2c9
MD
770 ua_sess->uid = usess->uid;
771 ua_sess->gid = usess->gid;
48842b30 772
fc34caaa
DG
773 ret = snprintf(ua_sess->path, PATH_MAX, "%s/%s-%d-%s", usess->pathname,
774 app->name, app->key.pid, datetime);
477d7741
MD
775 if (ret < 0) {
776 PERROR("asprintf UST shadow copy session");
777 /* TODO: We cannot return an error from here.. */
778 assert(0);
779 }
780
48842b30
DG
781 /* TODO: support all UST domain */
782
783 /* Iterate over all channels in global domain. */
bec39940
DG
784 cds_lfht_for_each_entry(usess->domain_global.channels->ht, &iter.iter,
785 uchan, node.node) {
786 struct lttng_ht_iter uiter;
ba767faf 787
bec39940
DG
788 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
789 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
5b4a0ec0 790 if (ua_chan_node != NULL) {
fc34caaa 791 /* Session exist. Contiuing. */
5b4a0ec0
DG
792 continue;
793 }
421cb601 794
5b4a0ec0
DG
795 DBG2("Channel %s not found on shadow session copy, creating it",
796 uchan->name);
797 ua_chan = alloc_ust_app_channel(uchan->name, &uchan->attr);
798 if (ua_chan == NULL) {
fc34caaa 799 /* malloc failed FIXME: Might want to do handle ENOMEM .. */
5b4a0ec0 800 continue;
48842b30
DG
801 }
802
5b4a0ec0 803 shadow_copy_channel(ua_chan, uchan);
bec39940 804 lttng_ht_add_unique_str(ua_sess->channels, &ua_chan->node);
48842b30
DG
805 }
806}
807
78f0bacd
DG
808/*
809 * Lookup sesison wrapper.
810 */
84cd17c6
MD
811static
812void __lookup_session_by_app(struct ltt_ust_session *usess,
bec39940 813 struct ust_app *app, struct lttng_ht_iter *iter)
84cd17c6
MD
814{
815 /* Get right UST app session from app */
2c348c10 816 lttng_ht_lookup(app->sessions, (void *)((unsigned long) usess->id), iter);
84cd17c6
MD
817}
818
421cb601
DG
819/*
820 * Return ust app session from the app session hashtable using the UST session
a991f516 821 * id.
421cb601 822 */
48842b30
DG
823static struct ust_app_session *lookup_session_by_app(
824 struct ltt_ust_session *usess, struct ust_app *app)
825{
bec39940
DG
826 struct lttng_ht_iter iter;
827 struct lttng_ht_node_ulong *node;
48842b30 828
84cd17c6 829 __lookup_session_by_app(usess, app, &iter);
bec39940 830 node = lttng_ht_iter_get_node_ulong(&iter);
48842b30
DG
831 if (node == NULL) {
832 goto error;
833 }
834
835 return caa_container_of(node, struct ust_app_session, node);
836
837error:
838 return NULL;
839}
840
421cb601
DG
841/*
842 * Create a UST session onto the tracer of app and add it the session
843 * hashtable.
844 *
845 * Return ust app session or NULL on error.
846 */
847static struct ust_app_session *create_ust_app_session(
848 struct ltt_ust_session *usess, struct ust_app *app)
849{
850 int ret;
851 struct ust_app_session *ua_sess;
852
853 ua_sess = lookup_session_by_app(usess, app);
854 if (ua_sess == NULL) {
a991f516
MD
855 DBG2("UST app pid: %d session id %d not found, creating it",
856 app->key.pid, usess->id);
421cb601
DG
857 ua_sess = alloc_ust_app_session();
858 if (ua_sess == NULL) {
859 /* Only malloc can failed so something is really wrong */
fc34caaa 860 goto end;
421cb601 861 }
477d7741 862 shadow_copy_session(ua_sess, usess, app);
421cb601
DG
863 }
864
865 if (ua_sess->handle == -1) {
866 ret = ustctl_create_session(app->key.sock);
867 if (ret < 0) {
fc34caaa 868 ERR("Creating session for app pid %d", app->key.pid);
421cb601
DG
869 goto error;
870 }
871
421cb601
DG
872 ua_sess->handle = ret;
873
874 /* Add ust app session to app's HT */
2c348c10 875 lttng_ht_node_init_ulong(&ua_sess->node, (unsigned long) ua_sess->id);
bec39940 876 lttng_ht_add_unique_ulong(app->sessions, &ua_sess->node);
421cb601
DG
877
878 DBG2("UST app session created successfully with handle %d", ret);
879 }
880
fc34caaa 881end:
421cb601
DG
882 return ua_sess;
883
884error:
fc34caaa 885 delete_ust_app_session(-1, ua_sess);
421cb601
DG
886 return NULL;
887}
888
55cc08a6
DG
889/*
890 * Create a context for the channel on the tracer.
891 */
892static
893int create_ust_app_channel_context(struct ust_app_session *ua_sess,
894 struct ust_app_channel *ua_chan, struct lttng_ust_context *uctx,
895 struct ust_app *app)
896{
897 int ret = 0;
bec39940
DG
898 struct lttng_ht_iter iter;
899 struct lttng_ht_node_ulong *node;
55cc08a6
DG
900 struct ust_app_ctx *ua_ctx;
901
902 DBG2("UST app adding context to channel %s", ua_chan->name);
903
bec39940
DG
904 lttng_ht_lookup(ua_chan->ctx, (void *)((unsigned long)uctx->ctx), &iter);
905 node = lttng_ht_iter_get_node_ulong(&iter);
55cc08a6
DG
906 if (node != NULL) {
907 ret = -EEXIST;
908 goto error;
909 }
910
911 ua_ctx = alloc_ust_app_ctx(uctx);
912 if (ua_ctx == NULL) {
913 /* malloc failed */
914 ret = -1;
915 goto error;
916 }
917
bec39940
DG
918 lttng_ht_node_init_ulong(&ua_ctx->node, (unsigned long) ua_ctx->ctx.ctx);
919 lttng_ht_add_unique_ulong(ua_chan->ctx, &ua_ctx->node);
55cc08a6
DG
920
921 ret = create_ust_channel_context(ua_chan, ua_ctx, app);
922 if (ret < 0) {
923 goto error;
924 }
925
926error:
927 return ret;
928}
929
930/*
931 * Create an UST context and enable it for the event on the tracer.
932 */
933static
934int create_ust_app_event_context(struct ust_app_session *ua_sess,
935 struct ust_app_event *ua_event, struct lttng_ust_context *uctx,
936 struct ust_app *app)
937{
938 int ret = 0;
bec39940
DG
939 struct lttng_ht_iter iter;
940 struct lttng_ht_node_ulong *node;
55cc08a6
DG
941 struct ust_app_ctx *ua_ctx;
942
943 DBG2("UST app adding context to event %s", ua_event->name);
944
bec39940
DG
945 lttng_ht_lookup(ua_event->ctx, (void *)((unsigned long)uctx->ctx), &iter);
946 node = lttng_ht_iter_get_node_ulong(&iter);
55cc08a6
DG
947 if (node != NULL) {
948 ret = -EEXIST;
949 goto error;
950 }
951
952 ua_ctx = alloc_ust_app_ctx(uctx);
953 if (ua_ctx == NULL) {
954 /* malloc failed */
955 ret = -1;
956 goto error;
957 }
958
bec39940
DG
959 lttng_ht_node_init_ulong(&ua_ctx->node, (unsigned long) ua_ctx->ctx.ctx);
960 lttng_ht_add_unique_ulong(ua_event->ctx, &ua_ctx->node);
55cc08a6
DG
961
962 ret = create_ust_event_context(ua_event, ua_ctx, app);
963 if (ret < 0) {
964 goto error;
965 }
966
967error:
968 return ret;
969}
970
edb67388
DG
971/*
972 * Enable on the tracer side a ust app event for the session and channel.
973 */
974static
975int enable_ust_app_event(struct ust_app_session *ua_sess,
35a9059d 976 struct ust_app_event *ua_event, struct ust_app *app)
edb67388
DG
977{
978 int ret;
979
980 ret = enable_ust_event(app, ua_sess, ua_event);
981 if (ret < 0) {
982 goto error;
983 }
984
985 ua_event->enabled = 1;
986
987error:
988 return ret;
989}
990
9730260e
DG
991/*
992 * Disable on the tracer side a ust app event for the session and channel.
993 */
994static int disable_ust_app_event(struct ust_app_session *ua_sess,
7f79d3a1 995 struct ust_app_event *ua_event, struct ust_app *app)
9730260e
DG
996{
997 int ret;
998
999 ret = disable_ust_event(app, ua_sess, ua_event);
1000 if (ret < 0) {
1001 goto error;
1002 }
1003
1004 ua_event->enabled = 0;
1005
1006error:
1007 return ret;
1008}
1009
78f0bacd
DG
1010/*
1011 * Lookup ust app channel for session and disable it on the tracer side.
1012 */
8535a6d9
DG
1013static
1014int disable_ust_app_channel(struct ust_app_session *ua_sess,
1015 struct ust_app_channel *ua_chan, struct ust_app *app)
78f0bacd 1016{
8535a6d9 1017 int ret;
78f0bacd
DG
1018
1019 ret = disable_ust_channel(app, ua_sess, ua_chan);
1020 if (ret < 0) {
1021 goto error;
1022 }
1023
8535a6d9
DG
1024 ua_chan->enabled = 0;
1025
78f0bacd
DG
1026error:
1027 return ret;
1028}
1029
1030/*
1031 * Lookup ust app channel for session and enable it on the tracer side.
1032 */
1033static int enable_ust_app_channel(struct ust_app_session *ua_sess,
1034 struct ltt_ust_channel *uchan, struct ust_app *app)
1035{
1036 int ret = 0;
bec39940
DG
1037 struct lttng_ht_iter iter;
1038 struct lttng_ht_node_str *ua_chan_node;
78f0bacd
DG
1039 struct ust_app_channel *ua_chan;
1040
bec39940
DG
1041 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &iter);
1042 ua_chan_node = lttng_ht_iter_get_node_str(&iter);
78f0bacd 1043 if (ua_chan_node == NULL) {
a991f516
MD
1044 DBG2("Unable to find channel %s in ust session id %u",
1045 uchan->name, ua_sess->id);
78f0bacd
DG
1046 goto error;
1047 }
1048
1049 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
1050
1051 ret = enable_ust_channel(app, ua_sess, ua_chan);
1052 if (ret < 0) {
1053 goto error;
1054 }
1055
1056error:
1057 return ret;
1058}
1059
284d8f55 1060/*
5b4a0ec0 1061 * Create UST app channel and create it on the tracer.
284d8f55 1062 */
5b4a0ec0
DG
1063static struct ust_app_channel *create_ust_app_channel(
1064 struct ust_app_session *ua_sess, struct ltt_ust_channel *uchan,
1065 struct ust_app *app)
1066{
1067 int ret = 0;
bec39940
DG
1068 struct lttng_ht_iter iter;
1069 struct lttng_ht_node_str *ua_chan_node;
5b4a0ec0
DG
1070 struct ust_app_channel *ua_chan;
1071
1072 /* Lookup channel in the ust app session */
bec39940
DG
1073 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &iter);
1074 ua_chan_node = lttng_ht_iter_get_node_str(&iter);
fc34caaa 1075 if (ua_chan_node != NULL) {
5b4a0ec0 1076 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
fc34caaa 1077 goto end;
5b4a0ec0
DG
1078 }
1079
fc34caaa
DG
1080 ua_chan = alloc_ust_app_channel(uchan->name, &uchan->attr);
1081 if (ua_chan == NULL) {
1082 /* Only malloc can fail here */
1083 goto error;
1084 }
1085 shadow_copy_channel(ua_chan, uchan);
1086
5b4a0ec0
DG
1087 ret = create_ust_channel(app, ua_sess, ua_chan);
1088 if (ret < 0) {
fc34caaa
DG
1089 /* Not found previously means that it does not exist on the tracer */
1090 assert(ret != -EEXIST);
5b4a0ec0
DG
1091 goto error;
1092 }
1093
58f3ca76
DG
1094 lttng_ht_add_unique_str(ua_sess->channels, &ua_chan->node);
1095
fc34caaa
DG
1096 DBG2("UST app create channel %s for PID %d completed", ua_chan->name,
1097 app->key.pid);
1098
1099end:
5b4a0ec0
DG
1100 return ua_chan;
1101
1102error:
fc34caaa 1103 delete_ust_app_channel(-1, ua_chan);
5b4a0ec0
DG
1104 return NULL;
1105}
1106
1107/*
1108 * Create UST app event and create it on the tracer side.
1109 */
edb67388
DG
1110static
1111int create_ust_app_event(struct ust_app_session *ua_sess,
1112 struct ust_app_channel *ua_chan, struct ltt_ust_event *uevent,
1113 struct ust_app *app)
284d8f55 1114{
edb67388 1115 int ret = 0;
bec39940
DG
1116 struct lttng_ht_iter iter;
1117 struct lttng_ht_node_str *ua_event_node;
5b4a0ec0 1118 struct ust_app_event *ua_event;
284d8f55 1119
5b4a0ec0 1120 /* Get event node */
bec39940
DG
1121 lttng_ht_lookup(ua_chan->events, (void *)uevent->attr.name, &iter);
1122 ua_event_node = lttng_ht_iter_get_node_str(&iter);
edb67388 1123 if (ua_event_node != NULL) {
fc34caaa 1124 ret = -EEXIST;
edb67388
DG
1125 goto end;
1126 }
5b4a0ec0 1127
edb67388
DG
1128 /* Does not exist so create one */
1129 ua_event = alloc_ust_app_event(uevent->attr.name, &uevent->attr);
1130 if (ua_event == NULL) {
1131 /* Only malloc can failed so something is really wrong */
1132 ret = -ENOMEM;
fc34caaa 1133 goto end;
5b4a0ec0 1134 }
edb67388 1135 shadow_copy_event(ua_event, uevent);
5b4a0ec0 1136
edb67388 1137 /* Create it on the tracer side */
5b4a0ec0 1138 ret = create_ust_event(app, ua_sess, ua_chan, ua_event);
284d8f55 1139 if (ret < 0) {
fc34caaa
DG
1140 /* Not found previously means that it does not exist on the tracer */
1141 assert(ret != -EEXIST);
284d8f55
DG
1142 goto error;
1143 }
1144
bec39940 1145 lttng_ht_add_unique_str(ua_chan->events, &ua_event->node);
284d8f55 1146
fc34caaa
DG
1147 DBG2("UST app create event %s for PID %d completed", ua_event->name,
1148 app->key.pid);
7f79d3a1 1149
edb67388 1150end:
fc34caaa
DG
1151 return ret;
1152
5b4a0ec0 1153error:
fc34caaa
DG
1154 /* Valid. Calling here is already in a read side lock */
1155 delete_ust_app_event(-1, ua_event);
edb67388 1156 return ret;
5b4a0ec0
DG
1157}
1158
1159/*
1160 * Create UST metadata and open it on the tracer side.
1161 */
1162static int create_ust_app_metadata(struct ust_app_session *ua_sess,
1163 char *pathname, struct ust_app *app)
1164{
1165 int ret = 0;
1166
1167 if (ua_sess->metadata == NULL) {
1168 /* Allocate UST metadata */
1169 ua_sess->metadata = trace_ust_create_metadata(pathname);
1170 if (ua_sess->metadata == NULL) {
fc34caaa 1171 /* malloc() failed */
5b4a0ec0
DG
1172 goto error;
1173 }
1174
1175 ret = open_ust_metadata(app, ua_sess);
1176 if (ret < 0) {
7db205b5
DG
1177 DBG3("Opening metadata failed. Cleaning up memory");
1178
fc34caaa
DG
1179 /* Cleanup failed metadata struct */
1180 free(ua_sess->metadata);
7db205b5
DG
1181 /*
1182 * This is very important because delete_ust_app_session check if
1183 * the pointer is null or not in order to delete the metadata.
1184 */
1185 ua_sess->metadata = NULL;
5b4a0ec0
DG
1186 goto error;
1187 }
1188
1189 DBG2("UST metadata opened for app pid %d", app->key.pid);
1190 }
1191
1192 /* Open UST metadata stream */
1193 if (ua_sess->metadata->stream_obj == NULL) {
1194 ret = create_ust_stream(app, ua_sess);
1195 if (ret < 0) {
1196 goto error;
1197 }
1198
e11d277b 1199 ret = run_as_mkdir(ua_sess->path, S_IRWXU | S_IRWXG,
67f747d8 1200 ua_sess->uid, ua_sess->gid);
5b4a0ec0
DG
1201 if (ret < 0) {
1202 PERROR("mkdir UST metadata");
1203 goto error;
1204 }
1205
477d7741
MD
1206 ret = snprintf(ua_sess->metadata->pathname, PATH_MAX,
1207 "%s/metadata", ua_sess->path);
5b4a0ec0
DG
1208 if (ret < 0) {
1209 PERROR("asprintf UST create stream");
1210 goto error;
1211 }
1212
1213 DBG2("UST metadata stream object created for app pid %d",
1214 app->key.pid);
1215 } else {
1216 ERR("Attempting to create stream without metadata opened");
1217 goto error;
1218 }
1219
1220 return 0;
1221
1222error:
1223 return -1;
1224}
1225
1226/*
1227 * Return pointer to traceable apps list.
1228 */
bec39940 1229struct lttng_ht *ust_app_get_ht(void)
5b4a0ec0
DG
1230{
1231 return ust_app_ht;
1232}
1233
1234/*
1235 * Return ust app pointer or NULL if not found.
1236 */
1237struct ust_app *ust_app_find_by_pid(pid_t pid)
1238{
bec39940
DG
1239 struct lttng_ht_node_ulong *node;
1240 struct lttng_ht_iter iter;
5b4a0ec0
DG
1241
1242 rcu_read_lock();
bec39940
DG
1243 lttng_ht_lookup(ust_app_ht, (void *)((unsigned long) pid), &iter);
1244 node = lttng_ht_iter_get_node_ulong(&iter);
5b4a0ec0
DG
1245 if (node == NULL) {
1246 DBG2("UST app no found with pid %d", pid);
1247 goto error;
1248 }
1249 rcu_read_unlock();
1250
1251 DBG2("Found UST app by pid %d", pid);
1252
1253 return caa_container_of(node, struct ust_app, node);
1254
1255error:
1256 rcu_read_unlock();
1257 return NULL;
1258}
1259
1260/*
1261 * Using pid and uid (of the app), allocate a new ust_app struct and
1262 * add it to the global traceable app list.
1263 *
0df502fd
MD
1264 * On success, return 0, else return malloc -ENOMEM, or -EINVAL if app
1265 * bitness is not supported.
5b4a0ec0
DG
1266 */
1267int ust_app_register(struct ust_register_msg *msg, int sock)
1268{
1269 struct ust_app *lta;
1270
7753dea8
MD
1271 if ((msg->bits_per_long == 64 && ust_consumerd64_fd == -EINVAL)
1272 || (msg->bits_per_long == 32 && ust_consumerd32_fd == -EINVAL)) {
f943b0fb 1273 ERR("Registration failed: application \"%s\" (pid: %d) has "
7753dea8
MD
1274 "%d-bit long, but no consumerd for this long size is available.\n",
1275 msg->name, msg->pid, msg->bits_per_long);
88ff5b7f 1276 close(sock);
0df502fd
MD
1277 return -EINVAL;
1278 }
5b4a0ec0
DG
1279 lta = zmalloc(sizeof(struct ust_app));
1280 if (lta == NULL) {
1281 PERROR("malloc");
1282 return -ENOMEM;
1283 }
1284
1285 lta->ppid = msg->ppid;
1286 lta->uid = msg->uid;
1287 lta->gid = msg->gid;
7753dea8 1288 lta->bits_per_long = msg->bits_per_long;
5b4a0ec0
DG
1289 lta->v_major = msg->major;
1290 lta->v_minor = msg->minor;
1291 strncpy(lta->name, msg->name, sizeof(lta->name));
1292 lta->name[16] = '\0';
bec39940 1293 lta->sessions = lttng_ht_new(0, LTTNG_HT_TYPE_ULONG);
5b4a0ec0
DG
1294
1295 /* Set key map */
1296 lta->key.pid = msg->pid;
bec39940 1297 lttng_ht_node_init_ulong(&lta->node, (unsigned long)lta->key.pid);
5b4a0ec0 1298 lta->key.sock = sock;
bec39940 1299 lttng_ht_node_init_ulong(&lta->key.node, (unsigned long)lta->key.sock);
5b4a0ec0
DG
1300
1301 rcu_read_lock();
bec39940
DG
1302 lttng_ht_add_unique_ulong(ust_app_sock_key_map, &lta->key.node);
1303 lttng_ht_add_unique_ulong(ust_app_ht, &lta->node);
5b4a0ec0
DG
1304 rcu_read_unlock();
1305
1306 DBG("App registered with pid:%d ppid:%d uid:%d gid:%d sock:%d name:%s"
1307 " (version %d.%d)", lta->key.pid, lta->ppid, lta->uid, lta->gid,
1308 lta->key.sock, lta->name, lta->v_major, lta->v_minor);
1309
1310 return 0;
1311}
1312
1313/*
1314 * Unregister app by removing it from the global traceable app list and freeing
1315 * the data struct.
1316 *
1317 * The socket is already closed at this point so no close to sock.
1318 */
1319void ust_app_unregister(int sock)
1320{
1321 struct ust_app *lta;
bec39940
DG
1322 struct lttng_ht_node_ulong *node;
1323 struct lttng_ht_iter iter;
525b0740 1324 int ret;
5b4a0ec0
DG
1325
1326 rcu_read_lock();
1327 lta = find_app_by_sock(sock);
1328 if (lta == NULL) {
1329 ERR("Unregister app sock %d not found!", sock);
1330 goto error;
1331 }
1332
1333 DBG("PID %d unregistering with sock %d", lta->key.pid, sock);
1334
886459c6
MD
1335 /* Remove application from socket hash table */
1336 lttng_ht_lookup(ust_app_sock_key_map, (void *)((unsigned long) sock), &iter);
1337 ret = lttng_ht_del(ust_app_sock_key_map, &iter);
1338 assert(!ret);
1339
5b4a0ec0 1340 /* Get the node reference for a call_rcu */
bec39940
DG
1341 lttng_ht_lookup(ust_app_ht, (void *)((unsigned long) lta->key.pid), &iter);
1342 node = lttng_ht_iter_get_node_ulong(&iter);
5b4a0ec0
DG
1343 if (node == NULL) {
1344 ERR("Unable to find app sock %d by pid %d", sock, lta->key.pid);
1345 goto error;
1346 }
284d8f55 1347
886459c6 1348 /* Remove application from PID hash table */
bec39940 1349 ret = lttng_ht_del(ust_app_ht, &iter);
525b0740 1350 assert(!ret);
5b4a0ec0 1351 call_rcu(&node->head, delete_ust_app_rcu);
284d8f55 1352error:
5b4a0ec0
DG
1353 rcu_read_unlock();
1354 return;
284d8f55
DG
1355}
1356
1357/*
5b4a0ec0 1358 * Return traceable_app_count
284d8f55 1359 */
5b4a0ec0 1360unsigned long ust_app_list_count(void)
284d8f55 1361{
5b4a0ec0 1362 unsigned long count;
284d8f55 1363
5b4a0ec0 1364 rcu_read_lock();
bec39940 1365 count = lttng_ht_get_count(ust_app_ht);
5b4a0ec0 1366 rcu_read_unlock();
284d8f55 1367
5b4a0ec0 1368 return count;
284d8f55
DG
1369}
1370
5b4a0ec0
DG
1371/*
1372 * Fill events array with all events name of all registered apps.
1373 */
1374int ust_app_list_events(struct lttng_event **events)
421cb601 1375{
5b4a0ec0
DG
1376 int ret, handle;
1377 size_t nbmem, count = 0;
bec39940 1378 struct lttng_ht_iter iter;
5b4a0ec0
DG
1379 struct ust_app *app;
1380 struct lttng_event *tmp;
421cb601 1381
5b4a0ec0
DG
1382 nbmem = UST_APP_EVENT_LIST_SIZE;
1383 tmp = zmalloc(nbmem * sizeof(struct lttng_event));
1384 if (tmp == NULL) {
1385 PERROR("zmalloc ust app events");
1386 ret = -ENOMEM;
421cb601
DG
1387 goto error;
1388 }
1389
5b4a0ec0 1390 rcu_read_lock();
421cb601 1391
bec39940 1392 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
90eaa0d2 1393 struct lttng_ust_tracepoint_iter uiter;
ac3bd9c0 1394
5b4a0ec0
DG
1395 handle = ustctl_tracepoint_list(app->key.sock);
1396 if (handle < 0) {
1397 ERR("UST app list events getting handle failed for app pid %d",
1398 app->key.pid);
1399 continue;
1400 }
421cb601 1401
5b4a0ec0 1402 while ((ret = ustctl_tracepoint_list_get(app->key.sock, handle,
90eaa0d2 1403 &uiter)) != -ENOENT) {
815564d8
MD
1404 if (count >= nbmem) {
1405 DBG2("Reallocating event list from %zu to %zu entries", nbmem,
1406 2 * nbmem);
1407 nbmem *= 2;
2f221590 1408 tmp = realloc(tmp, nbmem * sizeof(struct lttng_event));
5b4a0ec0
DG
1409 if (tmp == NULL) {
1410 PERROR("realloc ust app events");
1411 ret = -ENOMEM;
1412 goto rcu_error;
1413 }
1414 }
90eaa0d2
DG
1415 memcpy(tmp[count].name, uiter.name, LTTNG_UST_SYM_NAME_LEN);
1416 memcpy(tmp[count].loglevel, uiter.loglevel, LTTNG_UST_SYM_NAME_LEN);
1417 tmp[count].loglevel_value = uiter.loglevel_value;
5b4a0ec0
DG
1418 tmp[count].type = LTTNG_UST_TRACEPOINT;
1419 tmp[count].pid = app->key.pid;
1420 tmp[count].enabled = -1;
1421 count++;
421cb601 1422 }
421cb601
DG
1423 }
1424
5b4a0ec0
DG
1425 ret = count;
1426 *events = tmp;
421cb601 1427
5b4a0ec0 1428 DBG2("UST app list events done (%zu events)", count);
421cb601 1429
5b4a0ec0
DG
1430rcu_error:
1431 rcu_read_unlock();
421cb601 1432error:
5b4a0ec0 1433 return ret;
421cb601
DG
1434}
1435
5b4a0ec0
DG
1436/*
1437 * Free and clean all traceable apps of the global list.
1438 */
1439void ust_app_clean_list(void)
421cb601 1440{
5b4a0ec0 1441 int ret;
bec39940
DG
1442 struct lttng_ht_iter iter;
1443 struct lttng_ht_node_ulong *node;
421cb601 1444
5b4a0ec0 1445 DBG2("UST app cleaning registered apps hash table");
421cb601 1446
5b4a0ec0 1447 rcu_read_lock();
421cb601 1448
bec39940
DG
1449 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, node, node) {
1450 ret = lttng_ht_del(ust_app_ht, &iter);
525b0740 1451 assert(!ret);
bec39940 1452 call_rcu(&node->head, delete_ust_app_rcu);
421cb601 1453 }
bec39940
DG
1454 /* Destroy is done only when the ht is empty */
1455 lttng_ht_destroy(ust_app_ht);
421cb601 1456
bec39940
DG
1457 cds_lfht_for_each_entry(ust_app_sock_key_map->ht, &iter.iter, node, node) {
1458 ret = lttng_ht_del(ust_app_sock_key_map, &iter);
1459 assert(!ret);
1460 }
1461 /* Destroy is done only when the ht is empty */
1462 lttng_ht_destroy(ust_app_sock_key_map);
421cb601 1463
5b4a0ec0
DG
1464 rcu_read_unlock();
1465}
1466
1467/*
1468 * Init UST app hash table.
1469 */
1470void ust_app_ht_alloc(void)
1471{
bec39940
DG
1472 ust_app_ht = lttng_ht_new(0, LTTNG_HT_TYPE_ULONG);
1473 ust_app_sock_key_map = lttng_ht_new(0, LTTNG_HT_TYPE_ULONG);
421cb601
DG
1474}
1475
78f0bacd
DG
1476/*
1477 * For a specific UST session, disable the channel for all registered apps.
1478 */
35a9059d 1479int ust_app_disable_channel_glb(struct ltt_ust_session *usess,
78f0bacd
DG
1480 struct ltt_ust_channel *uchan)
1481{
1482 int ret = 0;
bec39940
DG
1483 struct lttng_ht_iter iter;
1484 struct lttng_ht_node_str *ua_chan_node;
78f0bacd
DG
1485 struct ust_app *app;
1486 struct ust_app_session *ua_sess;
8535a6d9 1487 struct ust_app_channel *ua_chan;
78f0bacd
DG
1488
1489 if (usess == NULL || uchan == NULL) {
1490 ERR("Disabling UST global channel with NULL values");
1491 ret = -1;
1492 goto error;
1493 }
1494
a991f516
MD
1495 DBG2("UST app disabling channel %s from global domain for session id %d",
1496 uchan->name, usess->id);
78f0bacd
DG
1497
1498 rcu_read_lock();
1499
1500 /* For every registered applications */
bec39940
DG
1501 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
1502 struct lttng_ht_iter uiter;
78f0bacd
DG
1503 ua_sess = lookup_session_by_app(usess, app);
1504 if (ua_sess == NULL) {
1505 continue;
1506 }
1507
8535a6d9 1508 /* Get channel */
bec39940
DG
1509 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
1510 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
8535a6d9
DG
1511 /* If the session if found for the app, the channel must be there */
1512 assert(ua_chan_node);
1513
1514 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
1515 /* The channel must not be already disabled */
1516 assert(ua_chan->enabled == 1);
1517
1518 /* Disable channel onto application */
1519 ret = disable_ust_app_channel(ua_sess, ua_chan, app);
78f0bacd
DG
1520 if (ret < 0) {
1521 /* XXX: We might want to report this error at some point... */
1522 continue;
1523 }
1524 }
1525
1526 rcu_read_unlock();
1527
1528error:
1529 return ret;
1530}
1531
1532/*
1533 * For a specific UST session, enable the channel for all registered apps.
1534 */
35a9059d 1535int ust_app_enable_channel_glb(struct ltt_ust_session *usess,
78f0bacd
DG
1536 struct ltt_ust_channel *uchan)
1537{
1538 int ret = 0;
bec39940 1539 struct lttng_ht_iter iter;
78f0bacd
DG
1540 struct ust_app *app;
1541 struct ust_app_session *ua_sess;
1542
1543 if (usess == NULL || uchan == NULL) {
1544 ERR("Adding UST global channel to NULL values");
1545 ret = -1;
1546 goto error;
1547 }
1548
a991f516
MD
1549 DBG2("UST app enabling channel %s to global domain for session id %d",
1550 uchan->name, usess->id);
78f0bacd
DG
1551
1552 rcu_read_lock();
1553
1554 /* For every registered applications */
bec39940 1555 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
78f0bacd
DG
1556 ua_sess = lookup_session_by_app(usess, app);
1557 if (ua_sess == NULL) {
1558 continue;
1559 }
1560
1561 /* Enable channel onto application */
1562 ret = enable_ust_app_channel(ua_sess, uchan, app);
1563 if (ret < 0) {
1564 /* XXX: We might want to report this error at some point... */
1565 continue;
1566 }
1567 }
1568
1569 rcu_read_unlock();
1570
1571error:
1572 return ret;
1573}
1574
b0a40d28
DG
1575/*
1576 * Disable an event in a channel and for a specific session.
1577 */
35a9059d
DG
1578int ust_app_disable_event_glb(struct ltt_ust_session *usess,
1579 struct ltt_ust_channel *uchan, struct ltt_ust_event *uevent)
b0a40d28
DG
1580{
1581 int ret = 0;
bec39940
DG
1582 struct lttng_ht_iter iter, uiter;
1583 struct lttng_ht_node_str *ua_chan_node, *ua_event_node;
b0a40d28
DG
1584 struct ust_app *app;
1585 struct ust_app_session *ua_sess;
1586 struct ust_app_channel *ua_chan;
1587 struct ust_app_event *ua_event;
1588
1589 DBG("UST app disabling event %s for all apps in channel "
a991f516 1590 "%s for session id %d", uevent->attr.name, uchan->name, usess->id);
b0a40d28
DG
1591
1592 rcu_read_lock();
1593
1594 /* For all registered applications */
bec39940 1595 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
b0a40d28
DG
1596 ua_sess = lookup_session_by_app(usess, app);
1597 if (ua_sess == NULL) {
1598 /* Next app */
1599 continue;
1600 }
1601
1602 /* Lookup channel in the ust app session */
bec39940
DG
1603 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
1604 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
b0a40d28 1605 if (ua_chan_node == NULL) {
a991f516
MD
1606 DBG2("Channel %s not found in session id %d for app pid %d."
1607 "Skipping", uchan->name, usess->id, app->key.pid);
b0a40d28
DG
1608 continue;
1609 }
1610 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
1611
bec39940
DG
1612 lttng_ht_lookup(ua_chan->events, (void *)uevent->attr.name, &uiter);
1613 ua_event_node = lttng_ht_iter_get_node_str(&uiter);
b0a40d28
DG
1614 if (ua_event_node == NULL) {
1615 DBG2("Event %s not found in channel %s for app pid %d."
35a9059d 1616 "Skipping", uevent->attr.name, uchan->name, app->key.pid);
b0a40d28
DG
1617 continue;
1618 }
1619 ua_event = caa_container_of(ua_event_node, struct ust_app_event, node);
1620
7f79d3a1 1621 ret = disable_ust_app_event(ua_sess, ua_event, app);
b0a40d28
DG
1622 if (ret < 0) {
1623 /* XXX: Report error someday... */
1624 continue;
1625 }
1626 }
1627
1628 rcu_read_unlock();
1629
1630 return ret;
1631}
1632
9730260e 1633/*
edb67388 1634 * For a specific UST session and UST channel, the event for all
9730260e
DG
1635 * registered apps.
1636 */
35a9059d 1637int ust_app_disable_all_event_glb(struct ltt_ust_session *usess,
9730260e
DG
1638 struct ltt_ust_channel *uchan)
1639{
1640 int ret = 0;
bec39940
DG
1641 struct lttng_ht_iter iter, uiter;
1642 struct lttng_ht_node_str *ua_chan_node;
9730260e
DG
1643 struct ust_app *app;
1644 struct ust_app_session *ua_sess;
1645 struct ust_app_channel *ua_chan;
1646 struct ust_app_event *ua_event;
1647
1648 DBG("UST app disabling all event for all apps in channel "
a991f516 1649 "%s for session id %d", uchan->name, usess->id);
9730260e
DG
1650
1651 rcu_read_lock();
1652
1653 /* For all registered applications */
bec39940 1654 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
9730260e 1655 ua_sess = lookup_session_by_app(usess, app);
edb67388
DG
1656 /* If ua_sess is NULL, there is a code flow error */
1657 assert(ua_sess);
9730260e
DG
1658
1659 /* Lookup channel in the ust app session */
bec39940
DG
1660 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
1661 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
edb67388
DG
1662 /* If the channel is not found, there is a code flow error */
1663 assert(ua_chan_node);
1664
9730260e
DG
1665 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
1666
1667 /* Disable each events of channel */
bec39940
DG
1668 cds_lfht_for_each_entry(ua_chan->events->ht, &uiter.iter, ua_event,
1669 node.node) {
7f79d3a1 1670 ret = disable_ust_app_event(ua_sess, ua_event, app);
9730260e
DG
1671 if (ret < 0) {
1672 /* XXX: Report error someday... */
1673 continue;
1674 }
1675 }
1676 }
1677
1678 rcu_read_unlock();
1679
1680 return ret;
1681}
1682
421cb601 1683/*
5b4a0ec0 1684 * For a specific UST session, create the channel for all registered apps.
421cb601 1685 */
35a9059d 1686int ust_app_create_channel_glb(struct ltt_ust_session *usess,
48842b30
DG
1687 struct ltt_ust_channel *uchan)
1688{
bec39940 1689 struct lttng_ht_iter iter;
48842b30
DG
1690 struct ust_app *app;
1691 struct ust_app_session *ua_sess;
1692 struct ust_app_channel *ua_chan;
1693
fc34caaa
DG
1694 /* Very wrong code flow */
1695 assert(usess);
1696 assert(uchan);
421cb601 1697
a991f516
MD
1698 DBG2("UST app adding channel %s to global domain for session id %d",
1699 uchan->name, usess->id);
48842b30
DG
1700
1701 rcu_read_lock();
421cb601 1702
5b4a0ec0 1703 /* For every registered applications */
bec39940 1704 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
edb67388
DG
1705 /*
1706 * Create session on the tracer side and add it to app session HT. Note
1707 * that if session exist, it will simply return a pointer to the ust
1708 * app session.
1709 */
421cb601 1710 ua_sess = create_ust_app_session(usess, app);
509cbaf8 1711 if (ua_sess == NULL) {
fc34caaa
DG
1712 /* Major problem here and it's maybe the tracer or malloc() */
1713 goto error;
48842b30
DG
1714 }
1715
421cb601
DG
1716 /* Create channel onto application */
1717 ua_chan = create_ust_app_channel(ua_sess, uchan, app);
1718 if (ua_chan == NULL) {
fc34caaa
DG
1719 /* Major problem here and it's maybe the tracer or malloc() */
1720 goto error;
48842b30 1721 }
48842b30 1722 }
5b4a0ec0 1723
48842b30
DG
1724 rcu_read_unlock();
1725
fc34caaa
DG
1726 return 0;
1727
421cb601 1728error:
fc34caaa 1729 return -1;
48842b30
DG
1730}
1731
5b4a0ec0 1732/*
edb67388 1733 * Enable event for a specific session and channel on the tracer.
5b4a0ec0 1734 */
35a9059d 1735int ust_app_enable_event_glb(struct ltt_ust_session *usess,
48842b30
DG
1736 struct ltt_ust_channel *uchan, struct ltt_ust_event *uevent)
1737{
1738 int ret = 0;
bec39940
DG
1739 struct lttng_ht_iter iter, uiter;
1740 struct lttng_ht_node_str *ua_chan_node, *ua_event_node;
48842b30
DG
1741 struct ust_app *app;
1742 struct ust_app_session *ua_sess;
1743 struct ust_app_channel *ua_chan;
1744 struct ust_app_event *ua_event;
48842b30 1745
a991f516
MD
1746 DBG("UST app enabling event %s for all apps for session id %d",
1747 uevent->attr.name, usess->id);
48842b30 1748
edb67388
DG
1749 /*
1750 * NOTE: At this point, this function is called only if the session and
1751 * channel passed are already created for all apps. and enabled on the
1752 * tracer also.
1753 */
1754
48842b30 1755 rcu_read_lock();
421cb601
DG
1756
1757 /* For all registered applications */
bec39940 1758 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
edb67388
DG
1759 ua_sess = lookup_session_by_app(usess, app);
1760 /* If ua_sess is NULL, there is a code flow error */
1761 assert(ua_sess);
ba767faf 1762
edb67388 1763 /* Lookup channel in the ust app session */
bec39940
DG
1764 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
1765 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
edb67388
DG
1766 /* If the channel is not found, there is a code flow error */
1767 assert(ua_chan_node);
1768
1769 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
1770
bec39940
DG
1771 lttng_ht_lookup(ua_chan->events, (void*)uevent->attr.name, &uiter);
1772 ua_event_node = lttng_ht_iter_get_node_str(&uiter);
35a9059d 1773 if (ua_event_node == NULL) {
7f79d3a1
DG
1774 DBG3("UST app enable event %s not found for app PID %d."
1775 "Skipping app", uevent->attr.name, app->key.pid);
35a9059d
DG
1776 continue;
1777 }
1778 ua_event = caa_container_of(ua_event_node, struct ust_app_event, node);
1779
1780 ret = enable_ust_app_event(ua_sess, ua_event, app);
1781 if (ret < 0) {
7f79d3a1 1782 goto error;
48842b30 1783 }
edb67388
DG
1784 }
1785
7f79d3a1 1786error:
edb67388 1787 rcu_read_unlock();
edb67388
DG
1788 return ret;
1789}
1790
1791/*
1792 * For a specific existing UST session and UST channel, creates the event for
1793 * all registered apps.
1794 */
35a9059d 1795int ust_app_create_event_glb(struct ltt_ust_session *usess,
edb67388
DG
1796 struct ltt_ust_channel *uchan, struct ltt_ust_event *uevent)
1797{
1798 int ret = 0;
bec39940
DG
1799 struct lttng_ht_iter iter, uiter;
1800 struct lttng_ht_node_str *ua_chan_node;
edb67388
DG
1801 struct ust_app *app;
1802 struct ust_app_session *ua_sess;
1803 struct ust_app_channel *ua_chan;
1804
a991f516
MD
1805 DBG("UST app creating event %s for all apps for session id %d",
1806 uevent->attr.name, usess->id);
edb67388 1807
edb67388
DG
1808 rcu_read_lock();
1809
1810 /* For all registered applications */
bec39940 1811 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
edb67388
DG
1812 ua_sess = lookup_session_by_app(usess, app);
1813 /* If ua_sess is NULL, there is a code flow error */
1814 assert(ua_sess);
48842b30
DG
1815
1816 /* Lookup channel in the ust app session */
bec39940
DG
1817 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
1818 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
edb67388
DG
1819 /* If the channel is not found, there is a code flow error */
1820 assert(ua_chan_node);
1821
48842b30
DG
1822 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
1823
edb67388
DG
1824 ret = create_ust_app_event(ua_sess, ua_chan, uevent, app);
1825 if (ret < 0) {
fc34caaa
DG
1826 if (ret != -EEXIST) {
1827 /* Possible value at this point: -ENOMEM. If so, we stop! */
1828 break;
1829 }
1830 DBG2("UST app event %s already exist on app PID %d",
1831 uevent->attr.name, app->key.pid);
5b4a0ec0 1832 continue;
48842b30 1833 }
48842b30 1834 }
5b4a0ec0 1835
48842b30
DG
1836 rcu_read_unlock();
1837
1838 return ret;
1839}
1840
5b4a0ec0
DG
1841/*
1842 * Start tracing for a specific UST session and app.
1843 */
421cb601 1844int ust_app_start_trace(struct ltt_ust_session *usess, struct ust_app *app)
48842b30
DG
1845{
1846 int ret = 0;
bec39940 1847 struct lttng_ht_iter iter;
48842b30
DG
1848 struct ust_app_session *ua_sess;
1849 struct ust_app_channel *ua_chan;
5b4a0ec0 1850 struct ltt_ust_stream *ustream;
7753dea8 1851 int consumerd_fd;
48842b30 1852
421cb601 1853 DBG("Starting tracing for ust app pid %d", app->key.pid);
5cf5d0e7 1854
509cbaf8
MD
1855 rcu_read_lock();
1856
421cb601
DG
1857 ua_sess = lookup_session_by_app(usess, app);
1858 if (ua_sess == NULL) {
509cbaf8 1859 goto error_rcu_unlock;
421cb601 1860 }
48842b30 1861
aea829b3
DG
1862 /* Upon restart, we skip the setup, already done */
1863 if (ua_sess->started) {
8be98f9a 1864 goto skip_setup;
aea829b3 1865 }
8be98f9a 1866
421cb601
DG
1867 ret = create_ust_app_metadata(ua_sess, usess->pathname, app);
1868 if (ret < 0) {
509cbaf8 1869 goto error_rcu_unlock;
421cb601 1870 }
48842b30 1871
421cb601 1872 /* For each channel */
bec39940
DG
1873 cds_lfht_for_each_entry(ua_sess->channels->ht, &iter.iter, ua_chan,
1874 node.node) {
421cb601
DG
1875 /* Create all streams */
1876 while (1) {
5b4a0ec0 1877 /* Create UST stream */
421cb601
DG
1878 ustream = zmalloc(sizeof(*ustream));
1879 if (ustream == NULL) {
1880 PERROR("zmalloc ust stream");
509cbaf8 1881 goto error_rcu_unlock;
421cb601 1882 }
48842b30 1883
421cb601
DG
1884 ret = ustctl_create_stream(app->key.sock, ua_chan->obj,
1885 &ustream->obj);
48842b30 1886 if (ret < 0) {
421cb601
DG
1887 /* Got all streams */
1888 break;
48842b30 1889 }
421cb601 1890 ustream->handle = ustream->obj->handle;
48842b30 1891
421cb601
DG
1892 /* Order is important */
1893 cds_list_add_tail(&ustream->list, &ua_chan->streams.head);
477d7741
MD
1894 ret = snprintf(ustream->pathname, PATH_MAX, "%s/%s_%u",
1895 ua_sess->path, ua_chan->name,
1896 ua_chan->streams.count++);
aba8e916
DG
1897 if (ret < 0) {
1898 PERROR("asprintf UST create stream");
421cb601 1899 continue;
aba8e916 1900 }
421cb601
DG
1901 DBG2("UST stream %d ready at %s", ua_chan->streams.count,
1902 ustream->pathname);
1903 }
421cb601 1904 }
aba8e916 1905
7753dea8
MD
1906 switch (app->bits_per_long) {
1907 case 64:
1908 consumerd_fd = ust_consumerd64_fd;
1909 break;
1910 case 32:
1911 consumerd_fd = ust_consumerd32_fd;
1912 break;
1913 default:
1914 ret = -EINVAL;
1915 goto error_rcu_unlock;
1916 }
aea829b3 1917
421cb601 1918 /* Setup UST consumer socket and send fds to it */
7753dea8 1919 ret = ust_consumer_send_session(consumerd_fd, ua_sess);
421cb601 1920 if (ret < 0) {
509cbaf8 1921 goto error_rcu_unlock;
421cb601 1922 }
8be98f9a 1923 ua_sess->started = 1;
48842b30 1924
8be98f9a 1925skip_setup:
421cb601
DG
1926 /* This start the UST tracing */
1927 ret = ustctl_start_session(app->key.sock, ua_sess->handle);
1928 if (ret < 0) {
1929 ERR("Error starting tracing for app pid: %d", app->key.pid);
509cbaf8 1930 goto error_rcu_unlock;
421cb601 1931 }
5b4a0ec0 1932
509cbaf8 1933 rcu_read_unlock();
48842b30 1934
421cb601
DG
1935 /* Quiescent wait after starting trace */
1936 ustctl_wait_quiescent(app->key.sock);
48842b30 1937
421cb601 1938 return 0;
48842b30 1939
509cbaf8
MD
1940error_rcu_unlock:
1941 rcu_read_unlock();
421cb601
DG
1942 return -1;
1943}
48842b30 1944
8be98f9a
MD
1945/*
1946 * Stop tracing for a specific UST session and app.
1947 */
1948int ust_app_stop_trace(struct ltt_ust_session *usess, struct ust_app *app)
1949{
1950 int ret = 0;
bec39940 1951 struct lttng_ht_iter iter;
8be98f9a 1952 struct ust_app_session *ua_sess;
6d3686da 1953 struct ust_app_channel *ua_chan;
8be98f9a
MD
1954
1955 DBG("Stopping tracing for ust app pid %d", app->key.pid);
1956
1957 rcu_read_lock();
1958
1959 ua_sess = lookup_session_by_app(usess, app);
1960 if (ua_sess == NULL) {
1961 /* Only malloc can failed so something is really wrong */
1962 goto error_rcu_unlock;
1963 }
1964
7db205b5
DG
1965 /* Not started, continuing. */
1966 if (ua_sess->started == 0) {
1967 goto end;
1968 }
1969
9d6c7d3f
DG
1970 /* This inhibits UST tracing */
1971 ret = ustctl_stop_session(app->key.sock, ua_sess->handle);
1972 if (ret < 0) {
1973 ERR("Error stopping tracing for app pid: %d", app->key.pid);
1974 goto error_rcu_unlock;
1975 }
1976
1977 /* Quiescent wait after stopping trace */
1978 ustctl_wait_quiescent(app->key.sock);
1979
1980 /* Flushing buffers */
bec39940
DG
1981 cds_lfht_for_each_entry(ua_sess->channels->ht, &iter.iter, ua_chan,
1982 node.node) {
6d3686da 1983 ret = ustctl_sock_flush_buffer(app->key.sock, ua_chan->obj);
8be98f9a 1984 if (ret < 0) {
7db205b5
DG
1985 ERR("UST app PID %d channel %s flush failed with ret %d",
1986 app->key.pid, ua_chan->name, ret);
6d3686da
DG
1987 /* Continuing flushing all buffers */
1988 continue;
8be98f9a
MD
1989 }
1990 }
8be98f9a 1991
90d97d10
DG
1992 /* Flush all buffers before stopping */
1993 ret = ustctl_sock_flush_buffer(app->key.sock, ua_sess->metadata->obj);
1994 if (ret < 0) {
7db205b5
DG
1995 ERR("UST app PID %d metadata flush failed with ret %d", app->key.pid,
1996 ret);
90d97d10
DG
1997 }
1998
7db205b5 1999 ua_sess->started = 0;
9d6c7d3f 2000
7db205b5
DG
2001end:
2002 rcu_read_unlock();
8be98f9a
MD
2003 return 0;
2004
2005error_rcu_unlock:
2006 rcu_read_unlock();
2007 return -1;
2008}
2009
84cd17c6
MD
2010/*
2011 * Destroy a specific UST session in apps.
2012 */
2013int ust_app_destroy_trace(struct ltt_ust_session *usess, struct ust_app *app)
2014{
2015 struct ust_app_session *ua_sess;
2016 struct lttng_ust_object_data obj;
bec39940
DG
2017 struct lttng_ht_iter iter;
2018 struct lttng_ht_node_ulong *node;
525b0740 2019 int ret;
84cd17c6
MD
2020
2021 DBG("Destroy tracing for ust app pid %d", app->key.pid);
2022
2023 rcu_read_lock();
2024
2025 __lookup_session_by_app(usess, app, &iter);
bec39940 2026 node = lttng_ht_iter_get_node_ulong(&iter);
84cd17c6
MD
2027 if (node == NULL) {
2028 /* Only malloc can failed so something is really wrong */
2029 goto error_rcu_unlock;
2030 }
2031 ua_sess = caa_container_of(node, struct ust_app_session, node);
bec39940 2032 ret = lttng_ht_del(app->sessions, &iter);
525b0740 2033 assert(!ret);
84cd17c6
MD
2034 obj.handle = ua_sess->handle;
2035 obj.shm_fd = -1;
2036 obj.wait_fd = -1;
2037 obj.memory_map_size = 0;
2038 ustctl_release_object(app->key.sock, &obj);
2039
7db205b5
DG
2040 delete_ust_app_session(app->key.sock, ua_sess);
2041
84cd17c6
MD
2042 rcu_read_unlock();
2043
2044 /* Quiescent wait after stopping trace */
2045 ustctl_wait_quiescent(app->key.sock);
2046
2047 return 0;
2048
2049error_rcu_unlock:
2050 rcu_read_unlock();
2051 return -1;
2052}
2053
5b4a0ec0
DG
2054/*
2055 * Start tracing for the UST session.
2056 */
421cb601
DG
2057int ust_app_start_trace_all(struct ltt_ust_session *usess)
2058{
2059 int ret = 0;
bec39940 2060 struct lttng_ht_iter iter;
421cb601 2061 struct ust_app *app;
48842b30 2062
421cb601
DG
2063 DBG("Starting all UST traces");
2064
2065 rcu_read_lock();
421cb601 2066
bec39940 2067 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
421cb601 2068 ret = ust_app_start_trace(usess, app);
48842b30 2069 if (ret < 0) {
5b4a0ec0
DG
2070 /* Continue to next apps even on error */
2071 continue;
48842b30 2072 }
48842b30 2073 }
5b4a0ec0 2074
48842b30
DG
2075 rcu_read_unlock();
2076
2077 return 0;
2078}
487cf67c 2079
8be98f9a
MD
2080/*
2081 * Start tracing for the UST session.
2082 */
2083int ust_app_stop_trace_all(struct ltt_ust_session *usess)
2084{
2085 int ret = 0;
bec39940 2086 struct lttng_ht_iter iter;
8be98f9a
MD
2087 struct ust_app *app;
2088
2089 DBG("Stopping all UST traces");
2090
2091 rcu_read_lock();
2092
bec39940 2093 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
8be98f9a
MD
2094 ret = ust_app_stop_trace(usess, app);
2095 if (ret < 0) {
2096 /* Continue to next apps even on error */
2097 continue;
2098 }
2099 }
2100
2101 rcu_read_unlock();
2102
2103 return 0;
2104}
2105
84cd17c6
MD
2106/*
2107 * Destroy app UST session.
2108 */
2109int ust_app_destroy_trace_all(struct ltt_ust_session *usess)
2110{
2111 int ret = 0;
bec39940 2112 struct lttng_ht_iter iter;
84cd17c6
MD
2113 struct ust_app *app;
2114
2115 DBG("Destroy all UST traces");
2116
2117 rcu_read_lock();
2118
bec39940 2119 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
84cd17c6
MD
2120 ret = ust_app_destroy_trace(usess, app);
2121 if (ret < 0) {
2122 /* Continue to next apps even on error */
2123 continue;
2124 }
2125 }
2126
2127 rcu_read_unlock();
2128
2129 return 0;
2130}
2131
5b4a0ec0
DG
2132/*
2133 * Add channels/events from UST global domain to registered apps at sock.
2134 */
487cf67c
DG
2135void ust_app_global_update(struct ltt_ust_session *usess, int sock)
2136{
2137 int ret = 0;
bec39940 2138 struct lttng_ht_iter iter, uiter;
487cf67c
DG
2139 struct ust_app *app;
2140 struct ust_app_session *ua_sess;
2141 struct ust_app_channel *ua_chan;
2142 struct ust_app_event *ua_event;
1f3580c7
DG
2143
2144 if (usess == NULL) {
5b4a0ec0 2145 ERR("No UST session on global update. Returning");
1f3580c7
DG
2146 goto error;
2147 }
2148
a991f516
MD
2149 DBG2("UST app global update for app sock %d for session id %d", sock,
2150 usess->id);
487cf67c 2151
284d8f55
DG
2152 rcu_read_lock();
2153
487cf67c
DG
2154 app = find_app_by_sock(sock);
2155 if (app == NULL) {
2156 ERR("Failed to update app sock %d", sock);
2157 goto error;
2158 }
2159
421cb601 2160 ua_sess = create_ust_app_session(usess, app);
487cf67c 2161 if (ua_sess == NULL) {
487cf67c
DG
2162 goto error;
2163 }
2164
284d8f55
DG
2165 /*
2166 * We can iterate safely here over all UST app session sicne the create ust
2167 * app session above made a shadow copy of the UST global domain from the
2168 * ltt ust session.
2169 */
bec39940
DG
2170 cds_lfht_for_each_entry(ua_sess->channels->ht, &iter.iter, ua_chan,
2171 node.node) {
284d8f55
DG
2172 ret = create_ust_channel(app, ua_sess, ua_chan);
2173 if (ret < 0) {
2174 /* FIXME: Should we quit here or continue... */
2175 continue;
487cf67c
DG
2176 }
2177
284d8f55 2178 /* For each events */
bec39940
DG
2179 cds_lfht_for_each_entry(ua_chan->events->ht, &uiter.iter, ua_event,
2180 node.node) {
284d8f55
DG
2181 ret = create_ust_event(app, ua_sess, ua_chan, ua_event);
2182 if (ret < 0) {
2183 /* FIXME: Should we quit here or continue... */
2184 continue;
487cf67c 2185 }
36dc12cc 2186 }
487cf67c
DG
2187 }
2188
36dc12cc 2189 if (usess->start_trace) {
421cb601 2190 ret = ust_app_start_trace(usess, app);
36dc12cc 2191 if (ret < 0) {
36dc12cc
DG
2192 goto error;
2193 }
2194
36dc12cc
DG
2195 DBG2("UST trace started for app pid %d", app->key.pid);
2196 }
2197
487cf67c
DG
2198error:
2199 rcu_read_unlock();
2200 return;
2201}
55cc08a6
DG
2202
2203/*
2204 * Add context to a specific channel for global UST domain.
2205 */
2206int ust_app_add_ctx_channel_glb(struct ltt_ust_session *usess,
2207 struct ltt_ust_channel *uchan, struct ltt_ust_context *uctx)
2208{
2209 int ret = 0;
bec39940
DG
2210 struct lttng_ht_node_str *ua_chan_node;
2211 struct lttng_ht_iter iter, uiter;
55cc08a6
DG
2212 struct ust_app_channel *ua_chan = NULL;
2213 struct ust_app_session *ua_sess;
2214 struct ust_app *app;
2215
2216 rcu_read_lock();
2217
bec39940 2218 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
55cc08a6
DG
2219 ua_sess = lookup_session_by_app(usess, app);
2220 if (ua_sess == NULL) {
2221 continue;
2222 }
2223
2224 /* Lookup channel in the ust app session */
bec39940
DG
2225 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
2226 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
55cc08a6
DG
2227 if (ua_chan_node == NULL) {
2228 continue;
2229 }
2230 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel,
2231 node);
2232
2233 ret = create_ust_app_channel_context(ua_sess, ua_chan, &uctx->ctx, app);
2234 if (ret < 0) {
2235 continue;
2236 }
2237 }
2238
55cc08a6
DG
2239 rcu_read_unlock();
2240 return ret;
2241}
2242
2243/*
2244 * Add context to a specific event in a channel for global UST domain.
2245 */
2246int ust_app_add_ctx_event_glb(struct ltt_ust_session *usess,
2247 struct ltt_ust_channel *uchan, struct ltt_ust_event *uevent,
2248 struct ltt_ust_context *uctx)
2249{
2250 int ret = 0;
bec39940
DG
2251 struct lttng_ht_node_str *ua_chan_node, *ua_event_node;
2252 struct lttng_ht_iter iter, uiter;
55cc08a6
DG
2253 struct ust_app_session *ua_sess;
2254 struct ust_app_event *ua_event;
2255 struct ust_app_channel *ua_chan = NULL;
2256 struct ust_app *app;
2257
2258 rcu_read_lock();
2259
bec39940 2260 cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, node.node) {
55cc08a6
DG
2261 ua_sess = lookup_session_by_app(usess, app);
2262 if (ua_sess == NULL) {
2263 continue;
2264 }
2265
2266 /* Lookup channel in the ust app session */
bec39940
DG
2267 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &uiter);
2268 ua_chan_node = lttng_ht_iter_get_node_str(&uiter);
55cc08a6
DG
2269 if (ua_chan_node == NULL) {
2270 continue;
2271 }
2272 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel,
2273 node);
2274
bec39940
DG
2275 lttng_ht_lookup(ua_chan->events, (void *)uevent->attr.name, &uiter);
2276 ua_event_node = lttng_ht_iter_get_node_str(&uiter);
55cc08a6
DG
2277 if (ua_event_node == NULL) {
2278 continue;
2279 }
2280 ua_event = caa_container_of(ua_event_node, struct ust_app_event,
2281 node);
2282
2283 ret = create_ust_app_event_context(ua_sess, ua_event, &uctx->ctx, app);
2284 if (ret < 0) {
2285 continue;
2286 }
2287 }
2288
55cc08a6
DG
2289 rcu_read_unlock();
2290 return ret;
2291}
76d45b40
DG
2292
2293/*
2294 * Enable event for a channel from a UST session for a specific PID.
2295 */
2296int ust_app_enable_event_pid(struct ltt_ust_session *usess,
2297 struct ltt_ust_channel *uchan, struct ltt_ust_event *uevent, pid_t pid)
2298{
2299 int ret = 0;
bec39940
DG
2300 struct lttng_ht_iter iter;
2301 struct lttng_ht_node_str *ua_chan_node, *ua_event_node;
76d45b40
DG
2302 struct ust_app *app;
2303 struct ust_app_session *ua_sess;
2304 struct ust_app_channel *ua_chan;
2305 struct ust_app_event *ua_event;
2306
2307 DBG("UST app enabling event %s for PID %d", uevent->attr.name, pid);
2308
2309 rcu_read_lock();
2310
2311 app = ust_app_find_by_pid(pid);
2312 if (app == NULL) {
2313 ERR("UST app enable event per PID %d not found", pid);
2314 ret = -1;
2315 goto error;
2316 }
2317
2318 ua_sess = lookup_session_by_app(usess, app);
2319 /* If ua_sess is NULL, there is a code flow error */
2320 assert(ua_sess);
2321
2322 /* Lookup channel in the ust app session */
bec39940
DG
2323 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &iter);
2324 ua_chan_node = lttng_ht_iter_get_node_str(&iter);
76d45b40
DG
2325 /* If the channel is not found, there is a code flow error */
2326 assert(ua_chan_node);
2327
2328 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
2329
bec39940
DG
2330 lttng_ht_lookup(ua_chan->events, (void *)uevent->attr.name, &iter);
2331 ua_event_node = lttng_ht_iter_get_node_str(&iter);
76d45b40
DG
2332 if (ua_event_node == NULL) {
2333 ret = create_ust_app_event(ua_sess, ua_chan, uevent, app);
2334 if (ret < 0) {
2335 goto error;
2336 }
2337 } else {
2338 ua_event = caa_container_of(ua_event_node, struct ust_app_event, node);
2339
2340 ret = enable_ust_app_event(ua_sess, ua_event, app);
2341 if (ret < 0) {
2342 goto error;
2343 }
2344 }
2345
2346error:
2347 rcu_read_unlock();
2348 return ret;
2349}
7f79d3a1
DG
2350
2351/*
2352 * Disable event for a channel from a UST session for a specific PID.
2353 */
2354int ust_app_disable_event_pid(struct ltt_ust_session *usess,
2355 struct ltt_ust_channel *uchan, struct ltt_ust_event *uevent, pid_t pid)
2356{
2357 int ret = 0;
bec39940
DG
2358 struct lttng_ht_iter iter;
2359 struct lttng_ht_node_str *ua_chan_node, *ua_event_node;
7f79d3a1
DG
2360 struct ust_app *app;
2361 struct ust_app_session *ua_sess;
2362 struct ust_app_channel *ua_chan;
2363 struct ust_app_event *ua_event;
2364
2365 DBG("UST app disabling event %s for PID %d", uevent->attr.name, pid);
2366
2367 rcu_read_lock();
2368
2369 app = ust_app_find_by_pid(pid);
2370 if (app == NULL) {
2371 ERR("UST app disable event per PID %d not found", pid);
2372 ret = -1;
2373 goto error;
2374 }
2375
2376 ua_sess = lookup_session_by_app(usess, app);
2377 /* If ua_sess is NULL, there is a code flow error */
2378 assert(ua_sess);
2379
2380 /* Lookup channel in the ust app session */
bec39940
DG
2381 lttng_ht_lookup(ua_sess->channels, (void *)uchan->name, &iter);
2382 ua_chan_node = lttng_ht_iter_get_node_str(&iter);
7f79d3a1
DG
2383 if (ua_chan_node == NULL) {
2384 /* Channel does not exist, skip disabling */
2385 goto error;
2386 }
2387 ua_chan = caa_container_of(ua_chan_node, struct ust_app_channel, node);
2388
bec39940
DG
2389 lttng_ht_lookup(ua_chan->events, (void *)uevent->attr.name, &iter);
2390 ua_event_node = lttng_ht_iter_get_node_str(&iter);
7f79d3a1
DG
2391 if (ua_event_node == NULL) {
2392 /* Event does not exist, skip disabling */
2393 goto error;
2394 }
2395 ua_event = caa_container_of(ua_event_node, struct ust_app_event, node);
2396
2397 ret = disable_ust_app_event(ua_sess, ua_event, app);
2398 if (ret < 0) {
2399 goto error;
2400 }
2401
2402error:
2403 rcu_read_unlock();
2404 return ret;
2405}
This page took 0.148093 seconds and 4 git commands to generate.