1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2010 Lennart Poettering
7 Copyright 2013 Thomas H.P. Andersen
9 systemd is free software; you can redistribute it and/or modify it
10 under the terms of the GNU Lesser General Public License as published by
11 the Free Software Foundation; either version 2.1 of the License, or
12 (at your option) any later version.
14 systemd is distributed in the hope that it will be useful, but
15 WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 Lesser General Public License for more details.
19 You should have received a copy of the GNU Lesser General Public License
20 along with systemd; If not, see <http://www.gnu.org/licenses/>.
26 #include "specifier.h"
29 static void test_specifier_printf(void) {
30 static const Specifier table[] = {
31 { 'a', specifier_string, (char*) "AAAA" },
32 { 'b', specifier_string, (char*) "BBBB" },
33 { 'm', specifier_machine_id, NULL },
34 { 'B', specifier_boot_id, NULL },
35 { 'H', specifier_host_name, NULL },
36 { 'v', specifier_kernel_release, NULL },
40 _cleanup_free_ char *w = NULL;
43 r = specifier_printf("xxx a=%a b=%b yyy", table, NULL, &w);
48 assert_se(streq(w, "xxx a=AAAA b=BBBB yyy"));
51 r = specifier_printf("machine=%m, boot=%B, host=%H, version=%v", table, NULL, &w);
57 static const char* const input_table_multiple[] = {
64 static const char* const input_table_one[] = {
69 static const char* const input_table_none[] = {
73 static const char* const input_table_quotes[] = {
81 #define QUOTES_STRING \
88 static const char * const input_table_spaces[] = {
96 #define SPACES_STRING \
103 static void test_strv_find(void) {
104 assert_se(strv_find((char **)input_table_multiple, "three"));
105 assert_se(!strv_find((char **)input_table_multiple, "four"));
108 static void test_strv_find_prefix(void) {
109 assert_se(strv_find_prefix((char **)input_table_multiple, "o"));
110 assert_se(strv_find_prefix((char **)input_table_multiple, "one"));
111 assert_se(strv_find_prefix((char **)input_table_multiple, ""));
112 assert_se(!strv_find_prefix((char **)input_table_multiple, "xxx"));
113 assert_se(!strv_find_prefix((char **)input_table_multiple, "onee"));
116 static void test_strv_join(void) {
117 _cleanup_free_ char *p = NULL, *q = NULL, *r = NULL, *s = NULL, *t = NULL;
119 p = strv_join((char **)input_table_multiple, ", ");
121 assert_se(streq(p, "one, two, three"));
123 q = strv_join((char **)input_table_multiple, ";");
125 assert_se(streq(q, "one;two;three"));
127 r = strv_join((char **)input_table_multiple, NULL);
129 assert_se(streq(r, "one two three"));
131 s = strv_join((char **)input_table_one, ", ");
133 assert_se(streq(s, "one"));
135 t = strv_join((char **)input_table_none, ", ");
137 assert_se(streq(t, ""));
140 static void test_strv_quote_unquote(const char* const *split, const char *quoted) {
141 _cleanup_free_ char *p;
142 _cleanup_strv_free_ char **s;
146 p = strv_join_quoted((char **)split);
148 printf("-%s- --- -%s-\n", p, quoted); /* fprintf deals with NULL, puts does not */
150 assert_se(streq(p, quoted));
152 r = strv_split_quoted(&s, quoted);
157 assert_se(streq(*t, *split));
162 static void test_strv_unquote(const char *quoted, const char **list) {
163 _cleanup_strv_free_ char **s;
164 _cleanup_free_ char *j;
169 r = strv_split_quoted(&s, quoted);
172 j = strv_join(s, " | ");
177 assert_se(streq(list[i++], *t));
179 assert_se(list[i] == NULL);
182 static void test_invalid_unquote(const char *quoted) {
186 r = strv_split_quoted(&s, quoted);
188 assert(r == -EINVAL);
191 static void test_strv_split(void) {
194 _cleanup_strv_free_ char **l = NULL;
195 const char str[] = "one,two,three";
197 l = strv_split(str, ",");
202 assert_se(streq(*s, input_table_multiple[i++]));
206 static void test_strv_split_newlines(void) {
209 _cleanup_strv_free_ char **l = NULL;
210 const char str[] = "one\ntwo\nthree";
212 l = strv_split_newlines(str);
217 assert_se(streq(*s, input_table_multiple[i++]));
221 static void test_strv_split_nulstr(void) {
222 _cleanup_strv_free_ char **l = NULL;
223 const char nulstr[] = "str0\0str1\0str2\0str3\0";
225 l = strv_split_nulstr (nulstr);
228 assert_se(streq(l[0], "str0"));
229 assert_se(streq(l[1], "str1"));
230 assert_se(streq(l[2], "str2"));
231 assert_se(streq(l[3], "str3"));
234 static void test_strv_parse_nulstr(void) {
235 _cleanup_strv_free_ char **l = NULL;
236 const char nulstr[] = "fuck\0fuck2\0fuck3\0\0fuck5\0\0xxx";
238 l = strv_parse_nulstr(nulstr, sizeof(nulstr)-1);
240 puts("Parse nulstr:");
243 assert_se(streq(l[0], "fuck"));
244 assert_se(streq(l[1], "fuck2"));
245 assert_se(streq(l[2], "fuck3"));
246 assert_se(streq(l[3], ""));
247 assert_se(streq(l[4], "fuck5"));
248 assert_se(streq(l[5], ""));
249 assert_se(streq(l[6], "xxx"));
252 static void test_strv_overlap(void) {
253 const char * const input_table[] = {
259 const char * const input_table_overlap[] = {
263 const char * const input_table_unique[] = {
270 assert_se(strv_overlap((char **)input_table, (char**)input_table_overlap));
271 assert_se(!strv_overlap((char **)input_table, (char**)input_table_unique));
274 static void test_strv_sort(void) {
275 const char* input_table[] = {
279 "CAPITAL LETTERS FIRST",
284 strv_sort((char **)input_table);
286 assert_se(streq(input_table[0], "CAPITAL LETTERS FIRST"));
287 assert_se(streq(input_table[1], "apple"));
288 assert_se(streq(input_table[2], "banana"));
289 assert_se(streq(input_table[3], "citrus"));
290 assert_se(streq(input_table[4], "durian"));
293 static void test_strv_extend_strv_concat(void) {
294 _cleanup_strv_free_ char **a = NULL, **b = NULL;
296 a = strv_new("without", "suffix", NULL);
297 b = strv_new("with", "suffix", NULL);
301 assert_se(strv_extend_strv_concat(&a, b, "_suffix") >= 0);
303 assert_se(streq(a[0], "without"));
304 assert_se(streq(a[1], "suffix"));
305 assert_se(streq(a[2], "with_suffix"));
306 assert_se(streq(a[3], "suffix_suffix"));
309 static void test_strv_extend_strv(void) {
310 _cleanup_strv_free_ char **a = NULL, **b = NULL;
312 a = strv_new("abc", "def", "ghi", NULL);
313 b = strv_new("jkl", "mno", "pqr", NULL);
317 assert_se(strv_extend_strv(&a, b) >= 0);
319 assert_se(streq(a[0], "abc"));
320 assert_se(streq(a[1], "def"));
321 assert_se(streq(a[2], "ghi"));
322 assert_se(streq(a[3], "jkl"));
323 assert_se(streq(a[4], "mno"));
324 assert_se(streq(a[5], "pqr"));
326 assert_se(strv_length(a) == 6);
329 static void test_strv_extend(void) {
330 _cleanup_strv_free_ char **a = NULL, **b = NULL;
332 a = strv_new("test", "test1", NULL);
334 assert_se(strv_extend(&a, "test2") >= 0);
335 assert_se(strv_extend(&b, "test3") >= 0);
337 assert_se(streq(a[0], "test"));
338 assert_se(streq(a[1], "test1"));
339 assert_se(streq(a[2], "test2"));
340 assert_se(streq(b[0], "test3"));
343 static void test_strv_extendf(void) {
344 _cleanup_strv_free_ char **a = NULL, **b = NULL;
346 a = strv_new("test", "test1", NULL);
348 assert_se(strv_extendf(&a, "test2 %s %d %s", "foo", 128, "bar") >= 0);
349 assert_se(strv_extendf(&b, "test3 %s %s %d", "bar", "foo", 128) >= 0);
351 assert_se(streq(a[0], "test"));
352 assert_se(streq(a[1], "test1"));
353 assert_se(streq(a[2], "test2 foo 128 bar"));
354 assert_se(streq(b[0], "test3 bar foo 128"));
357 static void test_strv_foreach(void) {
358 _cleanup_strv_free_ char **a;
362 a = strv_new("one", "two", "three", NULL);
366 STRV_FOREACH(check, a) {
367 assert_se(streq(*check, input_table_multiple[i++]));
371 static void test_strv_foreach_backwards(void) {
372 _cleanup_strv_free_ char **a;
376 a = strv_new("one", "two", "three", NULL);
380 STRV_FOREACH_BACKWARDS(check, a) {
381 assert_se(streq_ptr(*check, input_table_multiple[i--]));
385 static void test_strv_foreach_pair(void) {
386 _cleanup_strv_free_ char **a = NULL;
389 a = strv_new("pair_one", "pair_one",
390 "pair_two", "pair_two",
391 "pair_three", "pair_three",
394 STRV_FOREACH_PAIR(x, y, a) {
395 assert_se(streq(*x, *y));
399 static void test_strv_from_stdarg_alloca_one(char **l, const char *first, ...) {
403 j = strv_from_stdarg_alloca(first);
406 assert_se(streq_ptr(l[i], j[i]));
413 static void test_strv_from_stdarg_alloca(void) {
414 test_strv_from_stdarg_alloca_one(STRV_MAKE("foo", "bar"), "foo", "bar", NULL);
415 test_strv_from_stdarg_alloca_one(STRV_MAKE("foo"), "foo", NULL);
416 test_strv_from_stdarg_alloca_one(STRV_MAKE_EMPTY, NULL);
419 static void test_strv_push(void) {
420 _cleanup_strv_free_ char **a = NULL;
423 assert_se(i = strdup("foo"));
424 assert_se(strv_push(&a, i) >= 0);
426 assert_se(i = strdup("a"));
427 assert_se(j = strdup("b"));
428 assert_se(strv_push_pair(&a, i, j) >= 0);
430 assert_se(streq_ptr(a[0], "foo"));
431 assert_se(streq_ptr(a[1], "a"));
432 assert_se(streq_ptr(a[2], "b"));
433 assert_se(streq_ptr(a[3], NULL));
436 int main(int argc, char *argv[]) {
437 test_specifier_printf();
439 test_strv_foreach_backwards();
440 test_strv_foreach_pair();
442 test_strv_find_prefix();
445 test_strv_quote_unquote(input_table_multiple, "\"one\" \"two\" \"three\"");
446 test_strv_quote_unquote(input_table_one, "\"one\"");
447 test_strv_quote_unquote(input_table_none, "");
448 test_strv_quote_unquote(input_table_quotes, QUOTES_STRING);
449 test_strv_quote_unquote(input_table_spaces, SPACES_STRING);
451 test_strv_unquote(" foo=bar \"waldo\" zzz ", (const char*[]) { "foo=bar", "waldo", "zzz", NULL });
452 test_strv_unquote("", (const char*[]) { NULL });
453 test_strv_unquote(" ", (const char*[]) { NULL });
454 test_strv_unquote(" ", (const char*[]) { NULL });
455 test_strv_unquote(" x", (const char*[]) { "x", NULL });
456 test_strv_unquote("x ", (const char*[]) { "x", NULL });
457 test_strv_unquote(" x ", (const char*[]) { "x", NULL });
458 test_strv_unquote(" \"x\" ", (const char*[]) { "x", NULL });
459 test_strv_unquote(" 'x' ", (const char*[]) { "x", NULL });
460 test_strv_unquote(" 'x\"' ", (const char*[]) { "x\"", NULL });
461 test_strv_unquote(" \"x'\" ", (const char*[]) { "x'", NULL });
462 test_strv_unquote("a '--b=c \"d e\"'", (const char*[]) { "a", "--b=c \"d e\"", NULL });
464 test_invalid_unquote("a --b='c \"d e\"'");
465 test_invalid_unquote("a --b='c \"d e\" '");
466 test_invalid_unquote("a --b='c \"d e\"garbage");
467 test_invalid_unquote("'");
468 test_invalid_unquote("\"");
469 test_invalid_unquote("'x'y");
472 test_strv_split_newlines();
473 test_strv_split_nulstr();
474 test_strv_parse_nulstr();
477 test_strv_extend_strv();
478 test_strv_extend_strv_concat();
481 test_strv_from_stdarg_alloca();