summaryrefslogtreecommitdiff
path: root/src/shared/specifier.c
diff options
context:
space:
mode:
authorZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>2022-01-20 16:45:19 +0100
committerZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>2022-01-21 08:00:41 +0100
commit607f032858dd1c123481e37d00391029c5b54001 (patch)
tree790789ced94375525471a156979d4eaefd6b8c12 /src/shared/specifier.c
parent01c69460811f64e416c3e4a545ef84787bb6700b (diff)
downloadsystemd-607f032858dd1c123481e37d00391029c5b54001.tar.gz
core: add %y/%Y specifiers for the fragment path of the unit
Fixes #6308: people want to be able to link a unit file via 'systemctl enable' from a git checkout or such and refer to other files in the same repo. The new specifiers make that easy. %y/%Y is used because other more obvious choices like %d/%D or %p/%P are not available because at least on of the two letters is already used. The new specifiers are only available in units. Technically it would be trivial to add then in [Install] too, but I don't see how they could be useful, so I didn't do that. I added both %y and %Y because both were requested in the issue, and because I think both could be useful, depending on the case. %Y to refer to other files in the same repo, and %y in the case where a single repo has multiple unit files, and e.g. each unit has some corresponding asset named after the unit file.
Diffstat (limited to 'src/shared/specifier.c')
-rw-r--r--src/shared/specifier.c22
1 files changed, 22 insertions, 0 deletions
diff --git a/src/shared/specifier.c b/src/shared/specifier.c
index f8ab98541f..aef5b9c94d 100644
--- a/src/shared/specifier.c
+++ b/src/shared/specifier.c
@@ -18,6 +18,7 @@
#include "id128-util.h"
#include "macro.h"
#include "os-util.h"
+#include "path-util.h"
#include "specifier.h"
#include "string-util.h"
#include "strv.h"
@@ -121,6 +122,27 @@ int specifier_string(char specifier, const void *data, const char *root, const v
return 0;
}
+int specifier_real_path(char specifier, const void *data, const char *root, const void *userdata, char **ret) {
+ const char *path = data;
+
+ if (!path)
+ return -ENOENT;
+
+ return chase_symlinks(path, root, 0, ret, NULL);
+}
+
+int specifier_real_directory(char specifier, const void *data, const char *root, const void *userdata, char **ret) {
+ _cleanup_free_ char *path = NULL;
+ int r;
+
+ r = specifier_real_path(specifier, data, root, userdata, &path);
+ if (r < 0)
+ return r;
+
+ assert(path);
+ return path_extract_directory(path, ret);
+}
+
int specifier_machine_id(char specifier, const void *data, const char *root, const void *userdata, char **ret) {
sd_id128_t id;
char *n;