X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?a=blobdiff_plain;f=src%2Flibsystemd-bus%2Fbusctl.c;h=e962ba3f631e14d26d3382bd580c6c937876eb4d;hb=d8160f21fd295b451cee9679aa281fedf1cb8e8c;hp=bcacfcee851ee089e0aeb5f8fbc4c6a195a95084;hpb=71f2ab468d8413cffdb712083eb4d06dc8b2a271;p=elogind.git diff --git a/src/libsystemd-bus/busctl.c b/src/libsystemd-bus/busctl.c index bcacfcee8..e962ba3f6 100644 --- a/src/libsystemd-bus/busctl.c +++ b/src/libsystemd-bus/busctl.c @@ -35,8 +35,10 @@ static bool arg_no_pager = false; static char *arg_address = NULL; -static bool arg_no_unique = false; -static bool arg_no_machine = false; +static bool arg_unique = false; +static bool arg_acquired = false; +static bool arg_activatable = false; +static bool arg_show_machine = false; static char **arg_matches = NULL; static BusTransport arg_transport = BUS_TRANSPORT_LOCAL; static char *arg_host = NULL; @@ -53,13 +55,19 @@ static void pager_open_if_enabled(void) { static int list_bus_names(sd_bus *bus, char **argv) { _cleanup_strv_free_ char **acquired = NULL, **activatable = NULL; + _cleanup_free_ char **merged = NULL; + _cleanup_hashmap_free_ Hashmap *names = NULL; char **i; int r; size_t max_i = 0; + unsigned n = 0; + void *v; + char *k; + Iterator iterator; assert(bus); - r = sd_bus_list_names(bus, &acquired, &activatable); + r = sd_bus_list_names(bus, (arg_acquired || arg_unique) ? &acquired : NULL, arg_activatable ? &activatable : NULL); if (r < 0) { log_error("Failed to list names: %s", strerror(-r)); return r; @@ -67,56 +75,73 @@ static int list_bus_names(sd_bus *bus, char **argv) { pager_open_if_enabled(); - strv_sort(acquired); - strv_sort(activatable); + names = hashmap_new(string_hash_func, string_compare_func); + if (!names) + return log_oom(); - STRV_FOREACH(i, acquired) + STRV_FOREACH(i, acquired) { max_i = MAX(max_i, strlen(*i)); - STRV_FOREACH(i, activatable) + r = hashmap_put(names, *i, INT_TO_PTR(1)); + if (r < 0) { + log_error("Failed to add to hashmap: %s", strerror(-r)); + return r; + } + } + + STRV_FOREACH(i, activatable) { max_i = MAX(max_i, strlen(*i)); - printf("%-*s %*s %-*s %-*s %-*s", - (int) max_i, "NAME", 10, "PID", 15, "PROCESS", 16, "USER", 20, "CONNECTION"); + r = hashmap_put(names, *i, INT_TO_PTR(2)); + if (r < 0 && r != -EEXIST) { + log_error("Failed to add to hashmap: %s", strerror(-r)); + return r; + } + } + + merged = new(char*, hashmap_size(names) + 1); + HASHMAP_FOREACH_KEY(v, k, names, iterator) + merged[n++] = k; + + merged[n] = NULL; + strv_sort(merged); - if (!arg_no_machine) + printf("%-*s %*s %-*s %-*s %-*s %-*s %-*s", + (int) max_i, "NAME", 10, "PID", 15, "PROCESS", 16, "USER", 13, "CONNECTION", 25, "UNIT", 10, "SESSION"); + + if (arg_show_machine) puts(" MACHINE"); else putchar('\n'); - STRV_FOREACH(i, activatable) { + STRV_FOREACH(i, merged) { + _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL; + sd_id128_t mid; - /* Skip the bus driver */ - if (streq(*i, "org.freedesktop.DBus")) - continue; + if (hashmap_get(names, *i) == INT_TO_PTR(2)) { + /* Activatable */ - if (strv_contains(acquired, *i)) + printf("%-*s", (int) max_i, *i); + printf(" - - - (activatable) - - "); + if (arg_show_machine) + puts(" -"); + else + putchar('\n'); continue; - printf("%-*s", (int) max_i, *i); - printf(" - - - (activation) "); - if (arg_no_machine) - putchar('\n'); - else - puts(" -"); - } - - STRV_FOREACH(i, acquired) { - _cleanup_bus_creds_unref_ sd_bus_creds *creds = NULL; - sd_id128_t mid; + } - if (arg_no_unique && (*i)[0] == ':') + if (!arg_unique && (*i)[0] == ':') continue; - /* Skip the bus driver */ - if (streq(*i, "org.freedesktop.DBus")) + if (!arg_acquired && (*i)[0] != ':') continue; printf("%-*s", (int) max_i, *i); - r = sd_bus_get_owner(bus, *i, SD_BUS_CREDS_UID|SD_BUS_CREDS_PID|SD_BUS_CREDS_COMM|SD_BUS_CREDS_UNIQUE_NAME, &creds); + r = sd_bus_get_owner(bus, *i, SD_BUS_CREDS_UID|SD_BUS_CREDS_PID|SD_BUS_CREDS_COMM|SD_BUS_CREDS_UNIQUE_NAME|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_SESSION, &creds); if (r >= 0) { - const char *unique; + const char *unique, *session, *unit; pid_t pid; uid_t uid; @@ -147,23 +172,40 @@ static int list_bus_names(sd_bus *bus, char **argv) { r = sd_bus_creds_get_unique_name(creds, &unique); if (r >= 0) - printf(" %-20s", unique); + printf(" %-13s", unique); + else + fputs(" - ", stdout); + + r = sd_bus_creds_get_unit(creds, &unit); + if (r >= 0) { + _cleanup_free_ char *e; + + e = ellipsize(unit, 25, 100); + if (!e) + return log_oom(); + + printf(" %-25s", e); + } else + fputs(" - ", stdout); + + r = sd_bus_creds_get_session(creds, &session); + if (r >= 0) + printf(" %-10s", session); else - fputs(" - ", stdout); + fputs(" - ", stdout); } else - printf(" - - - - "); + printf(" - - - - - - "); - if (arg_no_machine) - putchar('\n'); - else { + if (arg_show_machine) { r = sd_bus_get_owner_machine_id(bus, *i, &mid); if (r >= 0) { char m[SD_ID128_STRING_MAX]; printf(" %s\n", sd_id128_to_string(mid, m)); } else puts(" -"); - } + } else + putchar('\n'); } return 0; @@ -277,12 +319,16 @@ static int help(void) { " -H --host=[USER@]HOST Operate on remote host\n" " -M --machine=CONTAINER Operate on local container\n" " --address=ADDRESS Connect to bus specified by address\n" - " --no-unique Only show well-known names\n" - " --no-machine Don't show machine ID column in list\n" + " --show-machine Show machine ID column in list\n" + " --unique Only show unique names\n" + " --acquired Only show acquired names\n" + " --activatable Only show activatable names\n" " --match=MATCH Only show matching messages\n\n" "Commands:\n" " list List bus names\n" - " monitor [SERVICE...] Show bus traffic\n", + " monitor [SERVICE...] Show bus traffic\n" + " status NAME Show name status\n" + " help Show this help\n", program_invocation_short_name); return 0; @@ -297,22 +343,26 @@ static int parse_argv(int argc, char *argv[]) { ARG_USER, ARG_ADDRESS, ARG_MATCH, - ARG_NO_UNIQUE, - ARG_NO_MACHINE, + ARG_SHOW_MACHINE, + ARG_UNIQUE, + ARG_ACQUIRED, + ARG_ACTIVATABLE }; static const struct option options[] = { - { "help", no_argument, NULL, 'h' }, - { "version", no_argument, NULL, ARG_VERSION }, - { "no-pager", no_argument, NULL, ARG_NO_PAGER }, - { "system", no_argument, NULL, ARG_SYSTEM }, - { "user", no_argument, NULL, ARG_USER }, - { "address", required_argument, NULL, ARG_ADDRESS }, - { "no-unique", no_argument, NULL, ARG_NO_UNIQUE }, - { "no-machine", no_argument, NULL, ARG_NO_MACHINE }, - { "match", required_argument, NULL, ARG_MATCH }, - { "host", required_argument, NULL, 'H' }, - { "machine", required_argument, NULL, 'M' }, + { "help", no_argument, NULL, 'h' }, + { "version", no_argument, NULL, ARG_VERSION }, + { "no-pager", no_argument, NULL, ARG_NO_PAGER }, + { "system", no_argument, NULL, ARG_SYSTEM }, + { "user", no_argument, NULL, ARG_USER }, + { "address", required_argument, NULL, ARG_ADDRESS }, + { "show-machine", no_argument, NULL, ARG_SHOW_MACHINE }, + { "unique", no_argument, NULL, ARG_UNIQUE }, + { "acquired", no_argument, NULL, ARG_ACQUIRED }, + { "activatable", no_argument, NULL, ARG_ACTIVATABLE }, + { "match", required_argument, NULL, ARG_MATCH }, + { "host", required_argument, NULL, 'H' }, + { "machine", required_argument, NULL, 'M' }, {}, }; @@ -349,12 +399,20 @@ static int parse_argv(int argc, char *argv[]) { arg_address = optarg; break; - case ARG_NO_UNIQUE: - arg_no_unique = true; + case ARG_SHOW_MACHINE: + arg_show_machine = true; break; - case ARG_NO_MACHINE: - arg_no_machine = true; + case ARG_UNIQUE: + arg_unique = true; + break; + + case ARG_ACQUIRED: + arg_acquired = true; + break; + + case ARG_ACTIVATABLE: + arg_activatable = true; break; case ARG_MATCH: @@ -380,6 +438,9 @@ static int parse_argv(int argc, char *argv[]) { } } + if (!arg_unique && !arg_acquired && !arg_activatable) + arg_unique = arg_acquired = arg_activatable = true; + return 1; }