]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/journal/journalctl.c
util-lib: split out allocation calls into alloc-util.[ch]
[thirdparty/systemd.git] / src / journal / journalctl.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4 This file is part of systemd.
5
6 Copyright 2011 Lennart Poettering
7
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
12
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
17
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
20 ***/
21
22 #include <errno.h>
23 #include <fcntl.h>
24 #include <fnmatch.h>
25 #include <getopt.h>
26 #include <linux/fs.h>
27 #include <locale.h>
28 #include <poll.h>
29 #include <signal.h>
30 #include <stddef.h>
31 #include <stdio.h>
32 #include <stdlib.h>
33 #include <string.h>
34 #include <sys/inotify.h>
35 #include <sys/stat.h>
36 #include <unistd.h>
37
38 #include "sd-bus.h"
39 #include "sd-journal.h"
40
41 #include "acl-util.h"
42 #include "alloc-util.h"
43 #include "bus-error.h"
44 #include "bus-util.h"
45 #include "catalog.h"
46 #include "chattr-util.h"
47 #include "fd-util.h"
48 #include "fileio.h"
49 #include "fs-util.h"
50 #include "fsprg.h"
51 #include "glob-util.h"
52 #include "hostname-util.h"
53 #include "io-util.h"
54 #include "journal-def.h"
55 #include "journal-internal.h"
56 #include "journal-qrcode.h"
57 #include "journal-vacuum.h"
58 #include "journal-verify.h"
59 #include "locale-util.h"
60 #include "log.h"
61 #include "logs-show.h"
62 #include "mkdir.h"
63 #include "pager.h"
64 #include "parse-util.h"
65 #include "path-util.h"
66 #include "rlimit-util.h"
67 #include "set.h"
68 #include "sigbus.h"
69 #include "strv.h"
70 #include "syslog-util.h"
71 #include "terminal-util.h"
72 #include "unit-name.h"
73 #include "user-util.h"
74
75 #define DEFAULT_FSS_INTERVAL_USEC (15*USEC_PER_MINUTE)
76
77 enum {
78 /* Special values for arg_lines */
79 ARG_LINES_DEFAULT = -2,
80 ARG_LINES_ALL = -1,
81 };
82
83 static OutputMode arg_output = OUTPUT_SHORT;
84 static bool arg_utc = false;
85 static bool arg_pager_end = false;
86 static bool arg_follow = false;
87 static bool arg_full = true;
88 static bool arg_all = false;
89 static bool arg_no_pager = false;
90 static int arg_lines = ARG_LINES_DEFAULT;
91 static bool arg_no_tail = false;
92 static bool arg_quiet = false;
93 static bool arg_merge = false;
94 static bool arg_boot = false;
95 static sd_id128_t arg_boot_id = {};
96 static int arg_boot_offset = 0;
97 static bool arg_dmesg = false;
98 static const char *arg_cursor = NULL;
99 static const char *arg_after_cursor = NULL;
100 static bool arg_show_cursor = false;
101 static const char *arg_directory = NULL;
102 static char **arg_file = NULL;
103 static int arg_priorities = 0xFF;
104 static const char *arg_verify_key = NULL;
105 #ifdef HAVE_GCRYPT
106 static usec_t arg_interval = DEFAULT_FSS_INTERVAL_USEC;
107 static bool arg_force = false;
108 #endif
109 static usec_t arg_since, arg_until;
110 static bool arg_since_set = false, arg_until_set = false;
111 static char **arg_syslog_identifier = NULL;
112 static char **arg_system_units = NULL;
113 static char **arg_user_units = NULL;
114 static const char *arg_field = NULL;
115 static bool arg_catalog = false;
116 static bool arg_reverse = false;
117 static int arg_journal_type = 0;
118 static char *arg_root = NULL;
119 static const char *arg_machine = NULL;
120 static uint64_t arg_vacuum_size = 0;
121 static uint64_t arg_vacuum_n_files = 0;
122 static usec_t arg_vacuum_time = 0;
123
124 static enum {
125 ACTION_SHOW,
126 ACTION_NEW_ID128,
127 ACTION_PRINT_HEADER,
128 ACTION_SETUP_KEYS,
129 ACTION_VERIFY,
130 ACTION_DISK_USAGE,
131 ACTION_LIST_CATALOG,
132 ACTION_DUMP_CATALOG,
133 ACTION_UPDATE_CATALOG,
134 ACTION_LIST_BOOTS,
135 ACTION_FLUSH,
136 ACTION_ROTATE,
137 ACTION_VACUUM,
138 } arg_action = ACTION_SHOW;
139
140 typedef struct BootId {
141 sd_id128_t id;
142 uint64_t first;
143 uint64_t last;
144 LIST_FIELDS(struct BootId, boot_list);
145 } BootId;
146
147 static void pager_open_if_enabled(void) {
148
149 if (arg_no_pager)
150 return;
151
152 pager_open(arg_pager_end);
153 }
154
155 static char *format_timestamp_maybe_utc(char *buf, size_t l, usec_t t) {
156
157 if (arg_utc)
158 return format_timestamp_utc(buf, l, t);
159
160 return format_timestamp(buf, l, t);
161 }
162
163 static int parse_boot_descriptor(const char *x, sd_id128_t *boot_id, int *offset) {
164 sd_id128_t id = SD_ID128_NULL;
165 int off = 0, r;
166
167 if (strlen(x) >= 32) {
168 char *t;
169
170 t = strndupa(x, 32);
171 r = sd_id128_from_string(t, &id);
172 if (r >= 0)
173 x += 32;
174
175 if (*x != '-' && *x != '+' && *x != 0)
176 return -EINVAL;
177
178 if (*x != 0) {
179 r = safe_atoi(x, &off);
180 if (r < 0)
181 return r;
182 }
183 } else {
184 r = safe_atoi(x, &off);
185 if (r < 0)
186 return r;
187 }
188
189 if (boot_id)
190 *boot_id = id;
191
192 if (offset)
193 *offset = off;
194
195 return 0;
196 }
197
198 static void help(void) {
199
200 pager_open_if_enabled();
201
202 printf("%s [OPTIONS...] [MATCHES...]\n\n"
203 "Query the journal.\n\n"
204 "Flags:\n"
205 " --system Show the system journal\n"
206 " --user Show the user journal for the current user\n"
207 " -M --machine=CONTAINER Operate on local container\n"
208 " -S --since=DATE Show entries not older than the specified date\n"
209 " -U --until=DATE Show entries not newer than the specified date\n"
210 " -c --cursor=CURSOR Show entries starting at the specified cursor\n"
211 " --after-cursor=CURSOR Show entries after the specified cursor\n"
212 " --show-cursor Print the cursor after all the entries\n"
213 " -b --boot[=ID] Show current boot or the specified boot\n"
214 " --list-boots Show terse information about recorded boots\n"
215 " -k --dmesg Show kernel message log from the current boot\n"
216 " -u --unit=UNIT Show logs from the specified unit\n"
217 " --user-unit=UNIT Show logs from the specified user unit\n"
218 " -t --identifier=STRING Show entries with the specified syslog identifier\n"
219 " -p --priority=RANGE Show entries with the specified priority\n"
220 " -e --pager-end Immediately jump to the end in the pager\n"
221 " -f --follow Follow the journal\n"
222 " -n --lines[=INTEGER] Number of journal entries to show\n"
223 " --no-tail Show all lines, even in follow mode\n"
224 " -r --reverse Show the newest entries first\n"
225 " -o --output=STRING Change journal output mode (short, short-iso,\n"
226 " short-precise, short-monotonic, verbose,\n"
227 " export, json, json-pretty, json-sse, cat)\n"
228 " --utc Express time in Coordinated Universal Time (UTC)\n"
229 " -x --catalog Add message explanations where available\n"
230 " --no-full Ellipsize fields\n"
231 " -a --all Show all fields, including long and unprintable\n"
232 " -q --quiet Do not show info messages and privilege warning\n"
233 " --no-pager Do not pipe output into a pager\n"
234 " -m --merge Show entries from all available journals\n"
235 " -D --directory=PATH Show journal files from directory\n"
236 " --file=PATH Show journal file\n"
237 " --root=ROOT Operate on catalog files underneath the root ROOT\n"
238 #ifdef HAVE_GCRYPT
239 " --interval=TIME Time interval for changing the FSS sealing key\n"
240 " --verify-key=KEY Specify FSS verification key\n"
241 " --force Override of the FSS key pair with --setup-keys\n"
242 #endif
243 "\nCommands:\n"
244 " -h --help Show this help text\n"
245 " --version Show package version\n"
246 " -F --field=FIELD List all values that a specified field takes\n"
247 " --new-id128 Generate a new 128-bit ID\n"
248 " --disk-usage Show total disk usage of all journal files\n"
249 " --vacuum-size=BYTES Reduce disk usage below specified size\n"
250 " --vacuum-files=INT Leave only the specified number of journal files\n"
251 " --vacuum-time=TIME Remove journal files older than specified time\n"
252 " --flush Flush all journal data from /run into /var\n"
253 " --rotate Request immediate rotation of the journal files\n"
254 " --header Show journal header information\n"
255 " --list-catalog Show all message IDs in the catalog\n"
256 " --dump-catalog Show entries in the message catalog\n"
257 " --update-catalog Update the message catalog database\n"
258 #ifdef HAVE_GCRYPT
259 " --setup-keys Generate a new FSS key pair\n"
260 " --verify Verify journal file consistency\n"
261 #endif
262 , program_invocation_short_name);
263 }
264
265 static int parse_argv(int argc, char *argv[]) {
266
267 enum {
268 ARG_VERSION = 0x100,
269 ARG_NO_PAGER,
270 ARG_NO_FULL,
271 ARG_NO_TAIL,
272 ARG_NEW_ID128,
273 ARG_LIST_BOOTS,
274 ARG_USER,
275 ARG_SYSTEM,
276 ARG_ROOT,
277 ARG_HEADER,
278 ARG_SETUP_KEYS,
279 ARG_FILE,
280 ARG_INTERVAL,
281 ARG_VERIFY,
282 ARG_VERIFY_KEY,
283 ARG_DISK_USAGE,
284 ARG_AFTER_CURSOR,
285 ARG_SHOW_CURSOR,
286 ARG_USER_UNIT,
287 ARG_LIST_CATALOG,
288 ARG_DUMP_CATALOG,
289 ARG_UPDATE_CATALOG,
290 ARG_FORCE,
291 ARG_UTC,
292 ARG_FLUSH,
293 ARG_ROTATE,
294 ARG_VACUUM_SIZE,
295 ARG_VACUUM_FILES,
296 ARG_VACUUM_TIME,
297 };
298
299 static const struct option options[] = {
300 { "help", no_argument, NULL, 'h' },
301 { "version" , no_argument, NULL, ARG_VERSION },
302 { "no-pager", no_argument, NULL, ARG_NO_PAGER },
303 { "pager-end", no_argument, NULL, 'e' },
304 { "follow", no_argument, NULL, 'f' },
305 { "force", no_argument, NULL, ARG_FORCE },
306 { "output", required_argument, NULL, 'o' },
307 { "all", no_argument, NULL, 'a' },
308 { "full", no_argument, NULL, 'l' },
309 { "no-full", no_argument, NULL, ARG_NO_FULL },
310 { "lines", optional_argument, NULL, 'n' },
311 { "no-tail", no_argument, NULL, ARG_NO_TAIL },
312 { "new-id128", no_argument, NULL, ARG_NEW_ID128 },
313 { "quiet", no_argument, NULL, 'q' },
314 { "merge", no_argument, NULL, 'm' },
315 { "boot", optional_argument, NULL, 'b' },
316 { "list-boots", no_argument, NULL, ARG_LIST_BOOTS },
317 { "this-boot", optional_argument, NULL, 'b' }, /* deprecated */
318 { "dmesg", no_argument, NULL, 'k' },
319 { "system", no_argument, NULL, ARG_SYSTEM },
320 { "user", no_argument, NULL, ARG_USER },
321 { "directory", required_argument, NULL, 'D' },
322 { "file", required_argument, NULL, ARG_FILE },
323 { "root", required_argument, NULL, ARG_ROOT },
324 { "header", no_argument, NULL, ARG_HEADER },
325 { "identifier", required_argument, NULL, 't' },
326 { "priority", required_argument, NULL, 'p' },
327 { "setup-keys", no_argument, NULL, ARG_SETUP_KEYS },
328 { "interval", required_argument, NULL, ARG_INTERVAL },
329 { "verify", no_argument, NULL, ARG_VERIFY },
330 { "verify-key", required_argument, NULL, ARG_VERIFY_KEY },
331 { "disk-usage", no_argument, NULL, ARG_DISK_USAGE },
332 { "cursor", required_argument, NULL, 'c' },
333 { "after-cursor", required_argument, NULL, ARG_AFTER_CURSOR },
334 { "show-cursor", no_argument, NULL, ARG_SHOW_CURSOR },
335 { "since", required_argument, NULL, 'S' },
336 { "until", required_argument, NULL, 'U' },
337 { "unit", required_argument, NULL, 'u' },
338 { "user-unit", required_argument, NULL, ARG_USER_UNIT },
339 { "field", required_argument, NULL, 'F' },
340 { "catalog", no_argument, NULL, 'x' },
341 { "list-catalog", no_argument, NULL, ARG_LIST_CATALOG },
342 { "dump-catalog", no_argument, NULL, ARG_DUMP_CATALOG },
343 { "update-catalog", no_argument, NULL, ARG_UPDATE_CATALOG },
344 { "reverse", no_argument, NULL, 'r' },
345 { "machine", required_argument, NULL, 'M' },
346 { "utc", no_argument, NULL, ARG_UTC },
347 { "flush", no_argument, NULL, ARG_FLUSH },
348 { "rotate", no_argument, NULL, ARG_ROTATE },
349 { "vacuum-size", required_argument, NULL, ARG_VACUUM_SIZE },
350 { "vacuum-files", required_argument, NULL, ARG_VACUUM_FILES },
351 { "vacuum-time", required_argument, NULL, ARG_VACUUM_TIME },
352 {}
353 };
354
355 int c, r;
356
357 assert(argc >= 0);
358 assert(argv);
359
360 while ((c = getopt_long(argc, argv, "hefo:aln::qmb::kD:p:c:S:U:t:u:F:xrM:", options, NULL)) >= 0)
361
362 switch (c) {
363
364 case 'h':
365 help();
366 return 0;
367
368 case ARG_VERSION:
369 return version();
370
371 case ARG_NO_PAGER:
372 arg_no_pager = true;
373 break;
374
375 case 'e':
376 arg_pager_end = true;
377
378 if (arg_lines == ARG_LINES_DEFAULT)
379 arg_lines = 1000;
380
381 break;
382
383 case 'f':
384 arg_follow = true;
385 break;
386
387 case 'o':
388 arg_output = output_mode_from_string(optarg);
389 if (arg_output < 0) {
390 log_error("Unknown output format '%s'.", optarg);
391 return -EINVAL;
392 }
393
394 if (arg_output == OUTPUT_EXPORT ||
395 arg_output == OUTPUT_JSON ||
396 arg_output == OUTPUT_JSON_PRETTY ||
397 arg_output == OUTPUT_JSON_SSE ||
398 arg_output == OUTPUT_CAT)
399 arg_quiet = true;
400
401 break;
402
403 case 'l':
404 arg_full = true;
405 break;
406
407 case ARG_NO_FULL:
408 arg_full = false;
409 break;
410
411 case 'a':
412 arg_all = true;
413 break;
414
415 case 'n':
416 if (optarg) {
417 if (streq(optarg, "all"))
418 arg_lines = ARG_LINES_ALL;
419 else {
420 r = safe_atoi(optarg, &arg_lines);
421 if (r < 0 || arg_lines < 0) {
422 log_error("Failed to parse lines '%s'", optarg);
423 return -EINVAL;
424 }
425 }
426 } else {
427 arg_lines = 10;
428
429 /* Hmm, no argument? Maybe the next
430 * word on the command line is
431 * supposed to be the argument? Let's
432 * see if there is one, and is
433 * parsable. */
434 if (optind < argc) {
435 int n;
436 if (streq(argv[optind], "all")) {
437 arg_lines = ARG_LINES_ALL;
438 optind++;
439 } else if (safe_atoi(argv[optind], &n) >= 0 && n >= 0) {
440 arg_lines = n;
441 optind++;
442 }
443 }
444 }
445
446 break;
447
448 case ARG_NO_TAIL:
449 arg_no_tail = true;
450 break;
451
452 case ARG_NEW_ID128:
453 arg_action = ACTION_NEW_ID128;
454 break;
455
456 case 'q':
457 arg_quiet = true;
458 break;
459
460 case 'm':
461 arg_merge = true;
462 break;
463
464 case 'b':
465 arg_boot = true;
466
467 if (optarg) {
468 r = parse_boot_descriptor(optarg, &arg_boot_id, &arg_boot_offset);
469 if (r < 0) {
470 log_error("Failed to parse boot descriptor '%s'", optarg);
471 return -EINVAL;
472 }
473 } else {
474
475 /* Hmm, no argument? Maybe the next
476 * word on the command line is
477 * supposed to be the argument? Let's
478 * see if there is one and is parsable
479 * as a boot descriptor... */
480
481 if (optind < argc &&
482 parse_boot_descriptor(argv[optind], &arg_boot_id, &arg_boot_offset) >= 0)
483 optind++;
484 }
485
486 break;
487
488 case ARG_LIST_BOOTS:
489 arg_action = ACTION_LIST_BOOTS;
490 break;
491
492 case 'k':
493 arg_boot = arg_dmesg = true;
494 break;
495
496 case ARG_SYSTEM:
497 arg_journal_type |= SD_JOURNAL_SYSTEM;
498 break;
499
500 case ARG_USER:
501 arg_journal_type |= SD_JOURNAL_CURRENT_USER;
502 break;
503
504 case 'M':
505 arg_machine = optarg;
506 break;
507
508 case 'D':
509 arg_directory = optarg;
510 break;
511
512 case ARG_FILE:
513 r = glob_extend(&arg_file, optarg);
514 if (r < 0)
515 return log_error_errno(r, "Failed to add paths: %m");
516 break;
517
518 case ARG_ROOT:
519 r = parse_path_argument_and_warn(optarg, true, &arg_root);
520 if (r < 0)
521 return r;
522 break;
523
524 case 'c':
525 arg_cursor = optarg;
526 break;
527
528 case ARG_AFTER_CURSOR:
529 arg_after_cursor = optarg;
530 break;
531
532 case ARG_SHOW_CURSOR:
533 arg_show_cursor = true;
534 break;
535
536 case ARG_HEADER:
537 arg_action = ACTION_PRINT_HEADER;
538 break;
539
540 case ARG_VERIFY:
541 arg_action = ACTION_VERIFY;
542 break;
543
544 case ARG_DISK_USAGE:
545 arg_action = ACTION_DISK_USAGE;
546 break;
547
548 case ARG_VACUUM_SIZE:
549 r = parse_size(optarg, 1024, &arg_vacuum_size);
550 if (r < 0) {
551 log_error("Failed to parse vacuum size: %s", optarg);
552 return r;
553 }
554
555 arg_action = ACTION_VACUUM;
556 break;
557
558 case ARG_VACUUM_FILES:
559 r = safe_atou64(optarg, &arg_vacuum_n_files);
560 if (r < 0) {
561 log_error("Failed to parse vacuum files: %s", optarg);
562 return r;
563 }
564
565 arg_action = ACTION_VACUUM;
566 break;
567
568 case ARG_VACUUM_TIME:
569 r = parse_sec(optarg, &arg_vacuum_time);
570 if (r < 0) {
571 log_error("Failed to parse vacuum time: %s", optarg);
572 return r;
573 }
574
575 arg_action = ACTION_VACUUM;
576 break;
577
578 #ifdef HAVE_GCRYPT
579 case ARG_FORCE:
580 arg_force = true;
581 break;
582
583 case ARG_SETUP_KEYS:
584 arg_action = ACTION_SETUP_KEYS;
585 break;
586
587
588 case ARG_VERIFY_KEY:
589 arg_action = ACTION_VERIFY;
590 arg_verify_key = optarg;
591 arg_merge = false;
592 break;
593
594 case ARG_INTERVAL:
595 r = parse_sec(optarg, &arg_interval);
596 if (r < 0 || arg_interval <= 0) {
597 log_error("Failed to parse sealing key change interval: %s", optarg);
598 return -EINVAL;
599 }
600 break;
601 #else
602 case ARG_SETUP_KEYS:
603 case ARG_VERIFY_KEY:
604 case ARG_INTERVAL:
605 case ARG_FORCE:
606 log_error("Forward-secure sealing not available.");
607 return -EOPNOTSUPP;
608 #endif
609
610 case 'p': {
611 const char *dots;
612
613 dots = strstr(optarg, "..");
614 if (dots) {
615 char *a;
616 int from, to, i;
617
618 /* a range */
619 a = strndup(optarg, dots - optarg);
620 if (!a)
621 return log_oom();
622
623 from = log_level_from_string(a);
624 to = log_level_from_string(dots + 2);
625 free(a);
626
627 if (from < 0 || to < 0) {
628 log_error("Failed to parse log level range %s", optarg);
629 return -EINVAL;
630 }
631
632 arg_priorities = 0;
633
634 if (from < to) {
635 for (i = from; i <= to; i++)
636 arg_priorities |= 1 << i;
637 } else {
638 for (i = to; i <= from; i++)
639 arg_priorities |= 1 << i;
640 }
641
642 } else {
643 int p, i;
644
645 p = log_level_from_string(optarg);
646 if (p < 0) {
647 log_error("Unknown log level %s", optarg);
648 return -EINVAL;
649 }
650
651 arg_priorities = 0;
652
653 for (i = 0; i <= p; i++)
654 arg_priorities |= 1 << i;
655 }
656
657 break;
658 }
659
660 case 'S':
661 r = parse_timestamp(optarg, &arg_since);
662 if (r < 0) {
663 log_error("Failed to parse timestamp: %s", optarg);
664 return -EINVAL;
665 }
666 arg_since_set = true;
667 break;
668
669 case 'U':
670 r = parse_timestamp(optarg, &arg_until);
671 if (r < 0) {
672 log_error("Failed to parse timestamp: %s", optarg);
673 return -EINVAL;
674 }
675 arg_until_set = true;
676 break;
677
678 case 't':
679 r = strv_extend(&arg_syslog_identifier, optarg);
680 if (r < 0)
681 return log_oom();
682 break;
683
684 case 'u':
685 r = strv_extend(&arg_system_units, optarg);
686 if (r < 0)
687 return log_oom();
688 break;
689
690 case ARG_USER_UNIT:
691 r = strv_extend(&arg_user_units, optarg);
692 if (r < 0)
693 return log_oom();
694 break;
695
696 case 'F':
697 arg_field = optarg;
698 break;
699
700 case 'x':
701 arg_catalog = true;
702 break;
703
704 case ARG_LIST_CATALOG:
705 arg_action = ACTION_LIST_CATALOG;
706 break;
707
708 case ARG_DUMP_CATALOG:
709 arg_action = ACTION_DUMP_CATALOG;
710 break;
711
712 case ARG_UPDATE_CATALOG:
713 arg_action = ACTION_UPDATE_CATALOG;
714 break;
715
716 case 'r':
717 arg_reverse = true;
718 break;
719
720 case ARG_UTC:
721 arg_utc = true;
722 break;
723
724 case ARG_FLUSH:
725 arg_action = ACTION_FLUSH;
726 break;
727
728 case ARG_ROTATE:
729 arg_action = ACTION_ROTATE;
730 break;
731
732 case '?':
733 return -EINVAL;
734
735 default:
736 assert_not_reached("Unhandled option");
737 }
738
739 if (arg_follow && !arg_no_tail && !arg_since && arg_lines == ARG_LINES_DEFAULT)
740 arg_lines = 10;
741
742 if (!!arg_directory + !!arg_file + !!arg_machine > 1) {
743 log_error("Please specify either -D/--directory= or --file= or -M/--machine=, not more than one.");
744 return -EINVAL;
745 }
746
747 if (arg_since_set && arg_until_set && arg_since > arg_until) {
748 log_error("--since= must be before --until=.");
749 return -EINVAL;
750 }
751
752 if (!!arg_cursor + !!arg_after_cursor + !!arg_since_set > 1) {
753 log_error("Please specify only one of --since=, --cursor=, and --after-cursor.");
754 return -EINVAL;
755 }
756
757 if (arg_follow && arg_reverse) {
758 log_error("Please specify either --reverse= or --follow=, not both.");
759 return -EINVAL;
760 }
761
762 if (!IN_SET(arg_action, ACTION_SHOW, ACTION_DUMP_CATALOG, ACTION_LIST_CATALOG) && optind < argc) {
763 log_error("Extraneous arguments starting with '%s'", argv[optind]);
764 return -EINVAL;
765 }
766
767 if ((arg_boot || arg_action == ACTION_LIST_BOOTS) && (arg_file || arg_directory || arg_merge)) {
768 log_error("Using --boot or --list-boots with --file, --directory or --merge is not supported.");
769 return -EINVAL;
770 }
771
772 return 1;
773 }
774
775 static int generate_new_id128(void) {
776 sd_id128_t id;
777 int r;
778 unsigned i;
779
780 r = sd_id128_randomize(&id);
781 if (r < 0)
782 return log_error_errno(r, "Failed to generate ID: %m");
783
784 printf("As string:\n"
785 SD_ID128_FORMAT_STR "\n\n"
786 "As UUID:\n"
787 "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x\n\n"
788 "As macro:\n"
789 "#define MESSAGE_XYZ SD_ID128_MAKE(",
790 SD_ID128_FORMAT_VAL(id),
791 SD_ID128_FORMAT_VAL(id));
792 for (i = 0; i < 16; i++)
793 printf("%02x%s", id.bytes[i], i != 15 ? "," : "");
794 fputs(")\n\n", stdout);
795
796 printf("As Python constant:\n"
797 ">>> import uuid\n"
798 ">>> MESSAGE_XYZ = uuid.UUID('" SD_ID128_FORMAT_STR "')\n",
799 SD_ID128_FORMAT_VAL(id));
800
801 return 0;
802 }
803
804 static int add_matches(sd_journal *j, char **args) {
805 char **i;
806 bool have_term = false;
807
808 assert(j);
809
810 STRV_FOREACH(i, args) {
811 int r;
812
813 if (streq(*i, "+")) {
814 if (!have_term)
815 break;
816 r = sd_journal_add_disjunction(j);
817 have_term = false;
818
819 } else if (path_is_absolute(*i)) {
820 _cleanup_free_ char *p, *t = NULL, *t2 = NULL;
821 const char *path;
822 _cleanup_free_ char *interpreter = NULL;
823 struct stat st;
824
825 p = canonicalize_file_name(*i);
826 path = p ? p : *i;
827
828 if (lstat(path, &st) < 0)
829 return log_error_errno(errno, "Couldn't stat file: %m");
830
831 if (S_ISREG(st.st_mode) && (0111 & st.st_mode)) {
832 if (executable_is_script(path, &interpreter) > 0) {
833 _cleanup_free_ char *comm;
834
835 comm = strndup(basename(path), 15);
836 if (!comm)
837 return log_oom();
838
839 t = strappend("_COMM=", comm);
840
841 /* Append _EXE only if the interpreter is not a link.
842 Otherwise, it might be outdated often. */
843 if (lstat(interpreter, &st) == 0 &&
844 !S_ISLNK(st.st_mode)) {
845 t2 = strappend("_EXE=", interpreter);
846 if (!t2)
847 return log_oom();
848 }
849 } else
850 t = strappend("_EXE=", path);
851 } else if (S_ISCHR(st.st_mode))
852 (void) asprintf(&t, "_KERNEL_DEVICE=c%u:%u", major(st.st_rdev), minor(st.st_rdev));
853 else if (S_ISBLK(st.st_mode))
854 (void) asprintf(&t, "_KERNEL_DEVICE=b%u:%u", major(st.st_rdev), minor(st.st_rdev));
855 else {
856 log_error("File is neither a device node, nor regular file, nor executable: %s", *i);
857 return -EINVAL;
858 }
859
860 if (!t)
861 return log_oom();
862
863 r = sd_journal_add_match(j, t, 0);
864 if (t2)
865 r = sd_journal_add_match(j, t2, 0);
866 have_term = true;
867
868 } else {
869 r = sd_journal_add_match(j, *i, 0);
870 have_term = true;
871 }
872
873 if (r < 0)
874 return log_error_errno(r, "Failed to add match '%s': %m", *i);
875 }
876
877 if (!strv_isempty(args) && !have_term) {
878 log_error("\"+\" can only be used between terms");
879 return -EINVAL;
880 }
881
882 return 0;
883 }
884
885 static void boot_id_free_all(BootId *l) {
886
887 while (l) {
888 BootId *i = l;
889 LIST_REMOVE(boot_list, l, i);
890 free(i);
891 }
892 }
893
894 static int discover_next_boot(
895 sd_journal *j,
896 BootId **boot,
897 bool advance_older,
898 bool read_realtime) {
899
900 int r;
901 char match[9+32+1] = "_BOOT_ID=";
902 _cleanup_free_ BootId *next_boot = NULL;
903
904 assert(j);
905 assert(boot);
906
907 /* We expect the journal to be on the last position of a boot
908 * (in relation to the direction we are going), so that the next
909 * invocation of sd_journal_next/previous will be from a different
910 * boot. We then collect any information we desire and then jump
911 * to the last location of the new boot by using a _BOOT_ID match
912 * coming from the other journal direction. */
913
914 /* Make sure we aren't restricted by any _BOOT_ID matches, so that
915 * we can actually advance to a *different* boot. */
916 sd_journal_flush_matches(j);
917
918 if (advance_older)
919 r = sd_journal_previous(j);
920 else
921 r = sd_journal_next(j);
922 if (r < 0)
923 return r;
924 else if (r == 0)
925 return 0; /* End of journal, yay. */
926
927 next_boot = new0(BootId, 1);
928 if (!next_boot)
929 return -ENOMEM;
930
931 r = sd_journal_get_monotonic_usec(j, NULL, &next_boot->id);
932 if (r < 0)
933 return r;
934
935 if (read_realtime) {
936 r = sd_journal_get_realtime_usec(j, &next_boot->first);
937 if (r < 0)
938 return r;
939 }
940
941 /* Now seek to the last occurrence of this boot ID. */
942 sd_id128_to_string(next_boot->id, match + 9);
943 r = sd_journal_add_match(j, match, sizeof(match) - 1);
944 if (r < 0)
945 return r;
946
947 if (advance_older)
948 r = sd_journal_seek_head(j);
949 else
950 r = sd_journal_seek_tail(j);
951 if (r < 0)
952 return r;
953
954 if (advance_older)
955 r = sd_journal_next(j);
956 else
957 r = sd_journal_previous(j);
958 if (r < 0)
959 return r;
960 else if (r == 0)
961 return -ENODATA; /* This shouldn't happen. We just came from this very boot ID. */
962
963 if (read_realtime) {
964 r = sd_journal_get_realtime_usec(j, &next_boot->last);
965 if (r < 0)
966 return r;
967 }
968
969 *boot = next_boot;
970 next_boot = NULL;
971
972 return 0;
973 }
974
975 static int get_boots(
976 sd_journal *j,
977 BootId **boots,
978 BootId *query_ref_boot,
979 int ref_boot_offset) {
980
981 bool skip_once;
982 int r, count = 0;
983 BootId *head = NULL, *tail = NULL;
984 const bool advance_older = query_ref_boot && ref_boot_offset <= 0;
985
986 assert(j);
987
988 /* Adjust for the asymmetry that offset 0 is
989 * the last (and current) boot, while 1 is considered the
990 * (chronological) first boot in the journal. */
991 skip_once = query_ref_boot && sd_id128_is_null(query_ref_boot->id) && ref_boot_offset < 0;
992
993 /* Advance to the earliest/latest occurrence of our reference
994 * boot ID (taking our lookup direction into account), so that
995 * discover_next_boot() can do its job.
996 * If no reference is given, the journal head/tail will do,
997 * they're "virtual" boots after all. */
998 if (query_ref_boot && !sd_id128_is_null(query_ref_boot->id)) {
999 char match[9+32+1] = "_BOOT_ID=";
1000
1001 sd_journal_flush_matches(j);
1002
1003 sd_id128_to_string(query_ref_boot->id, match + 9);
1004 r = sd_journal_add_match(j, match, sizeof(match) - 1);
1005 if (r < 0)
1006 return r;
1007
1008 if (advance_older)
1009 r = sd_journal_seek_head(j);
1010 else
1011 r = sd_journal_seek_tail(j);
1012 if (r < 0)
1013 return r;
1014
1015 if (advance_older)
1016 r = sd_journal_next(j);
1017 else
1018 r = sd_journal_previous(j);
1019 if (r < 0)
1020 return r;
1021 else if (r == 0)
1022 goto finish;
1023 else if (ref_boot_offset == 0) {
1024 count = 1;
1025 goto finish;
1026 }
1027 } else {
1028 if (advance_older)
1029 r = sd_journal_seek_tail(j);
1030 else
1031 r = sd_journal_seek_head(j);
1032 if (r < 0)
1033 return r;
1034
1035 /* No sd_journal_next/previous here. */
1036 }
1037
1038 for (;;) {
1039 _cleanup_free_ BootId *current = NULL;
1040
1041 r = discover_next_boot(j, &current, advance_older, !query_ref_boot);
1042 if (r < 0) {
1043 boot_id_free_all(head);
1044 return r;
1045 }
1046
1047 if (!current)
1048 break;
1049
1050 if (query_ref_boot) {
1051 if (!skip_once)
1052 ref_boot_offset += advance_older ? 1 : -1;
1053 skip_once = false;
1054
1055 if (ref_boot_offset == 0) {
1056 count = 1;
1057 query_ref_boot->id = current->id;
1058 break;
1059 }
1060 } else {
1061 LIST_INSERT_AFTER(boot_list, head, tail, current);
1062 tail = current;
1063 current = NULL;
1064 count++;
1065 }
1066 }
1067
1068 finish:
1069 if (boots)
1070 *boots = head;
1071
1072 sd_journal_flush_matches(j);
1073
1074 return count;
1075 }
1076
1077 static int list_boots(sd_journal *j) {
1078 int w, i, count;
1079 BootId *id, *all_ids;
1080
1081 assert(j);
1082
1083 count = get_boots(j, &all_ids, NULL, 0);
1084 if (count < 0)
1085 return log_error_errno(count, "Failed to determine boots: %m");
1086 if (count == 0)
1087 return count;
1088
1089 pager_open_if_enabled();
1090
1091 /* numbers are one less, but we need an extra char for the sign */
1092 w = DECIMAL_STR_WIDTH(count - 1) + 1;
1093
1094 i = 0;
1095 LIST_FOREACH(boot_list, id, all_ids) {
1096 char a[FORMAT_TIMESTAMP_MAX], b[FORMAT_TIMESTAMP_MAX];
1097
1098 printf("% *i " SD_ID128_FORMAT_STR " %s—%s\n",
1099 w, i - count + 1,
1100 SD_ID128_FORMAT_VAL(id->id),
1101 format_timestamp_maybe_utc(a, sizeof(a), id->first),
1102 format_timestamp_maybe_utc(b, sizeof(b), id->last));
1103 i++;
1104 }
1105
1106 boot_id_free_all(all_ids);
1107
1108 return 0;
1109 }
1110
1111 static int add_boot(sd_journal *j) {
1112 char match[9+32+1] = "_BOOT_ID=";
1113 int r;
1114 BootId ref_boot_id = {};
1115
1116 assert(j);
1117
1118 if (!arg_boot)
1119 return 0;
1120
1121 if (arg_boot_offset == 0 && sd_id128_equal(arg_boot_id, SD_ID128_NULL))
1122 return add_match_this_boot(j, arg_machine);
1123
1124 ref_boot_id.id = arg_boot_id;
1125 r = get_boots(j, NULL, &ref_boot_id, arg_boot_offset);
1126 assert(r <= 1);
1127 if (r <= 0) {
1128 const char *reason = (r == 0) ? "No such boot ID in journal" : strerror(-r);
1129
1130 if (sd_id128_is_null(arg_boot_id))
1131 log_error("Failed to look up boot %+i: %s", arg_boot_offset, reason);
1132 else
1133 log_error("Failed to look up boot ID "SD_ID128_FORMAT_STR"%+i: %s",
1134 SD_ID128_FORMAT_VAL(arg_boot_id), arg_boot_offset, reason);
1135
1136 return r == 0 ? -ENODATA : r;
1137 }
1138
1139 sd_id128_to_string(ref_boot_id.id, match + 9);
1140
1141 r = sd_journal_add_match(j, match, sizeof(match) - 1);
1142 if (r < 0)
1143 return log_error_errno(r, "Failed to add match: %m");
1144
1145 r = sd_journal_add_conjunction(j);
1146 if (r < 0)
1147 return log_error_errno(r, "Failed to add conjunction: %m");
1148
1149 return 0;
1150 }
1151
1152 static int add_dmesg(sd_journal *j) {
1153 int r;
1154 assert(j);
1155
1156 if (!arg_dmesg)
1157 return 0;
1158
1159 r = sd_journal_add_match(j, "_TRANSPORT=kernel", strlen("_TRANSPORT=kernel"));
1160 if (r < 0)
1161 return log_error_errno(r, "Failed to add match: %m");
1162
1163 r = sd_journal_add_conjunction(j);
1164 if (r < 0)
1165 return log_error_errno(r, "Failed to add conjunction: %m");
1166
1167 return 0;
1168 }
1169
1170 static int get_possible_units(
1171 sd_journal *j,
1172 const char *fields,
1173 char **patterns,
1174 Set **units) {
1175
1176 _cleanup_set_free_free_ Set *found;
1177 const char *field;
1178 int r;
1179
1180 found = set_new(&string_hash_ops);
1181 if (!found)
1182 return -ENOMEM;
1183
1184 NULSTR_FOREACH(field, fields) {
1185 const void *data;
1186 size_t size;
1187
1188 r = sd_journal_query_unique(j, field);
1189 if (r < 0)
1190 return r;
1191
1192 SD_JOURNAL_FOREACH_UNIQUE(j, data, size) {
1193 char **pattern, *eq;
1194 size_t prefix;
1195 _cleanup_free_ char *u = NULL;
1196
1197 eq = memchr(data, '=', size);
1198 if (eq)
1199 prefix = eq - (char*) data + 1;
1200 else
1201 prefix = 0;
1202
1203 u = strndup((char*) data + prefix, size - prefix);
1204 if (!u)
1205 return -ENOMEM;
1206
1207 STRV_FOREACH(pattern, patterns)
1208 if (fnmatch(*pattern, u, FNM_NOESCAPE) == 0) {
1209 log_debug("Matched %s with pattern %s=%s", u, field, *pattern);
1210
1211 r = set_consume(found, u);
1212 u = NULL;
1213 if (r < 0 && r != -EEXIST)
1214 return r;
1215
1216 break;
1217 }
1218 }
1219 }
1220
1221 *units = found;
1222 found = NULL;
1223 return 0;
1224 }
1225
1226 /* This list is supposed to return the superset of unit names
1227 * possibly matched by rules added with add_matches_for_unit... */
1228 #define SYSTEM_UNITS \
1229 "_SYSTEMD_UNIT\0" \
1230 "COREDUMP_UNIT\0" \
1231 "UNIT\0" \
1232 "OBJECT_SYSTEMD_UNIT\0" \
1233 "_SYSTEMD_SLICE\0"
1234
1235 /* ... and add_matches_for_user_unit */
1236 #define USER_UNITS \
1237 "_SYSTEMD_USER_UNIT\0" \
1238 "USER_UNIT\0" \
1239 "COREDUMP_USER_UNIT\0" \
1240 "OBJECT_SYSTEMD_USER_UNIT\0"
1241
1242 static int add_units(sd_journal *j) {
1243 _cleanup_strv_free_ char **patterns = NULL;
1244 int r, count = 0;
1245 char **i;
1246
1247 assert(j);
1248
1249 STRV_FOREACH(i, arg_system_units) {
1250 _cleanup_free_ char *u = NULL;
1251
1252 r = unit_name_mangle(*i, UNIT_NAME_GLOB, &u);
1253 if (r < 0)
1254 return r;
1255
1256 if (string_is_glob(u)) {
1257 r = strv_push(&patterns, u);
1258 if (r < 0)
1259 return r;
1260 u = NULL;
1261 } else {
1262 r = add_matches_for_unit(j, u);
1263 if (r < 0)
1264 return r;
1265 r = sd_journal_add_disjunction(j);
1266 if (r < 0)
1267 return r;
1268 count ++;
1269 }
1270 }
1271
1272 if (!strv_isempty(patterns)) {
1273 _cleanup_set_free_free_ Set *units = NULL;
1274 Iterator it;
1275 char *u;
1276
1277 r = get_possible_units(j, SYSTEM_UNITS, patterns, &units);
1278 if (r < 0)
1279 return r;
1280
1281 SET_FOREACH(u, units, it) {
1282 r = add_matches_for_unit(j, u);
1283 if (r < 0)
1284 return r;
1285 r = sd_journal_add_disjunction(j);
1286 if (r < 0)
1287 return r;
1288 count ++;
1289 }
1290 }
1291
1292 patterns = strv_free(patterns);
1293
1294 STRV_FOREACH(i, arg_user_units) {
1295 _cleanup_free_ char *u = NULL;
1296
1297 r = unit_name_mangle(*i, UNIT_NAME_GLOB, &u);
1298 if (r < 0)
1299 return r;
1300
1301 if (string_is_glob(u)) {
1302 r = strv_push(&patterns, u);
1303 if (r < 0)
1304 return r;
1305 u = NULL;
1306 } else {
1307 r = add_matches_for_user_unit(j, u, getuid());
1308 if (r < 0)
1309 return r;
1310 r = sd_journal_add_disjunction(j);
1311 if (r < 0)
1312 return r;
1313 count ++;
1314 }
1315 }
1316
1317 if (!strv_isempty(patterns)) {
1318 _cleanup_set_free_free_ Set *units = NULL;
1319 Iterator it;
1320 char *u;
1321
1322 r = get_possible_units(j, USER_UNITS, patterns, &units);
1323 if (r < 0)
1324 return r;
1325
1326 SET_FOREACH(u, units, it) {
1327 r = add_matches_for_user_unit(j, u, getuid());
1328 if (r < 0)
1329 return r;
1330 r = sd_journal_add_disjunction(j);
1331 if (r < 0)
1332 return r;
1333 count ++;
1334 }
1335 }
1336
1337 /* Complain if the user request matches but nothing whatsoever was
1338 * found, since otherwise everything would be matched. */
1339 if (!(strv_isempty(arg_system_units) && strv_isempty(arg_user_units)) && count == 0)
1340 return -ENODATA;
1341
1342 r = sd_journal_add_conjunction(j);
1343 if (r < 0)
1344 return r;
1345
1346 return 0;
1347 }
1348
1349 static int add_priorities(sd_journal *j) {
1350 char match[] = "PRIORITY=0";
1351 int i, r;
1352 assert(j);
1353
1354 if (arg_priorities == 0xFF)
1355 return 0;
1356
1357 for (i = LOG_EMERG; i <= LOG_DEBUG; i++)
1358 if (arg_priorities & (1 << i)) {
1359 match[sizeof(match)-2] = '0' + i;
1360
1361 r = sd_journal_add_match(j, match, strlen(match));
1362 if (r < 0)
1363 return log_error_errno(r, "Failed to add match: %m");
1364 }
1365
1366 r = sd_journal_add_conjunction(j);
1367 if (r < 0)
1368 return log_error_errno(r, "Failed to add conjunction: %m");
1369
1370 return 0;
1371 }
1372
1373
1374 static int add_syslog_identifier(sd_journal *j) {
1375 int r;
1376 char **i;
1377
1378 assert(j);
1379
1380 STRV_FOREACH(i, arg_syslog_identifier) {
1381 char *u;
1382
1383 u = strjoina("SYSLOG_IDENTIFIER=", *i);
1384 r = sd_journal_add_match(j, u, 0);
1385 if (r < 0)
1386 return r;
1387 r = sd_journal_add_disjunction(j);
1388 if (r < 0)
1389 return r;
1390 }
1391
1392 r = sd_journal_add_conjunction(j);
1393 if (r < 0)
1394 return r;
1395
1396 return 0;
1397 }
1398
1399 static int setup_keys(void) {
1400 #ifdef HAVE_GCRYPT
1401 size_t mpk_size, seed_size, state_size, i;
1402 uint8_t *mpk, *seed, *state;
1403 int fd = -1, r;
1404 sd_id128_t machine, boot;
1405 char *p = NULL, *k = NULL;
1406 struct FSSHeader h;
1407 uint64_t n;
1408 struct stat st;
1409
1410 r = stat("/var/log/journal", &st);
1411 if (r < 0 && errno != ENOENT && errno != ENOTDIR)
1412 return log_error_errno(errno, "stat(\"%s\") failed: %m", "/var/log/journal");
1413
1414 if (r < 0 || !S_ISDIR(st.st_mode)) {
1415 log_error("%s is not a directory, must be using persistent logging for FSS.",
1416 "/var/log/journal");
1417 return r < 0 ? -errno : -ENOTDIR;
1418 }
1419
1420 r = sd_id128_get_machine(&machine);
1421 if (r < 0)
1422 return log_error_errno(r, "Failed to get machine ID: %m");
1423
1424 r = sd_id128_get_boot(&boot);
1425 if (r < 0)
1426 return log_error_errno(r, "Failed to get boot ID: %m");
1427
1428 if (asprintf(&p, "/var/log/journal/" SD_ID128_FORMAT_STR "/fss",
1429 SD_ID128_FORMAT_VAL(machine)) < 0)
1430 return log_oom();
1431
1432 if (arg_force) {
1433 r = unlink(p);
1434 if (r < 0 && errno != ENOENT) {
1435 r = log_error_errno(errno, "unlink(\"%s\") failed: %m", p);
1436 goto finish;
1437 }
1438 } else if (access(p, F_OK) >= 0) {
1439 log_error("Sealing key file %s exists already. Use --force to recreate.", p);
1440 r = -EEXIST;
1441 goto finish;
1442 }
1443
1444 if (asprintf(&k, "/var/log/journal/" SD_ID128_FORMAT_STR "/fss.tmp.XXXXXX",
1445 SD_ID128_FORMAT_VAL(machine)) < 0) {
1446 r = log_oom();
1447 goto finish;
1448 }
1449
1450 mpk_size = FSPRG_mskinbytes(FSPRG_RECOMMENDED_SECPAR);
1451 mpk = alloca(mpk_size);
1452
1453 seed_size = FSPRG_RECOMMENDED_SEEDLEN;
1454 seed = alloca(seed_size);
1455
1456 state_size = FSPRG_stateinbytes(FSPRG_RECOMMENDED_SECPAR);
1457 state = alloca(state_size);
1458
1459 fd = open("/dev/random", O_RDONLY|O_CLOEXEC|O_NOCTTY);
1460 if (fd < 0) {
1461 r = log_error_errno(errno, "Failed to open /dev/random: %m");
1462 goto finish;
1463 }
1464
1465 log_info("Generating seed...");
1466 r = loop_read_exact(fd, seed, seed_size, true);
1467 if (r < 0) {
1468 log_error_errno(r, "Failed to read random seed: %m");
1469 goto finish;
1470 }
1471
1472 log_info("Generating key pair...");
1473 FSPRG_GenMK(NULL, mpk, seed, seed_size, FSPRG_RECOMMENDED_SECPAR);
1474
1475 log_info("Generating sealing key...");
1476 FSPRG_GenState0(state, mpk, seed, seed_size);
1477
1478 assert(arg_interval > 0);
1479
1480 n = now(CLOCK_REALTIME);
1481 n /= arg_interval;
1482
1483 safe_close(fd);
1484 fd = mkostemp_safe(k, O_WRONLY|O_CLOEXEC);
1485 if (fd < 0) {
1486 r = log_error_errno(errno, "Failed to open %s: %m", k);
1487 goto finish;
1488 }
1489
1490 /* Enable secure remove, exclusion from dump, synchronous
1491 * writing and in-place updating */
1492 r = chattr_fd(fd, FS_SECRM_FL|FS_NODUMP_FL|FS_SYNC_FL|FS_NOCOW_FL, FS_SECRM_FL|FS_NODUMP_FL|FS_SYNC_FL|FS_NOCOW_FL);
1493 if (r < 0)
1494 log_warning_errno(errno, "Failed to set file attributes: %m");
1495
1496 zero(h);
1497 memcpy(h.signature, "KSHHRHLP", 8);
1498 h.machine_id = machine;
1499 h.boot_id = boot;
1500 h.header_size = htole64(sizeof(h));
1501 h.start_usec = htole64(n * arg_interval);
1502 h.interval_usec = htole64(arg_interval);
1503 h.fsprg_secpar = htole16(FSPRG_RECOMMENDED_SECPAR);
1504 h.fsprg_state_size = htole64(state_size);
1505
1506 r = loop_write(fd, &h, sizeof(h), false);
1507 if (r < 0) {
1508 log_error_errno(r, "Failed to write header: %m");
1509 goto finish;
1510 }
1511
1512 r = loop_write(fd, state, state_size, false);
1513 if (r < 0) {
1514 log_error_errno(r, "Failed to write state: %m");
1515 goto finish;
1516 }
1517
1518 if (link(k, p) < 0) {
1519 r = log_error_errno(errno, "Failed to link file: %m");
1520 goto finish;
1521 }
1522
1523 if (on_tty()) {
1524 fprintf(stderr,
1525 "\n"
1526 "The new key pair has been generated. The " ANSI_HIGHLIGHT "secret sealing key" ANSI_NORMAL " has been written to\n"
1527 "the following local file. This key file is automatically updated when the\n"
1528 "sealing key is advanced. It should not be used on multiple hosts.\n"
1529 "\n"
1530 "\t%s\n"
1531 "\n"
1532 "Please write down the following " ANSI_HIGHLIGHT "secret verification key" ANSI_NORMAL ". It should be stored\n"
1533 "at a safe location and should not be saved locally on disk.\n"
1534 "\n\t" ANSI_HIGHLIGHT_RED, p);
1535 fflush(stderr);
1536 }
1537 for (i = 0; i < seed_size; i++) {
1538 if (i > 0 && i % 3 == 0)
1539 putchar('-');
1540 printf("%02x", ((uint8_t*) seed)[i]);
1541 }
1542
1543 printf("/%llx-%llx\n", (unsigned long long) n, (unsigned long long) arg_interval);
1544
1545 if (on_tty()) {
1546 char tsb[FORMAT_TIMESPAN_MAX], *hn;
1547
1548 fprintf(stderr,
1549 ANSI_NORMAL "\n"
1550 "The sealing key is automatically changed every %s.\n",
1551 format_timespan(tsb, sizeof(tsb), arg_interval, 0));
1552
1553 hn = gethostname_malloc();
1554
1555 if (hn) {
1556 hostname_cleanup(hn);
1557 fprintf(stderr, "\nThe keys have been generated for host %s/" SD_ID128_FORMAT_STR ".\n", hn, SD_ID128_FORMAT_VAL(machine));
1558 } else
1559 fprintf(stderr, "\nThe keys have been generated for host " SD_ID128_FORMAT_STR ".\n", SD_ID128_FORMAT_VAL(machine));
1560
1561 #ifdef HAVE_QRENCODE
1562 /* If this is not an UTF-8 system don't print any QR codes */
1563 if (is_locale_utf8()) {
1564 fputs("\nTo transfer the verification key to your phone please scan the QR code below:\n\n", stderr);
1565 print_qr_code(stderr, seed, seed_size, n, arg_interval, hn, machine);
1566 }
1567 #endif
1568 free(hn);
1569 }
1570
1571 r = 0;
1572
1573 finish:
1574 safe_close(fd);
1575
1576 if (k) {
1577 unlink(k);
1578 free(k);
1579 }
1580
1581 free(p);
1582
1583 return r;
1584 #else
1585 log_error("Forward-secure sealing not available.");
1586 return -EOPNOTSUPP;
1587 #endif
1588 }
1589
1590 static int verify(sd_journal *j) {
1591 int r = 0;
1592 Iterator i;
1593 JournalFile *f;
1594
1595 assert(j);
1596
1597 log_show_color(true);
1598
1599 ORDERED_HASHMAP_FOREACH(f, j->files, i) {
1600 int k;
1601 usec_t first = 0, validated = 0, last = 0;
1602
1603 #ifdef HAVE_GCRYPT
1604 if (!arg_verify_key && JOURNAL_HEADER_SEALED(f->header))
1605 log_notice("Journal file %s has sealing enabled but verification key has not been passed using --verify-key=.", f->path);
1606 #endif
1607
1608 k = journal_file_verify(f, arg_verify_key, &first, &validated, &last, true);
1609 if (k == -EINVAL) {
1610 /* If the key was invalid give up right-away. */
1611 return k;
1612 } else if (k < 0) {
1613 log_warning_errno(k, "FAIL: %s (%m)", f->path);
1614 r = k;
1615 } else {
1616 char a[FORMAT_TIMESTAMP_MAX], b[FORMAT_TIMESTAMP_MAX], c[FORMAT_TIMESPAN_MAX];
1617 log_info("PASS: %s", f->path);
1618
1619 if (arg_verify_key && JOURNAL_HEADER_SEALED(f->header)) {
1620 if (validated > 0) {
1621 log_info("=> Validated from %s to %s, final %s entries not sealed.",
1622 format_timestamp_maybe_utc(a, sizeof(a), first),
1623 format_timestamp_maybe_utc(b, sizeof(b), validated),
1624 format_timespan(c, sizeof(c), last > validated ? last - validated : 0, 0));
1625 } else if (last > 0)
1626 log_info("=> No sealing yet, %s of entries not sealed.",
1627 format_timespan(c, sizeof(c), last - first, 0));
1628 else
1629 log_info("=> No sealing yet, no entries in file.");
1630 }
1631 }
1632 }
1633
1634 return r;
1635 }
1636
1637 static int access_check_var_log_journal(sd_journal *j) {
1638 #ifdef HAVE_ACL
1639 _cleanup_strv_free_ char **g = NULL;
1640 const char* dir;
1641 #endif
1642 int r;
1643
1644 assert(j);
1645
1646 if (arg_quiet)
1647 return 0;
1648
1649 /* If we are root, we should have access, don't warn. */
1650 if (getuid() == 0)
1651 return 0;
1652
1653 /* If we are in the 'systemd-journal' group, we should have
1654 * access too. */
1655 r = in_group("systemd-journal");
1656 if (r < 0)
1657 return log_error_errno(r, "Failed to check if we are in the 'systemd-journal' group: %m");
1658 if (r > 0)
1659 return 0;
1660
1661 #ifdef HAVE_ACL
1662 if (laccess("/run/log/journal", F_OK) >= 0)
1663 dir = "/run/log/journal";
1664 else
1665 dir = "/var/log/journal";
1666
1667 /* If we are in any of the groups listed in the journal ACLs,
1668 * then all is good, too. Let's enumerate all groups from the
1669 * default ACL of the directory, which generally should allow
1670 * access to most journal files too. */
1671 r = acl_search_groups(dir, &g);
1672 if (r < 0)
1673 return log_error_errno(r, "Failed to search journal ACL: %m");
1674 if (r > 0)
1675 return 0;
1676
1677 /* Print a pretty list, if there were ACLs set. */
1678 if (!strv_isempty(g)) {
1679 _cleanup_free_ char *s = NULL;
1680
1681 /* Thre are groups in the ACL, let's list them */
1682 r = strv_extend(&g, "systemd-journal");
1683 if (r < 0)
1684 return log_oom();
1685
1686 strv_sort(g);
1687 strv_uniq(g);
1688
1689 s = strv_join(g, "', '");
1690 if (!s)
1691 return log_oom();
1692
1693 log_notice("Hint: You are currently not seeing messages from other users and the system.\n"
1694 " Users in groups '%s' can see all messages.\n"
1695 " Pass -q to turn off this notice.", s);
1696 return 1;
1697 }
1698 #endif
1699
1700 /* If no ACLs were found, print a short version of the message. */
1701 log_notice("Hint: You are currently not seeing messages from other users and the system.\n"
1702 " Users in the 'systemd-journal' group can see all messages. Pass -q to\n"
1703 " turn off this notice.");
1704
1705 return 1;
1706 }
1707
1708 static int access_check(sd_journal *j) {
1709 Iterator it;
1710 void *code;
1711 int r = 0;
1712
1713 assert(j);
1714
1715 if (set_isempty(j->errors)) {
1716 if (ordered_hashmap_isempty(j->files))
1717 log_notice("No journal files were found.");
1718
1719 return 0;
1720 }
1721
1722 if (set_contains(j->errors, INT_TO_PTR(-EACCES))) {
1723 (void) access_check_var_log_journal(j);
1724
1725 if (ordered_hashmap_isempty(j->files))
1726 r = log_error_errno(EACCES, "No journal files were opened due to insufficient permissions.");
1727 }
1728
1729 SET_FOREACH(code, j->errors, it) {
1730 int err;
1731
1732 err = -PTR_TO_INT(code);
1733 assert(err > 0);
1734
1735 if (err == EACCES)
1736 continue;
1737
1738 log_warning_errno(err, "Error was encountered while opening journal files: %m");
1739 if (r == 0)
1740 r = -err;
1741 }
1742
1743 return r;
1744 }
1745
1746 static int flush_to_var(void) {
1747 _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
1748 _cleanup_bus_flush_close_unref_ sd_bus *bus = NULL;
1749 _cleanup_close_ int watch_fd = -1;
1750 int r;
1751
1752 /* Quick exit */
1753 if (access("/run/systemd/journal/flushed", F_OK) >= 0)
1754 return 0;
1755
1756 /* OK, let's actually do the full logic, send SIGUSR1 to the
1757 * daemon and set up inotify to wait for the flushed file to appear */
1758 r = bus_connect_system_systemd(&bus);
1759 if (r < 0)
1760 return log_error_errno(r, "Failed to get D-Bus connection: %m");
1761
1762 r = sd_bus_call_method(
1763 bus,
1764 "org.freedesktop.systemd1",
1765 "/org/freedesktop/systemd1",
1766 "org.freedesktop.systemd1.Manager",
1767 "KillUnit",
1768 &error,
1769 NULL,
1770 "ssi", "systemd-journald.service", "main", SIGUSR1);
1771 if (r < 0) {
1772 log_error("Failed to kill journal service: %s", bus_error_message(&error, r));
1773 return r;
1774 }
1775
1776 mkdir_p("/run/systemd/journal", 0755);
1777
1778 watch_fd = inotify_init1(IN_NONBLOCK|IN_CLOEXEC);
1779 if (watch_fd < 0)
1780 return log_error_errno(errno, "Failed to create inotify watch: %m");
1781
1782 r = inotify_add_watch(watch_fd, "/run/systemd/journal", IN_CREATE|IN_DONT_FOLLOW|IN_ONLYDIR);
1783 if (r < 0)
1784 return log_error_errno(errno, "Failed to watch journal directory: %m");
1785
1786 for (;;) {
1787 if (access("/run/systemd/journal/flushed", F_OK) >= 0)
1788 break;
1789
1790 if (errno != ENOENT)
1791 return log_error_errno(errno, "Failed to check for existence of /run/systemd/journal/flushed: %m");
1792
1793 r = fd_wait_for_event(watch_fd, POLLIN, USEC_INFINITY);
1794 if (r < 0)
1795 return log_error_errno(r, "Failed to wait for event: %m");
1796
1797 r = flush_fd(watch_fd);
1798 if (r < 0)
1799 return log_error_errno(r, "Failed to flush inotify events: %m");
1800 }
1801
1802 return 0;
1803 }
1804
1805 static int rotate(void) {
1806 _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
1807 _cleanup_bus_flush_close_unref_ sd_bus *bus = NULL;
1808 int r;
1809
1810 r = bus_connect_system_systemd(&bus);
1811 if (r < 0)
1812 return log_error_errno(r, "Failed to get D-Bus connection: %m");
1813
1814 r = sd_bus_call_method(
1815 bus,
1816 "org.freedesktop.systemd1",
1817 "/org/freedesktop/systemd1",
1818 "org.freedesktop.systemd1.Manager",
1819 "KillUnit",
1820 &error,
1821 NULL,
1822 "ssi", "systemd-journald.service", "main", SIGUSR2);
1823 if (r < 0)
1824 return log_error_errno(r, "Failed to kill journal service: %s", bus_error_message(&error, r));
1825
1826 return 0;
1827 }
1828
1829 int main(int argc, char *argv[]) {
1830 int r;
1831 _cleanup_journal_close_ sd_journal *j = NULL;
1832 bool need_seek = false;
1833 sd_id128_t previous_boot_id;
1834 bool previous_boot_id_valid = false, first_line = true;
1835 int n_shown = 0;
1836 bool ellipsized = false;
1837
1838 setlocale(LC_ALL, "");
1839 log_parse_environment();
1840 log_open();
1841
1842 r = parse_argv(argc, argv);
1843 if (r <= 0)
1844 goto finish;
1845
1846 signal(SIGWINCH, columns_lines_cache_reset);
1847 sigbus_install();
1848
1849 /* Increase max number of open files to 16K if we can, we
1850 * might needs this when browsing journal files, which might
1851 * be split up into many files. */
1852 setrlimit_closest(RLIMIT_NOFILE, &RLIMIT_MAKE_CONST(16384));
1853
1854 if (arg_action == ACTION_NEW_ID128) {
1855 r = generate_new_id128();
1856 goto finish;
1857 }
1858
1859 if (arg_action == ACTION_FLUSH) {
1860 r = flush_to_var();
1861 goto finish;
1862 }
1863
1864 if (arg_action == ACTION_ROTATE) {
1865 r = rotate();
1866 goto finish;
1867 }
1868
1869 if (arg_action == ACTION_SETUP_KEYS) {
1870 r = setup_keys();
1871 goto finish;
1872 }
1873
1874 if (arg_action == ACTION_UPDATE_CATALOG ||
1875 arg_action == ACTION_LIST_CATALOG ||
1876 arg_action == ACTION_DUMP_CATALOG) {
1877
1878 _cleanup_free_ char *database;
1879
1880 database = path_join(arg_root, CATALOG_DATABASE, NULL);
1881 if (!database) {
1882 r = log_oom();
1883 goto finish;
1884 }
1885
1886 if (arg_action == ACTION_UPDATE_CATALOG) {
1887 r = catalog_update(database, arg_root, catalog_file_dirs);
1888 if (r < 0)
1889 log_error_errno(r, "Failed to list catalog: %m");
1890 } else {
1891 bool oneline = arg_action == ACTION_LIST_CATALOG;
1892
1893 pager_open_if_enabled();
1894 if (optind < argc)
1895 r = catalog_list_items(stdout, database,
1896 oneline, argv + optind);
1897 else
1898 r = catalog_list(stdout, database, oneline);
1899 if (r < 0)
1900 log_error_errno(r, "Failed to list catalog: %m");
1901 }
1902
1903 goto finish;
1904 }
1905
1906 if (arg_directory)
1907 r = sd_journal_open_directory(&j, arg_directory, arg_journal_type);
1908 else if (arg_file)
1909 r = sd_journal_open_files(&j, (const char**) arg_file, 0);
1910 else if (arg_machine)
1911 r = sd_journal_open_container(&j, arg_machine, 0);
1912 else
1913 r = sd_journal_open(&j, !arg_merge*SD_JOURNAL_LOCAL_ONLY + arg_journal_type);
1914 if (r < 0) {
1915 log_error_errno(r, "Failed to open %s: %m",
1916 arg_directory ? arg_directory : arg_file ? "files" : "journal");
1917 goto finish;
1918 }
1919
1920 r = access_check(j);
1921 if (r < 0)
1922 goto finish;
1923
1924 if (arg_action == ACTION_VERIFY) {
1925 r = verify(j);
1926 goto finish;
1927 }
1928
1929 if (arg_action == ACTION_PRINT_HEADER) {
1930 journal_print_header(j);
1931 r = 0;
1932 goto finish;
1933 }
1934
1935 if (arg_action == ACTION_DISK_USAGE) {
1936 uint64_t bytes = 0;
1937 char sbytes[FORMAT_BYTES_MAX];
1938
1939 r = sd_journal_get_usage(j, &bytes);
1940 if (r < 0)
1941 goto finish;
1942
1943 printf("Archived and active journals take up %s on disk.\n",
1944 format_bytes(sbytes, sizeof(sbytes), bytes));
1945 goto finish;
1946 }
1947
1948 if (arg_action == ACTION_VACUUM) {
1949 Directory *d;
1950 Iterator i;
1951
1952 HASHMAP_FOREACH(d, j->directories_by_path, i) {
1953 int q;
1954
1955 if (d->is_root)
1956 continue;
1957
1958 q = journal_directory_vacuum(d->path, arg_vacuum_size, arg_vacuum_n_files, arg_vacuum_time, NULL, true);
1959 if (q < 0) {
1960 log_error_errno(q, "Failed to vacuum %s: %m", d->path);
1961 r = q;
1962 }
1963 }
1964
1965 goto finish;
1966 }
1967
1968 if (arg_action == ACTION_LIST_BOOTS) {
1969 r = list_boots(j);
1970 goto finish;
1971 }
1972
1973 /* add_boot() must be called first!
1974 * It may need to seek the journal to find parent boot IDs. */
1975 r = add_boot(j);
1976 if (r < 0)
1977 goto finish;
1978
1979 r = add_dmesg(j);
1980 if (r < 0)
1981 goto finish;
1982
1983 r = add_units(j);
1984 if (r < 0) {
1985 log_error_errno(r, "Failed to add filter for units: %m");
1986 goto finish;
1987 }
1988
1989 r = add_syslog_identifier(j);
1990 if (r < 0) {
1991 log_error_errno(r, "Failed to add filter for syslog identifiers: %m");
1992 goto finish;
1993 }
1994
1995 r = add_priorities(j);
1996 if (r < 0)
1997 goto finish;
1998
1999 r = add_matches(j, argv + optind);
2000 if (r < 0)
2001 goto finish;
2002
2003 if (_unlikely_(log_get_max_level() >= LOG_DEBUG)) {
2004 _cleanup_free_ char *filter;
2005
2006 filter = journal_make_match_string(j);
2007 if (!filter)
2008 return log_oom();
2009
2010 log_debug("Journal filter: %s", filter);
2011 }
2012
2013 if (arg_field) {
2014 const void *data;
2015 size_t size;
2016
2017 r = sd_journal_set_data_threshold(j, 0);
2018 if (r < 0) {
2019 log_error_errno(r, "Failed to unset data size threshold: %m");
2020 goto finish;
2021 }
2022
2023 r = sd_journal_query_unique(j, arg_field);
2024 if (r < 0) {
2025 log_error_errno(r, "Failed to query unique data objects: %m");
2026 goto finish;
2027 }
2028
2029 SD_JOURNAL_FOREACH_UNIQUE(j, data, size) {
2030 const void *eq;
2031
2032 if (arg_lines >= 0 && n_shown >= arg_lines)
2033 break;
2034
2035 eq = memchr(data, '=', size);
2036 if (eq)
2037 printf("%.*s\n", (int) (size - ((const uint8_t*) eq - (const uint8_t*) data + 1)), (const char*) eq + 1);
2038 else
2039 printf("%.*s\n", (int) size, (const char*) data);
2040
2041 n_shown ++;
2042 }
2043
2044 r = 0;
2045 goto finish;
2046 }
2047
2048 /* Opening the fd now means the first sd_journal_wait() will actually wait */
2049 if (arg_follow) {
2050 r = sd_journal_get_fd(j);
2051 if (r < 0) {
2052 log_error_errno(r, "Failed to get journal fd: %m");
2053 goto finish;
2054 }
2055 }
2056
2057 if (arg_cursor || arg_after_cursor) {
2058 r = sd_journal_seek_cursor(j, arg_cursor ?: arg_after_cursor);
2059 if (r < 0) {
2060 log_error_errno(r, "Failed to seek to cursor: %m");
2061 goto finish;
2062 }
2063
2064 if (!arg_reverse)
2065 r = sd_journal_next_skip(j, 1 + !!arg_after_cursor);
2066 else
2067 r = sd_journal_previous_skip(j, 1 + !!arg_after_cursor);
2068
2069 if (arg_after_cursor && r < 2) {
2070 /* We couldn't find the next entry after the cursor. */
2071 if (arg_follow)
2072 need_seek = true;
2073 else
2074 arg_lines = 0;
2075 }
2076
2077 } else if (arg_since_set && !arg_reverse) {
2078 r = sd_journal_seek_realtime_usec(j, arg_since);
2079 if (r < 0) {
2080 log_error_errno(r, "Failed to seek to date: %m");
2081 goto finish;
2082 }
2083 r = sd_journal_next(j);
2084
2085 } else if (arg_until_set && arg_reverse) {
2086 r = sd_journal_seek_realtime_usec(j, arg_until);
2087 if (r < 0) {
2088 log_error_errno(r, "Failed to seek to date: %m");
2089 goto finish;
2090 }
2091 r = sd_journal_previous(j);
2092
2093 } else if (arg_lines >= 0) {
2094 r = sd_journal_seek_tail(j);
2095 if (r < 0) {
2096 log_error_errno(r, "Failed to seek to tail: %m");
2097 goto finish;
2098 }
2099
2100 r = sd_journal_previous_skip(j, arg_lines);
2101
2102 } else if (arg_reverse) {
2103 r = sd_journal_seek_tail(j);
2104 if (r < 0) {
2105 log_error_errno(r, "Failed to seek to tail: %m");
2106 goto finish;
2107 }
2108
2109 r = sd_journal_previous(j);
2110
2111 } else {
2112 r = sd_journal_seek_head(j);
2113 if (r < 0) {
2114 log_error_errno(r, "Failed to seek to head: %m");
2115 goto finish;
2116 }
2117
2118 r = sd_journal_next(j);
2119 }
2120
2121 if (r < 0) {
2122 log_error_errno(r, "Failed to iterate through journal: %m");
2123 goto finish;
2124 }
2125 if (r == 0) {
2126 if (arg_follow)
2127 need_seek = true;
2128 else {
2129 printf("-- No entries --\n");
2130 goto finish;
2131 }
2132 }
2133
2134 if (!arg_follow)
2135 pager_open_if_enabled();
2136
2137 if (!arg_quiet) {
2138 usec_t start, end;
2139 char start_buf[FORMAT_TIMESTAMP_MAX], end_buf[FORMAT_TIMESTAMP_MAX];
2140
2141 r = sd_journal_get_cutoff_realtime_usec(j, &start, &end);
2142 if (r < 0) {
2143 log_error_errno(r, "Failed to get cutoff: %m");
2144 goto finish;
2145 }
2146
2147 if (r > 0) {
2148 if (arg_follow)
2149 printf("-- Logs begin at %s. --\n",
2150 format_timestamp_maybe_utc(start_buf, sizeof(start_buf), start));
2151 else
2152 printf("-- Logs begin at %s, end at %s. --\n",
2153 format_timestamp_maybe_utc(start_buf, sizeof(start_buf), start),
2154 format_timestamp_maybe_utc(end_buf, sizeof(end_buf), end));
2155 }
2156 }
2157
2158 for (;;) {
2159 while (arg_lines < 0 || n_shown < arg_lines || (arg_follow && !first_line)) {
2160 int flags;
2161
2162 if (need_seek) {
2163 if (!arg_reverse)
2164 r = sd_journal_next(j);
2165 else
2166 r = sd_journal_previous(j);
2167 if (r < 0) {
2168 log_error_errno(r, "Failed to iterate through journal: %m");
2169 goto finish;
2170 }
2171 if (r == 0)
2172 break;
2173 }
2174
2175 if (arg_until_set && !arg_reverse) {
2176 usec_t usec;
2177
2178 r = sd_journal_get_realtime_usec(j, &usec);
2179 if (r < 0) {
2180 log_error_errno(r, "Failed to determine timestamp: %m");
2181 goto finish;
2182 }
2183 if (usec > arg_until)
2184 goto finish;
2185 }
2186
2187 if (arg_since_set && arg_reverse) {
2188 usec_t usec;
2189
2190 r = sd_journal_get_realtime_usec(j, &usec);
2191 if (r < 0) {
2192 log_error_errno(r, "Failed to determine timestamp: %m");
2193 goto finish;
2194 }
2195 if (usec < arg_since)
2196 goto finish;
2197 }
2198
2199 if (!arg_merge && !arg_quiet) {
2200 sd_id128_t boot_id;
2201
2202 r = sd_journal_get_monotonic_usec(j, NULL, &boot_id);
2203 if (r >= 0) {
2204 if (previous_boot_id_valid &&
2205 !sd_id128_equal(boot_id, previous_boot_id))
2206 printf("%s-- Reboot --%s\n",
2207 ansi_highlight(), ansi_normal());
2208
2209 previous_boot_id = boot_id;
2210 previous_boot_id_valid = true;
2211 }
2212 }
2213
2214 flags =
2215 arg_all * OUTPUT_SHOW_ALL |
2216 arg_full * OUTPUT_FULL_WIDTH |
2217 on_tty() * OUTPUT_COLOR |
2218 arg_catalog * OUTPUT_CATALOG |
2219 arg_utc * OUTPUT_UTC;
2220
2221 r = output_journal(stdout, j, arg_output, 0, flags, &ellipsized);
2222 need_seek = true;
2223 if (r == -EADDRNOTAVAIL)
2224 break;
2225 else if (r < 0 || ferror(stdout))
2226 goto finish;
2227
2228 n_shown++;
2229 }
2230
2231 if (!arg_follow) {
2232 if (arg_show_cursor) {
2233 _cleanup_free_ char *cursor = NULL;
2234
2235 r = sd_journal_get_cursor(j, &cursor);
2236 if (r < 0 && r != -EADDRNOTAVAIL)
2237 log_error_errno(r, "Failed to get cursor: %m");
2238 else if (r >= 0)
2239 printf("-- cursor: %s\n", cursor);
2240 }
2241
2242 break;
2243 }
2244
2245 r = sd_journal_wait(j, (uint64_t) -1);
2246 if (r < 0) {
2247 log_error_errno(r, "Couldn't wait for journal event: %m");
2248 goto finish;
2249 }
2250
2251 first_line = false;
2252 }
2253
2254 finish:
2255 pager_close();
2256
2257 strv_free(arg_file);
2258
2259 strv_free(arg_syslog_identifier);
2260 strv_free(arg_system_units);
2261 strv_free(arg_user_units);
2262
2263 free(arg_root);
2264
2265 return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS;
2266 }