1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2012 Lennart Poettering
7 Copyright 2013 Zbigniew Jędrzejewski-Szmek
8 Copyright 2014 Ronny Chevalier
10 systemd is free software; you can redistribute it and/or modify it
11 under the terms of the GNU Lesser General Public License as published by
12 the Free Software Foundation; either version 2.1 of the License, or
13 (at your option) any later version.
15 systemd is distributed in the hope that it will be useful, but
16 WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 Lesser General Public License for more details.
20 You should have received a copy of the GNU Lesser General Public License
21 along with systemd; If not, see <http://www.gnu.org/licenses/>.
27 #include <sys/types.h>
32 #include "unit-name.h"
33 #include "unit-printf.h"
35 #include "specifier.h"
38 #include "test-helper.h"
40 static void test_replacements(void) {
41 #define expect(pattern, repl, expected) \
43 _cleanup_free_ char *t = \
44 unit_name_replace_instance(pattern, repl); \
46 assert(streq(t, expected)); \
49 expect("foo@.service", "waldo", "foo@waldo.service");
50 expect("foo@xyz.service", "waldo", "foo@waldo.service");
51 expect("xyz", "waldo", "xyz");
52 expect("", "waldo", "");
53 expect("foo.service", "waldo", "foo.service");
54 expect(".service", "waldo", ".service");
55 expect("foo@", "waldo", "foo@waldo");
56 expect("@bar", "waldo", "@waldo");
58 puts("-------------------------------------------------");
60 #define expect(path, suffix, expected) \
62 _cleanup_free_ char *k, *t = \
63 unit_name_from_path(path, suffix); \
65 k = unit_name_to_path(t); \
67 assert(streq(k, expected ? expected : path)); \
70 expect("/waldo", ".mount", NULL);
71 expect("/waldo/quuix", ".mount", NULL);
72 expect("/waldo/quuix/", ".mount", "/waldo/quuix");
73 expect("/", ".mount", NULL);
74 expect("///", ".mount", "/");
76 puts("-------------------------------------------------");
78 #define expect(pattern, path, suffix, expected) \
80 _cleanup_free_ char *t = \
81 unit_name_from_path_instance(pattern, path, suffix); \
83 assert(streq(t, expected)); \
86 expect("waldo", "/waldo", ".mount", "waldo@waldo.mount");
87 expect("waldo", "/waldo////quuix////", ".mount", "waldo@waldo-quuix.mount");
88 expect("waldo", "/", ".mount", "waldo@-.mount");
89 expect("wa--ldo", "/--", ".mount", "wa--ldo@\\x2d\\x2d.mount");
91 puts("-------------------------------------------------");
93 #define expect(pattern) \
95 _cleanup_free_ char *k, *t; \
96 assert_se(t = unit_name_mangle(pattern, MANGLE_NOGLOB)); \
97 assert_se(k = unit_name_mangle(t, MANGLE_NOGLOB)); \
99 assert_se(streq(t, k)); \
104 expect("üxknürz.service");
105 expect("foobar-meh...waldi.service");
106 expect("_____####----.....service");
107 expect("_____##@;;;,,,##----.....service");
108 expect("xxx@@@@/////\\\\\\\\\\yyy.service");
113 static int test_unit_printf(void) {
118 _cleanup_free_ char *mid, *bid, *host, *root_uid;
121 assert_se(specifier_machine_id('m', NULL, NULL, &mid) >= 0 && mid);
122 assert_se(specifier_boot_id('b', NULL, NULL, &bid) >= 0 && bid);
123 assert_se((host = gethostname_malloc()));
125 assert_se((root = getpwnam("root")));
126 assert_se(asprintf(&root_uid, "%d", (int) root->pw_uid) > 0);
128 r = manager_new(SYSTEMD_USER, &m);
129 if (r == -EPERM || r == -EACCES || r == -EADDRINUSE) {
130 puts("manager_new: Permission denied. Skipping test.");
131 return EXIT_TEST_SKIP;
135 #define expect(unit, pattern, expected) \
138 _cleanup_free_ char *t; \
139 assert_se(unit_full_printf(unit, pattern, &t) >= 0); \
140 printf("result: %s\nexpect: %s\n", t, expected); \
141 if ((e = endswith(expected, "*"))) \
142 assert(strncmp(t, e, e-expected)); \
144 assert(streq(t, expected)); \
147 assert_se(setenv("USER", "root", 1) == 0);
148 assert_se(setenv("HOME", "/root", 1) == 0);
150 assert_se(u = unit_new(m, sizeof(Service)));
151 assert_se(unit_add_name(u, "blah.service") == 0);
152 assert_se(unit_add_name(u, "blah.service") == 0);
155 expect(u, "%%", "%");
156 expect(u, "%%s", "%s");
157 expect(u, "%", ""); // REALLY?
160 expect(u, "%n", "blah.service");
161 expect(u, "%N", "blah");
162 expect(u, "%p", "blah");
163 expect(u, "%P", "blah");
165 expect(u, "%u", root->pw_name);
166 expect(u, "%U", root_uid);
167 expect(u, "%h", root->pw_dir);
168 expect(u, "%m", mid);
169 expect(u, "%b", bid);
170 expect(u, "%H", host);
171 expect(u, "%t", "/run/user/*");
174 assert_se(u2 = unit_new(m, sizeof(Service)));
175 assert_se(unit_add_name(u2, "blah@foo-foo.service") == 0);
176 assert_se(unit_add_name(u2, "blah@foo-foo.service") == 0);
178 expect(u2, "%n", "blah@foo-foo.service");
179 expect(u2, "%N", "blah@foo-foo");
180 expect(u2, "%p", "blah");
181 expect(u2, "%P", "blah");
182 expect(u2, "%i", "foo-foo");
183 expect(u2, "%I", "foo/foo");
184 expect(u2, "%u", root->pw_name);
185 expect(u2, "%U", root_uid);
186 expect(u2, "%h", root->pw_dir);
187 expect(u2, "%m", mid);
188 expect(u2, "%b", bid);
189 expect(u2, "%H", host);
190 expect(u2, "%t", "/run/user/*");
197 static void test_unit_instance_is_valid(void) {
198 assert_se(unit_instance_is_valid("fooBar"));
199 assert_se(unit_instance_is_valid("foo-bar"));
200 assert_se(unit_instance_is_valid("foo.stUff"));
201 assert_se(unit_instance_is_valid("fOo123.stuff"));
202 assert_se(unit_instance_is_valid("@f_oo123.Stuff"));
204 assert_se(!unit_instance_is_valid("$¢£"));
205 assert_se(!unit_instance_is_valid(""));
206 assert_se(!unit_instance_is_valid("foo bar"));
207 assert_se(!unit_instance_is_valid("foo/bar"));
210 static void test_unit_prefix_is_valid(void) {
211 assert_se(unit_prefix_is_valid("fooBar"));
212 assert_se(unit_prefix_is_valid("foo-bar"));
213 assert_se(unit_prefix_is_valid("foo.stUff"));
214 assert_se(unit_prefix_is_valid("fOo123.stuff"));
215 assert_se(unit_prefix_is_valid("foo123.Stuff"));
217 assert_se(!unit_prefix_is_valid("$¢£"));
218 assert_se(!unit_prefix_is_valid(""));
219 assert_se(!unit_prefix_is_valid("foo bar"));
220 assert_se(!unit_prefix_is_valid("foo/bar"));
221 assert_se(!unit_prefix_is_valid("@foo-bar"));
224 static void test_unit_name_change_suffix(void) {
227 r = unit_name_change_suffix("foo.bar", ".service");
229 assert_se(streq(r, "foo.service"));
232 r = unit_name_change_suffix("foo@stuff.bar", ".boo");
234 assert_se(streq(r, "foo@stuff.boo"));
238 static void test_unit_name_build(void) {
241 r = unit_name_build("foo", "bar", ".service");
243 assert_se(streq(r, "foo@bar.service"));
246 r = unit_name_build("fo0-stUff_b", "bar", ".mount");
248 assert_se(streq(r, "fo0-stUff_b@bar.mount"));
251 r = unit_name_build("foo", NULL, ".service");
253 assert_se(streq(r, "foo.service"));
257 static void test_unit_name_is_instance(void) {
258 assert_se(unit_name_is_instance("a@b.service"));
259 assert_se(unit_name_is_instance("a-c_c01Aj@b05Dii_-oioi.service"));
261 assert_se(!unit_name_is_instance("a.service"));
262 assert_se(!unit_name_is_instance("junk"));
263 assert_se(!unit_name_is_instance(""));
266 static void test_build_subslice(void) {
270 assert_se(build_subslice("-.slice", "foo", &a) >= 0);
271 assert_se(build_subslice(a, "bar", &b) >= 0);
273 assert_se(build_subslice(b, "barfoo", &a) >= 0);
275 assert_se(build_subslice(a, "foobar", &b) >= 0);
277 assert_se(streq(b, "foo-bar-barfoo-foobar.slice"));
280 assert_se(build_subslice("foo.service", "bar", &a) < 0);
281 assert_se(build_subslice("foo", "bar", &a) < 0);
284 static void test_unit_name_to_instance(void) {
288 r = unit_name_to_instance("foo@bar.service", &instance);
290 assert_se(streq(instance, "bar"));
293 r = unit_name_to_instance("fo0-stUff_b@b.e", &instance);
295 assert_se(streq(instance, "b"));
298 r = unit_name_to_instance("foo.bar", &instance);
300 assert_se(!instance);
302 r = unit_name_to_instance("fooj@unk", &instance);
306 static void test_unit_name_escape(void) {
307 _cleanup_free_ char *r;
309 r = unit_name_escape("ab+-c.a/bc@foo.service");
311 assert_se(streq(r, "ab\\x2b\\x2dc.a-bc\\x40foo.service"));
314 int main(int argc, char* argv[]) {
317 TEST_REQ_RUNNING_SYSTEMD(rc = test_unit_printf());
318 test_unit_instance_is_valid();
319 test_unit_prefix_is_valid();
320 test_unit_name_change_suffix();
321 test_unit_name_build();
322 test_unit_name_is_instance();
323 test_build_subslice();
324 test_unit_name_to_instance();
325 test_unit_name_escape();