From 6d8d68c8077d2ad8b2b5d8cea78ce4ef4500252d Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Mon, 21 May 2012 15:27:26 +0200 Subject: [PATCH] unit: introduce RequiredBy= setting in [Install], to complement WantedBy= (cherry picked from commit 78d54bd42b87818f5d0ef862d247f9db4844fadd) --- man/systemd.unit.xml | 2 ++ src/install.c | 57 ++++++++++++++++++++++++++++++++++---- src/load-fragment-gperf.gperf.m4 | 1 + 3 files changed, 55 insertions(+), 5 deletions(-) diff --git a/man/systemd.unit.xml b/man/systemd.unit.xml index 30559b9..f2e28dc 100644 --- a/man/systemd.unit.xml +++ b/man/systemd.unit.xml @@ -914,9 +914,11 @@ WantedBy= + RequiredBy= Installs a symlink in the .wants/ + resp. .requires/ subdirectory for a unit. This has the effect that when the listed unit name is activated the unit listing it is diff --git a/src/install.c b/src/install.c index b5c49bd..be610e4 100644 --- a/src/install.c +++ b/src/install.c @@ -40,6 +40,7 @@ typedef struct { char **aliases; char **wanted_by; + char **required_by; } InstallInfo; typedef struct { @@ -880,6 +881,7 @@ static void install_info_free(InstallInfo *i) { free(i->path); strv_free(i->aliases); strv_free(i->wanted_by); + strv_free(i->required_by); free(i); } @@ -1018,9 +1020,10 @@ static int unit_file_load( bool allow_symlink) { const ConfigTableItem items[] = { - { "Install", "Alias", config_parse_strv, 0, &info->aliases }, - { "Install", "WantedBy", config_parse_strv, 0, &info->wanted_by }, - { "Install", "Also", config_parse_also, 0, c }, + { "Install", "Alias", config_parse_strv, 0, &info->aliases }, + { "Install", "WantedBy", config_parse_strv, 0, &info->wanted_by }, + { "Install", "RequiredBy", config_parse_strv, 0, &info->required_by }, + { "Install", "Also", config_parse_also, 0, c }, { NULL, NULL, NULL, 0, NULL } }; @@ -1047,7 +1050,10 @@ static int unit_file_load( if (r < 0) return r; - return strv_length(info->aliases) + strv_length(info->wanted_by); + return + strv_length(info->aliases) + + strv_length(info->wanted_by) + + strv_length(info->required_by); } static int unit_file_search( @@ -1118,7 +1124,10 @@ static int unit_file_can_install( r = unit_file_search(&c, i, paths, root_dir, allow_symlink); if (r >= 0) - r = strv_length(i->aliases) + strv_length(i->wanted_by); + r = + strv_length(i->aliases) + + strv_length(i->wanted_by) + + strv_length(i->required_by); install_context_done(&c); @@ -1238,6 +1247,40 @@ static int install_info_symlink_wants( return r; } +static int install_info_symlink_requires( + InstallInfo *i, + const char *config_path, + bool force, + UnitFileChange **changes, + unsigned *n_changes) { + + char **s; + int r = 0, q; + + assert(i); + assert(config_path); + + STRV_FOREACH(s, i->required_by) { + char *path; + + if (!unit_name_is_valid_no_type(*s, true)) { + r = -EINVAL; + continue; + } + + if (asprintf(&path, "%s/%s.requires/%s", config_path, *s, i->name) < 0) + return -ENOMEM; + + q = create_symlink(i->path, path, force, changes, n_changes); + free(path); + + if (r == 0) + r = q; + } + + return r; +} + static int install_info_symlink_link( InstallInfo *i, LookupPaths *paths, @@ -1287,6 +1330,10 @@ static int install_info_apply( if (r == 0) r = q; + q = install_info_symlink_requires(i, config_path, force, changes, n_changes); + if (r == 0) + r = q; + q = install_info_symlink_link(i, paths, config_path, force, changes, n_changes); if (r == 0) r = q; diff --git a/src/load-fragment-gperf.gperf.m4 b/src/load-fragment-gperf.gperf.m4 index e2b6522..9f0b20d 100644 --- a/src/load-fragment-gperf.gperf.m4 +++ b/src/load-fragment-gperf.gperf.m4 @@ -220,4 +220,5 @@ Path.DirectoryMode, config_parse_mode, 0, m4_dnl The [Install] section is ignored here. Install.Alias, NULL, 0, 0 Install.WantedBy, NULL, 0, 0 +Install.RequiredBy, NULL, 0, 0 Install.Also, NULL, 0, 0