]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/cgls/cgls.c
cgls: don't show empty cgroups by default
[thirdparty/systemd.git] / src / cgls / cgls.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4 This file is part of systemd.
5
6 Copyright 2010 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 <limits.h>
23 #include <stdio.h>
24 #include <unistd.h>
25 #include <errno.h>
26 #include <getopt.h>
27 #include <string.h>
28
29 #include "cgroup-show.h"
30 #include "cgroup-util.h"
31 #include "log.h"
32 #include "util.h"
33 #include "pager.h"
34 #include "build.h"
35
36 static bool arg_no_pager = false;
37 static bool arg_kernel_threads = false;
38 static bool arg_all = false;
39
40 static void help(void) {
41
42 printf("%s [OPTIONS...] [CGROUP...]\n\n"
43 "Recursively show control group contents.\n\n"
44 " -h --help Show this help\n"
45 " --version Show package version\n"
46 " --no-pager Do not pipe output into a pager\n"
47 " -a --all Show all groups, including empty\n"
48 " -k Include kernel threads in output\n",
49 program_invocation_short_name);
50 }
51
52 static int parse_argv(int argc, char *argv[]) {
53
54 enum {
55 ARG_NO_PAGER = 0x100,
56 ARG_VERSION
57 };
58
59 static const struct option options[] = {
60 { "help", no_argument, NULL, 'h' },
61 { "version", no_argument, NULL, ARG_VERSION },
62 { "no-pager", no_argument, NULL, ARG_NO_PAGER },
63 { "all", no_argument, NULL, 'a' },
64 { NULL, 0, NULL, 0 }
65 };
66
67 int c;
68
69 assert(argc >= 1);
70 assert(argv);
71
72 while ((c = getopt_long(argc, argv, "hka", options, NULL)) >= 0) {
73
74 switch (c) {
75
76 case 'h':
77 help();
78 return 0;
79
80 case ARG_VERSION:
81 puts(PACKAGE_STRING);
82 puts(DISTRIBUTION);
83 puts(SYSTEMD_FEATURES);
84 return 0;
85
86 case ARG_NO_PAGER:
87 arg_no_pager = true;
88 break;
89
90 case 'a':
91 arg_all = true;
92 break;
93
94 case 'k':
95 arg_kernel_threads = true;
96 break;
97
98 case '?':
99 return -EINVAL;
100
101 default:
102 log_error("Unknown option code %c", c);
103 return -EINVAL;
104 }
105 }
106
107 return 1;
108 }
109
110 int main(int argc, char *argv[]) {
111 int r = 0, retval = EXIT_FAILURE;
112
113 log_parse_environment();
114 log_open();
115
116 r = parse_argv(argc, argv);
117 if (r < 0)
118 goto finish;
119 else if (r == 0) {
120 retval = EXIT_SUCCESS;
121 goto finish;
122 }
123
124 if (!arg_no_pager)
125 pager_open();
126
127 if (optind < argc) {
128 unsigned i;
129
130 for (i = (unsigned) optind; i < (unsigned) argc; i++) {
131 int q;
132 printf("%s:\n", argv[i]);
133
134 q = show_cgroup_by_path(argv[i], NULL, 0, arg_kernel_threads, arg_all);
135 if (q < 0)
136 r = q;
137 }
138
139 } else {
140 char *p;
141
142 p = get_current_dir_name();
143 if (!p) {
144 log_error("Cannot determine current working directory: %m");
145 goto finish;
146 }
147
148 if (path_startswith(p, "/sys/fs/cgroup")) {
149 printf("Working Directory %s:\n", p);
150 r = show_cgroup_by_path(p, NULL, 0, arg_kernel_threads, arg_all);
151 } else {
152 char *root = NULL;
153 const char *t = NULL;
154
155 r = cg_get_by_pid(SYSTEMD_CGROUP_CONTROLLER, 1, &root);
156 if (r < 0)
157 t = "/";
158 else {
159 if (endswith(root, "/system"))
160 root[strlen(root)-7] = 0;
161
162 t = root[0] ? root : "/";
163 }
164
165 r = show_cgroup(SYSTEMD_CGROUP_CONTROLLER, t, NULL, 0, arg_kernel_threads, arg_all);
166 free(root);
167 }
168
169 free(p);
170 }
171
172 if (r < 0)
173 log_error("Failed to list cgroup tree: %s", strerror(-r));
174
175 retval = EXIT_SUCCESS;
176
177 finish:
178 pager_close();
179
180 return retval;
181 }