mirror of
https://github.com/systemd/systemd.git
synced 2024-10-30 14:55:37 +03:00
commit
912f7a9877
5
TODO
5
TODO
@ -334,11 +334,6 @@ Features:
|
||||
* networkd/udev: implement SR_IOV configuration in .link files:
|
||||
http://lists.freedesktop.org/archives/systemd-devel/2015-January/027451.html
|
||||
|
||||
* Rework systemctl's GetAll property parsing to use the generic bus_map_all_properties() API
|
||||
|
||||
* Port various tools to make use of verbs.[ch], where applicable: busctl,
|
||||
coredumpctl, hostnamectl, localectl, timedatectl
|
||||
|
||||
* hostnamectl: show root image uuid
|
||||
|
||||
* sysfs set api in libudev is not const
|
||||
|
@ -121,6 +121,10 @@
|
||||
<xi:include href="standard-options.xml" xpointer="help" />
|
||||
<xi:include href="standard-options.xml" xpointer="version" />
|
||||
</variablelist>
|
||||
</refsect1>
|
||||
|
||||
<refsect1>
|
||||
<title>Commands</title>
|
||||
|
||||
<para>The following commands are understood:</para>
|
||||
|
||||
@ -128,9 +132,8 @@
|
||||
<varlistentry>
|
||||
<term><command>status</command></term>
|
||||
|
||||
<listitem><para>Show current system
|
||||
hostname and related
|
||||
information.</para></listitem>
|
||||
<listitem><para>Show current system hostname and related information. If no command is specified,
|
||||
this is the implied default.</para></listitem>
|
||||
</varlistentry>
|
||||
|
||||
<varlistentry>
|
||||
|
@ -118,6 +118,10 @@
|
||||
<xi:include href="standard-options.xml" xpointer="version" />
|
||||
<xi:include href="standard-options.xml" xpointer="no-pager" />
|
||||
</variablelist>
|
||||
</refsect1>
|
||||
|
||||
<refsect1>
|
||||
<title>Commands</title>
|
||||
|
||||
<para>The following commands are understood:</para>
|
||||
|
||||
@ -125,8 +129,8 @@
|
||||
<varlistentry>
|
||||
<term><command>status</command></term>
|
||||
|
||||
<listitem><para>Show current settings of the system locale and
|
||||
keyboard mapping.</para></listitem>
|
||||
<listitem><para>Show current settings of the system locale and keyboard mapping.
|
||||
If no command is specified, this is the implied default.</para></listitem>
|
||||
</varlistentry>
|
||||
|
||||
<varlistentry>
|
||||
|
@ -98,6 +98,10 @@
|
||||
<xi:include href="standard-options.xml" xpointer="version" />
|
||||
<xi:include href="standard-options.xml" xpointer="no-pager" />
|
||||
</variablelist>
|
||||
</refsect1>
|
||||
|
||||
<refsect1>
|
||||
<title>Commands</title>
|
||||
|
||||
<para>The following commands are understood:</para>
|
||||
|
||||
@ -109,6 +113,7 @@
|
||||
including whether network time synchronization through
|
||||
<filename>systemd-timesyncd.service</filename> is active. Even if it is
|
||||
inactive, a different service might still synchronize the clock.
|
||||
If no command is specified, this is the implied default.
|
||||
</para></listitem>
|
||||
</varlistentry>
|
||||
|
||||
|
@ -474,6 +474,7 @@ static int acquire_host_info(sd_bus *bus, struct host_info **hi) {
|
||||
"/org/freedesktop/hostname1",
|
||||
hostname_map,
|
||||
&error,
|
||||
NULL,
|
||||
host);
|
||||
if (r < 0)
|
||||
log_debug_errno(r, "Failed to get host information from systemd-hostnamed: %s", bus_error_message(&error, r));
|
||||
@ -483,6 +484,7 @@ static int acquire_host_info(sd_bus *bus, struct host_info **hi) {
|
||||
"/org/freedesktop/systemd1",
|
||||
manager_map,
|
||||
&error,
|
||||
NULL,
|
||||
host);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to get host information from systemd: %s", bus_error_message(&error, r));
|
||||
@ -1027,7 +1029,7 @@ static int analyze_critical_chain(int argc, char *argv[], void *userdata) {
|
||||
}
|
||||
unit_times_hashmap = h;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
puts("The time after the unit is active or started is printed after the \"@\" character.\n"
|
||||
"The time the unit takes to start is printed after the \"+\" character.\n");
|
||||
@ -1060,7 +1062,7 @@ static int analyze_blame(int argc, char *argv[], void *userdata) {
|
||||
|
||||
qsort(times, n, sizeof(struct unit_times), compare_unit_time);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
for (i = 0; i < (unsigned) n; i++) {
|
||||
char ts[FORMAT_TIMESPAN_MAX];
|
||||
@ -1283,7 +1285,7 @@ static int dump(int argc, char *argv[], void *userdata) {
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to create bus connection: %m");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
@ -1445,7 +1447,7 @@ static void dump_syscall_filter(const SyscallFilterSet *set) {
|
||||
static int dump_syscall_filters(int argc, char *argv[], void *userdata) {
|
||||
bool first = true;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (strv_isempty(strv_skip(argv, 1))) {
|
||||
int i;
|
||||
@ -1607,7 +1609,7 @@ static int do_verify(int argc, char *argv[], void *userdata) {
|
||||
|
||||
static int help(int argc, char *argv[], void *userdata) {
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
printf("%s [OPTIONS...] {COMMAND} ...\n\n"
|
||||
"Profile systemd, show unit dependencies, check unit files.\n\n"
|
||||
|
@ -42,6 +42,7 @@
|
||||
#include "terminal-util.h"
|
||||
#include "user-util.h"
|
||||
#include "util.h"
|
||||
#include "verbs.h"
|
||||
|
||||
static bool arg_no_pager = false;
|
||||
static bool arg_legend = true;
|
||||
@ -68,7 +69,82 @@ static usec_t arg_timeout = 0;
|
||||
#define NAME_IS_ACQUIRED INT_TO_PTR(1)
|
||||
#define NAME_IS_ACTIVATABLE INT_TO_PTR(2)
|
||||
|
||||
static int list_bus_names(sd_bus *bus, char **argv) {
|
||||
static int acquire_bus(bool set_monitor, sd_bus **ret) {
|
||||
_cleanup_(sd_bus_unrefp) sd_bus *bus = NULL;
|
||||
int r;
|
||||
|
||||
r = sd_bus_new(&bus);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to allocate bus: %m");
|
||||
|
||||
if (set_monitor) {
|
||||
r = sd_bus_set_monitor(bus, true);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to set monitor mode: %m");
|
||||
|
||||
r = sd_bus_negotiate_creds(bus, true, _SD_BUS_CREDS_ALL);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to enable credentials: %m");
|
||||
|
||||
r = sd_bus_negotiate_timestamp(bus, true);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to enable timestamps: %m");
|
||||
|
||||
r = sd_bus_negotiate_fds(bus, true);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to enable fds: %m");
|
||||
}
|
||||
|
||||
r = sd_bus_set_bus_client(bus, true);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to set bus client: %m");
|
||||
|
||||
r = sd_bus_set_watch_bind(bus, arg_watch_bind);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to set watch-bind setting to '%s': %m", yes_no(arg_watch_bind));
|
||||
|
||||
if (arg_address)
|
||||
r = sd_bus_set_address(bus, arg_address);
|
||||
else {
|
||||
switch (arg_transport) {
|
||||
|
||||
case BUS_TRANSPORT_LOCAL:
|
||||
if (arg_user) {
|
||||
bus->is_user = true;
|
||||
r = bus_set_address_user(bus);
|
||||
} else {
|
||||
bus->is_system = true;
|
||||
r = bus_set_address_system(bus);
|
||||
}
|
||||
break;
|
||||
|
||||
case BUS_TRANSPORT_REMOTE:
|
||||
r = bus_set_address_system_remote(bus, arg_host);
|
||||
break;
|
||||
|
||||
case BUS_TRANSPORT_MACHINE:
|
||||
r = bus_set_address_system_machine(bus, arg_host);
|
||||
break;
|
||||
|
||||
default:
|
||||
assert_not_reached("Hmm, unknown transport type.");
|
||||
}
|
||||
}
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to set address: %m");
|
||||
|
||||
r = sd_bus_start(bus);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to connect to bus: %m");
|
||||
|
||||
*ret = bus;
|
||||
bus = NULL;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int list_bus_names(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_strv_free_ char **acquired = NULL, **activatable = NULL;
|
||||
_cleanup_free_ char **merged = NULL;
|
||||
_cleanup_hashmap_free_ Hashmap *names = NULL;
|
||||
@ -80,16 +156,18 @@ static int list_bus_names(sd_bus *bus, char **argv) {
|
||||
char *k;
|
||||
Iterator iterator;
|
||||
|
||||
assert(bus);
|
||||
|
||||
if (!arg_unique && !arg_acquired && !arg_activatable)
|
||||
arg_unique = arg_acquired = arg_activatable = true;
|
||||
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_list_names(bus, (arg_acquired || arg_unique) ? &acquired : NULL, arg_activatable ? &activatable : NULL);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to list names: %m");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
names = hashmap_new(&string_hash_ops);
|
||||
if (!names)
|
||||
@ -112,6 +190,9 @@ static int list_bus_names(sd_bus *bus, char **argv) {
|
||||
}
|
||||
|
||||
merged = new(char*, hashmap_size(names) + 1);
|
||||
if (!merged)
|
||||
return log_oom();
|
||||
|
||||
HASHMAP_FOREACH_KEY(v, k, names, iterator)
|
||||
merged[n++] = k;
|
||||
|
||||
@ -283,8 +364,6 @@ static void print_subtree(const char *prefix, const char *path, char **l) {
|
||||
|
||||
static void print_tree(const char *prefix, char **l) {
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
|
||||
prefix = strempty(prefix);
|
||||
|
||||
if (arg_list) {
|
||||
@ -403,7 +482,7 @@ static int tree_one(sd_bus *bus, const char *service, const char *prefix, bool m
|
||||
p = NULL;
|
||||
}
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
l = set_get_strv(done);
|
||||
if (!l)
|
||||
@ -417,14 +496,19 @@ static int tree_one(sd_bus *bus, const char *service, const char *prefix, bool m
|
||||
return r;
|
||||
}
|
||||
|
||||
static int tree(sd_bus *bus, char **argv) {
|
||||
static int tree(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
char **i;
|
||||
int r = 0;
|
||||
|
||||
if (!arg_unique && !arg_acquired)
|
||||
arg_acquired = true;
|
||||
|
||||
if (strv_length(argv) <= 1) {
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (argc <= 1) {
|
||||
_cleanup_strv_free_ char **names = NULL;
|
||||
bool not_first = false;
|
||||
|
||||
@ -432,7 +516,7 @@ static int tree(sd_bus *bus, char **argv) {
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to get name list: %m");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
STRV_FOREACH(i, names) {
|
||||
int q;
|
||||
@ -462,7 +546,7 @@ static int tree(sd_bus *bus, char **argv) {
|
||||
printf("\n");
|
||||
|
||||
if (argv[2]) {
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
printf("Service %s%s%s:\n", ansi_highlight(), *i, ansi_normal());
|
||||
}
|
||||
|
||||
@ -848,7 +932,7 @@ static const char *strdash(const char *x) {
|
||||
return isempty(x) ? "-" : x;
|
||||
}
|
||||
|
||||
static int introspect(sd_bus *bus, char **argv) {
|
||||
static int introspect(int argc, char **argv, void *userdata) {
|
||||
static const struct hash_ops member_hash_ops = {
|
||||
.hash = member_hash_func,
|
||||
.compare = member_compare_func,
|
||||
@ -861,27 +945,19 @@ static int introspect(sd_bus *bus, char **argv) {
|
||||
.on_property = on_property,
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *reply_xml = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(member_set_freep) Set *members = NULL;
|
||||
unsigned name_width, type_width, signature_width, result_width, j, k = 0;
|
||||
Member *m, **sorted = NULL;
|
||||
Iterator i;
|
||||
Member *m;
|
||||
const char *xml;
|
||||
int r;
|
||||
unsigned name_width, type_width, signature_width, result_width;
|
||||
Member **sorted = NULL;
|
||||
unsigned k = 0, j, n_args;
|
||||
|
||||
n_args = strv_length(argv);
|
||||
if (n_args < 3) {
|
||||
log_error("Requires service and object path argument.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (n_args > 4) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
members = set_new(&member_hash_ops);
|
||||
if (!members)
|
||||
@ -976,7 +1052,7 @@ static int introspect(sd_bus *bus, char **argv) {
|
||||
return bus_log_parse_error(r);
|
||||
}
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
name_width = STRLEN("NAME");
|
||||
type_width = STRLEN("TYPE");
|
||||
@ -1071,7 +1147,8 @@ static int message_pcap(sd_bus_message *m, FILE *f) {
|
||||
return bus_message_pcap_frame(m, arg_snaplen, f);
|
||||
}
|
||||
|
||||
static int monitor(sd_bus *bus, char *argv[], int (*dump)(sd_bus_message *m, FILE *f)) {
|
||||
static int monitor(int argc, char **argv, int (*dump)(sd_bus_message *m, FILE *f)) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *message = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
char **i;
|
||||
@ -1080,6 +1157,10 @@ static int monitor(sd_bus *bus, char *argv[], int (*dump)(sd_bus_message *m, FIL
|
||||
bool is_monitor = false;
|
||||
int r;
|
||||
|
||||
r = acquire_bus(true, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
/* upgrade connection; it's not used for anything else after this call */
|
||||
r = sd_bus_message_new_method_call(bus, &message, "org.freedesktop.DBus", "/org/freedesktop/DBus", "org.freedesktop.DBus.Monitoring", "BecomeMonitor");
|
||||
if (r < 0)
|
||||
@ -1186,7 +1267,11 @@ static int monitor(sd_bus *bus, char *argv[], int (*dump)(sd_bus_message *m, FIL
|
||||
}
|
||||
}
|
||||
|
||||
static int capture(sd_bus *bus, char *argv[]) {
|
||||
static int verb_monitor(int argc, char **argv, void *userdata) {
|
||||
return monitor(argc, argv, message_dump);
|
||||
}
|
||||
|
||||
static int verb_capture(int argc, char **argv, void *userdata) {
|
||||
int r;
|
||||
|
||||
if (isatty(fileno(stdout)) > 0) {
|
||||
@ -1196,7 +1281,7 @@ static int capture(sd_bus *bus, char *argv[]) {
|
||||
|
||||
bus_pcap_header(arg_snaplen, stdout);
|
||||
|
||||
r = monitor(bus, argv, message_pcap);
|
||||
r = monitor(argc, argv, message_pcap);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -1208,19 +1293,17 @@ static int capture(sd_bus *bus, char *argv[]) {
|
||||
return r;
|
||||
}
|
||||
|
||||
static int status(sd_bus *bus, char *argv[]) {
|
||||
static int status(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_(sd_bus_creds_unrefp) sd_bus_creds *creds = NULL;
|
||||
pid_t pid;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (strv_length(argv) > 2) {
|
||||
log_error("Expects no or one argument.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (argv[1]) {
|
||||
if (!isempty(argv[1])) {
|
||||
r = parse_pid(argv[1], &pid);
|
||||
if (r < 0)
|
||||
r = sd_bus_get_name_creds(
|
||||
@ -1515,17 +1598,15 @@ static int message_append_cmdline(sd_bus_message *m, const char *signature, char
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int call(sd_bus *bus, char *argv[]) {
|
||||
static int call(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL, *reply = NULL;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
|
||||
if (strv_length(argv) < 5) {
|
||||
log_error("Expects at least four arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_new_method_call(bus, &m, argv[1], argv[2], argv[3], argv[4]);
|
||||
if (r < 0)
|
||||
@ -1581,7 +1662,7 @@ static int call(sd_bus *bus, char *argv[]) {
|
||||
if (r == 0 && !arg_quiet) {
|
||||
|
||||
if (arg_verbose) {
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = bus_message_dump(reply, stdout, 0);
|
||||
if (r < 0)
|
||||
@ -1602,19 +1683,15 @@ static int call(sd_bus *bus, char *argv[]) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int get_property(sd_bus *bus, char *argv[]) {
|
||||
static int get_property(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
unsigned n;
|
||||
char **i;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
|
||||
n = strv_length(argv);
|
||||
if (n < 5) {
|
||||
log_error("Expects at least four arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
STRV_FOREACH(i, argv + 4) {
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
|
||||
@ -1636,7 +1713,7 @@ static int get_property(sd_bus *bus, char *argv[]) {
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
if (arg_verbose) {
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = bus_message_dump(reply, stdout, BUS_MESSAGE_DUMP_SUBTREE_ONLY);
|
||||
if (r < 0)
|
||||
@ -1660,20 +1737,16 @@ static int get_property(sd_bus *bus, char *argv[]) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int set_property(sd_bus *bus, char *argv[]) {
|
||||
static int set_property(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
unsigned n;
|
||||
char **p;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
|
||||
n = strv_length(argv);
|
||||
if (n < 6) {
|
||||
log_error("Expects at least five arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
r = acquire_bus(false, &bus);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_new_method_call(bus, &m, argv[1], argv[2], "org.freedesktop.DBus.Properties", "Set");
|
||||
if (r < 0)
|
||||
@ -1687,7 +1760,7 @@ static int set_property(sd_bus *bus, char *argv[]) {
|
||||
if (r < 0)
|
||||
return bus_log_create_error(r);
|
||||
|
||||
p = argv+6;
|
||||
p = argv + 6;
|
||||
r = message_append_cmdline(m, argv[5], &p);
|
||||
if (r < 0)
|
||||
return r;
|
||||
@ -1758,6 +1831,10 @@ static int help(void) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int verb_help(int argc, char **argv, void *userdata) {
|
||||
return help();
|
||||
}
|
||||
|
||||
static int parse_argv(int argc, char *argv[]) {
|
||||
|
||||
enum {
|
||||
@ -1978,46 +2055,26 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int busctl_main(sd_bus *bus, int argc, char *argv[]) {
|
||||
assert(bus);
|
||||
static int busctl_main(int argc, char *argv[]) {
|
||||
|
||||
if (optind >= argc ||
|
||||
streq(argv[optind], "list"))
|
||||
return list_bus_names(bus, argv + optind);
|
||||
static const Verb verbs[] = {
|
||||
{ "list", VERB_ANY, 1, VERB_DEFAULT, list_bus_names },
|
||||
{ "status", VERB_ANY, 2, 0, status },
|
||||
{ "monitor", VERB_ANY, VERB_ANY, 0, verb_monitor },
|
||||
{ "capture", VERB_ANY, VERB_ANY, 0, verb_capture },
|
||||
{ "tree", VERB_ANY, VERB_ANY, 0, tree },
|
||||
{ "introspect", 3, 4, 0, introspect },
|
||||
{ "call", 5, VERB_ANY, 0, call },
|
||||
{ "get-property", 5, VERB_ANY, 0, get_property },
|
||||
{ "set-property", 6, VERB_ANY, 0, set_property },
|
||||
{ "help", VERB_ANY, VERB_ANY, 0, verb_help },
|
||||
{}
|
||||
};
|
||||
|
||||
if (streq(argv[optind], "monitor"))
|
||||
return monitor(bus, argv + optind, message_dump);
|
||||
|
||||
if (streq(argv[optind], "capture"))
|
||||
return capture(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "status"))
|
||||
return status(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "tree"))
|
||||
return tree(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "introspect"))
|
||||
return introspect(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "call"))
|
||||
return call(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "get-property"))
|
||||
return get_property(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "set-property"))
|
||||
return set_property(bus, argv + optind);
|
||||
|
||||
if (streq(argv[optind], "help"))
|
||||
return help();
|
||||
|
||||
log_error("Unknown command '%s'", argv[optind]);
|
||||
return -EINVAL;
|
||||
return dispatch_verb(argc, argv, verbs, NULL);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
sd_bus *bus = NULL;
|
||||
int r;
|
||||
|
||||
log_parse_environment();
|
||||
@ -2027,98 +2084,14 @@ int main(int argc, char *argv[]) {
|
||||
if (r <= 0)
|
||||
goto finish;
|
||||
|
||||
r = sd_bus_new(&bus);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to allocate bus: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (STRPTR_IN_SET(argv[optind], "monitor", "capture")) {
|
||||
|
||||
r = sd_bus_set_monitor(bus, true);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to set monitor mode: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
r = sd_bus_negotiate_creds(bus, true, _SD_BUS_CREDS_ALL);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to enable credentials: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
r = sd_bus_negotiate_timestamp(bus, true);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to enable timestamps: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
r = sd_bus_negotiate_fds(bus, true);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to enable fds: %m");
|
||||
goto finish;
|
||||
}
|
||||
}
|
||||
|
||||
r = sd_bus_set_bus_client(bus, true);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to set bus client: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
r = sd_bus_set_watch_bind(bus, arg_watch_bind);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to set watch-bind setting to '%s': %m", yes_no(arg_watch_bind));
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (arg_address)
|
||||
r = sd_bus_set_address(bus, arg_address);
|
||||
else {
|
||||
switch (arg_transport) {
|
||||
|
||||
case BUS_TRANSPORT_LOCAL:
|
||||
if (arg_user) {
|
||||
bus->is_user = true;
|
||||
r = bus_set_address_user(bus);
|
||||
} else {
|
||||
bus->is_system = true;
|
||||
r = bus_set_address_system(bus);
|
||||
}
|
||||
break;
|
||||
|
||||
case BUS_TRANSPORT_REMOTE:
|
||||
r = bus_set_address_system_remote(bus, arg_host);
|
||||
break;
|
||||
|
||||
case BUS_TRANSPORT_MACHINE:
|
||||
r = bus_set_address_system_machine(bus, arg_host);
|
||||
break;
|
||||
|
||||
default:
|
||||
assert_not_reached("Hmm, unknown transport type.");
|
||||
}
|
||||
}
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to set address: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
r = sd_bus_start(bus);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to connect to bus: %m");
|
||||
goto finish;
|
||||
}
|
||||
|
||||
r = busctl_main(bus, argc, argv);
|
||||
r = busctl_main(argc, argv);
|
||||
|
||||
finish:
|
||||
/* make sure we terminate the bus connection first, and then close the
|
||||
* pager, see issue #3543 for the details. */
|
||||
sd_bus_flush_close_unref(bus);
|
||||
pager_close();
|
||||
|
||||
strv_free(arg_matches);
|
||||
arg_matches = strv_free(arg_matches);
|
||||
|
||||
return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS;
|
||||
}
|
||||
|
@ -176,11 +176,9 @@ int main(int argc, char *argv[]) {
|
||||
if (r <= 0)
|
||||
goto finish;
|
||||
|
||||
if (!arg_no_pager) {
|
||||
r = pager_open(arg_no_pager, false);
|
||||
if (r > 0 && arg_full < 0)
|
||||
arg_full = true;
|
||||
}
|
||||
r = pager_open(arg_no_pager, false);
|
||||
if (r > 0 && arg_full < 0)
|
||||
arg_full = true;
|
||||
|
||||
output_flags =
|
||||
arg_all * OUTPUT_SHOW_ALL |
|
||||
|
@ -2326,7 +2326,7 @@ int main(int argc, char *argv[]) {
|
||||
goto finish;
|
||||
|
||||
if (IN_SET(arg_action, ACTION_TEST, ACTION_HELP, ACTION_DUMP_CONFIGURATION_ITEMS))
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (arg_action != ACTION_RUN)
|
||||
skip_setup = true;
|
||||
|
@ -51,18 +51,11 @@
|
||||
#include "terminal-util.h"
|
||||
#include "user-util.h"
|
||||
#include "util.h"
|
||||
#include "verbs.h"
|
||||
|
||||
#define SHORT_BUS_CALL_TIMEOUT_USEC (3 * USEC_PER_SEC)
|
||||
|
||||
static usec_t arg_since = USEC_INFINITY, arg_until = USEC_INFINITY;
|
||||
|
||||
static enum {
|
||||
ACTION_NONE,
|
||||
ACTION_INFO,
|
||||
ACTION_LIST,
|
||||
ACTION_DUMP,
|
||||
ACTION_GDB,
|
||||
} arg_action = ACTION_LIST;
|
||||
static const char* arg_field = NULL;
|
||||
static const char *arg_directory = NULL;
|
||||
static bool arg_no_pager = false;
|
||||
@ -70,7 +63,6 @@ static int arg_no_legend = false;
|
||||
static int arg_one = false;
|
||||
static FILE* arg_output = NULL;
|
||||
static bool arg_reverse = false;
|
||||
static char** arg_matches = NULL;
|
||||
static bool arg_quiet = false;
|
||||
|
||||
static int add_match(sd_journal *j, const char *match) {
|
||||
@ -102,7 +94,7 @@ static int add_match(sd_journal *j, const char *match) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int add_matches(sd_journal *j) {
|
||||
static int add_matches(sd_journal *j, char **matches) {
|
||||
char **match;
|
||||
int r;
|
||||
|
||||
@ -114,7 +106,7 @@ static int add_matches(sd_journal *j) {
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to add match \"%s\": %m", "MESSAGE_ID=" SD_MESSAGE_BACKTRACE_STR);
|
||||
|
||||
STRV_FOREACH(match, arg_matches) {
|
||||
STRV_FOREACH(match, matches) {
|
||||
r = add_match(j, *match);
|
||||
if (r < 0)
|
||||
return r;
|
||||
@ -123,7 +115,44 @@ static int add_matches(sd_journal *j) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void help(void) {
|
||||
static int acquire_journal(sd_journal **ret, char **matches) {
|
||||
_cleanup_(sd_journal_closep) sd_journal *j = NULL;
|
||||
int r;
|
||||
|
||||
assert(ret);
|
||||
|
||||
if (arg_directory) {
|
||||
r = sd_journal_open_directory(&j, arg_directory, 0);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to open journals in directory: %s: %m", arg_directory);
|
||||
} else {
|
||||
r = sd_journal_open(&j, SD_JOURNAL_LOCAL_ONLY);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to open journal: %m");
|
||||
}
|
||||
|
||||
r = journal_access_check_and_warn(j, arg_quiet, true);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = add_matches(j, matches);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (DEBUG_LOGGING) {
|
||||
_cleanup_free_ char *filter;
|
||||
|
||||
filter = journal_make_match_string(j);
|
||||
log_debug("Journal filter: %s", filter);
|
||||
}
|
||||
|
||||
*ret = j;
|
||||
j = NULL;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int help(void) {
|
||||
printf("%s [OPTIONS...]\n\n"
|
||||
"List or retrieve coredumps from the journal.\n\n"
|
||||
"Flags:\n"
|
||||
@ -145,6 +174,8 @@ static void help(void) {
|
||||
" dump [MATCHES...] Print first matching coredump to stdout\n"
|
||||
" gdb [MATCHES...] Start gdb for the first matching coredump\n"
|
||||
, program_invocation_short_name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int parse_argv(int argc, char *argv[]) {
|
||||
@ -177,12 +208,9 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
while ((c = getopt_long(argc, argv, "ho:F:1D:rS:U:q", options, NULL)) >= 0)
|
||||
switch(c) {
|
||||
case 'h':
|
||||
arg_action = ACTION_NONE;
|
||||
help();
|
||||
return 0;
|
||||
return help();
|
||||
|
||||
case ARG_VERSION:
|
||||
arg_action = ACTION_NONE;
|
||||
return version();
|
||||
|
||||
case ARG_NO_PAGER:
|
||||
@ -254,31 +282,7 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (optind < argc) {
|
||||
const char *cmd = argv[optind++];
|
||||
if (streq(cmd, "list"))
|
||||
arg_action = ACTION_LIST;
|
||||
else if (streq(cmd, "dump"))
|
||||
arg_action = ACTION_DUMP;
|
||||
else if (streq(cmd, "gdb"))
|
||||
arg_action = ACTION_GDB;
|
||||
else if (streq(cmd, "info"))
|
||||
arg_action = ACTION_INFO;
|
||||
else {
|
||||
log_error("Unknown action '%s'", cmd);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
if (arg_field && arg_action != ACTION_LIST) {
|
||||
log_error("Option --field/-F only makes sense with list");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (optind < argc)
|
||||
arg_matches = argv + optind;
|
||||
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int retrieve(const void *data,
|
||||
@ -631,10 +635,10 @@ static int focus(sd_journal *j) {
|
||||
return r;
|
||||
}
|
||||
|
||||
static int print_entry(sd_journal *j, unsigned n_found) {
|
||||
static int print_entry(sd_journal *j, unsigned n_found, bool verb_is_info) {
|
||||
assert(j);
|
||||
|
||||
if (arg_action == ACTION_INFO)
|
||||
if (verb_is_info)
|
||||
return print_info(stdout, j, n_found);
|
||||
else if (arg_field)
|
||||
return print_field(stdout, j);
|
||||
@ -642,11 +646,19 @@ static int print_entry(sd_journal *j, unsigned n_found) {
|
||||
return print_list(stdout, j, n_found);
|
||||
}
|
||||
|
||||
static int dump_list(sd_journal *j) {
|
||||
static int dump_list(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_journal_closep) sd_journal *j = NULL;
|
||||
unsigned n_found = 0;
|
||||
bool verb_is_info;
|
||||
int r;
|
||||
|
||||
assert(j);
|
||||
verb_is_info = (argc >= 1 && streq(argv[0], "info"));
|
||||
|
||||
r = acquire_journal(&j, argv + 1);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
/* The coredumps are likely to compressed, and for just
|
||||
* listing them we don't need to decompress them, so let's
|
||||
@ -658,7 +670,7 @@ static int dump_list(sd_journal *j) {
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
return print_entry(j, 0);
|
||||
return print_entry(j, 0, verb_is_info);
|
||||
} else {
|
||||
if (arg_since != USEC_INFINITY && !arg_reverse)
|
||||
r = sd_journal_seek_realtime_usec(j, arg_since);
|
||||
@ -703,7 +715,7 @@ static int dump_list(sd_journal *j) {
|
||||
continue;
|
||||
}
|
||||
|
||||
r = print_entry(j, n_found++);
|
||||
r = print_entry(j, n_found++, verb_is_info);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
@ -856,10 +868,18 @@ error:
|
||||
return r;
|
||||
}
|
||||
|
||||
static int dump_core(sd_journal* j) {
|
||||
static int dump_core(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_journal_closep) sd_journal *j = NULL;
|
||||
int r;
|
||||
|
||||
assert(j);
|
||||
if (arg_field) {
|
||||
log_error("Option --field/-F only makes sense with list");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
r = acquire_journal(&j, argv + 1);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = focus(j);
|
||||
if (r < 0)
|
||||
@ -878,7 +898,8 @@ static int dump_core(sd_journal* j) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int run_gdb(sd_journal *j) {
|
||||
static int run_gdb(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_journal_closep) sd_journal *j = NULL;
|
||||
_cleanup_free_ char *exe = NULL, *path = NULL;
|
||||
bool unlink_path = false;
|
||||
const char *data;
|
||||
@ -886,7 +907,14 @@ static int run_gdb(sd_journal *j) {
|
||||
pid_t pid;
|
||||
int r;
|
||||
|
||||
assert(j);
|
||||
if (arg_field) {
|
||||
log_error("Option --field/-F only makes sense with list");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
r = acquire_journal(&j, argv + 1);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = focus(j);
|
||||
if (r < 0)
|
||||
@ -1007,73 +1035,35 @@ static int check_units_active(void) {
|
||||
return c;
|
||||
}
|
||||
|
||||
static int coredumpctl_main(int argc, char *argv[]) {
|
||||
|
||||
static const Verb verbs[] = {
|
||||
{ "list", VERB_ANY, VERB_ANY, VERB_DEFAULT, dump_list },
|
||||
{ "info", VERB_ANY, VERB_ANY, 0, dump_list },
|
||||
{ "dump", VERB_ANY, VERB_ANY, 0, dump_core },
|
||||
{ "gdb", VERB_ANY, VERB_ANY, 0, run_gdb },
|
||||
{}
|
||||
};
|
||||
|
||||
return dispatch_verb(argc, argv, verbs, NULL);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
_cleanup_(sd_journal_closep) sd_journal*j = NULL;
|
||||
int r = 0, units_active;
|
||||
int r, units_active;
|
||||
|
||||
setlocale(LC_ALL, "");
|
||||
log_parse_environment();
|
||||
log_open();
|
||||
|
||||
r = parse_argv(argc, argv);
|
||||
if (r < 0)
|
||||
goto end;
|
||||
|
||||
if (arg_action == ACTION_NONE)
|
||||
if (r <= 0)
|
||||
goto end;
|
||||
|
||||
sigbus_install();
|
||||
|
||||
if (arg_directory) {
|
||||
r = sd_journal_open_directory(&j, arg_directory, 0);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to open journals in directory: %s: %m", arg_directory);
|
||||
goto end;
|
||||
}
|
||||
} else {
|
||||
r = sd_journal_open(&j, SD_JOURNAL_LOCAL_ONLY);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to open journal: %m");
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
|
||||
r = journal_access_check_and_warn(j, arg_quiet, true);
|
||||
if (r < 0)
|
||||
goto end;
|
||||
|
||||
r = add_matches(j);
|
||||
if (r < 0)
|
||||
goto end;
|
||||
|
||||
if (DEBUG_LOGGING) {
|
||||
_cleanup_free_ char *filter;
|
||||
|
||||
filter = journal_make_match_string(j);
|
||||
log_debug("Journal filter: %s", filter);
|
||||
}
|
||||
|
||||
units_active = check_units_active(); /* error is treated the same as 0 */
|
||||
|
||||
switch(arg_action) {
|
||||
|
||||
case ACTION_LIST:
|
||||
case ACTION_INFO:
|
||||
pager_open(arg_no_pager, false);
|
||||
r = dump_list(j);
|
||||
break;
|
||||
|
||||
case ACTION_DUMP:
|
||||
r = dump_core(j);
|
||||
break;
|
||||
|
||||
case ACTION_GDB:
|
||||
r = run_gdb(j);
|
||||
break;
|
||||
|
||||
default:
|
||||
assert_not_reached("Shouldn't be here");
|
||||
}
|
||||
r = coredumpctl_main(argc, argv);
|
||||
|
||||
if (units_active > 0)
|
||||
printf("%s-- Notice: %d systemd-coredump@.service %s, output may be incomplete.%s\n",
|
||||
|
@ -662,7 +662,7 @@ int main(int argc, char *argv[]) {
|
||||
else if (arg_diff)
|
||||
arg_flags |= SHOW_OVERRIDDEN;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (optind < argc) {
|
||||
int i;
|
||||
|
@ -34,6 +34,7 @@
|
||||
#include "hostname-util.h"
|
||||
#include "spawn-polkit-agent.h"
|
||||
#include "util.h"
|
||||
#include "verbs.h"
|
||||
|
||||
static bool arg_ask_password = true;
|
||||
static BusTransport arg_transport = BUS_TRANSPORT_LOCAL;
|
||||
@ -43,19 +44,19 @@ static bool arg_pretty = false;
|
||||
static bool arg_static = false;
|
||||
|
||||
typedef struct StatusInfo {
|
||||
char *hostname;
|
||||
char *static_hostname;
|
||||
char *pretty_hostname;
|
||||
char *icon_name;
|
||||
char *chassis;
|
||||
char *deployment;
|
||||
char *location;
|
||||
char *kernel_name;
|
||||
char *kernel_release;
|
||||
char *os_pretty_name;
|
||||
char *os_cpe_name;
|
||||
char *virtualization;
|
||||
char *architecture;
|
||||
const char *hostname;
|
||||
const char *static_hostname;
|
||||
const char *pretty_hostname;
|
||||
const char *icon_name;
|
||||
const char *chassis;
|
||||
const char *deployment;
|
||||
const char *location;
|
||||
const char *kernel_name;
|
||||
const char *kernel_release;
|
||||
const char *os_pretty_name;
|
||||
const char *os_cpe_name;
|
||||
const char *virtualization;
|
||||
const char *architecture;
|
||||
} StatusInfo;
|
||||
|
||||
static void print_status_info(StatusInfo *i) {
|
||||
@ -162,6 +163,7 @@ static int show_all_names(sd_bus *bus, sd_bus_error *error) {
|
||||
{}
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *host_message = NULL, *manager_message = NULL;
|
||||
int r;
|
||||
|
||||
r = bus_map_all_properties(bus,
|
||||
@ -169,42 +171,28 @@ static int show_all_names(sd_bus *bus, sd_bus_error *error) {
|
||||
"/org/freedesktop/hostname1",
|
||||
hostname_map,
|
||||
error,
|
||||
&host_message,
|
||||
&info);
|
||||
if (r < 0)
|
||||
goto fail;
|
||||
return r;
|
||||
|
||||
bus_map_all_properties(bus,
|
||||
"org.freedesktop.systemd1",
|
||||
"/org/freedesktop/systemd1",
|
||||
manager_map,
|
||||
error,
|
||||
&info);
|
||||
r = bus_map_all_properties(bus,
|
||||
"org.freedesktop.systemd1",
|
||||
"/org/freedesktop/systemd1",
|
||||
manager_map,
|
||||
error,
|
||||
&manager_message,
|
||||
&info);
|
||||
|
||||
print_status_info(&info);
|
||||
|
||||
fail:
|
||||
free(info.hostname);
|
||||
free(info.static_hostname);
|
||||
free(info.pretty_hostname);
|
||||
free(info.icon_name);
|
||||
free(info.chassis);
|
||||
free(info.deployment);
|
||||
free(info.location);
|
||||
free(info.kernel_name);
|
||||
free(info.kernel_release);
|
||||
free(info.os_pretty_name);
|
||||
free(info.os_cpe_name);
|
||||
free(info.virtualization);
|
||||
free(info.architecture);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
static int show_status(int argc, char **argv, void *userdata) {
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
|
||||
if (arg_pretty || arg_static || arg_transient) {
|
||||
const char *attr;
|
||||
|
||||
@ -247,14 +235,12 @@ static int set_simple_string(sd_bus *bus, const char *method, const char *value)
|
||||
return r;
|
||||
}
|
||||
|
||||
static int set_hostname(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_hostname(int argc, char **argv, void *userdata) {
|
||||
_cleanup_free_ char *h = NULL;
|
||||
const char *hostname = args[1];
|
||||
const char *hostname = argv[1];
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
if (!arg_pretty && !arg_static && !arg_transient)
|
||||
arg_pretty = arg_static = arg_transient = true;
|
||||
|
||||
@ -301,35 +287,23 @@ static int set_hostname(sd_bus *bus, char **args, unsigned n) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int set_icon_name(sd_bus *bus, char **args, unsigned n) {
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
return set_simple_string(bus, "SetIconName", args[1]);
|
||||
static int set_icon_name(int argc, char **argv, void *userdata) {
|
||||
return set_simple_string(userdata, "SetIconName", argv[1]);
|
||||
}
|
||||
|
||||
static int set_chassis(sd_bus *bus, char **args, unsigned n) {
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
return set_simple_string(bus, "SetChassis", args[1]);
|
||||
static int set_chassis(int argc, char **argv, void *userdata) {
|
||||
return set_simple_string(userdata, "SetChassis", argv[1]);
|
||||
}
|
||||
|
||||
static int set_deployment(sd_bus *bus, char **args, unsigned n) {
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
return set_simple_string(bus, "SetDeployment", args[1]);
|
||||
static int set_deployment(int argc, char **argv, void *userdata) {
|
||||
return set_simple_string(userdata, "SetDeployment", argv[1]);
|
||||
}
|
||||
|
||||
static int set_location(sd_bus *bus, char **args, unsigned n) {
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
return set_simple_string(bus, "SetLocation", args[1]);
|
||||
static int set_location(int argc, char **argv, void *userdata) {
|
||||
return set_simple_string(userdata, "SetLocation", argv[1]);
|
||||
}
|
||||
|
||||
static void help(void) {
|
||||
static int help(void) {
|
||||
printf("%s [OPTIONS...] COMMAND ...\n\n"
|
||||
"Query or change system hostname.\n\n"
|
||||
" -h --help Show this help\n"
|
||||
@ -348,6 +322,12 @@ static void help(void) {
|
||||
" set-deployment NAME Set deployment environment for host\n"
|
||||
" set-location NAME Set location for host\n"
|
||||
, program_invocation_short_name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int verb_help(int argc, char **argv, void *userdata) {
|
||||
return help();
|
||||
}
|
||||
|
||||
static int parse_argv(int argc, char *argv[]) {
|
||||
@ -382,8 +362,7 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
switch (c) {
|
||||
|
||||
case 'h':
|
||||
help();
|
||||
return 0;
|
||||
return help();
|
||||
|
||||
case ARG_VERSION:
|
||||
return version();
|
||||
@ -426,82 +405,18 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
|
||||
static int hostnamectl_main(sd_bus *bus, int argc, char *argv[]) {
|
||||
|
||||
static const struct {
|
||||
const char* verb;
|
||||
const enum {
|
||||
MORE,
|
||||
LESS,
|
||||
EQUAL
|
||||
} argc_cmp;
|
||||
const int argc;
|
||||
int (* const dispatch)(sd_bus *bus, char **args, unsigned n);
|
||||
} verbs[] = {
|
||||
{ "status", LESS, 1, show_status },
|
||||
{ "set-hostname", EQUAL, 2, set_hostname },
|
||||
{ "set-icon-name", EQUAL, 2, set_icon_name },
|
||||
{ "set-chassis", EQUAL, 2, set_chassis },
|
||||
{ "set-deployment", EQUAL, 2, set_deployment },
|
||||
{ "set-location", EQUAL, 2, set_location },
|
||||
static const Verb verbs[] = {
|
||||
{ "status", VERB_ANY, 1, VERB_DEFAULT, show_status },
|
||||
{ "set-hostname", 2, 2, 0, set_hostname },
|
||||
{ "set-icon-name", 2, 2, 0, set_icon_name },
|
||||
{ "set-chassis", 2, 2, 0, set_chassis },
|
||||
{ "set-deployment", 2, 2, 0, set_deployment },
|
||||
{ "set-location", 2, 2, 0, set_location },
|
||||
{ "help", VERB_ANY, VERB_ANY, 0, verb_help }, /* Not documented, but supported since it is created. */
|
||||
{}
|
||||
};
|
||||
|
||||
int left;
|
||||
unsigned i;
|
||||
|
||||
assert(argc >= 0);
|
||||
assert(argv);
|
||||
|
||||
left = argc - optind;
|
||||
|
||||
if (left <= 0)
|
||||
/* Special rule: no arguments means "status" */
|
||||
i = 0;
|
||||
else {
|
||||
if (streq(argv[optind], "help")) {
|
||||
help();
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (i = 0; i < ELEMENTSOF(verbs); i++)
|
||||
if (streq(argv[optind], verbs[i].verb))
|
||||
break;
|
||||
|
||||
if (i >= ELEMENTSOF(verbs)) {
|
||||
log_error("Unknown operation %s", argv[optind]);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
switch (verbs[i].argc_cmp) {
|
||||
|
||||
case EQUAL:
|
||||
if (left != verbs[i].argc) {
|
||||
log_error("Invalid number of arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case MORE:
|
||||
if (left < verbs[i].argc) {
|
||||
log_error("Too few arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case LESS:
|
||||
if (left > verbs[i].argc) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
assert_not_reached("Unknown comparison operator.");
|
||||
}
|
||||
|
||||
return verbs[i].dispatch(bus, argv + optind, left);
|
||||
return dispatch_verb(argc, argv, verbs, bus);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
|
@ -753,7 +753,7 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
}
|
||||
|
||||
static int hwdb_main(int argc, char *argv[]) {
|
||||
const Verb verbs[] = {
|
||||
static const Verb verbs[] = {
|
||||
{ "update", 1, 1, 0, hwdb_update },
|
||||
{ "query", 2, 2, 0, hwdb_query },
|
||||
{},
|
||||
|
@ -316,7 +316,7 @@ static int parse_boot_descriptor(const char *x, sd_id128_t *boot_id, int *offset
|
||||
|
||||
static void help(void) {
|
||||
|
||||
pager_open(arg_no_pager, arg_pager_end);
|
||||
(void) pager_open(arg_no_pager, arg_pager_end);
|
||||
|
||||
printf("%s [OPTIONS...] [MATCHES...]\n\n"
|
||||
"Query the journal.\n\n"
|
||||
@ -1369,7 +1369,7 @@ static int list_boots(sd_journal *j) {
|
||||
if (count == 0)
|
||||
return count;
|
||||
|
||||
pager_open(arg_no_pager, arg_pager_end);
|
||||
(void) pager_open(arg_no_pager, arg_pager_end);
|
||||
|
||||
/* numbers are one less, but we need an extra char for the sign */
|
||||
w = DECIMAL_STR_WIDTH(count - 1) + 1;
|
||||
@ -2135,7 +2135,7 @@ int main(int argc, char *argv[]) {
|
||||
} else {
|
||||
bool oneline = arg_action == ACTION_LIST_CATALOG;
|
||||
|
||||
pager_open(arg_no_pager, arg_pager_end);
|
||||
(void) pager_open(arg_no_pager, arg_pager_end);
|
||||
|
||||
if (optind < argc)
|
||||
r = catalog_list_items(stdout, database, oneline, argv + optind);
|
||||
@ -2492,7 +2492,7 @@ int main(int argc, char *argv[]) {
|
||||
need_seek = true;
|
||||
|
||||
if (!arg_follow)
|
||||
pager_open(arg_no_pager, arg_pager_end);
|
||||
(void) pager_open(arg_no_pager, arg_pager_end);
|
||||
|
||||
if (!arg_quiet && (arg_lines != 0 || arg_follow)) {
|
||||
usec_t start, end;
|
||||
|
@ -39,6 +39,7 @@
|
||||
#include "spawn-polkit-agent.h"
|
||||
#include "strv.h"
|
||||
#include "util.h"
|
||||
#include "verbs.h"
|
||||
#include "virt.h"
|
||||
|
||||
static bool arg_no_pager = false;
|
||||
@ -49,23 +50,17 @@ static bool arg_convert = true;
|
||||
|
||||
typedef struct StatusInfo {
|
||||
char **locale;
|
||||
char *vconsole_keymap;
|
||||
char *vconsole_keymap_toggle;
|
||||
char *x11_layout;
|
||||
char *x11_model;
|
||||
char *x11_variant;
|
||||
char *x11_options;
|
||||
const char *vconsole_keymap;
|
||||
const char *vconsole_keymap_toggle;
|
||||
const char *x11_layout;
|
||||
const char *x11_model;
|
||||
const char *x11_variant;
|
||||
const char *x11_options;
|
||||
} StatusInfo;
|
||||
|
||||
static void status_info_clear(StatusInfo *info) {
|
||||
if (info) {
|
||||
strv_free(info->locale);
|
||||
free(info->vconsole_keymap);
|
||||
free(info->vconsole_keymap_toggle);
|
||||
free(info->x11_layout);
|
||||
free(info->x11_model);
|
||||
free(info->x11_variant);
|
||||
free(info->x11_options);
|
||||
zero(*info);
|
||||
}
|
||||
}
|
||||
@ -142,7 +137,7 @@ static void print_status_info(StatusInfo *i) {
|
||||
printf(" X11 Options: %s\n", i->x11_options);
|
||||
}
|
||||
|
||||
static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
static int show_status(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(status_info_clear) StatusInfo info = {};
|
||||
static const struct bus_properties_map map[] = {
|
||||
{ "VConsoleKeymap", "s", NULL, offsetof(StatusInfo, vconsole_keymap) },
|
||||
@ -157,6 +152,8 @@ static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
@ -166,6 +163,7 @@ static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
"/org/freedesktop/locale1",
|
||||
map,
|
||||
&error,
|
||||
&m,
|
||||
&info);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
@ -176,13 +174,13 @@ static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
return r;
|
||||
}
|
||||
|
||||
static int set_locale(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_locale(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
assert(args);
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
@ -196,7 +194,7 @@ static int set_locale(sd_bus *bus, char **args, unsigned n) {
|
||||
if (r < 0)
|
||||
return bus_log_create_error(r);
|
||||
|
||||
r = sd_bus_message_append_strv(m, args + 1);
|
||||
r = sd_bus_message_append_strv(m, argv + 1);
|
||||
if (r < 0)
|
||||
return bus_log_create_error(r);
|
||||
|
||||
@ -213,39 +211,32 @@ static int set_locale(sd_bus *bus, char **args, unsigned n) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int list_locales(sd_bus *bus, char **args, unsigned n) {
|
||||
static int list_locales(int argc, char **argv, void *userdata) {
|
||||
_cleanup_strv_free_ char **l = NULL;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
|
||||
r = get_locales(&l);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to read list of locales: %m");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
strv_print(l);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int set_vconsole_keymap(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_vconsole_keymap(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
const char *map, *toggle_map;
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
assert(args);
|
||||
|
||||
if (n > 3) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
map = args[1];
|
||||
toggle_map = n > 2 ? args[2] : "";
|
||||
map = argv[1];
|
||||
toggle_map = argc > 2 ? argv[2] : "";
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
@ -262,42 +253,33 @@ static int set_vconsole_keymap(sd_bus *bus, char **args, unsigned n) {
|
||||
return r;
|
||||
}
|
||||
|
||||
static int list_vconsole_keymaps(sd_bus *bus, char **args, unsigned n) {
|
||||
static int list_vconsole_keymaps(int argc, char **argv, void *userdata) {
|
||||
_cleanup_strv_free_ char **l = NULL;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
|
||||
r = get_keymaps(&l);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to read list of keymaps: %m");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
strv_print(l);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int set_x11_keymap(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_x11_keymap(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
const char *layout, *model, *variant, *options;
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
assert(args);
|
||||
|
||||
if (n > 5) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
layout = args[1];
|
||||
model = n > 2 ? args[2] : "";
|
||||
variant = n > 3 ? args[3] : "";
|
||||
options = n > 4 ? args[4] : "";
|
||||
layout = argv[1];
|
||||
model = argc > 2 ? argv[2] : "";
|
||||
variant = argc > 3 ? argv[3] : "";
|
||||
options = argc > 4 ? argv[4] : "";
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
@ -315,7 +297,7 @@ static int set_x11_keymap(sd_bus *bus, char **args, unsigned n) {
|
||||
return r;
|
||||
}
|
||||
|
||||
static int list_x11_keymaps(sd_bus *bus, char **args, unsigned n) {
|
||||
static int list_x11_keymaps(int argc, char **argv, void *userdata) {
|
||||
_cleanup_fclose_ FILE *f = NULL;
|
||||
_cleanup_strv_free_ char **list = NULL;
|
||||
char line[LINE_MAX];
|
||||
@ -328,22 +310,17 @@ static int list_x11_keymaps(sd_bus *bus, char **args, unsigned n) {
|
||||
} state = NONE, look_for;
|
||||
int r;
|
||||
|
||||
if (n > 2) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
f = fopen("/usr/share/X11/xkb/rules/base.lst", "re");
|
||||
if (!f)
|
||||
return log_error_errno(errno, "Failed to open keyboard mapping list. %m");
|
||||
|
||||
if (streq(args[0], "list-x11-keymap-models"))
|
||||
if (streq(argv[0], "list-x11-keymap-models"))
|
||||
look_for = MODELS;
|
||||
else if (streq(args[0], "list-x11-keymap-layouts"))
|
||||
else if (streq(argv[0], "list-x11-keymap-layouts"))
|
||||
look_for = LAYOUTS;
|
||||
else if (streq(args[0], "list-x11-keymap-variants"))
|
||||
else if (streq(argv[0], "list-x11-keymap-variants"))
|
||||
look_for = VARIANTS;
|
||||
else if (streq(args[0], "list-x11-keymap-options"))
|
||||
else if (streq(argv[0], "list-x11-keymap-options"))
|
||||
look_for = OPTIONS;
|
||||
else
|
||||
assert_not_reached("Wrong parameter");
|
||||
@ -376,7 +353,7 @@ static int list_x11_keymaps(sd_bus *bus, char **args, unsigned n) {
|
||||
|
||||
w = l + strcspn(l, WHITESPACE);
|
||||
|
||||
if (n > 1) {
|
||||
if (argc > 1) {
|
||||
char *e;
|
||||
|
||||
if (*w == 0)
|
||||
@ -392,7 +369,7 @@ static int list_x11_keymaps(sd_bus *bus, char **args, unsigned n) {
|
||||
|
||||
*e = 0;
|
||||
|
||||
if (!streq(w, args[1]))
|
||||
if (!streq(w, argv[1]))
|
||||
continue;
|
||||
} else
|
||||
*w = 0;
|
||||
@ -410,13 +387,13 @@ static int list_x11_keymaps(sd_bus *bus, char **args, unsigned n) {
|
||||
strv_sort(list);
|
||||
strv_uniq(list);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
strv_print(list);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void help(void) {
|
||||
static int help(void) {
|
||||
printf("%s [OPTIONS...] COMMAND ...\n\n"
|
||||
"Query or change system locale and keyboard settings.\n\n"
|
||||
" -h --help Show this help\n"
|
||||
@ -440,6 +417,12 @@ static void help(void) {
|
||||
" Show known X11 keyboard mapping variants\n"
|
||||
" list-x11-keymap-options Show known X11 keyboard mapping options\n"
|
||||
, program_invocation_short_name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int verb_help(int argc, char **argv, void *userdata) {
|
||||
return help();
|
||||
}
|
||||
|
||||
static int parse_argv(int argc, char *argv[]) {
|
||||
@ -472,8 +455,7 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
switch (c) {
|
||||
|
||||
case 'h':
|
||||
help();
|
||||
return 0;
|
||||
return help();
|
||||
|
||||
case ARG_VERSION:
|
||||
return version();
|
||||
@ -512,86 +494,22 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
|
||||
static int localectl_main(sd_bus *bus, int argc, char *argv[]) {
|
||||
|
||||
static const struct {
|
||||
const char* verb;
|
||||
const enum {
|
||||
MORE,
|
||||
LESS,
|
||||
EQUAL
|
||||
} argc_cmp;
|
||||
const int argc;
|
||||
int (* const dispatch)(sd_bus *bus, char **args, unsigned n);
|
||||
} verbs[] = {
|
||||
{ "status", LESS, 1, show_status },
|
||||
{ "set-locale", MORE, 2, set_locale },
|
||||
{ "list-locales", EQUAL, 1, list_locales },
|
||||
{ "set-keymap", MORE, 2, set_vconsole_keymap },
|
||||
{ "list-keymaps", EQUAL, 1, list_vconsole_keymaps },
|
||||
{ "set-x11-keymap", MORE, 2, set_x11_keymap },
|
||||
{ "list-x11-keymap-models", EQUAL, 1, list_x11_keymaps },
|
||||
{ "list-x11-keymap-layouts", EQUAL, 1, list_x11_keymaps },
|
||||
{ "list-x11-keymap-variants", LESS, 2, list_x11_keymaps },
|
||||
{ "list-x11-keymap-options", EQUAL, 1, list_x11_keymaps },
|
||||
static const Verb verbs[] = {
|
||||
{ "status", VERB_ANY, 1, VERB_DEFAULT, show_status },
|
||||
{ "set-locale", 2, VERB_ANY, 0, set_locale },
|
||||
{ "list-locales", VERB_ANY, 1, 0, list_locales },
|
||||
{ "set-keymap", 2, 3, 0, set_vconsole_keymap },
|
||||
{ "list-keymaps", VERB_ANY, 1, 0, list_vconsole_keymaps },
|
||||
{ "set-x11-keymap", 2, 5, 0, set_x11_keymap },
|
||||
{ "list-x11-keymap-models", VERB_ANY, 1, 0, list_x11_keymaps },
|
||||
{ "list-x11-keymap-layouts", VERB_ANY, 1, 0, list_x11_keymaps },
|
||||
{ "list-x11-keymap-variants", VERB_ANY, 2, 0, list_x11_keymaps },
|
||||
{ "list-x11-keymap-options", VERB_ANY, 1, 0, list_x11_keymaps },
|
||||
{ "help", VERB_ANY, VERB_ANY, 0, verb_help }, /* Not documented, but supported since it is created. */
|
||||
{}
|
||||
};
|
||||
|
||||
int left;
|
||||
unsigned i;
|
||||
|
||||
assert(argc >= 0);
|
||||
assert(argv);
|
||||
|
||||
left = argc - optind;
|
||||
|
||||
if (left <= 0)
|
||||
/* Special rule: no arguments means "status" */
|
||||
i = 0;
|
||||
else {
|
||||
if (streq(argv[optind], "help")) {
|
||||
help();
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (i = 0; i < ELEMENTSOF(verbs); i++)
|
||||
if (streq(argv[optind], verbs[i].verb))
|
||||
break;
|
||||
|
||||
if (i >= ELEMENTSOF(verbs)) {
|
||||
log_error("Unknown operation %s", argv[optind]);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
switch (verbs[i].argc_cmp) {
|
||||
|
||||
case EQUAL:
|
||||
if (left != verbs[i].argc) {
|
||||
log_error("Invalid number of arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case MORE:
|
||||
if (left < verbs[i].argc) {
|
||||
log_error("Too few arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case LESS:
|
||||
if (left > verbs[i].argc) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
assert_not_reached("Unknown comparison operator.");
|
||||
}
|
||||
|
||||
return verbs[i].dispatch(bus, argv + optind, left);
|
||||
return dispatch_verb(argc, argv, verbs, bus);
|
||||
}
|
||||
|
||||
int main(int argc, char*argv[]) {
|
||||
|
@ -111,7 +111,7 @@ static int list_sessions(int argc, char *argv[], void *userdata) {
|
||||
assert(bus);
|
||||
assert(argv);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
@ -186,7 +186,7 @@ static int list_users(int argc, char *argv[], void *userdata) {
|
||||
assert(bus);
|
||||
assert(argv);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
@ -231,7 +231,7 @@ static int list_seats(int argc, char *argv[], void *userdata) {
|
||||
assert(bus);
|
||||
assert(argv);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
@ -307,77 +307,52 @@ static int show_unit_cgroup(sd_bus *bus, const char *interface, const char *unit
|
||||
}
|
||||
|
||||
typedef struct SessionStatusInfo {
|
||||
char *id;
|
||||
const char *id;
|
||||
uid_t uid;
|
||||
char *name;
|
||||
const char *name;
|
||||
struct dual_timestamp timestamp;
|
||||
unsigned int vtnr;
|
||||
char *seat;
|
||||
char *tty;
|
||||
char *display;
|
||||
int remote;
|
||||
char *remote_host;
|
||||
char *remote_user;
|
||||
char *service;
|
||||
const char *seat;
|
||||
const char *tty;
|
||||
const char *display;
|
||||
bool remote;
|
||||
const char *remote_host;
|
||||
const char *remote_user;
|
||||
const char *service;
|
||||
pid_t leader;
|
||||
char *type;
|
||||
char *class;
|
||||
char *state;
|
||||
char *scope;
|
||||
char *desktop;
|
||||
const char *type;
|
||||
const char *class;
|
||||
const char *state;
|
||||
const char *scope;
|
||||
const char *desktop;
|
||||
} SessionStatusInfo;
|
||||
|
||||
typedef struct UserStatusInfo {
|
||||
uid_t uid;
|
||||
int linger;
|
||||
char *name;
|
||||
bool linger;
|
||||
const char *name;
|
||||
struct dual_timestamp timestamp;
|
||||
char *state;
|
||||
const char *state;
|
||||
char **sessions;
|
||||
char *display;
|
||||
char *slice;
|
||||
const char *display;
|
||||
const char *slice;
|
||||
} UserStatusInfo;
|
||||
|
||||
typedef struct SeatStatusInfo {
|
||||
char *id;
|
||||
char *active_session;
|
||||
const char *id;
|
||||
const char *active_session;
|
||||
char **sessions;
|
||||
} SeatStatusInfo;
|
||||
|
||||
static void session_status_info_clear(SessionStatusInfo *info) {
|
||||
if (info) {
|
||||
free(info->id);
|
||||
free(info->name);
|
||||
free(info->seat);
|
||||
free(info->tty);
|
||||
free(info->display);
|
||||
free(info->remote_host);
|
||||
free(info->remote_user);
|
||||
free(info->service);
|
||||
free(info->type);
|
||||
free(info->class);
|
||||
free(info->state);
|
||||
free(info->scope);
|
||||
free(info->desktop);
|
||||
zero(*info);
|
||||
}
|
||||
}
|
||||
|
||||
static void user_status_info_clear(UserStatusInfo *info) {
|
||||
if (info) {
|
||||
free(info->name);
|
||||
free(info->state);
|
||||
strv_free(info->sessions);
|
||||
free(info->display);
|
||||
free(info->slice);
|
||||
zero(*info);
|
||||
}
|
||||
}
|
||||
|
||||
static void seat_status_info_clear(SeatStatusInfo *info) {
|
||||
if (info) {
|
||||
free(info->id);
|
||||
free(info->active_session);
|
||||
strv_free(info->sessions);
|
||||
zero(*info);
|
||||
}
|
||||
@ -395,22 +370,9 @@ static int prop_map_first_of_struct(sd_bus *bus, const char *member, sd_bus_mess
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (IN_SET(contents[0], 's', 'o')) {
|
||||
const char *s;
|
||||
char **p = (char **) userdata;
|
||||
|
||||
r = sd_bus_message_read_basic(m, contents[0], &s);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = free_and_strdup(p, s);
|
||||
if (r < 0)
|
||||
return r;
|
||||
} else {
|
||||
r = sd_bus_message_read_basic(m, contents[0], userdata);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
r = sd_bus_message_read_basic(m, contents[0], userdata);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_skip(m, contents+1);
|
||||
if (r < 0)
|
||||
@ -471,12 +433,13 @@ static int print_session_status_info(sd_bus *bus, const char *path, bool *new_li
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
char since1[FORMAT_TIMESTAMP_RELATIVE_MAX], *s1;
|
||||
char since2[FORMAT_TIMESTAMP_MAX], *s2;
|
||||
_cleanup_(session_status_info_clear) SessionStatusInfo i = {};
|
||||
SessionStatusInfo i = {};
|
||||
int r;
|
||||
|
||||
r = bus_map_all_properties(bus, "org.freedesktop.login1", path, map, &error, &i);
|
||||
r = bus_map_all_properties(bus, "org.freedesktop.login1", path, map, &error, &m, &i);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
|
||||
@ -601,12 +564,13 @@ static int print_user_status_info(sd_bus *bus, const char *path, bool *new_line)
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
char since1[FORMAT_TIMESTAMP_RELATIVE_MAX], *s1;
|
||||
char since2[FORMAT_TIMESTAMP_MAX], *s2;
|
||||
_cleanup_(user_status_info_clear) UserStatusInfo i = {};
|
||||
int r;
|
||||
|
||||
r = bus_map_all_properties(bus, "org.freedesktop.login1", path, map, &error, &i);
|
||||
r = bus_map_all_properties(bus, "org.freedesktop.login1", path, map, &error, &m, &i);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
|
||||
@ -676,10 +640,11 @@ static int print_seat_status_info(sd_bus *bus, const char *path, bool *new_line)
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
_cleanup_(seat_status_info_clear) SeatStatusInfo i = {};
|
||||
int r;
|
||||
|
||||
r = bus_map_all_properties(bus, "org.freedesktop.login1", path, map, &error, &i);
|
||||
r = bus_map_all_properties(bus, "org.freedesktop.login1", path, map, &error, &m, &i);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
|
||||
@ -723,40 +688,41 @@ static int print_seat_status_info(sd_bus *bus, const char *path, bool *new_line)
|
||||
|
||||
#define property(name, fmt, ...) \
|
||||
do { \
|
||||
if (arg_value) \
|
||||
if (value) \
|
||||
printf(fmt "\n", __VA_ARGS__); \
|
||||
else \
|
||||
printf("%s=" fmt "\n", name, __VA_ARGS__); \
|
||||
} while (0)
|
||||
|
||||
static int print_property(const char *name, sd_bus_message *m, const char *contents) {
|
||||
static int print_property(const char *name, sd_bus_message *m, bool value, bool all) {
|
||||
char type;
|
||||
const char *contents;
|
||||
int r;
|
||||
|
||||
assert(name);
|
||||
assert(m);
|
||||
assert(contents);
|
||||
|
||||
if (arg_property && !strv_find(arg_property, name))
|
||||
/* skip what we didn't read */
|
||||
return sd_bus_message_skip(m, contents);
|
||||
r = sd_bus_message_peek_type(m, &type, &contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
switch (contents[0]) {
|
||||
switch (type) {
|
||||
|
||||
case SD_BUS_TYPE_STRUCT_BEGIN:
|
||||
case SD_BUS_TYPE_STRUCT:
|
||||
|
||||
if (contents[1] == SD_BUS_TYPE_STRING && STR_IN_SET(name, "Display", "Seat", "ActiveSession")) {
|
||||
if (contents[0] == SD_BUS_TYPE_STRING && STR_IN_SET(name, "Display", "Seat", "ActiveSession")) {
|
||||
const char *s;
|
||||
|
||||
r = sd_bus_message_read(m, "(so)", &s, NULL);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
if (arg_all || !isempty(s))
|
||||
if (all || !isempty(s))
|
||||
property(name, "%s", s);
|
||||
|
||||
return 0;
|
||||
return 1;
|
||||
|
||||
} else if (contents[1] == SD_BUS_TYPE_UINT32 && streq(name, "User")) {
|
||||
} else if (contents[0] == SD_BUS_TYPE_UINT32 && streq(name, "User")) {
|
||||
uint32_t uid;
|
||||
|
||||
r = sd_bus_message_read(m, "(uo)", &uid, NULL);
|
||||
@ -769,14 +735,13 @@ static int print_property(const char *name, sd_bus_message *m, const char *conte
|
||||
}
|
||||
|
||||
property(name, UID_FMT, uid);
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case SD_BUS_TYPE_ARRAY:
|
||||
|
||||
if (contents[1] == SD_BUS_TYPE_STRUCT_BEGIN && streq(name, "Sessions")) {
|
||||
if (contents[0] == SD_BUS_TYPE_STRUCT_BEGIN && streq(name, "Sessions")) {
|
||||
const char *s;
|
||||
bool space = false;
|
||||
|
||||
@ -784,7 +749,7 @@ static int print_property(const char *name, sd_bus_message *m, const char *conte
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
if (!arg_value)
|
||||
if (!value)
|
||||
printf("%s=", name);
|
||||
|
||||
while ((r = sd_bus_message_read(m, "(so)", &s, NULL)) > 0) {
|
||||
@ -792,7 +757,7 @@ static int print_property(const char *name, sd_bus_message *m, const char *conte
|
||||
space = true;
|
||||
}
|
||||
|
||||
if (space || !arg_value)
|
||||
if (space || !value)
|
||||
printf("\n");
|
||||
|
||||
if (r < 0)
|
||||
@ -802,25 +767,11 @@ static int print_property(const char *name, sd_bus_message *m, const char *conte
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
r = bus_print_property(name, m, arg_value, arg_all);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
if (r == 0) {
|
||||
r = sd_bus_message_skip(m, contents);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
if (arg_all)
|
||||
printf("%s=[unprintable]\n", name);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -833,58 +784,12 @@ static int show_properties(sd_bus *bus, const char *path, bool *new_line) {
|
||||
assert(path);
|
||||
assert(new_line);
|
||||
|
||||
r = sd_bus_call_method(
|
||||
bus,
|
||||
"org.freedesktop.login1",
|
||||
path,
|
||||
"org.freedesktop.DBus.Properties",
|
||||
"GetAll",
|
||||
&error,
|
||||
&reply,
|
||||
"s", "");
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to get properties: %s", bus_error_message(&error, r));
|
||||
|
||||
r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_ARRAY, "{sv}");
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
if (*new_line)
|
||||
printf("\n");
|
||||
|
||||
*new_line = true;
|
||||
|
||||
while ((r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_DICT_ENTRY, "sv")) > 0) {
|
||||
const char *name, *contents;
|
||||
|
||||
r = sd_bus_message_read(reply, "s", &name);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
r = sd_bus_message_peek_type(reply, NULL, &contents);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_VARIANT, contents);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
r = print_property(name, reply, contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_exit_container(reply);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
r = sd_bus_message_exit_container(reply);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
}
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
r = sd_bus_message_exit_container(reply);
|
||||
r = bus_print_all_properties(bus, "org.freedesktop.login1", path, print_property, arg_property, arg_value, arg_all, NULL);
|
||||
if (r < 0)
|
||||
return bus_log_parse_error(r);
|
||||
|
||||
@ -903,7 +808,7 @@ static int show_session(int argc, char *argv[], void *userdata) {
|
||||
|
||||
properties = !strstr(argv[0], "status");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (argc <= 1) {
|
||||
const char *session, *p = "/org/freedesktop/login1/session/self";
|
||||
@ -955,7 +860,7 @@ static int show_user(int argc, char *argv[], void *userdata) {
|
||||
|
||||
properties = !strstr(argv[0], "status");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (argc <= 1) {
|
||||
/* If not argument is specified inspect the manager
|
||||
@ -1015,7 +920,7 @@ static int show_seat(int argc, char *argv[], void *userdata) {
|
||||
|
||||
properties = !strstr(argv[0], "status");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (argc <= 1) {
|
||||
/* If not argument is specified inspect the manager
|
||||
|
@ -207,7 +207,7 @@ static int list_machines(int argc, char *argv[], void *userdata) {
|
||||
|
||||
assert(bus);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
"org.freedesktop.machine1",
|
||||
@ -363,7 +363,7 @@ static int list_images(int argc, char *argv[], void *userdata) {
|
||||
|
||||
assert(bus);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
"org.freedesktop.machine1",
|
||||
@ -639,12 +639,12 @@ static int print_uid_shift(sd_bus *bus, const char *name) {
|
||||
}
|
||||
|
||||
typedef struct MachineStatusInfo {
|
||||
char *name;
|
||||
const char *name;
|
||||
sd_id128_t id;
|
||||
char *class;
|
||||
char *service;
|
||||
char *unit;
|
||||
char *root_directory;
|
||||
const char *class;
|
||||
const char *service;
|
||||
const char *unit;
|
||||
const char *root_directory;
|
||||
pid_t leader;
|
||||
struct dual_timestamp timestamp;
|
||||
int *netif;
|
||||
@ -653,11 +653,6 @@ typedef struct MachineStatusInfo {
|
||||
|
||||
static void machine_status_info_clear(MachineStatusInfo *info) {
|
||||
if (info) {
|
||||
free(info->name);
|
||||
free(info->class);
|
||||
free(info->service);
|
||||
free(info->unit);
|
||||
free(info->root_directory);
|
||||
free(info->netif);
|
||||
zero(*info);
|
||||
}
|
||||
@ -803,6 +798,7 @@ static int show_machine_info(const char *verb, sd_bus *bus, const char *path, bo
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
_cleanup_(machine_status_info_clear) MachineStatusInfo info = {};
|
||||
int r;
|
||||
|
||||
@ -816,6 +812,7 @@ static int show_machine_info(const char *verb, sd_bus *bus, const char *path, bo
|
||||
path,
|
||||
map,
|
||||
&error,
|
||||
&m,
|
||||
&info);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
@ -841,7 +838,7 @@ static int show_machine_properties(sd_bus *bus, const char *path, bool *new_line
|
||||
|
||||
*new_line = true;
|
||||
|
||||
r = bus_print_all_properties(bus, "org.freedesktop.machine1", path, arg_property, arg_value, arg_all);
|
||||
r = bus_print_all_properties(bus, "org.freedesktop.machine1", path, NULL, arg_property, arg_value, arg_all, NULL);
|
||||
if (r < 0)
|
||||
log_error_errno(r, "Could not get properties: %m");
|
||||
|
||||
@ -860,7 +857,7 @@ static int show_machine(int argc, char *argv[], void *userdata) {
|
||||
|
||||
properties = !strstr(argv[0], "status");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (properties && argc <= 1) {
|
||||
|
||||
@ -994,10 +991,10 @@ static int print_image_machine_info(sd_bus *bus, const char *name) {
|
||||
}
|
||||
|
||||
typedef struct ImageStatusInfo {
|
||||
char *name;
|
||||
char *path;
|
||||
char *type;
|
||||
int read_only;
|
||||
const char *name;
|
||||
const char *path;
|
||||
const char *type;
|
||||
bool read_only;
|
||||
usec_t crtime;
|
||||
usec_t mtime;
|
||||
uint64_t usage;
|
||||
@ -1006,16 +1003,6 @@ typedef struct ImageStatusInfo {
|
||||
uint64_t limit_exclusive;
|
||||
} ImageStatusInfo;
|
||||
|
||||
static void image_status_info_clear(ImageStatusInfo *info) {
|
||||
if (!info)
|
||||
return;
|
||||
|
||||
free(info->name);
|
||||
free(info->path);
|
||||
free(info->type);
|
||||
zero(*info);
|
||||
}
|
||||
|
||||
static void print_image_status_info(sd_bus *bus, ImageStatusInfo *i) {
|
||||
char ts_relative[FORMAT_TIMESTAMP_RELATIVE_MAX], *s1;
|
||||
char ts_absolute[FORMAT_TIMESTAMP_MAX], *s2;
|
||||
@ -1093,7 +1080,8 @@ static int show_image_info(sd_bus *bus, const char *path, bool *new_line) {
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(image_status_info_clear) ImageStatusInfo info = {};
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
ImageStatusInfo info = {};
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
@ -1105,6 +1093,7 @@ static int show_image_info(sd_bus *bus, const char *path, bool *new_line) {
|
||||
path,
|
||||
map,
|
||||
&error,
|
||||
&m,
|
||||
&info);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
@ -1119,20 +1108,11 @@ static int show_image_info(sd_bus *bus, const char *path, bool *new_line) {
|
||||
}
|
||||
|
||||
typedef struct PoolStatusInfo {
|
||||
char *path;
|
||||
const char *path;
|
||||
uint64_t usage;
|
||||
uint64_t limit;
|
||||
} PoolStatusInfo;
|
||||
|
||||
static void pool_status_info_clear(PoolStatusInfo *info) {
|
||||
if (info) {
|
||||
free(info->path);
|
||||
zero(*info);
|
||||
info->usage = -1;
|
||||
info->limit = -1;
|
||||
}
|
||||
}
|
||||
|
||||
static void print_pool_status_info(sd_bus *bus, PoolStatusInfo *i) {
|
||||
char bs[FORMAT_BYTES_MAX], *s;
|
||||
|
||||
@ -1157,12 +1137,13 @@ static int show_pool_info(sd_bus *bus) {
|
||||
{}
|
||||
};
|
||||
|
||||
_cleanup_(pool_status_info_clear) PoolStatusInfo info = {
|
||||
PoolStatusInfo info = {
|
||||
.usage = (uint64_t) -1,
|
||||
.limit = (uint64_t) -1,
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
@ -1172,6 +1153,7 @@ static int show_pool_info(sd_bus *bus) {
|
||||
"/org/freedesktop/machine1",
|
||||
map,
|
||||
&error,
|
||||
&m,
|
||||
&info);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Could not get properties: %s", bus_error_message(&error, r));
|
||||
@ -1194,7 +1176,7 @@ static int show_image_properties(sd_bus *bus, const char *path, bool *new_line)
|
||||
|
||||
*new_line = true;
|
||||
|
||||
r = bus_print_all_properties(bus, "org.freedesktop.machine1", path, arg_property, arg_value, arg_all);
|
||||
r = bus_print_all_properties(bus, "org.freedesktop.machine1", path, NULL, arg_property, arg_value, arg_all, NULL);
|
||||
if (r < 0)
|
||||
log_error_errno(r, "Could not get properties: %m");
|
||||
|
||||
@ -1213,7 +1195,7 @@ static int show_image(int argc, char *argv[], void *userdata) {
|
||||
|
||||
properties = !strstr(argv[0], "status");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (argc <= 1) {
|
||||
|
||||
@ -2543,7 +2525,7 @@ static int list_transfers(int argc, char *argv[], void *userdata) {
|
||||
double progress;
|
||||
int r;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
"org.freedesktop.import1",
|
||||
@ -2758,7 +2740,7 @@ static int clean_images(int argc, char *argv[], void *userdata) {
|
||||
}
|
||||
|
||||
static int help(int argc, char *argv[], void *userdata) {
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
printf("%s [OPTIONS...] {COMMAND} ...\n\n"
|
||||
"Send control commands to or query the virtual machine and container\n"
|
||||
|
@ -1529,7 +1529,7 @@ static int list_devices(void) {
|
||||
|
||||
qsort_safe(items, n, sizeof(struct item), compare_item);
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
fputs(ansi_underline(), stdout);
|
||||
for (c = 0; c < _COLUMN_MAX; c++) {
|
||||
|
@ -273,7 +273,7 @@ static int list_links(int argc, char *argv[], void *userdata) {
|
||||
if (c < 0)
|
||||
return c;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (arg_legend)
|
||||
printf("%3s %-16s %-18s %-11s %-10s\n",
|
||||
@ -897,7 +897,7 @@ static int link_status(int argc, char *argv[], void *userdata) {
|
||||
_cleanup_free_ LinkInfo *links = NULL;
|
||||
int r, c, i;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
r = sd_netlink_open(&rtnl);
|
||||
if (r < 0)
|
||||
@ -993,7 +993,7 @@ static int link_lldp_status(int argc, char *argv[], void *userdata) {
|
||||
if (c < 0)
|
||||
return c;
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (arg_legend)
|
||||
printf("%-16s %-17s %-16s %-11s %-17s %-16s\n",
|
||||
@ -1156,11 +1156,11 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
}
|
||||
|
||||
static int networkctl_main(int argc, char *argv[]) {
|
||||
const Verb verbs[] = {
|
||||
{ "list", VERB_ANY, VERB_ANY, VERB_DEFAULT, list_links },
|
||||
{ "status", VERB_ANY, VERB_ANY, 0, link_status },
|
||||
{ "lldp", VERB_ANY, VERB_ANY, 0, link_lldp_status },
|
||||
{ "label", VERB_ANY, VERB_ANY, 0, list_address_labels},
|
||||
static const Verb verbs[] = {
|
||||
{ "list", VERB_ANY, VERB_ANY, VERB_DEFAULT, list_links },
|
||||
{ "status", VERB_ANY, VERB_ANY, 0, link_status },
|
||||
{ "lldp", VERB_ANY, VERB_ANY, 0, link_lldp_status },
|
||||
{ "label", VERB_ANY, VERB_ANY, 0, list_address_labels },
|
||||
{}
|
||||
};
|
||||
|
||||
|
@ -1185,13 +1185,13 @@ static int status_ifindex(sd_bus *bus, int ifindex, const char *name, bool *empt
|
||||
|
||||
struct link_info {
|
||||
uint64_t scopes_mask;
|
||||
char *llmnr;
|
||||
char *mdns;
|
||||
char *dnssec;
|
||||
const char *llmnr;
|
||||
const char *mdns;
|
||||
const char *dnssec;
|
||||
char **dns;
|
||||
char **domains;
|
||||
char **ntas;
|
||||
int dnssec_supported;
|
||||
bool dnssec_supported;
|
||||
} link_info = {};
|
||||
|
||||
static const struct bus_properties_map property_map[] = {
|
||||
@ -1207,6 +1207,7 @@ static int status_ifindex(sd_bus *bus, int ifindex, const char *name, bool *empt
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
_cleanup_free_ char *ifi = NULL, *p = NULL;
|
||||
char ifname[IF_NAMESIZE] = "";
|
||||
char **i;
|
||||
@ -1235,13 +1236,14 @@ static int status_ifindex(sd_bus *bus, int ifindex, const char *name, bool *empt
|
||||
p,
|
||||
property_map,
|
||||
&error,
|
||||
&m,
|
||||
&link_info);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to get link data for %i: %s", ifindex, bus_error_message(&error, r));
|
||||
goto finish;
|
||||
}
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
if (*empty_line)
|
||||
fputc('\n', stdout);
|
||||
@ -1293,9 +1295,6 @@ static int status_ifindex(sd_bus *bus, int ifindex, const char *name, bool *empt
|
||||
finish:
|
||||
strv_free(link_info.dns);
|
||||
strv_free(link_info.domains);
|
||||
free(link_info.llmnr);
|
||||
free(link_info.mdns);
|
||||
free(link_info.dnssec);
|
||||
strv_free(link_info.ntas);
|
||||
return r;
|
||||
}
|
||||
@ -1418,16 +1417,25 @@ static int status_global(sd_bus *bus, bool *empty_line) {
|
||||
char **dns;
|
||||
char **domains;
|
||||
char **ntas;
|
||||
const char *llmnr;
|
||||
const char *mdns;
|
||||
const char *dnssec;
|
||||
bool dnssec_supported;
|
||||
} global_info = {};
|
||||
|
||||
static const struct bus_properties_map property_map[] = {
|
||||
{ "DNS", "a(iiay)", map_global_dns_servers, offsetof(struct global_info, dns) },
|
||||
{ "Domains", "a(isb)", map_global_domains, offsetof(struct global_info, domains) },
|
||||
{ "DNSSECNegativeTrustAnchors", "as", NULL, offsetof(struct global_info, ntas) },
|
||||
{ "DNS", "a(iiay)", map_global_dns_servers, offsetof(struct global_info, dns) },
|
||||
{ "Domains", "a(isb)", map_global_domains, offsetof(struct global_info, domains) },
|
||||
{ "DNSSECNegativeTrustAnchors", "as", NULL, offsetof(struct global_info, ntas) },
|
||||
{ "LLMNR", "s", NULL, offsetof(struct global_info, llmnr) },
|
||||
{ "MulticastDNS", "s", NULL, offsetof(struct global_info, mdns) },
|
||||
{ "DNSSEC", "s", NULL, offsetof(struct global_info, dnssec) },
|
||||
{ "DNSSECSupported", "b", NULL, offsetof(struct global_info, dnssec_supported) },
|
||||
{}
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
char **i;
|
||||
int r;
|
||||
|
||||
@ -1439,6 +1447,7 @@ static int status_global(sd_bus *bus, bool *empty_line) {
|
||||
"/org/freedesktop/resolve1",
|
||||
property_map,
|
||||
&error,
|
||||
&m,
|
||||
&global_info);
|
||||
if (r < 0) {
|
||||
log_error_errno(r, "Failed to get global data: %s", bus_error_message(&error, r));
|
||||
@ -1450,9 +1459,19 @@ static int status_global(sd_bus *bus, bool *empty_line) {
|
||||
goto finish;
|
||||
}
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
|
||||
printf("%sGlobal%s\n", ansi_highlight(), ansi_normal());
|
||||
|
||||
printf(" LLMNR setting: %s\n"
|
||||
"MulticastDNS setting: %s\n"
|
||||
" DNSSEC setting: %s\n"
|
||||
" DNSSEC supported: %s\n",
|
||||
strna(global_info.llmnr),
|
||||
strna(global_info.mdns),
|
||||
strna(global_info.dnssec),
|
||||
yes_no(global_info.dnssec_supported));
|
||||
|
||||
STRV_FOREACH(i, global_info.dns) {
|
||||
printf(" %s %s\n",
|
||||
i == global_info.dns ? "DNS Servers:" : " ",
|
||||
|
@ -31,6 +31,8 @@
|
||||
#include "user-util.h"
|
||||
#include "utf8.h"
|
||||
|
||||
BUS_DEFINE_PROPERTY_GET_ENUM(bus_property_get_resolve_support, resolve_support, ResolveSupport);
|
||||
|
||||
static int reply_query_state(DnsQuery *q) {
|
||||
|
||||
switch (q->state) {
|
||||
@ -1425,6 +1427,23 @@ static int bus_property_get_dnssec_supported(
|
||||
return sd_bus_message_append(reply, "b", manager_dnssec_supported(m));
|
||||
}
|
||||
|
||||
static int bus_property_get_dnssec_mode(
|
||||
sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *reply,
|
||||
void *userdata,
|
||||
sd_bus_error *error) {
|
||||
|
||||
Manager *m = userdata;
|
||||
|
||||
assert(reply);
|
||||
assert(m);
|
||||
|
||||
return sd_bus_message_append(reply, "s", dnssec_mode_to_string(manager_get_dnssec_mode(m)));
|
||||
}
|
||||
|
||||
static int bus_property_get_ntas(
|
||||
sd_bus *bus,
|
||||
const char *path,
|
||||
@ -1814,10 +1833,13 @@ static int bus_method_unregister_service(sd_bus_message *message, void *userdata
|
||||
static const sd_bus_vtable resolve_vtable[] = {
|
||||
SD_BUS_VTABLE_START(0),
|
||||
SD_BUS_PROPERTY("LLMNRHostname", "s", NULL, offsetof(Manager, llmnr_hostname), 0),
|
||||
SD_BUS_PROPERTY("LLMNR", "s", bus_property_get_resolve_support, offsetof(Manager, llmnr_support), 0),
|
||||
SD_BUS_PROPERTY("MulticastDNS", "s", bus_property_get_resolve_support, offsetof(Manager, mdns_support), 0),
|
||||
SD_BUS_PROPERTY("DNS", "a(iiay)", bus_property_get_dns_servers, 0, 0),
|
||||
SD_BUS_PROPERTY("Domains", "a(isb)", bus_property_get_domains, 0, 0),
|
||||
SD_BUS_PROPERTY("TransactionStatistics", "(tt)", bus_property_get_transaction_statistics, 0, 0),
|
||||
SD_BUS_PROPERTY("CacheStatistics", "(ttt)", bus_property_get_cache_statistics, 0, 0),
|
||||
SD_BUS_PROPERTY("DNSSEC", "s", bus_property_get_dnssec_mode, 0, 0),
|
||||
SD_BUS_PROPERTY("DNSSECStatistics", "(tttt)", bus_property_get_dnssec_statistics, 0, 0),
|
||||
SD_BUS_PROPERTY("DNSSECSupported", "b", bus_property_get_dnssec_supported, 0, 0),
|
||||
SD_BUS_PROPERTY("DNSSECNegativeTrustAnchors", "as", bus_property_get_ntas, 0, 0),
|
||||
|
@ -24,3 +24,6 @@
|
||||
|
||||
int manager_connect_bus(Manager *m);
|
||||
int bus_dns_server_append(sd_bus_message *reply, DnsServer *s, bool with_ifindex);
|
||||
int bus_property_get_resolve_support(sd_bus *bus, const char *path, const char *interface,
|
||||
const char *property, sd_bus_message *reply,
|
||||
void *userdata, sd_bus_error *error);
|
||||
|
@ -28,8 +28,6 @@
|
||||
#include "resolved-resolv-conf.h"
|
||||
#include "strv.h"
|
||||
|
||||
static BUS_DEFINE_PROPERTY_GET_ENUM(property_get_resolve_support, resolve_support, ResolveSupport);
|
||||
|
||||
static int property_get_dnssec_mode(
|
||||
sd_bus *bus,
|
||||
const char *path,
|
||||
@ -533,8 +531,8 @@ const sd_bus_vtable link_vtable[] = {
|
||||
SD_BUS_PROPERTY("ScopesMask", "t", property_get_scopes_mask, 0, 0),
|
||||
SD_BUS_PROPERTY("DNS", "a(iay)", property_get_dns, 0, 0),
|
||||
SD_BUS_PROPERTY("Domains", "a(sb)", property_get_domains, 0, 0),
|
||||
SD_BUS_PROPERTY("LLMNR", "s", property_get_resolve_support, offsetof(Link, llmnr_support), 0),
|
||||
SD_BUS_PROPERTY("MulticastDNS", "s", property_get_resolve_support, offsetof(Link, mdns_support), 0),
|
||||
SD_BUS_PROPERTY("LLMNR", "s", bus_property_get_resolve_support, offsetof(Link, llmnr_support), 0),
|
||||
SD_BUS_PROPERTY("MulticastDNS", "s", bus_property_get_resolve_support, offsetof(Link, mdns_support), 0),
|
||||
SD_BUS_PROPERTY("DNSSEC", "s", property_get_dnssec_mode, 0, 0),
|
||||
SD_BUS_PROPERTY("DNSSECNegativeTrustAnchors", "as", property_get_ntas, 0, 0),
|
||||
SD_BUS_PROPERTY("DNSSECSupported", "b", property_get_dnssec_supported, 0, 0),
|
||||
|
@ -876,6 +876,7 @@ static int run_context_update(RunContext *c, const char *path) {
|
||||
path,
|
||||
map,
|
||||
&error,
|
||||
NULL,
|
||||
c);
|
||||
if (r < 0) {
|
||||
sd_event_exit(c->event, EXIT_FAILURE);
|
||||
|
@ -656,15 +656,15 @@ int bus_connect_user_systemd(sd_bus **_bus) {
|
||||
printf("%s=" fmt "\n", name, __VA_ARGS__); \
|
||||
} while (0)
|
||||
|
||||
int bus_print_property(const char *name, sd_bus_message *property, bool value, bool all) {
|
||||
int bus_print_property(const char *name, sd_bus_message *m, bool value, bool all) {
|
||||
char type;
|
||||
const char *contents;
|
||||
int r;
|
||||
|
||||
assert(name);
|
||||
assert(property);
|
||||
assert(m);
|
||||
|
||||
r = sd_bus_message_peek_type(property, &type, &contents);
|
||||
r = sd_bus_message_peek_type(m, &type, &contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -673,7 +673,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_STRING: {
|
||||
const char *s;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &s);
|
||||
r = sd_bus_message_read_basic(m, type, &s);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -692,7 +692,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_BOOLEAN: {
|
||||
int b;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &b);
|
||||
r = sd_bus_message_read_basic(m, type, &b);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -704,7 +704,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_UINT64: {
|
||||
uint64_t u;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &u);
|
||||
r = sd_bus_message_read_basic(m, type, &u);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -781,7 +781,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_INT64: {
|
||||
int64_t i;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &i);
|
||||
r = sd_bus_message_read_basic(m, type, &i);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -793,7 +793,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_UINT32: {
|
||||
uint32_t u;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &u);
|
||||
r = sd_bus_message_read_basic(m, type, &u);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -818,7 +818,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_INT32: {
|
||||
int32_t i;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &i);
|
||||
r = sd_bus_message_read_basic(m, type, &i);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -829,7 +829,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
case SD_BUS_TYPE_DOUBLE: {
|
||||
double d;
|
||||
|
||||
r = sd_bus_message_read_basic(property, type, &d);
|
||||
r = sd_bus_message_read_basic(m, type, &d);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -842,11 +842,11 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
bool first = true;
|
||||
const char *str;
|
||||
|
||||
r = sd_bus_message_enter_container(property, SD_BUS_TYPE_ARRAY, contents);
|
||||
r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
while ((r = sd_bus_message_read_basic(property, SD_BUS_TYPE_STRING, &str)) > 0) {
|
||||
while ((r = sd_bus_message_read_basic(m, SD_BUS_TYPE_STRING, &str)) > 0) {
|
||||
bool good;
|
||||
|
||||
if (first && !value)
|
||||
@ -868,7 +868,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
if (!first || all)
|
||||
puts("");
|
||||
|
||||
r = sd_bus_message_exit_container(property);
|
||||
r = sd_bus_message_exit_container(m);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -878,7 +878,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
const uint8_t *u;
|
||||
size_t n;
|
||||
|
||||
r = sd_bus_message_read_array(property, SD_BUS_TYPE_BYTE, (const void**) &u, &n);
|
||||
r = sd_bus_message_read_array(m, SD_BUS_TYPE_BYTE, (const void**) &u, &n);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -900,7 +900,7 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
uint32_t *u;
|
||||
size_t n;
|
||||
|
||||
r = sd_bus_message_read_array(property, SD_BUS_TYPE_UINT32, (const void**) &u, &n);
|
||||
r = sd_bus_message_read_array(m, SD_BUS_TYPE_UINT32, (const void**) &u, &n);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -925,7 +925,97 @@ int bus_print_property(const char *name, sd_bus_message *property, bool value, b
|
||||
return 0;
|
||||
}
|
||||
|
||||
int bus_print_all_properties(sd_bus *bus, const char *dest, const char *path, char **filter, bool value, bool all) {
|
||||
int bus_message_print_all_properties(
|
||||
sd_bus_message *m,
|
||||
bus_message_print_t func,
|
||||
char **filter,
|
||||
bool value,
|
||||
bool all,
|
||||
Set **found_properties) {
|
||||
|
||||
int r;
|
||||
|
||||
assert(m);
|
||||
|
||||
r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, "{sv}");
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
while ((r = sd_bus_message_enter_container(m, SD_BUS_TYPE_DICT_ENTRY, "sv")) > 0) {
|
||||
const char *name;
|
||||
const char *contents;
|
||||
|
||||
r = sd_bus_message_read_basic(m, SD_BUS_TYPE_STRING, &name);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (found_properties) {
|
||||
r = set_ensure_allocated(found_properties, &string_hash_ops);
|
||||
if (r < 0)
|
||||
return log_oom();
|
||||
|
||||
r = set_put(*found_properties, name);
|
||||
if (r < 0 && r != EEXIST)
|
||||
return log_oom();
|
||||
}
|
||||
|
||||
if (!filter || strv_find(filter, name)) {
|
||||
r = sd_bus_message_peek_type(m, NULL, &contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_enter_container(m, SD_BUS_TYPE_VARIANT, contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (func)
|
||||
r = func(name, m, value, all);
|
||||
if (!func || r == 0)
|
||||
r = bus_print_property(name, m, value, all);
|
||||
if (r < 0)
|
||||
return r;
|
||||
if (r == 0) {
|
||||
if (all)
|
||||
printf("%s=[unprintable]\n", name);
|
||||
/* skip what we didn't read */
|
||||
r = sd_bus_message_skip(m, contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
r = sd_bus_message_exit_container(m);
|
||||
if (r < 0)
|
||||
return r;
|
||||
} else {
|
||||
r = sd_bus_message_skip(m, "v");
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
r = sd_bus_message_exit_container(m);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_exit_container(m);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int bus_print_all_properties(
|
||||
sd_bus *bus,
|
||||
const char *dest,
|
||||
const char *path,
|
||||
bus_message_print_t func,
|
||||
char **filter,
|
||||
bool value,
|
||||
bool all,
|
||||
Set **found_properties) {
|
||||
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
int r;
|
||||
@ -944,60 +1034,7 @@ int bus_print_all_properties(sd_bus *bus, const char *dest, const char *path, ch
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_ARRAY, "{sv}");
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
while ((r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_DICT_ENTRY, "sv")) > 0) {
|
||||
const char *name;
|
||||
const char *contents;
|
||||
|
||||
r = sd_bus_message_read_basic(reply, SD_BUS_TYPE_STRING, &name);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (!filter || strv_find(filter, name)) {
|
||||
r = sd_bus_message_peek_type(reply, NULL, &contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_VARIANT, contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = bus_print_property(name, reply, value, all);
|
||||
if (r < 0)
|
||||
return r;
|
||||
if (r == 0) {
|
||||
if (all)
|
||||
printf("%s=[unprintable]\n", name);
|
||||
/* skip what we didn't read */
|
||||
r = sd_bus_message_skip(reply, contents);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
r = sd_bus_message_exit_container(reply);
|
||||
if (r < 0)
|
||||
return r;
|
||||
} else {
|
||||
r = sd_bus_message_skip(reply, "v");
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
r = sd_bus_message_exit_container(reply);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = sd_bus_message_exit_container(reply);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
return 0;
|
||||
return bus_message_print_all_properties(reply, func, filter, value, all, found_properties);
|
||||
}
|
||||
|
||||
int bus_map_id128(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_error *error, void *userdata) {
|
||||
@ -1020,7 +1057,7 @@ int bus_map_id128(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_err
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_error *error, void *userdata) {
|
||||
static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_error *error, void *userdata, bool copy_string) {
|
||||
char type;
|
||||
int r;
|
||||
|
||||
@ -1031,7 +1068,7 @@ static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_
|
||||
switch (type) {
|
||||
|
||||
case SD_BUS_TYPE_STRING: {
|
||||
char **p = userdata;
|
||||
const char **p = userdata;
|
||||
const char *s;
|
||||
|
||||
r = sd_bus_message_read_basic(m, type, &s);
|
||||
@ -1041,7 +1078,11 @@ static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_
|
||||
if (isempty(s))
|
||||
s = NULL;
|
||||
|
||||
return free_and_strdup(p, s);
|
||||
if (copy_string)
|
||||
return free_and_strdup((char **) userdata, s);
|
||||
|
||||
*p = s;
|
||||
return 0;
|
||||
}
|
||||
|
||||
case SD_BUS_TYPE_ARRAY: {
|
||||
@ -1060,13 +1101,13 @@ static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_
|
||||
|
||||
case SD_BUS_TYPE_BOOLEAN: {
|
||||
unsigned b;
|
||||
int *p = userdata;
|
||||
bool *p = userdata;
|
||||
|
||||
r = sd_bus_message_read_basic(m, type, &b);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
*p = b;
|
||||
*p = !!b;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1111,6 +1152,7 @@ static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_
|
||||
int bus_message_map_all_properties(
|
||||
sd_bus_message *m,
|
||||
const struct bus_properties_map *map,
|
||||
bool copy_string,
|
||||
sd_bus_error *error,
|
||||
void *userdata) {
|
||||
|
||||
@ -1153,7 +1195,7 @@ int bus_message_map_all_properties(
|
||||
if (map[i].set)
|
||||
r = prop->set(sd_bus_message_get_bus(m), member, m, error, v);
|
||||
else
|
||||
r = map_basic(sd_bus_message_get_bus(m), member, m, error, v);
|
||||
r = map_basic(sd_bus_message_get_bus(m), member, m, error, v, copy_string);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -1179,6 +1221,7 @@ int bus_message_map_all_properties(
|
||||
int bus_message_map_properties_changed(
|
||||
sd_bus_message *m,
|
||||
const struct bus_properties_map *map,
|
||||
bool copy_string,
|
||||
sd_bus_error *error,
|
||||
void *userdata) {
|
||||
|
||||
@ -1188,7 +1231,7 @@ int bus_message_map_properties_changed(
|
||||
assert(m);
|
||||
assert(map);
|
||||
|
||||
r = bus_message_map_all_properties(m, map, error, userdata);
|
||||
r = bus_message_map_all_properties(m, map, copy_string, error, userdata);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@ -1219,6 +1262,7 @@ int bus_map_all_properties(
|
||||
const char *path,
|
||||
const struct bus_properties_map *map,
|
||||
sd_bus_error *error,
|
||||
sd_bus_message **reply,
|
||||
void *userdata) {
|
||||
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
@ -1241,7 +1285,14 @@ int bus_map_all_properties(
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
return bus_message_map_all_properties(m, map, error, userdata);
|
||||
r = bus_message_map_all_properties(m, map, !reply, error, userdata);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (reply)
|
||||
*reply = sd_bus_message_ref(m);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
int bus_connect_transport(BusTransport transport, const char *host, bool user, sd_bus **ret) {
|
||||
|
@ -51,9 +51,9 @@ struct bus_properties_map {
|
||||
|
||||
int bus_map_id128(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_error *error, void *userdata);
|
||||
|
||||
int bus_message_map_all_properties(sd_bus_message *m, const struct bus_properties_map *map, sd_bus_error *error, void *userdata);
|
||||
int bus_message_map_properties_changed(sd_bus_message *m, const struct bus_properties_map *map, sd_bus_error *error, void *userdata);
|
||||
int bus_map_all_properties(sd_bus *bus, const char *destination, const char *path, const struct bus_properties_map *map, sd_bus_error *error, void *userdata);
|
||||
int bus_message_map_all_properties(sd_bus_message *m, const struct bus_properties_map *map, bool copy_string, sd_bus_error *error, void *userdata);
|
||||
int bus_message_map_properties_changed(sd_bus_message *m, const struct bus_properties_map *map, bool copy_string, sd_bus_error *error, void *userdata);
|
||||
int bus_map_all_properties(sd_bus *bus, const char *destination, const char *path, const struct bus_properties_map *map, sd_bus_error *error, sd_bus_message **reply, void *userdata);
|
||||
|
||||
int bus_async_unregister_and_exit(sd_event *e, sd_bus *bus, const char *name);
|
||||
|
||||
@ -76,8 +76,11 @@ int bus_connect_user_systemd(sd_bus **_bus);
|
||||
int bus_connect_transport(BusTransport transport, const char *host, bool user, sd_bus **bus);
|
||||
int bus_connect_transport_systemd(BusTransport transport, const char *host, bool user, sd_bus **bus);
|
||||
|
||||
typedef int (*bus_message_print_t) (const char *name, sd_bus_message *m, bool value, bool all);
|
||||
|
||||
int bus_print_property(const char *name, sd_bus_message *property, bool value, bool all);
|
||||
int bus_print_all_properties(sd_bus *bus, const char *dest, const char *path, char **filter, bool value, bool all);
|
||||
int bus_message_print_all_properties(sd_bus_message *m, bus_message_print_t func, char **filter, bool value, bool all, Set **found_properties);
|
||||
int bus_print_all_properties(sd_bus *bus, const char *dest, const char *path, bus_message_print_t func, char **filter, bool value, bool all, Set **found_properties);
|
||||
|
||||
int bus_property_get_bool(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *reply, void *userdata, sd_bus_error *error);
|
||||
int bus_property_set_bool(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *value, void *userdata, sd_bus_error *error);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -34,6 +34,7 @@
|
||||
#include "strv.h"
|
||||
#include "terminal-util.h"
|
||||
#include "util.h"
|
||||
#include "verbs.h"
|
||||
|
||||
static bool arg_no_pager = false;
|
||||
static bool arg_ask_password = true;
|
||||
@ -43,23 +44,16 @@ static bool arg_adjust_system_clock = false;
|
||||
|
||||
typedef struct StatusInfo {
|
||||
usec_t time;
|
||||
char *timezone;
|
||||
const char *timezone;
|
||||
|
||||
usec_t rtc_time;
|
||||
int rtc_local;
|
||||
bool rtc_local;
|
||||
|
||||
int ntp_enabled;
|
||||
int ntp_capable;
|
||||
int ntp_synced;
|
||||
bool ntp_enabled;
|
||||
bool ntp_capable;
|
||||
bool ntp_synced;
|
||||
} StatusInfo;
|
||||
|
||||
static void status_info_clear(StatusInfo *info) {
|
||||
if (info) {
|
||||
free(info->timezone);
|
||||
zero(*info);
|
||||
}
|
||||
}
|
||||
|
||||
static void print_status_info(const StatusInfo *i) {
|
||||
char a[LINE_MAX];
|
||||
struct tm tm;
|
||||
@ -143,8 +137,8 @@ static void print_status_info(const StatusInfo *i) {
|
||||
" 'timedatectl set-local-rtc 0'.%s\n", ansi_highlight(), ansi_normal());
|
||||
}
|
||||
|
||||
static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
_cleanup_(status_info_clear) StatusInfo info = {};
|
||||
static int show_status(int argc, char **argv, void *userdata) {
|
||||
StatusInfo info = {};
|
||||
static const struct bus_properties_map map[] = {
|
||||
{ "Timezone", "s", NULL, offsetof(StatusInfo, timezone) },
|
||||
{ "LocalRTC", "b", NULL, offsetof(StatusInfo, rtc_local) },
|
||||
@ -157,6 +151,8 @@ static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
};
|
||||
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
_cleanup_(sd_bus_message_unrefp) sd_bus_message *m = NULL;
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(bus);
|
||||
@ -166,6 +162,7 @@ static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
"/org/freedesktop/timedate1",
|
||||
map,
|
||||
&error,
|
||||
&m,
|
||||
&info);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to query server: %s", bus_error_message(&error, r));
|
||||
@ -175,22 +172,18 @@ static int show_status(sd_bus *bus, char **args, unsigned n) {
|
||||
return r;
|
||||
}
|
||||
|
||||
static int set_time(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_time(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
bool relative = false, interactive = arg_ask_password;
|
||||
sd_bus *bus = userdata;
|
||||
usec_t t;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
r = parse_timestamp(args[1], &t);
|
||||
if (r < 0) {
|
||||
log_error("Failed to parse time specification: %s", args[1]);
|
||||
return r;
|
||||
}
|
||||
r = parse_timestamp(argv[1], &t);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to parse time specification '%s': %m", argv[1]);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
"org.freedesktop.timedate1",
|
||||
@ -199,20 +192,18 @@ static int set_time(sd_bus *bus, char **args, unsigned n) {
|
||||
"SetTime",
|
||||
&error,
|
||||
NULL,
|
||||
"xbb", (int64_t)t, relative, interactive);
|
||||
"xbb", (int64_t) t, relative, interactive);
|
||||
if (r < 0)
|
||||
log_error("Failed to set time: %s", bus_error_message(&error, -r));
|
||||
log_error("Failed to set time: %s", bus_error_message(&error, r));
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int set_timezone(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_timezone(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
sd_bus *bus = userdata;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
@ -222,27 +213,23 @@ static int set_timezone(sd_bus *bus, char **args, unsigned n) {
|
||||
"SetTimezone",
|
||||
&error,
|
||||
NULL,
|
||||
"sb", args[1], arg_ask_password);
|
||||
"sb", argv[1], arg_ask_password);
|
||||
if (r < 0)
|
||||
log_error("Failed to set time zone: %s", bus_error_message(&error, -r));
|
||||
log_error("Failed to set time zone: %s", bus_error_message(&error, r));
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int set_local_rtc(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_local_rtc(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
sd_bus *bus = userdata;
|
||||
int r, b;
|
||||
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
b = parse_boolean(args[1]);
|
||||
if (b < 0) {
|
||||
log_error("Failed to parse local RTC setting: %s", args[1]);
|
||||
return b;
|
||||
}
|
||||
b = parse_boolean(argv[1]);
|
||||
if (b < 0)
|
||||
return log_error_errno(b, "Failed to parse local RTC setting '%s': %m", argv[1]);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
"org.freedesktop.timedate1",
|
||||
@ -253,25 +240,21 @@ static int set_local_rtc(sd_bus *bus, char **args, unsigned n) {
|
||||
NULL,
|
||||
"bbb", b, arg_adjust_system_clock, arg_ask_password);
|
||||
if (r < 0)
|
||||
log_error("Failed to set local RTC: %s", bus_error_message(&error, -r));
|
||||
log_error("Failed to set local RTC: %s", bus_error_message(&error, r));
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int set_ntp(sd_bus *bus, char **args, unsigned n) {
|
||||
static int set_ntp(int argc, char **argv, void *userdata) {
|
||||
_cleanup_(sd_bus_error_free) sd_bus_error error = SD_BUS_ERROR_NULL;
|
||||
sd_bus *bus = userdata;
|
||||
int b, r;
|
||||
|
||||
assert(args);
|
||||
assert(n == 2);
|
||||
|
||||
polkit_agent_open_if_enabled(arg_transport, arg_ask_password);
|
||||
|
||||
b = parse_boolean(args[1]);
|
||||
if (b < 0) {
|
||||
log_error("Failed to parse NTP setting: %s", args[1]);
|
||||
return b;
|
||||
}
|
||||
b = parse_boolean(argv[1]);
|
||||
if (b < 0)
|
||||
return log_error_errno(b, "Failed to parse NTP setting '%s': %m", argv[1]);
|
||||
|
||||
r = sd_bus_call_method(bus,
|
||||
"org.freedesktop.timedate1",
|
||||
@ -282,29 +265,26 @@ static int set_ntp(sd_bus *bus, char **args, unsigned n) {
|
||||
NULL,
|
||||
"bb", b, arg_ask_password);
|
||||
if (r < 0)
|
||||
log_error("Failed to set ntp: %s", bus_error_message(&error, -r));
|
||||
log_error("Failed to set ntp: %s", bus_error_message(&error, r));
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int list_timezones(sd_bus *bus, char **args, unsigned n) {
|
||||
static int list_timezones(int argc, char **argv, void *userdata) {
|
||||
_cleanup_strv_free_ char **zones = NULL;
|
||||
int r;
|
||||
|
||||
assert(args);
|
||||
assert(n == 1);
|
||||
|
||||
r = get_timezones(&zones);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to read list of time zones: %m");
|
||||
|
||||
pager_open(arg_no_pager, false);
|
||||
(void) pager_open(arg_no_pager, false);
|
||||
strv_print(zones);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void help(void) {
|
||||
static int help(void) {
|
||||
printf("%s [OPTIONS...] COMMAND ...\n\n"
|
||||
"Query or change system time and date settings.\n\n"
|
||||
" -h --help Show this help message\n"
|
||||
@ -322,6 +302,12 @@ static void help(void) {
|
||||
" set-local-rtc BOOL Control whether RTC is in local time\n"
|
||||
" set-ntp BOOL Enable or disable network time synchronization\n",
|
||||
program_invocation_short_name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int verb_help(int argc, char **argv, void *userdata) {
|
||||
return help();
|
||||
}
|
||||
|
||||
static int parse_argv(int argc, char *argv[]) {
|
||||
@ -354,8 +340,7 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
switch (c) {
|
||||
|
||||
case 'h':
|
||||
help();
|
||||
return 0;
|
||||
return help();
|
||||
|
||||
case ARG_VERSION:
|
||||
return version();
|
||||
@ -394,82 +379,18 @@ static int parse_argv(int argc, char *argv[]) {
|
||||
|
||||
static int timedatectl_main(sd_bus *bus, int argc, char *argv[]) {
|
||||
|
||||
static const struct {
|
||||
const char* verb;
|
||||
const enum {
|
||||
MORE,
|
||||
LESS,
|
||||
EQUAL
|
||||
} argc_cmp;
|
||||
const int argc;
|
||||
int (* const dispatch)(sd_bus *bus, char **args, unsigned n);
|
||||
} verbs[] = {
|
||||
{ "status", LESS, 1, show_status },
|
||||
{ "set-time", EQUAL, 2, set_time },
|
||||
{ "set-timezone", EQUAL, 2, set_timezone },
|
||||
{ "list-timezones", EQUAL, 1, list_timezones },
|
||||
{ "set-local-rtc", EQUAL, 2, set_local_rtc },
|
||||
{ "set-ntp", EQUAL, 2, set_ntp, },
|
||||
static const Verb verbs[] = {
|
||||
{ "status", VERB_ANY, 1, VERB_DEFAULT, show_status },
|
||||
{ "set-time", 2, 2, 0, set_time },
|
||||
{ "set-timezone", 2, 2, 0, set_timezone },
|
||||
{ "list-timezones", VERB_ANY, 1, 0, list_timezones },
|
||||
{ "set-local-rtc", 2, 2, 0, set_local_rtc },
|
||||
{ "set-ntp", 2, 2, 0, set_ntp },
|
||||
{ "help", VERB_ANY, VERB_ANY, 0, verb_help }, /* Not documented, but supported since it is created. */
|
||||
{}
|
||||
};
|
||||
|
||||
int left;
|
||||
unsigned i;
|
||||
|
||||
assert(argc >= 0);
|
||||
assert(argv);
|
||||
|
||||
left = argc - optind;
|
||||
|
||||
if (left <= 0)
|
||||
/* Special rule: no arguments means "status" */
|
||||
i = 0;
|
||||
else {
|
||||
if (streq(argv[optind], "help")) {
|
||||
help();
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (i = 0; i < ELEMENTSOF(verbs); i++)
|
||||
if (streq(argv[optind], verbs[i].verb))
|
||||
break;
|
||||
|
||||
if (i >= ELEMENTSOF(verbs)) {
|
||||
log_error("Unknown operation %s", argv[optind]);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
switch (verbs[i].argc_cmp) {
|
||||
|
||||
case EQUAL:
|
||||
if (left != verbs[i].argc) {
|
||||
log_error("Invalid number of arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case MORE:
|
||||
if (left < verbs[i].argc) {
|
||||
log_error("Too few arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case LESS:
|
||||
if (left > verbs[i].argc) {
|
||||
log_error("Too many arguments.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
assert_not_reached("Unknown comparison operator.");
|
||||
}
|
||||
|
||||
return verbs[i].dispatch(bus, argv + optind, left);
|
||||
return dispatch_verb(argc, argv, verbs, bus);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
|
Loading…
Reference in New Issue
Block a user