From afba41995de65d8f378b138ea6d9804be32625a3 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= Date: Tue, 23 Apr 2013 23:49:46 -0400 Subject: [PATCH] systemctl: show reverse dependencies or before/after ordering Also update completion scripts a bit. --- man/systemctl.xml | 23 ++++++++++ shell-completion/bash/systemctl | 4 +- shell-completion/systemd-zsh-completion.zsh | 7 ++- src/systemctl/systemctl.c | 50 +++++++++++++++++---- 4 files changed, 73 insertions(+), 11 deletions(-) diff --git a/man/systemctl.xml b/man/systemctl.xml index 96cd10810..2739df69d 100644 --- a/man/systemctl.xml +++ b/man/systemctl.xml @@ -142,6 +142,29 @@ along with systemd; If not, see . + + + + + Show reverse dependencies between units with + list-dependencies, i.e. units with + dependencies of type Wants= or + Requires= on the given unit. + + + + + + + + + + Show which units are started after, resp. before + with list-dependencies. + + + + diff --git a/shell-completion/bash/systemctl b/shell-completion/bash/systemctl index f5829b72f..191b8d13e 100644 --- a/shell-completion/bash/systemctl +++ b/shell-completion/bash/systemctl @@ -70,7 +70,7 @@ _systemctl () { local i verb comps mode local -A OPTS=( - [STANDALONE]='--all -a --defaults --fail --ignore-dependencies --failed --force -f --full --global + [STANDALONE]='--all -a --reverse --after --before --defaults --fail --ignore-dependencies --failed --force -f --full --global --help -h --no-ask-password --no-block --no-legend --no-pager --no-reload --no-wall --quiet -q --privileged -P --system --user --version --runtime' [ARG]='--host -H --kill-mode --kill-who --property -p --signal -s --type -t --root' @@ -117,7 +117,7 @@ _systemctl () { fi local -A VERBS=( - [ALL_UNITS]='is-active is-failed is-enabled status show mask preset help' + [ALL_UNITS]='is-active is-failed is-enabled status show mask preset help list-dependencies' [ENABLED_UNITS]='disable' [DISABLED_UNITS]='enable' [REENABLABLE_UNITS]='reenable' diff --git a/shell-completion/systemd-zsh-completion.zsh b/shell-completion/systemd-zsh-completion.zsh index 8b60859c2..73db3786d 100644 --- a/shell-completion/systemd-zsh-completion.zsh +++ b/shell-completion/systemd-zsh-completion.zsh @@ -12,6 +12,9 @@ _ctls() {-t,--type=}'[List only units of a particular type]:unit type:(automount device mount path service snapshot socket swap target timer)' \ \*{-p,--property=}'[Show only properties by specific name]:unit property' \ {-a,--all}'[Show all units/properties, including dead/empty ones]' \ + '--reverse[Show reverse dependencies]' \ + '--after[Show units ordered after]' \ + '--before[Show units ordered before]' \ '--failed[Show only failed units]' \ "--full[Don't ellipsize unit names on output]" \ '--fail[When queueing a new job, fail if conflicting jobs are pending]' \ @@ -348,6 +351,8 @@ _outputmodes() { "disable:Disable one or more unit files" "reenable:Reenable one or more unit files" "preset:Enable/disable one or more unit files based on preset configuration" + "help:Show documentation for specified units" + "list-dependencies:Show unit dependency tree" "mask:Mask one or more units" "unmask:Unmask one or more units" "link:Link one or more units files into the search path" @@ -462,7 +467,7 @@ _systemctl_disabled_units(){_sys_disabled_units=($(__systemctl list-unit-files _systemctl_masked_units() {_sys_masked_units=( $(__systemctl list-unit-files | { while read a b; do [[ $b == "masked" ]] && echo " $a"; done; }) )} # Completion functions for ALL_UNITS -for fun in is-active is-failed is-enabled status show mask preset ; do +for fun in is-active is-failed is-enabled status show mask preset help list-dependencies ; do (( $+functions[_systemctl_$fun] )) || _systemctl_$fun() { _systemctl_really_all_units diff --git a/src/systemctl/systemctl.c b/src/systemctl/systemctl.c index b94f7f795..6067781cf 100644 --- a/src/systemctl/systemctl.c +++ b/src/systemctl/systemctl.c @@ -72,6 +72,12 @@ static char **arg_types = NULL; static char **arg_load_states = NULL; static char **arg_properties = NULL; static bool arg_all = false; +static enum dependency { + DEPENDENCY_FORWARD, + DEPENDENCY_REVERSE, + DEPENDENCY_AFTER, + DEPENDENCY_BEFORE, +} arg_dependency = DEPENDENCY_FORWARD; static const char *arg_job_mode = "replace"; static UnitFileScope arg_scope = UNIT_FILE_SYSTEM; static bool arg_no_block = false; @@ -979,12 +985,19 @@ static int list_dependencies_print(const char *name, int level, unsigned int bra } static int list_dependencies_get_dependencies(DBusConnection *bus, const char *name, char ***deps) { - static const char dependencies[] = - "Requires\0" - "RequiresOverridable\0" - "Requisite\0" - "RequisiteOverridable\0" - "Wants\0"; + static const char *dependencies[] = { + [DEPENDENCY_FORWARD] = "Requires\0" + "RequiresOverridable\0" + "Requisite\0" + "RequisiteOverridable\0" + "Wants\0", + [DEPENDENCY_REVERSE] = "RequiredBy\0" + "RequiredByOverridable\0" + "WantedBy\0" + "PartOf\0", + [DEPENDENCY_AFTER] = "After\0", + [DEPENDENCY_BEFORE] = "Before\0", + }; _cleanup_free_ char *path; const char *interface = "org.freedesktop.systemd1.Unit"; @@ -1049,7 +1062,8 @@ static int list_dependencies_get_dependencies(DBusConnection *bus, const char *n dbus_message_iter_recurse(&sub2, &sub3); dbus_message_iter_next(&sub); - if (!nulstr_contains(dependencies, prop)) + assert(arg_dependency < ELEMENTSOF(dependencies)); + if (!nulstr_contains(dependencies[arg_dependency], prop)) continue; if (dbus_message_iter_get_arg_type(&sub3) == DBUS_TYPE_ARRAY) { @@ -4479,6 +4493,7 @@ static int systemctl_help(void) { " -a --all Show all loaded units/properties, including dead/empty\n" " ones. To list all units installed on the system, use\n" " the 'list-unit-files' command instead.\n" + " --reverse Show reverse dependencies with 'list-dependencies'\n" " --failed Show only failed units\n" " --full Don't ellipsize unit names on output\n" " --fail When queueing a new job, fail if conflicting jobs are\n" @@ -4544,7 +4559,8 @@ static int systemctl_help(void) { " unset-cgroup [NAME] [CGROUP...] Remove unit from a control group\n" " load [NAME...] Load one or more units\n" " list-dependencies [NAME] Recursively show units which are required\n" - " or wanted by this unit\n\n" + " or wanted by this unit or by which this\n" + " unit is required or wanted\n\n" "Unit File Commands:\n" " list-unit-files List installed unit files\n" " enable [NAME...] Enable one or more unit files\n" @@ -4680,6 +4696,9 @@ static int systemctl_parse_argv(int argc, char *argv[]) { enum { ARG_FAIL = 0x100, + ARG_REVERSE, + ARG_AFTER, + ARG_BEFORE, ARG_SHOW_TYPES, ARG_IRREVERSIBLE, ARG_IGNORE_DEPENDENCIES, @@ -4707,6 +4726,9 @@ static int systemctl_parse_argv(int argc, char *argv[]) { { "type", required_argument, NULL, 't' }, { "property", required_argument, NULL, 'p' }, { "all", no_argument, NULL, 'a' }, + { "reverse", no_argument, NULL, ARG_REVERSE }, + { "after", no_argument, NULL, ARG_AFTER }, + { "before", no_argument, NULL, ARG_BEFORE }, { "show-types", no_argument, NULL, ARG_SHOW_TYPES }, { "failed", no_argument, NULL, ARG_FAILED }, { "full", no_argument, NULL, ARG_FULL }, @@ -4829,6 +4851,18 @@ static int systemctl_parse_argv(int argc, char *argv[]) { arg_all = true; break; + case ARG_REVERSE: + arg_dependency = DEPENDENCY_REVERSE; + break; + + case ARG_AFTER: + arg_dependency = DEPENDENCY_AFTER; + break; + + case ARG_BEFORE: + arg_dependency = DEPENDENCY_BEFORE; + break; + case ARG_SHOW_TYPES: arg_show_types = true; break; -- 2.30.2