lttngtop without arguments starts a local live trace
[lttngtop.git] / src / lttng-session.c
CommitLineData
f248b7d8
JD
1#define _GNU_SOURCE /* See feature_test_macros(7) */
2#include <stdlib.h>
3#include <unistd.h>
4#include <sys/types.h>
5#include <stdio.h>
6#include <stdint.h>
7#include <inttypes.h>
6a1b139c 8#include <string.h>
f248b7d8
JD
9
10#define event_list "lttng_statedump_start,lttng_statedump_end," \
11 "lttng_statedump_process_state,lttng_statedump_file_descriptor," \
12 "lttng_statedump_vm_map,lttng_statedump_network_interface," \
13 "lttng_statedump_interrupt,sched_process_free," \
14 "sched_switch,sched_process_fork"
15#define context_list "-t pid -t procname -t tid -t ppid "
16
17static
18int check_or_start_sessiond()
19{
20 int ret;
21 int sudo = 0;
22
23 ret = system("pgrep -u root lttng-sessiond >/dev/null");
24 if (ret == 0)
25 goto end;
26
27 if (getuid() != 0) {
28 fprintf(stderr, "Trying to start lttng-sessiond with sudo\n");
29 ret = system("sudo -l lttng-sessiond >/dev/null");
30 if (ret < 0) {
31 fprintf(stderr, "[error] You are not root and not "
32 "allowed by sudo to start lttng-sessiond\n");
33 ret = -1;
34 goto end;
35 }
26d63ddf
JD
36 ret = system("sudo -l lttng >/dev/null");
37 if (ret < 0) {
38 fprintf(stderr, "[error] You are not root and not "
39 "allowed by sudo to use lttng\n");
40 ret = -1;
41 goto end;
42 }
f248b7d8
JD
43 sudo = 1;
44 }
45
46 if (sudo)
47 ret = system("sudo lttng-sessiond -d");
48 else
49 ret = system("lttng-sessiond -d");
50
51 if (ret != 0) {
52 fprintf(stderr, "Error starting lttng-sessiond as root\n");
53 ret = -1;
54 goto end;
55 }
56
57end:
58 return ret;
59}
60
61static
62int check_or_start_relayd()
63{
64 int ret;
65
66 ret = system("pgrep lttng-relayd >/dev/null");
67 if (ret == 0)
68 goto end;
69
70 ret = system("lttng-relayd -d");
71 if (ret != 0) {
72 fprintf(stderr, "Error starting lttng-relayd\n");
73 ret = -1;
74 goto end;
75 }
76
77end:
78 return ret;
79}
80
81/*
82 * Return 0 if in tracing group or root, 1 if sudo is needed (and working),
83 * a negative value on error.
84 */
85static
86int check_tracing_group()
87{
88 int ret;
89
90 ret = getuid();
91 if (ret == 0)
92 goto end;
93
94 ret = system("groups|grep tracing >/dev/null");
95 if (ret == 0) {
96 goto end;
97 }
98
99 ret = system("sudo lttng --version >/dev/null");
100 if (ret != 0) {
101 fprintf(stderr, "Error executing lttng with sudo, you need to "
102 "be root or in the \"tracing\" group to start "
103 "kernel tracing\n");
104 ret = -1;
105 goto end;
106 } else {
107 ret = 1;
108 }
109
110end:
111 return ret;
112}
113
114static
115int check_lttng_modules(int sudo)
116{
117 int ret;
118
119 if (sudo) {
120 ret = system("sudo lttng list -k | grep sched_switch >/dev/null");
121 } else {
122 ret = system("lttng list -k | grep sched_switch >/dev/null");
123 }
124 if (ret != 0) {
125 fprintf(stderr, "Error listing kernel events, "
126 "lttng-modules might not be installed\n");
127 goto end;
128 }
129
130end:
131 return ret;
132}
133
134static
135int check_requirements(int *sudo)
136{
137 int ret;
138
139 ret = check_or_start_sessiond();
140 if (ret < 0)
141 goto end;
142 ret = check_or_start_relayd();
143 if (ret < 0)
144 goto end;
145 ret = check_tracing_group();
146 if (ret < 0)
147 goto end;
148 else if (ret == 1)
149 *sudo = 1;
150
151 ret = check_lttng_modules(*sudo);
152 if (ret < 0)
153 goto end;
154end:
155 return ret;
156}
157
158/*
159 * Allocate a random string, must be freed by the caller.
160 */
161static
162char *random_session_name()
163{
164 uint64_t id;
165 char *str = NULL;
166 int ret;
167
168 FILE *f = fopen( "/dev/urandom", "r");
169 if (!f) {
170 perror("fopen");
171 goto end;
172 }
173
174 ret = fread(&id, 1, sizeof(uint64_t), f);
175 if (ret < sizeof(id)) {
176 perror("fread");
177 goto end;
178 }
179
180 ret = asprintf(&str, "lttngtop-%" PRIu64, id);
181 if (ret < 0) {
182 fprintf(stderr, "Error allocating session name");
183 str = NULL;
184 goto end;
185 }
186
187 ret = fclose(f);
188 if (ret != 0) {
189 perror("fclose");
190 goto end;
191 }
192
193end:
194 return str;
195}
196
197static
198int check_session_name(char *name, int sudo)
199{
200 int ret;
201 char cmd[1024];
202
203 ret = sprintf(cmd, "%s lttng list | grep %s >/dev/null",
204 (sudo) ? "sudo" : " ", name);
205 if (ret < 0) {
206 fprintf(stderr, "Allocating cmd\n");
207 goto end;
208 }
209
210 ret = (system(cmd));
211 if (ret == 0) {
212 fprintf(stderr, "Error: session %s already exist, either we "
213 "are not random enough or something is "
214 "really wrong\n", name);
215 ret = -1;
216 goto end;
217 }
218
219end:
220 return ret;
221}
222
223static
224int local_session(char *name, int sudo)
225{
226 int ret;
227 char cmd[1024];
228
229 ret = sprintf(cmd, "%s lttng create %s >/dev/null",
230 (sudo) ? "sudo" : " ", name);
231 if (ret < 0) {
232 fprintf(stderr, "Allocating cmd\n");
233 goto end;
234 }
235 ret = (system(cmd));
236 if (ret != 0) {
237 fprintf(stderr, "Error: creating the session\n");
238 ret = -1;
239 goto end;
240 }
241
242end:
243 return ret;
244}
245
246static
26d63ddf
JD
247int live_local_session(char *name, int sudo)
248{
249 int ret;
250 char cmd[1024];
251
252 ret = sprintf(cmd, "%s lttng create %s --live 1000000 -U net://localhost >/dev/null",
253 (sudo) ? "sudo" : " ", name);
254 if (ret < 0) {
255 fprintf(stderr, "Allocating cmd\n");
256 goto end;
257 }
258 ret = (system(cmd));
259 if (ret != 0) {
260 fprintf(stderr, "Error: creating the session\n");
261 ret = -1;
262 goto end;
263 }
264
265end:
266 return ret;
267}
268
269static
270int enable_events(char *name, int sudo)
f248b7d8
JD
271{
272 int ret;
273 char cmd[1024];
274
275 ret = sprintf(cmd, "%s lttng enable-event -s %s -k %s >/dev/null",
276 (sudo) ? "sudo" : " ", name, event_list);
277 if (ret < 0) {
278 fprintf(stderr, "Allocating cmd\n");
279 goto end;
280 }
281
282 ret = (system(cmd));
283 if (ret != 0) {
284 fprintf(stderr, "Error: enabling events\n");
285 ret = -1;
286 goto end;
287 }
288
289end:
290 return ret;
291}
292
293static
294int add_contexts(char *name, int sudo)
295{
296 int ret;
297 char cmd[1024];
298
299 ret = sprintf(cmd, "%s lttng add-context -s %s -k %s >/dev/null",
300 (sudo) ? "sudo" : " ", name, context_list);
301 if (ret < 0) {
302 fprintf(stderr, "allocating cmd\n");
303 goto end;
304 }
305
306 ret = (system(cmd));
307 if (ret != 0) {
308 fprintf(stderr, "error: adding contexts\n");
309 ret = -1;
310 goto end;
311 }
312
313end:
314 return ret;
315}
316
317static
6a1b139c 318int start(char *name, int sudo, int local, int print)
f248b7d8
JD
319{
320 int ret;
321 char cmd[1024];
322
323 ret = sprintf(cmd, "%s lttng start %s >/dev/null",
324 (sudo) ? "sudo" : " ", name);
325 if (ret < 0) {
326 fprintf(stderr, "allocating cmd\n");
327 goto end;
328 }
329
330 ret = (system(cmd));
331 if (ret != 0) {
332 fprintf(stderr, "error: starting the session %s\n", name);
333 ret = -1;
334 goto end;
335 }
336
6a1b139c
JD
337 if (!print)
338 goto end;
339
26d63ddf
JD
340 if (local) {
341 ret = sprintf(cmd, "%s lttng list|grep %s|cut -d'(' -f2|cut -d ')' -f1",
342 (sudo) ? "sudo" : " ", name);
343 } else {
6a1b139c 344 ret = sprintf(cmd, "babeltrace -i lttng-live net://localhost|grep %s|cut -d' ' -f1",
26d63ddf
JD
345 name);
346 }
f248b7d8
JD
347 if (ret < 0) {
348 fprintf(stderr, "allocating cmd\n");
349 goto end;
350 }
26d63ddf
JD
351 fprintf(stderr, "%s session started : ",
352 (local) ? "Local" : "Live");
f248b7d8
JD
353 ret = (system(cmd));
354 if (ret != 0) {
355 fprintf(stderr, "error: listing the sessions\n");
356 ret = -1;
357 goto end;
358 }
359
360end:
361 return ret;
362}
363
6a1b139c
JD
364static
365char *live_path(char *name)
366{
367 FILE *fp;
368 int ret;
369 char path[1035];
370 char cmd[1024];
371 char *out = NULL;
372
373 ret = sprintf(cmd, "lttngtop -r net://localhost|grep %s|cut -d' ' -f1",
374 name);
375 if (ret < 0) {
376 fprintf(stderr, "allocating cmd\n");
377 goto end;
378 }
379
380 fp = popen(cmd, "r");
381 if (fp == NULL) {
382 printf("Failed to run command\n" );
383 goto end;
384 }
385
386 /* Read the output a line at a time - output it. */
387 out = fgets(path, sizeof(path)-1, fp);
388 if (out)
389 out = strdup(path);
390
391 /* close */
392 pclose(fp);
393
394end:
395 return out;
396}
397
f248b7d8 398static
26d63ddf 399int destroy(char *name)
f248b7d8
JD
400{
401 int ret;
26d63ddf 402 int sudo = 0;
f248b7d8
JD
403 char cmd[1024];
404
26d63ddf
JD
405 if (getuid() != 0) {
406 ret = system("sudo -l lttng >/dev/null");
407 if (ret < 0) {
408 fprintf(stderr, "[error] You are not root and not "
409 "allowed by sudo to use lttng\n");
410 ret = -1;
411 goto end;
412 }
413 sudo = 1;
414 }
415
f248b7d8
JD
416 ret = sprintf(cmd, "%s lttng destroy %s >/dev/null",
417 (sudo) ? "sudo" : " ", name);
418 if (ret < 0) {
419 fprintf(stderr, "allocating cmd\n");
420 goto end;
421 }
422
423 ret = (system(cmd));
424 if (ret != 0) {
425 fprintf(stderr, "error: destroying the session %s\n", name);
426 ret = -1;
427 goto end;
428 }
429
430end:
431 return ret;
432}
433
434int create_local_session()
435{
436 int ret;
437 char *name;
438 int sudo = 0;
439
440 ret = check_requirements(&sudo);
441
442 name = random_session_name();
443 if (!name) {
444 ret = -1;
445 goto end;
446 }
447
448 ret = check_session_name(name, sudo);
449 if (ret < 0) {
450 goto end_free;
451 }
452
453 ret = local_session(name, sudo);
454 if (ret < 0) {
455 goto end_free;
456 }
457
26d63ddf 458 ret = enable_events(name, sudo);
f248b7d8
JD
459 if (ret < 0) {
460 goto end_free;
461 }
462
463 ret = add_contexts(name, sudo);
464 if (ret < 0) {
465 goto end_free;
466 }
467
6a1b139c 468 ret = start(name, sudo, 1, 1);
f248b7d8
JD
469 if (ret < 0) {
470 goto end_free;
471 }
472
473end_free:
474 free(name);
475end:
476 return ret;
477}
478
6a1b139c 479int destroy_live_local_session(char *name)
26d63ddf
JD
480{
481 return destroy(name);
482}
483
6a1b139c 484int create_live_local_session(char **session_path, char **session_name, int print)
f248b7d8 485{
26d63ddf
JD
486 int ret;
487 char *name;
488 int sudo = 0;
489
490 ret = check_requirements(&sudo);
491
492 name = random_session_name();
493 if (!name) {
494 ret = -1;
495 goto end;
496 }
497
498 ret = check_session_name(name, sudo);
499 if (ret < 0) {
500 goto end_free;
501 }
502
503 ret = live_local_session(name, sudo);
504 if (ret < 0) {
505 goto end_free;
506 }
507
508 ret = enable_events(name, sudo);
509 if (ret < 0) {
510 goto end_free;
511 }
512
513 ret = add_contexts(name, sudo);
514 if (ret < 0) {
515 goto end_free;
516 }
517
6a1b139c 518 ret = start(name, sudo, 0, print);
26d63ddf
JD
519 if (ret < 0) {
520 goto end_free;
521 }
522
6a1b139c
JD
523 if (session_path)
524 *session_path = live_path(name);
525 if (session_name) {
526 *session_name = name;
527 goto end;
528 }
529
26d63ddf
JD
530end_free:
531 free(name);
532end:
533 return ret;
f248b7d8 534}
This page took 0.066511 seconds and 4 git commands to generate.