]> git.ipfire.org Git - thirdparty/systemd.git/blame - src/test/test-util.c
cpu-set-util: Accept commas as separators in parse_cpu_set_and_warn
[thirdparty/systemd.git] / src / test / test-util.c
CommitLineData
539ad707
TA
1/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3/***
4 This file is part of systemd.
5
6 Copyright 2010 Lennart Poettering
7 Copyright 2013 Thomas H.P. Andersen
8
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.
13
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.
18
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/>.
21***/
22
618234a5 23#include <errno.h>
dbd73f9e 24#include <fcntl.h>
d6dd604b 25#include <locale.h>
8e211000 26#include <math.h>
618234a5
LP
27#include <signal.h>
28#include <string.h>
df241a67 29#include <sys/types.h>
8852362b 30#include <sys/wait.h>
df241a67 31#include <sys/xattr.h>
618234a5 32#include <unistd.h>
539ad707 33
b5efdb8a 34#include "alloc-util.h"
618234a5
LP
35#include "conf-parser.h"
36#include "cpu-set-util.h"
65b3903f 37#include "def.h"
4f5dd394 38#include "escape.h"
c004493c 39#include "fd-util.h"
65b3903f 40#include "fileio.h"
f4f15635 41#include "fs-util.h"
6550203e 42#include "fstab-util.h"
7d50b32a 43#include "glob-util.h"
6550203e 44#include "hexdecoct.h"
c004493c 45#include "io-util.h"
618234a5 46#include "mkdir.h"
6bedfcbb 47#include "parse-util.h"
89a5a90c 48#include "path-util.h"
4e731273 49#include "proc-cmdline.h"
0b452006 50#include "process-util.h"
618234a5 51#include "rm-rf.h"
24882e06 52#include "signal-util.h"
8fcde012 53#include "stat-util.h"
07630cea 54#include "string-util.h"
618234a5 55#include "strv.h"
6bedfcbb 56#include "user-util.h"
618234a5
LP
57#include "util.h"
58#include "virt.h"
49cf4170 59#include "web-util.h"
7d50b32a 60#include "xattr-util.h"
539ad707
TA
61
62static void test_streq_ptr(void) {
8354c34e
TA
63 assert_se(streq_ptr(NULL, NULL));
64 assert_se(!streq_ptr("abc", "cdef"));
539ad707
TA
65}
66
625e870b
DH
67static void test_align_power2(void) {
68 unsigned long i, p2;
69
70 assert_se(ALIGN_POWER2(0) == 0);
71 assert_se(ALIGN_POWER2(1) == 1);
72 assert_se(ALIGN_POWER2(2) == 2);
73 assert_se(ALIGN_POWER2(3) == 4);
74 assert_se(ALIGN_POWER2(12) == 16);
75
76 assert_se(ALIGN_POWER2(ULONG_MAX) == 0);
77 assert_se(ALIGN_POWER2(ULONG_MAX - 1) == 0);
78 assert_se(ALIGN_POWER2(ULONG_MAX - 1024) == 0);
79 assert_se(ALIGN_POWER2(ULONG_MAX / 2) == ULONG_MAX / 2 + 1);
80 assert_se(ALIGN_POWER2(ULONG_MAX + 1) == 0);
81
82 for (i = 1; i < 131071; ++i) {
83 for (p2 = 1; p2 < i; p2 <<= 1)
84 /* empty */ ;
85
86 assert_se(ALIGN_POWER2(i) == p2);
87 }
88
89 for (i = ULONG_MAX - 1024; i < ULONG_MAX; ++i) {
90 for (p2 = 1; p2 && p2 < i; p2 <<= 1)
91 /* empty */ ;
92
93 assert_se(ALIGN_POWER2(i) == p2);
94 }
95}
96
7242d742
DH
97static void test_max(void) {
98 static const struct {
99 int a;
100 int b[CONST_MAX(10, 100)];
101 } val1 = {
102 .a = CONST_MAX(10, 100),
103 };
104 int d = 0;
105
106 assert_cc(sizeof(val1.b) == sizeof(int) * 100);
107
108 /* CONST_MAX returns (void) instead of a value if the passed arguments
109 * are not of the same type or not constant expressions. */
110 assert_cc(__builtin_types_compatible_p(typeof(CONST_MAX(1, 10)), int));
7242d742
DH
111 assert_cc(__builtin_types_compatible_p(typeof(CONST_MAX(1, 1U)), void));
112
113 assert_se(val1.a == 100);
114 assert_se(MAX(++d, 0) == 1);
115 assert_se(d == 1);
40a1eebd
DH
116
117 assert_cc(MAXSIZE(char[3], uint16_t) == 3);
118 assert_cc(MAXSIZE(char[3], uint32_t) == 4);
119 assert_cc(MAXSIZE(char, long) == sizeof(long));
667a0377
DH
120
121 assert_se(MAX(-5, 5) == 5);
122 assert_se(MAX(5, 5) == 5);
123 assert_se(MAX(MAX(1, MAX(2, MAX(3, 4))), 5) == 5);
124 assert_se(MAX(MAX(1, MAX(2, MAX(3, 2))), 1) == 3);
125 assert_se(MAX(MIN(1, MIN(2, MIN(3, 4))), 5) == 5);
126 assert_se(MAX(MAX(1, MIN(2, MIN(3, 2))), 1) == 2);
127 assert_se(LESS_BY(8, 4) == 4);
128 assert_se(LESS_BY(8, 8) == 0);
129 assert_se(LESS_BY(4, 8) == 0);
130 assert_se(LESS_BY(16, LESS_BY(8, 4)) == 12);
131 assert_se(LESS_BY(4, LESS_BY(8, 4)) == 0);
132 assert_se(CLAMP(-5, 0, 1) == 0);
133 assert_se(CLAMP(5, 0, 1) == 1);
134 assert_se(CLAMP(5, -10, 1) == 1);
135 assert_se(CLAMP(5, -10, 10) == 5);
136 assert_se(CLAMP(CLAMP(0, -10, 10), CLAMP(-5, 10, 20), CLAMP(100, -5, 20)) == 10);
7242d742
DH
137}
138
fb835651
DH
139static void test_container_of(void) {
140 struct mytype {
141 uint8_t pad1[3];
142 uint64_t v1;
143 uint8_t pad2[2];
144 uint32_t v2;
145 } _packed_ myval = { };
146
147 assert_cc(sizeof(myval) == 17);
148 assert_se(container_of(&myval.v1, struct mytype, v1) == &myval);
149 assert_se(container_of(&myval.v2, struct mytype, v2) == &myval);
150 assert_se(container_of(&container_of(&myval.v2,
151 struct mytype,
152 v2)->v1,
153 struct mytype,
154 v1) == &myval);
155}
156
95d78c7e
DH
157static void test_alloca(void) {
158 static const uint8_t zero[997] = { };
159 char *t;
160
161 t = alloca_align(17, 512);
162 assert_se(!((uintptr_t)t & 0xff));
163 memzero(t, 17);
164
165 t = alloca0_align(997, 1024);
166 assert_se(!((uintptr_t)t & 0x1ff));
167 assert_se(!memcmp(t, zero, 997));
168}
169
180a60bc
DH
170static void test_div_round_up(void) {
171 int div;
172
173 /* basic tests */
174 assert_se(DIV_ROUND_UP(0, 8) == 0);
175 assert_se(DIV_ROUND_UP(1, 8) == 1);
176 assert_se(DIV_ROUND_UP(8, 8) == 1);
177 assert_se(DIV_ROUND_UP(12, 8) == 2);
178 assert_se(DIV_ROUND_UP(16, 8) == 2);
179
180 /* test multiple evaluation */
181 div = 0;
182 assert_se(DIV_ROUND_UP(div++, 8) == 0 && div == 1);
183 assert_se(DIV_ROUND_UP(++div, 8) == 1 && div == 2);
184 assert_se(DIV_ROUND_UP(8, div++) == 4 && div == 3);
185 assert_se(DIV_ROUND_UP(8, ++div) == 2 && div == 4);
186
187 /* overflow test with exact division */
188 assert_se(sizeof(0U) == 4);
189 assert_se(0xfffffffaU % 10U == 0U);
190 assert_se(0xfffffffaU / 10U == 429496729U);
191 assert_se(DIV_ROUND_UP(0xfffffffaU, 10U) == 429496729U);
192 assert_se((0xfffffffaU + 10U - 1U) / 10U == 0U);
193 assert_se(0xfffffffaU / 10U + !!(0xfffffffaU % 10U) == 429496729U);
194
195 /* overflow test with rounded division */
196 assert_se(0xfffffffdU % 10U == 3U);
197 assert_se(0xfffffffdU / 10U == 429496729U);
198 assert_se(DIV_ROUND_UP(0xfffffffdU, 10U) == 429496730U);
199 assert_se((0xfffffffdU + 10U - 1U) / 10U == 0U);
200 assert_se(0xfffffffdU / 10U + !!(0xfffffffdU % 10U) == 429496730U);
201}
202
539ad707 203static void test_first_word(void) {
8354c34e
TA
204 assert_se(first_word("Hello", ""));
205 assert_se(first_word("Hello", "Hello"));
206 assert_se(first_word("Hello world", "Hello"));
207 assert_se(first_word("Hello\tworld", "Hello"));
208 assert_se(first_word("Hello\nworld", "Hello"));
209 assert_se(first_word("Hello\rworld", "Hello"));
210 assert_se(first_word("Hello ", "Hello"));
211
212 assert_se(!first_word("Hello", "Hellooo"));
213 assert_se(!first_word("Hello", "xxxxx"));
214 assert_se(!first_word("Hellooo", "Hello"));
215}
216
dbd73f9e
TA
217static void test_close_many(void) {
218 int fds[3];
219 char name0[] = "/tmp/test-close-many.XXXXXX";
220 char name1[] = "/tmp/test-close-many.XXXXXX";
221 char name2[] = "/tmp/test-close-many.XXXXXX";
222
2d5bdf5b
LP
223 fds[0] = mkostemp_safe(name0, O_RDWR|O_CLOEXEC);
224 fds[1] = mkostemp_safe(name1, O_RDWR|O_CLOEXEC);
225 fds[2] = mkostemp_safe(name2, O_RDWR|O_CLOEXEC);
dbd73f9e
TA
226
227 close_many(fds, 2);
228
229 assert_se(fcntl(fds[0], F_GETFD) == -1);
230 assert_se(fcntl(fds[1], F_GETFD) == -1);
231 assert_se(fcntl(fds[2], F_GETFD) >= 0);
232
03e334a1 233 safe_close(fds[2]);
dbd73f9e
TA
234
235 unlink(name0);
236 unlink(name1);
237 unlink(name2);
238}
239
8354c34e
TA
240static void test_parse_boolean(void) {
241 assert_se(parse_boolean("1") == 1);
242 assert_se(parse_boolean("y") == 1);
243 assert_se(parse_boolean("Y") == 1);
244 assert_se(parse_boolean("yes") == 1);
245 assert_se(parse_boolean("YES") == 1);
246 assert_se(parse_boolean("true") == 1);
247 assert_se(parse_boolean("TRUE") == 1);
248 assert_se(parse_boolean("on") == 1);
249 assert_se(parse_boolean("ON") == 1);
250
251 assert_se(parse_boolean("0") == 0);
252 assert_se(parse_boolean("n") == 0);
253 assert_se(parse_boolean("N") == 0);
254 assert_se(parse_boolean("no") == 0);
255 assert_se(parse_boolean("NO") == 0);
256 assert_se(parse_boolean("false") == 0);
257 assert_se(parse_boolean("FALSE") == 0);
258 assert_se(parse_boolean("off") == 0);
259 assert_se(parse_boolean("OFF") == 0);
260
261 assert_se(parse_boolean("garbage") < 0);
262 assert_se(parse_boolean("") < 0);
0f625d0b 263 assert_se(parse_boolean("full") < 0);
539ad707
TA
264}
265
8d99e5f5
TA
266static void test_parse_pid(void) {
267 int r;
268 pid_t pid;
269
270 r = parse_pid("100", &pid);
271 assert_se(r == 0);
272 assert_se(pid == 100);
273
274 r = parse_pid("0x7FFFFFFF", &pid);
275 assert_se(r == 0);
276 assert_se(pid == 2147483647);
277
278 pid = 65; /* pid is left unchanged on ERANGE. Set to known arbitrary value. */
279 r = parse_pid("0", &pid);
280 assert_se(r == -ERANGE);
281 assert_se(pid == 65);
282
283 pid = 65; /* pid is left unchanged on ERANGE. Set to known arbitrary value. */
284 r = parse_pid("-100", &pid);
285 assert_se(r == -ERANGE);
286 assert_se(pid == 65);
287
288 pid = 65; /* pid is left unchanged on ERANGE. Set to known arbitrary value. */
289 r = parse_pid("0xFFFFFFFFFFFFFFFFF", &pid);
bdf7026e 290 assert_se(r == -ERANGE);
8d99e5f5 291 assert_se(pid == 65);
348637b2
LP
292
293 r = parse_pid("junk", &pid);
294 assert_se(r == -EINVAL);
8d99e5f5
TA
295}
296
297static void test_parse_uid(void) {
298 int r;
299 uid_t uid;
300
301 r = parse_uid("100", &uid);
302 assert_se(r == 0);
303 assert_se(uid == 100);
ff9265d0
DM
304
305 r = parse_uid("65535", &uid);
306 assert_se(r == -ENXIO);
ef5c570e
LP
307
308 r = parse_uid("asdsdas", &uid);
309 assert_se(r == -EINVAL);
ff9265d0
DM
310}
311
312static void test_safe_atou16(void) {
313 int r;
314 uint16_t l;
315
316 r = safe_atou16("12345", &l);
317 assert_se(r == 0);
318 assert_se(l == 12345);
319
320 r = safe_atou16("123456", &l);
321 assert_se(r == -ERANGE);
322
323 r = safe_atou16("junk", &l);
324 assert_se(r == -EINVAL);
325}
326
327static void test_safe_atoi16(void) {
328 int r;
329 int16_t l;
330
331 r = safe_atoi16("-12345", &l);
332 assert_se(r == 0);
333 assert_se(l == -12345);
334
335 r = safe_atoi16("36536", &l);
336 assert_se(r == -ERANGE);
337
338 r = safe_atoi16("junk", &l);
339 assert_se(r == -EINVAL);
8d99e5f5
TA
340}
341
342static void test_safe_atolli(void) {
343 int r;
344 long long l;
345
346 r = safe_atolli("12345", &l);
347 assert_se(r == 0);
348 assert_se(l == 12345);
349
350 r = safe_atolli("junk", &l);
351 assert_se(r == -EINVAL);
352}
353
354static void test_safe_atod(void) {
355 int r;
356 double d;
d6dd604b
LP
357 char *e;
358
359 r = safe_atod("junk", &d);
360 assert_se(r == -EINVAL);
8d99e5f5
TA
361
362 r = safe_atod("0.2244", &d);
363 assert_se(r == 0);
8e211000 364 assert_se(fabs(d - 0.2244) < 0.000001);
8d99e5f5 365
d6dd604b 366 r = safe_atod("0,5", &d);
8d99e5f5 367 assert_se(r == -EINVAL);
d6dd604b
LP
368
369 errno = 0;
370 strtod("0,5", &e);
371 assert_se(*e == ',');
372
373 /* Check if this really is locale independent */
926446f4 374 if (setlocale(LC_NUMERIC, "de_DE.utf8")) {
d6dd604b 375
926446f4
DH
376 r = safe_atod("0.2244", &d);
377 assert_se(r == 0);
378 assert_se(fabs(d - 0.2244) < 0.000001);
d6dd604b 379
926446f4
DH
380 r = safe_atod("0,5", &d);
381 assert_se(r == -EINVAL);
d6dd604b 382
926446f4
DH
383 errno = 0;
384 assert_se(fabs(strtod("0,5", &e) - 0.5) < 0.00001);
385 }
d6dd604b
LP
386
387 /* And check again, reset */
926446f4 388 assert_se(setlocale(LC_NUMERIC, "C"));
d6dd604b
LP
389
390 r = safe_atod("0.2244", &d);
391 assert_se(r == 0);
8e211000 392 assert_se(fabs(d - 0.2244) < 0.000001);
d6dd604b
LP
393
394 r = safe_atod("0,5", &d);
395 assert_se(r == -EINVAL);
396
397 errno = 0;
398 strtod("0,5", &e);
399 assert_se(*e == ',');
8d99e5f5
TA
400}
401
dbd73f9e 402static void test_strappend(void) {
998b087f 403 _cleanup_free_ char *t1, *t2, *t3, *t4;
dbd73f9e 404
998b087f
TA
405 t1 = strappend(NULL, NULL);
406 assert_se(streq(t1, ""));
dbd73f9e 407
998b087f
TA
408 t2 = strappend(NULL, "suf");
409 assert_se(streq(t2, "suf"));
dbd73f9e 410
998b087f
TA
411 t3 = strappend("pre", NULL);
412 assert_se(streq(t3, "pre"));
dbd73f9e 413
998b087f
TA
414 t4 = strappend("pre", "suf");
415 assert_se(streq(t4, "presuf"));
dbd73f9e
TA
416}
417
1ef04f0b 418static void test_strstrip(void) {
998b087f
TA
419 char *r;
420 char input[] = " hello, waldo. ";
1ef04f0b 421
998b087f
TA
422 r = strstrip(input);
423 assert_se(streq(r, "hello, waldo."));
1ef04f0b
TA
424}
425
426static void test_delete_chars(void) {
998b087f
TA
427 char *r;
428 char input[] = " hello, waldo. abc";
1ef04f0b 429
998b087f
TA
430 r = delete_chars(input, WHITESPACE);
431 assert_se(streq(r, "hello,waldo.abc"));
1ef04f0b
TA
432}
433
434static void test_in_charset(void) {
998b087f
TA
435 assert_se(in_charset("dddaaabbbcccc", "abcd"));
436 assert_se(!in_charset("dddaaabbbcccc", "abc f"));
1ef04f0b
TA
437}
438
44f4c86c
DB
439static void test_hexchar(void) {
440 assert_se(hexchar(0xa) == 'a');
441 assert_se(hexchar(0x0) == '0');
442}
443
444static void test_unhexchar(void) {
445 assert_se(unhexchar('a') == 0xA);
446 assert_se(unhexchar('A') == 0xA);
447 assert_se(unhexchar('0') == 0x0);
448}
449
919a7f5f
TG
450static void test_base32hexchar(void) {
451 assert_se(base32hexchar(0) == '0');
452 assert_se(base32hexchar(9) == '9');
453 assert_se(base32hexchar(10) == 'A');
454 assert_se(base32hexchar(31) == 'V');
455}
456
457static void test_unbase32hexchar(void) {
458 assert_se(unbase32hexchar('0') == 0);
459 assert_se(unbase32hexchar('9') == 9);
460 assert_se(unbase32hexchar('A') == 10);
461 assert_se(unbase32hexchar('V') == 31);
462 assert_se(unbase32hexchar('=') == -EINVAL);
463}
464
13a5d76b
TG
465static void test_base64char(void) {
466 assert_se(base64char(0) == 'A');
467 assert_se(base64char(26) == 'a');
468 assert_se(base64char(63) == '/');
469}
470
471static void test_unbase64char(void) {
472 assert_se(unbase64char('A') == 0);
473 assert_se(unbase64char('Z') == 25);
474 assert_se(unbase64char('a') == 26);
475 assert_se(unbase64char('z') == 51);
476 assert_se(unbase64char('0') == 52);
477 assert_se(unbase64char('9') == 61);
478 assert_se(unbase64char('+') == 62);
479 assert_se(unbase64char('/') == 63);
480 assert_se(unbase64char('=') == -EINVAL);
481}
482
44f4c86c
DB
483static void test_octchar(void) {
484 assert_se(octchar(00) == '0');
485 assert_se(octchar(07) == '7');
486}
487
488static void test_unoctchar(void) {
489 assert_se(unoctchar('0') == 00);
490 assert_se(unoctchar('7') == 07);
491}
492
493static void test_decchar(void) {
494 assert_se(decchar(0) == '0');
495 assert_se(decchar(9) == '9');
496}
497
498static void test_undecchar(void) {
499 assert_se(undecchar('0') == 0);
500 assert_se(undecchar('9') == 9);
501}
502
30494563
TG
503static void test_unhexmem(void) {
504 const char *hex = "efa214921";
505 const char *hex_invalid = "efa214921o";
506 _cleanup_free_ char *hex2 = NULL;
507 _cleanup_free_ void *mem = NULL;
508 size_t len;
509
510 assert_se(unhexmem(hex, strlen(hex), &mem, &len) == 0);
511 assert_se(unhexmem(hex, strlen(hex) + 1, &mem, &len) == -EINVAL);
512 assert_se(unhexmem(hex_invalid, strlen(hex_invalid), &mem, &len) == -EINVAL);
513
514 assert_se((hex2 = hexmem(mem, len)));
515
516 free(mem);
517
518 assert_se(memcmp(hex, hex2, strlen(hex)) == 0);
519
520 free(hex2);
521
522 assert_se(unhexmem(hex, strlen(hex) - 1, &mem, &len) == 0);
523 assert_se((hex2 = hexmem(mem, len)));
524 assert_se(memcmp(hex, hex2, strlen(hex) - 1) == 0);
525}
526
919a7f5f
TG
527/* https://tools.ietf.org/html/rfc4648#section-10 */
528static void test_base32hexmem(void) {
529 char *b32;
530
531 b32 = base32hexmem("", strlen(""), true);
532 assert_se(b32);
533 assert_se(streq(b32, ""));
534 free(b32);
535
536 b32 = base32hexmem("f", strlen("f"), true);
537 assert_se(b32);
538 assert_se(streq(b32, "CO======"));
539 free(b32);
540
541 b32 = base32hexmem("fo", strlen("fo"), true);
542 assert_se(b32);
543 assert_se(streq(b32, "CPNG===="));
544 free(b32);
545
546 b32 = base32hexmem("foo", strlen("foo"), true);
547 assert_se(b32);
548 assert_se(streq(b32, "CPNMU==="));
549 free(b32);
550
551 b32 = base32hexmem("foob", strlen("foob"), true);
552 assert_se(b32);
553 assert_se(streq(b32, "CPNMUOG="));
554 free(b32);
555
556 b32 = base32hexmem("fooba", strlen("fooba"), true);
557 assert_se(b32);
558 assert_se(streq(b32, "CPNMUOJ1"));
559 free(b32);
560
561 b32 = base32hexmem("foobar", strlen("foobar"), true);
562 assert_se(b32);
563 assert_se(streq(b32, "CPNMUOJ1E8======"));
564 free(b32);
565
566 b32 = base32hexmem("", strlen(""), false);
567 assert_se(b32);
568 assert_se(streq(b32, ""));
569 free(b32);
570
571 b32 = base32hexmem("f", strlen("f"), false);
572 assert_se(b32);
573 assert_se(streq(b32, "CO"));
574 free(b32);
575
576 b32 = base32hexmem("fo", strlen("fo"), false);
577 assert_se(b32);
578 assert_se(streq(b32, "CPNG"));
579 free(b32);
580
581 b32 = base32hexmem("foo", strlen("foo"), false);
582 assert_se(b32);
583 assert_se(streq(b32, "CPNMU"));
584 free(b32);
585
586 b32 = base32hexmem("foob", strlen("foob"), false);
587 assert_se(b32);
588 assert_se(streq(b32, "CPNMUOG"));
589 free(b32);
590
591 b32 = base32hexmem("fooba", strlen("fooba"), false);
592 assert_se(b32);
593 assert_se(streq(b32, "CPNMUOJ1"));
594 free(b32);
595
596 b32 = base32hexmem("foobar", strlen("foobar"), false);
597 assert_se(b32);
598 assert_se(streq(b32, "CPNMUOJ1E8"));
599 free(b32);
600}
601
602static void test_unbase32hexmem(void) {
603 void *mem;
604 size_t len;
605
606 assert_se(unbase32hexmem("", strlen(""), true, &mem, &len) == 0);
607 assert_se(streq(strndupa(mem, len), ""));
608 free(mem);
609
610 assert_se(unbase32hexmem("CO======", strlen("CO======"), true, &mem, &len) == 0);
611 assert_se(streq(strndupa(mem, len), "f"));
612 free(mem);
613
614 assert_se(unbase32hexmem("CPNG====", strlen("CPNG===="), true, &mem, &len) == 0);
615 assert_se(streq(strndupa(mem, len), "fo"));
616 free(mem);
617
618 assert_se(unbase32hexmem("CPNMU===", strlen("CPNMU==="), true, &mem, &len) == 0);
619 assert_se(streq(strndupa(mem, len), "foo"));
620 free(mem);
621
622 assert_se(unbase32hexmem("CPNMUOG=", strlen("CPNMUOG="), true, &mem, &len) == 0);
623 assert_se(streq(strndupa(mem, len), "foob"));
624 free(mem);
625
626 assert_se(unbase32hexmem("CPNMUOJ1", strlen("CPNMUOJ1"), true, &mem, &len) == 0);
627 assert_se(streq(strndupa(mem, len), "fooba"));
628 free(mem);
629
630 assert_se(unbase32hexmem("CPNMUOJ1E8======", strlen("CPNMUOJ1E8======"), true, &mem, &len) == 0);
631 assert_se(streq(strndupa(mem, len), "foobar"));
632 free(mem);
633
634 assert_se(unbase32hexmem("A", strlen("A"), true, &mem, &len) == -EINVAL);
635 assert_se(unbase32hexmem("A=======", strlen("A======="), true, &mem, &len) == -EINVAL);
636 assert_se(unbase32hexmem("AAA=====", strlen("AAA====="), true, &mem, &len) == -EINVAL);
637 assert_se(unbase32hexmem("AAAAAA==", strlen("AAAAAA=="), true, &mem, &len) == -EINVAL);
638 assert_se(unbase32hexmem("AB======", strlen("AB======"), true, &mem, &len) == -EINVAL);
639 assert_se(unbase32hexmem("AAAB====", strlen("AAAB===="), true, &mem, &len) == -EINVAL);
640 assert_se(unbase32hexmem("AAAAB===", strlen("AAAAB==="), true, &mem, &len) == -EINVAL);
641 assert_se(unbase32hexmem("AAAAAAB=", strlen("AAAAAAB="), true, &mem, &len) == -EINVAL);
642
ff9265d0
DM
643 assert_se(unbase32hexmem("XPNMUOJ1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
644 assert_se(unbase32hexmem("CXNMUOJ1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
645 assert_se(unbase32hexmem("CPXMUOJ1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
646 assert_se(unbase32hexmem("CPNXUOJ1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
647 assert_se(unbase32hexmem("CPNMXOJ1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
648 assert_se(unbase32hexmem("CPNMUXJ1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
649 assert_se(unbase32hexmem("CPNMUOX1", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
650 assert_se(unbase32hexmem("CPNMUOJX", strlen("CPNMUOJ1"), true, &mem, &len) == -EINVAL);
651
919a7f5f
TG
652 assert_se(unbase32hexmem("", strlen(""), false, &mem, &len) == 0);
653 assert_se(streq(strndupa(mem, len), ""));
654 free(mem);
655
656 assert_se(unbase32hexmem("CO", strlen("CO"), false, &mem, &len) == 0);
657 assert_se(streq(strndupa(mem, len), "f"));
658 free(mem);
659
660 assert_se(unbase32hexmem("CPNG", strlen("CPNG"), false, &mem, &len) == 0);
661 assert_se(streq(strndupa(mem, len), "fo"));
662 free(mem);
663
664 assert_se(unbase32hexmem("CPNMU", strlen("CPNMU"), false, &mem, &len) == 0);
665 assert_se(streq(strndupa(mem, len), "foo"));
666 free(mem);
667
668 assert_se(unbase32hexmem("CPNMUOG", strlen("CPNMUOG"), false, &mem, &len) == 0);
669 assert_se(streq(strndupa(mem, len), "foob"));
670 free(mem);
671
672 assert_se(unbase32hexmem("CPNMUOJ1", strlen("CPNMUOJ1"), false, &mem, &len) == 0);
673 assert_se(streq(strndupa(mem, len), "fooba"));
674 free(mem);
675
676 assert_se(unbase32hexmem("CPNMUOJ1E8", strlen("CPNMUOJ1E8"), false, &mem, &len) == 0);
677 assert_se(streq(strndupa(mem, len), "foobar"));
678 free(mem);
679
680 assert_se(unbase32hexmem("CPNMUOG=", strlen("CPNMUOG="), false, &mem, &len) == -EINVAL);
681 assert_se(unbase32hexmem("CPNMUOJ1E8======", strlen("CPNMUOJ1E8======"), false, &mem, &len) == -EINVAL);
682 assert_se(unbase32hexmem("A", strlen("A"), false, &mem, &len) == -EINVAL);
683 assert_se(unbase32hexmem("A", strlen("A"), false, &mem, &len) == -EINVAL);
684 assert_se(unbase32hexmem("AAA", strlen("AAA"), false, &mem, &len) == -EINVAL);
685 assert_se(unbase32hexmem("AAAAAA", strlen("AAAAAA"), false, &mem, &len) == -EINVAL);
686 assert_se(unbase32hexmem("AB", strlen("AB"), false, &mem, &len) == -EINVAL);
687 assert_se(unbase32hexmem("AAAB", strlen("AAAB"), false, &mem, &len) == -EINVAL);
688 assert_se(unbase32hexmem("AAAAB", strlen("AAAAB"), false, &mem, &len) == -EINVAL);
689 assert_se(unbase32hexmem("AAAAAAB", strlen("AAAAAAB"), false, &mem, &len) == -EINVAL);
690}
691
13a5d76b
TG
692/* https://tools.ietf.org/html/rfc4648#section-10 */
693static void test_base64mem(void) {
694 char *b64;
695
696 b64 = base64mem("", strlen(""));
697 assert_se(b64);
698 assert_se(streq(b64, ""));
699 free(b64);
700
701 b64 = base64mem("f", strlen("f"));
702 assert_se(b64);
703 assert_se(streq(b64, "Zg=="));
704 free(b64);
705
706 b64 = base64mem("fo", strlen("fo"));
707 assert_se(b64);
708 assert_se(streq(b64, "Zm8="));
709 free(b64);
710
711 b64 = base64mem("foo", strlen("foo"));
712 assert_se(b64);
713 assert_se(streq(b64, "Zm9v"));
714 free(b64);
715
716 b64 = base64mem("foob", strlen("foob"));
717 assert_se(b64);
718 assert_se(streq(b64, "Zm9vYg=="));
719 free(b64);
720
721 b64 = base64mem("fooba", strlen("fooba"));
722 assert_se(b64);
723 assert_se(streq(b64, "Zm9vYmE="));
724 free(b64);
725
726 b64 = base64mem("foobar", strlen("foobar"));
727 assert_se(b64);
728 assert_se(streq(b64, "Zm9vYmFy"));
729 free(b64);
730}
731
732static void test_unbase64mem(void) {
733 void *mem;
734 size_t len;
735
736 assert_se(unbase64mem("", strlen(""), &mem, &len) == 0);
737 assert_se(streq(strndupa(mem, len), ""));
738 free(mem);
739
740 assert_se(unbase64mem("Zg==", strlen("Zg=="), &mem, &len) == 0);
741 assert_se(streq(strndupa(mem, len), "f"));
742 free(mem);
743
744 assert_se(unbase64mem("Zm8=", strlen("Zm8="), &mem, &len) == 0);
745 assert_se(streq(strndupa(mem, len), "fo"));
746 free(mem);
747
748 assert_se(unbase64mem("Zm9v", strlen("Zm9v"), &mem, &len) == 0);
749 assert_se(streq(strndupa(mem, len), "foo"));
750 free(mem);
751
752 assert_se(unbase64mem("Zm9vYg==", strlen("Zm9vYg=="), &mem, &len) == 0);
753 assert_se(streq(strndupa(mem, len), "foob"));
754 free(mem);
755
756 assert_se(unbase64mem("Zm9vYmE=", strlen("Zm9vYmE="), &mem, &len) == 0);
757 assert_se(streq(strndupa(mem, len), "fooba"));
758 free(mem);
759
760 assert_se(unbase64mem("Zm9vYmFy", strlen("Zm9vYmFy"), &mem, &len) == 0);
761 assert_se(streq(strndupa(mem, len), "foobar"));
762 free(mem);
763
764 assert_se(unbase64mem("A", strlen("A"), &mem, &len) == -EINVAL);
765 assert_se(unbase64mem("A====", strlen("A===="), &mem, &len) == -EINVAL);
766 assert_se(unbase64mem("AAB==", strlen("AAB=="), &mem, &len) == -EINVAL);
767 assert_se(unbase64mem("AAAB=", strlen("AAAB="), &mem, &len) == -EINVAL);
768}
769
b4ecc959
TA
770static void test_cescape(void) {
771 _cleanup_free_ char *escaped;
e0a33e7b
LP
772
773 assert_se(escaped = cescape("abc\\\"\b\f\n\r\t\v\a\003\177\234\313"));
927be00c 774 assert_se(streq(escaped, "abc\\\\\\\"\\b\\f\\n\\r\\t\\v\\a\\003\\177\\234\\313"));
b4ecc959
TA
775}
776
777static void test_cunescape(void) {
778 _cleanup_free_ char *unescaped;
e0a33e7b 779
527b7a42
LP
780 assert_se(cunescape("abc\\\\\\\"\\b\\f\\a\\n\\r\\t\\v\\003\\177\\234\\313\\000\\x00", 0, &unescaped) < 0);
781 assert_se(cunescape("abc\\\\\\\"\\b\\f\\a\\n\\r\\t\\v\\003\\177\\234\\313\\000\\x00", UNESCAPE_RELAX, &unescaped) >= 0);
f3ee6297 782 assert_se(streq_ptr(unescaped, "abc\\\"\b\f\a\n\r\t\v\003\177\234\313\\000\\x00"));
97b11eed 783 unescaped = mfree(unescaped);
7f769619
ZJS
784
785 /* incomplete sequences */
527b7a42
LP
786 assert_se(cunescape("\\x0", 0, &unescaped) < 0);
787 assert_se(cunescape("\\x0", UNESCAPE_RELAX, &unescaped) >= 0);
7f769619 788 assert_se(streq_ptr(unescaped, "\\x0"));
97b11eed 789 unescaped = mfree(unescaped);
7f769619 790
527b7a42
LP
791 assert_se(cunescape("\\x", 0, &unescaped) < 0);
792 assert_se(cunescape("\\x", UNESCAPE_RELAX, &unescaped) >= 0);
7f769619 793 assert_se(streq_ptr(unescaped, "\\x"));
97b11eed 794 unescaped = mfree(unescaped);
7f769619 795
527b7a42
LP
796 assert_se(cunescape("\\", 0, &unescaped) < 0);
797 assert_se(cunescape("\\", UNESCAPE_RELAX, &unescaped) >= 0);
7f769619 798 assert_se(streq_ptr(unescaped, "\\"));
97b11eed 799 unescaped = mfree(unescaped);
7f769619 800
527b7a42
LP
801 assert_se(cunescape("\\11", 0, &unescaped) < 0);
802 assert_se(cunescape("\\11", UNESCAPE_RELAX, &unescaped) >= 0);
7f769619 803 assert_se(streq_ptr(unescaped, "\\11"));
97b11eed 804 unescaped = mfree(unescaped);
7f769619 805
527b7a42
LP
806 assert_se(cunescape("\\1", 0, &unescaped) < 0);
807 assert_se(cunescape("\\1", UNESCAPE_RELAX, &unescaped) >= 0);
7f769619 808 assert_se(streq_ptr(unescaped, "\\1"));
97b11eed 809 unescaped = mfree(unescaped);
f3ee6297
LP
810
811 assert_se(cunescape("\\u0000", 0, &unescaped) < 0);
812 assert_se(cunescape("\\u00DF\\U000000df\\u03a0\\U00000041", UNESCAPE_RELAX, &unescaped) >= 0);
813 assert_se(streq_ptr(unescaped, "ßßΠA"));
97b11eed 814 unescaped = mfree(unescaped);
3b51f8dd
DM
815
816 assert_se(cunescape("\\073", 0, &unescaped) >= 0);
817 assert_se(streq_ptr(unescaped, ";"));
b4ecc959
TA
818}
819
1ef04f0b 820static void test_foreach_word(void) {
a2a5291b 821 const char *word, *state;
1ef04f0b
TA
822 size_t l;
823 int i = 0;
824 const char test[] = "test abc d\te f ";
825 const char * const expected[] = {
826 "test",
827 "abc",
828 "d",
829 "e",
830 "f",
831 "",
832 NULL
833 };
834
a2a5291b
ZJS
835 FOREACH_WORD(word, l, test, state)
836 assert_se(strneq(expected[i++], word, l));
1ef04f0b
TA
837}
838
ba774317 839static void check(const char *test, char** expected, bool trailing) {
a2a5291b 840 const char *word, *state;
539ad707 841 size_t l;
1ef04f0b 842 int i = 0;
1ef04f0b 843
ba774317 844 printf("<<<%s>>>\n", test);
a2a5291b 845 FOREACH_WORD_QUOTED(word, l, test, state) {
1ef04f0b 846 _cleanup_free_ char *t = NULL;
539ad707 847
a2a5291b
ZJS
848 assert_se(t = strndup(word, l));
849 assert_se(strneq(expected[i++], word, l));
539ad707 850 printf("<%s>\n", t);
539ad707 851 }
ba774317 852 printf("<<<%s>>>\n", state);
e50221bf 853 assert_se(expected[i] == NULL);
ba774317
ZJS
854 assert_se(isempty(state) == !trailing);
855}
856
857static void test_foreach_word_quoted(void) {
858 check("test a b c 'd' e '' '' hhh '' '' \"a b c\"",
859 STRV_MAKE("test",
860 "a",
861 "b",
862 "c",
863 "d",
864 "e",
865 "",
866 "",
867 "hhh",
868 "",
869 "",
870 "a b c"),
871 false);
872
873 check("test \"xxx",
874 STRV_MAKE("test"),
875 true);
876
877 check("test\\",
878 STRV_MAKE_EMPTY,
879 true);
539ad707
TA
880}
881
0d585d82
TA
882static void test_memdup_multiply(void) {
883 int org[] = {1, 2, 3};
884 int *dup;
885
886 dup = (int*)memdup_multiply(org, sizeof(int), 3);
887
888 assert_se(dup);
889 assert_se(dup[0] == 1);
890 assert_se(dup[1] == 2);
891 assert_se(dup[2] == 3);
892 free(dup);
893}
894
144e51ec 895static void test_u64log2(void) {
bdf7026e
TA
896 assert_se(u64log2(0) == 0);
897 assert_se(u64log2(8) == 3);
898 assert_se(u64log2(9) == 3);
899 assert_se(u64log2(15) == 3);
900 assert_se(u64log2(16) == 4);
901 assert_se(u64log2(1024*1024) == 20);
902 assert_se(u64log2(1024*1024+5) == 20);
144e51ec
CR
903}
904
2a371001
ZJS
905static void test_protect_errno(void) {
906 errno = 12;
907 {
908 PROTECT_ERRNO;
909 errno = 11;
910 }
bdf7026e 911 assert_se(errno == 12);
2a371001
ZJS
912}
913
5556b5fe 914static void test_parse_size(void) {
59f448cf 915 uint64_t bytes;
b32ff512 916
5556b5fe 917 assert_se(parse_size("111", 1024, &bytes) == 0);
b32ff512
ZJS
918 assert_se(bytes == 111);
919
9480794b
ZJS
920 assert_se(parse_size("111.4", 1024, &bytes) == 0);
921 assert_se(bytes == 111);
922
5556b5fe 923 assert_se(parse_size(" 112 B", 1024, &bytes) == 0);
b32ff512
ZJS
924 assert_se(bytes == 112);
925
9480794b
ZJS
926 assert_se(parse_size(" 112.6 B", 1024, &bytes) == 0);
927 assert_se(bytes == 112);
928
929 assert_se(parse_size("3.5 K", 1024, &bytes) == 0);
930 assert_se(bytes == 3*1024 + 512);
931
932 assert_se(parse_size("3. K", 1024, &bytes) == 0);
933 assert_se(bytes == 3*1024);
934
935 assert_se(parse_size("3.0 K", 1024, &bytes) == 0);
b32ff512
ZJS
936 assert_se(bytes == 3*1024);
937
840292be 938 assert_se(parse_size("3. 0 K", 1024, &bytes) == -EINVAL);
b32ff512 939
9480794b
ZJS
940 assert_se(parse_size(" 4 M 11.5K", 1024, &bytes) == 0);
941 assert_se(bytes == 4*1024*1024 + 11 * 1024 + 512);
942
840292be
ZJS
943 assert_se(parse_size("3B3.5G", 1024, &bytes) == -EINVAL);
944
945 assert_se(parse_size("3.5G3B", 1024, &bytes) == 0);
9480794b 946 assert_se(bytes == 3ULL*1024*1024*1024 + 512*1024*1024 + 3);
b32ff512 947
840292be
ZJS
948 assert_se(parse_size("3.5G 4B", 1024, &bytes) == 0);
949 assert_se(bytes == 3ULL*1024*1024*1024 + 512*1024*1024 + 4);
950
951 assert_se(parse_size("3B3G4T", 1024, &bytes) == -EINVAL);
952
953 assert_se(parse_size("4T3G3B", 1024, &bytes) == 0);
954 assert_se(bytes == (4ULL*1024 + 3)*1024*1024*1024 + 3);
955
956 assert_se(parse_size(" 4 T 3 G 3 B", 1024, &bytes) == 0);
b32ff512
ZJS
957 assert_se(bytes == (4ULL*1024 + 3)*1024*1024*1024 + 3);
958
5556b5fe 959 assert_se(parse_size("12P", 1024, &bytes) == 0);
b32ff512
ZJS
960 assert_se(bytes == 12ULL * 1024*1024*1024*1024*1024);
961
840292be
ZJS
962 assert_se(parse_size("12P12P", 1024, &bytes) == -EINVAL);
963
5556b5fe 964 assert_se(parse_size("3E 2P", 1024, &bytes) == 0);
b32ff512
ZJS
965 assert_se(bytes == (3 * 1024 + 2ULL) * 1024*1024*1024*1024*1024);
966
5556b5fe 967 assert_se(parse_size("12X", 1024, &bytes) == -EINVAL);
b32ff512 968
9480794b
ZJS
969 assert_se(parse_size("12.5X", 1024, &bytes) == -EINVAL);
970
971 assert_se(parse_size("12.5e3", 1024, &bytes) == -EINVAL);
972
5556b5fe
LP
973 assert_se(parse_size("1024E", 1024, &bytes) == -ERANGE);
974 assert_se(parse_size("-1", 1024, &bytes) == -ERANGE);
975 assert_se(parse_size("-1024E", 1024, &bytes) == -ERANGE);
b32ff512 976
5556b5fe 977 assert_se(parse_size("-1024P", 1024, &bytes) == -ERANGE);
b32ff512 978
5556b5fe 979 assert_se(parse_size("-10B 20K", 1024, &bytes) == -ERANGE);
b32ff512
ZJS
980}
981
5f05235f
FB
982static void test_parse_cpu_set(void) {
983 cpu_set_t *c = NULL;
984 int ncpus;
985 int cpu;
986
987 /* Simple range (from CPUAffinity example) */
765d143b 988 ncpus = parse_cpu_set_and_warn("1 2", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
989 assert_se(ncpus >= 1024);
990 assert_se(CPU_ISSET_S(1, CPU_ALLOC_SIZE(ncpus), c));
991 assert_se(CPU_ISSET_S(2, CPU_ALLOC_SIZE(ncpus), c));
992 assert_se(CPU_COUNT_S(CPU_ALLOC_SIZE(ncpus), c) == 2);
993 c = mfree(c);
994
995 /* A more interesting range */
765d143b 996 ncpus = parse_cpu_set_and_warn("0 1 2 3 8 9 10 11", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
997 assert_se(ncpus >= 1024);
998 assert_se(CPU_COUNT_S(CPU_ALLOC_SIZE(ncpus), c) == 8);
999 for (cpu = 0; cpu < 4; cpu++)
1000 assert_se(CPU_ISSET_S(cpu, CPU_ALLOC_SIZE(ncpus), c));
1001 for (cpu = 8; cpu < 12; cpu++)
1002 assert_se(CPU_ISSET_S(cpu, CPU_ALLOC_SIZE(ncpus), c));
1003 c = mfree(c);
1004
1005 /* Quoted strings */
765d143b 1006 ncpus = parse_cpu_set_and_warn("8 '9' 10 \"11\"", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
1007 assert_se(ncpus >= 1024);
1008 assert_se(CPU_COUNT_S(CPU_ALLOC_SIZE(ncpus), c) == 4);
1009 for (cpu = 8; cpu < 12; cpu++)
1010 assert_se(CPU_ISSET_S(cpu, CPU_ALLOC_SIZE(ncpus), c));
1011 c = mfree(c);
1012
1013 /* Use commas as separators */
765d143b 1014 ncpus = parse_cpu_set_and_warn("0,1,2,3 8,9,10,11", &c, NULL, "fake", 1, "CPUAffinity");
4fc66acb
FB
1015 assert_se(ncpus >= 1024);
1016 assert_se(CPU_COUNT_S(CPU_ALLOC_SIZE(ncpus), c) == 8);
1017 for (cpu = 0; cpu < 4; cpu++)
1018 assert_se(CPU_ISSET_S(cpu, CPU_ALLOC_SIZE(ncpus), c));
1019 for (cpu = 8; cpu < 12; cpu++)
1020 assert_se(CPU_ISSET_S(cpu, CPU_ALLOC_SIZE(ncpus), c));
1021 c = mfree(c);
1022
1023 /* Commas with spaces (and trailing comma, space) */
1024 ncpus = parse_cpu_set_and_warn("0, 1, 2, 3, 4, 5, 6, 7, ", &c, NULL, "fake", 1, "CPUAffinity");
1025 assert_se(ncpus >= 1024);
1026 assert_se(CPU_COUNT_S(CPU_ALLOC_SIZE(ncpus), c) == 8);
1027 for (cpu = 0; cpu < 8; cpu++)
1028 assert_se(CPU_ISSET_S(cpu, CPU_ALLOC_SIZE(ncpus), c));
1029 c = mfree(c);
5f05235f
FB
1030
1031 /* Ranges */
765d143b 1032 ncpus = parse_cpu_set_and_warn("0-3,8-11", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
1033 assert_se(ncpus < 0);
1034 assert_se(!c);
1035
1036 /* Garbage */
765d143b 1037 ncpus = parse_cpu_set_and_warn("0 1 2 3 garbage", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
1038 assert_se(ncpus < 0);
1039 assert_se(!c);
1040
1041 /* Empty string */
1042 c = NULL;
765d143b 1043 ncpus = parse_cpu_set_and_warn("", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
1044 assert_se(ncpus == 0); /* empty string returns 0 */
1045 assert_se(!c);
1046
1047 /* Runnaway quoted string */
765d143b 1048 ncpus = parse_cpu_set_and_warn("0 1 2 3 \"4 5 6 7 ", &c, NULL, "fake", 1, "CPUAffinity");
5f05235f
FB
1049 assert_se(ncpus < 0);
1050 assert_se(!c);
1051}
1052
59f448cf
LP
1053static void test_config_parse_iec_uint64(void) {
1054 uint64_t offset = 0;
1055 assert_se(config_parse_iec_uint64(NULL, "/this/file", 11, "Section", 22, "Size", 0, "4M", &offset, NULL) == 0);
9480794b
ZJS
1056 assert_se(offset == 4 * 1024 * 1024);
1057
59f448cf 1058 assert_se(config_parse_iec_uint64(NULL, "/this/file", 11, "Section", 22, "Size", 0, "4.5M", &offset, NULL) == 0);
9480794b
ZJS
1059}
1060
b4ecc959
TA
1061static void test_strextend(void) {
1062 _cleanup_free_ char *str = strdup("0123");
1063 strextend(&str, "456", "78", "9", NULL);
1064 assert_se(streq(str, "0123456789"));
1065}
1066
1067static void test_strrep(void) {
1068 _cleanup_free_ char *one, *three, *zero;
1069 one = strrep("waldo", 1);
1070 three = strrep("waldo", 3);
1071 zero = strrep("waldo", 0);
1072
1073 assert_se(streq(one, "waldo"));
1074 assert_se(streq(three, "waldowaldowaldo"));
1075 assert_se(streq(zero, ""));
1076}
1077
d4ac85c6
LP
1078static void test_split_pair(void) {
1079 _cleanup_free_ char *a = NULL, *b = NULL;
1080
1081 assert_se(split_pair("", "", &a, &b) == -EINVAL);
1082 assert_se(split_pair("foo=bar", "", &a, &b) == -EINVAL);
1083 assert_se(split_pair("", "=", &a, &b) == -EINVAL);
1084 assert_se(split_pair("foo=bar", "=", &a, &b) >= 0);
1085 assert_se(streq(a, "foo"));
1086 assert_se(streq(b, "bar"));
1087 free(a);
1088 free(b);
1089 assert_se(split_pair("==", "==", &a, &b) >= 0);
1090 assert_se(streq(a, ""));
1091 assert_se(streq(b, ""));
1092 free(a);
1093 free(b);
1094
1095 assert_se(split_pair("===", "==", &a, &b) >= 0);
1096 assert_se(streq(a, ""));
1097 assert_se(streq(b, "="));
1098}
1099
22f5f628
DR
1100static void test_fstab_node_to_udev_node(void) {
1101 char *n;
1102
1103 n = fstab_node_to_udev_node("LABEL=applé/jack");
1104 puts(n);
1105 assert_se(streq(n, "/dev/disk/by-label/applé\\x2fjack"));
1106 free(n);
1107
1108 n = fstab_node_to_udev_node("PARTLABEL=pinkié pie");
1109 puts(n);
1110 assert_se(streq(n, "/dev/disk/by-partlabel/pinkié\\x20pie"));
1111 free(n);
1112
1113 n = fstab_node_to_udev_node("UUID=037b9d94-148e-4ee4-8d38-67bfe15bb535");
1114 puts(n);
1115 assert_se(streq(n, "/dev/disk/by-uuid/037b9d94-148e-4ee4-8d38-67bfe15bb535"));
1116 free(n);
1117
1118 n = fstab_node_to_udev_node("PARTUUID=037b9d94-148e-4ee4-8d38-67bfe15bb535");
1119 puts(n);
1120 assert_se(streq(n, "/dev/disk/by-partuuid/037b9d94-148e-4ee4-8d38-67bfe15bb535"));
1121 free(n);
1122
22f5f628
DR
1123 n = fstab_node_to_udev_node("PONIES=awesome");
1124 puts(n);
1125 assert_se(streq(n, "PONIES=awesome"));
1126 free(n);
1127
1128 n = fstab_node_to_udev_node("/dev/xda1");
1129 puts(n);
1130 assert_se(streq(n, "/dev/xda1"));
1131 free(n);
1132}
1133
893fa014
ZJS
1134static void test_get_files_in_directory(void) {
1135 _cleanup_strv_free_ char **l = NULL, **t = NULL;
1136
1137 assert_se(get_files_in_directory("/tmp", &l) >= 0);
510b857f 1138 assert_se(get_files_in_directory(".", &t) >= 0);
893fa014
ZJS
1139 assert_se(get_files_in_directory(".", NULL) >= 0);
1140}
1141
cabb7806
LP
1142static void test_in_set(void) {
1143 assert_se(IN_SET(1, 1));
1144 assert_se(IN_SET(1, 1, 2, 3, 4));
1145 assert_se(IN_SET(2, 1, 2, 3, 4));
1146 assert_se(IN_SET(3, 1, 2, 3, 4));
1147 assert_se(IN_SET(4, 1, 2, 3, 4));
1148 assert_se(!IN_SET(0, 1));
1149 assert_se(!IN_SET(0, 1, 2, 3, 4));
1150}
1151
87b02843
ZJS
1152static void test_writing_tmpfile(void) {
1153 char name[] = "/tmp/test-systemd_writing_tmpfile.XXXXXX";
39883f62 1154 _cleanup_free_ char *contents = NULL;
65b3903f
ZJS
1155 size_t size;
1156 int fd, r;
65b3903f 1157 struct iovec iov[3];
39883f62 1158
65b3903f
ZJS
1159 IOVEC_SET_STRING(iov[0], "abc\n");
1160 IOVEC_SET_STRING(iov[1], ALPHANUMERICAL "\n");
1161 IOVEC_SET_STRING(iov[2], "");
1162
2d5bdf5b 1163 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
87b02843 1164 printf("tmpfile: %s", name);
65b3903f 1165
87b02843 1166 r = writev(fd, iov, 3);
bdf7026e 1167 assert_se(r >= 0);
65b3903f
ZJS
1168
1169 r = read_full_file(name, &contents, &size);
bdf7026e 1170 assert_se(r == 0);
65b3903f 1171 printf("contents: %s", contents);
bdf7026e 1172 assert_se(streq(contents, "abc\n" ALPHANUMERICAL "\n"));
40edd236
RC
1173
1174 unlink(name);
65b3903f
ZJS
1175}
1176
29bfbcd6
LP
1177static void test_hexdump(void) {
1178 uint8_t data[146];
1179 unsigned i;
1180
1181 hexdump(stdout, NULL, 0);
1182 hexdump(stdout, "", 0);
1183 hexdump(stdout, "", 1);
1184 hexdump(stdout, "x", 1);
1185 hexdump(stdout, "x", 2);
1186 hexdump(stdout, "foobar", 7);
1187 hexdump(stdout, "f\nobar", 7);
1188 hexdump(stdout, "xxxxxxxxxxxxxxxxxxxxyz", 23);
1189
1190 for (i = 0; i < ELEMENTSOF(data); i++)
1191 data[i] = i*2;
1192
1193 hexdump(stdout, data, sizeof(data));
1194}
1195
8fe90522
ZJS
1196static void test_log2i(void) {
1197 assert_se(log2i(1) == 0);
1198 assert_se(log2i(2) == 1);
1199 assert_se(log2i(3) == 1);
1200 assert_se(log2i(4) == 2);
1201 assert_se(log2i(32) == 5);
1202 assert_se(log2i(33) == 5);
1203 assert_se(log2i(63) == 5);
1204 assert_se(log2i(INT_MAX) == sizeof(int)*8-2);
1205}
1206
c4a7b2c5
LP
1207static void test_foreach_string(void) {
1208 const char * const t[] = {
1209 "foo",
1210 "bar",
1211 "waldo",
1212 NULL
1213 };
1214 const char *x;
1215 unsigned i = 0;
1216
1217 FOREACH_STRING(x, "foo", "bar", "waldo")
1218 assert_se(streq_ptr(t[i++], x));
1219
1220 assert_se(i == 3);
1221
1222 FOREACH_STRING(x, "zzz")
1223 assert_se(streq(x, "zzz"));
1224}
1225
ae6c3cc0 1226static void test_filename_is_valid(void) {
927be00c
RC
1227 char foo[FILENAME_MAX+2];
1228 int i;
1229
ae6c3cc0
LP
1230 assert_se(!filename_is_valid(""));
1231 assert_se(!filename_is_valid("/bar/foo"));
1232 assert_se(!filename_is_valid("/"));
1233 assert_se(!filename_is_valid("."));
1234 assert_se(!filename_is_valid(".."));
927be00c
RC
1235
1236 for (i=0; i<FILENAME_MAX+1; i++)
1237 foo[i] = 'a';
1238 foo[FILENAME_MAX+1] = '\0';
1239
ae6c3cc0 1240 assert_se(!filename_is_valid(foo));
927be00c 1241
ae6c3cc0
LP
1242 assert_se(filename_is_valid("foo_bar-333"));
1243 assert_se(filename_is_valid("o.o"));
927be00c
RC
1244}
1245
1cb1767a
ZJS
1246static void test_string_has_cc(void) {
1247 assert_se(string_has_cc("abc\1", NULL));
1248 assert_se(string_has_cc("abc\x7f", NULL));
1249 assert_se(string_has_cc("abc\x7f", NULL));
1250 assert_se(string_has_cc("abc\t\x7f", "\t"));
1251 assert_se(string_has_cc("abc\t\x7f", "\t"));
1252 assert_se(string_has_cc("\x7f", "\t"));
1253 assert_se(string_has_cc("\x7f", "\t\a"));
1254
1255 assert_se(!string_has_cc("abc\t\t", "\t"));
1256 assert_se(!string_has_cc("abc\t\t\a", "\t\a"));
1257 assert_se(!string_has_cc("a\ab\tc", "\t\a"));
1258}
1259
927be00c
RC
1260static void test_ascii_strlower(void) {
1261 char a[] = "AabBcC Jk Ii Od LKJJJ kkd LK";
1262 assert_se(streq(ascii_strlower(a), "aabbcc jk ii od lkjjj kkd lk"));
1263}
1264
1265static void test_files_same(void) {
1266 _cleanup_close_ int fd = -1;
1267 char name[] = "/tmp/test-files_same.XXXXXX";
1268 char name_alias[] = "/tmp/test-files_same.alias";
1269
1270 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1271 assert_se(fd >= 0);
1272 assert_se(symlink(name, name_alias) >= 0);
1273
1274 assert_se(files_same(name, name));
1275 assert_se(files_same(name, name_alias));
1276
1277 unlink(name);
1278 unlink(name_alias);
1279}
1280
1281static void test_is_valid_documentation_url(void) {
a2e03378
LP
1282 assert_se(documentation_url_is_valid("http://www.freedesktop.org/wiki/Software/systemd"));
1283 assert_se(documentation_url_is_valid("https://www.kernel.org/doc/Documentation/binfmt_misc.txt"));
1284 assert_se(documentation_url_is_valid("file:/foo/foo"));
1285 assert_se(documentation_url_is_valid("man:systemd.special(7)"));
1286 assert_se(documentation_url_is_valid("info:bar"));
1287
1288 assert_se(!documentation_url_is_valid("foo:"));
1289 assert_se(!documentation_url_is_valid("info:"));
1290 assert_se(!documentation_url_is_valid(""));
927be00c
RC
1291}
1292
1293static void test_file_in_same_dir(void) {
eee84633
DH
1294 char *t;
1295
1296 t = file_in_same_dir("/", "a");
1297 assert_se(streq(t, "/a"));
1298 free(t);
1299
1300 t = file_in_same_dir("/", "/a");
1301 assert_se(streq(t, "/a"));
1302 free(t);
1303
1304 t = file_in_same_dir("", "a");
1305 assert_se(streq(t, "a"));
1306 free(t);
1307
1308 t = file_in_same_dir("a/", "a");
1309 assert_se(streq(t, "a/a"));
1310 free(t);
1311
1312 t = file_in_same_dir("bar/foo", "bar");
1313 assert_se(streq(t, "bar/bar"));
1314 free(t);
927be00c
RC
1315}
1316
1317static void test_endswith(void) {
1318 assert_se(endswith("foobar", "bar"));
1319 assert_se(endswith("foobar", ""));
1320 assert_se(endswith("foobar", "foobar"));
1321 assert_se(endswith("", ""));
1322
1323 assert_se(!endswith("foobar", "foo"));
1324 assert_se(!endswith("foobar", "foobarfoofoo"));
1325}
1326
ff9265d0
DM
1327static void test_endswith_no_case(void) {
1328 assert_se(endswith_no_case("fooBAR", "bar"));
1329 assert_se(endswith_no_case("foobar", ""));
1330 assert_se(endswith_no_case("foobar", "FOOBAR"));
1331 assert_se(endswith_no_case("", ""));
1332
1333 assert_se(!endswith_no_case("foobar", "FOO"));
1334 assert_se(!endswith_no_case("foobar", "FOOBARFOOFOO"));
1335}
1336
927be00c
RC
1337static void test_close_nointr(void) {
1338 char name[] = "/tmp/test-test-close_nointr.XXXXXX";
1339 int fd;
1340
1341 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1342 assert_se(fd >= 0);
1343 assert_se(close_nointr(fd) >= 0);
1344 assert_se(close_nointr(fd) < 0);
1345
1346 unlink(name);
1347}
1348
1349
1350static void test_unlink_noerrno(void) {
1351 char name[] = "/tmp/test-close_nointr.XXXXXX";
1352 int fd;
1353
1354 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1355 assert_se(fd >= 0);
1356 assert_se(close_nointr(fd) >= 0);
1357
1358 {
1359 PROTECT_ERRNO;
1360 errno = -42;
1361 assert_se(unlink_noerrno(name) >= 0);
1362 assert_se(errno == -42);
1363 assert_se(unlink_noerrno(name) < 0);
1364 assert_se(errno == -42);
1365 }
1366}
1367
1368static void test_readlink_and_make_absolute(void) {
1369 char tempdir[] = "/tmp/test-readlink_and_make_absolute";
1370 char name[] = "/tmp/test-readlink_and_make_absolute/original";
1371 char name2[] = "test-readlink_and_make_absolute/original";
1372 char name_alias[] = "/tmp/test-readlink_and_make_absolute-alias";
1373 char *r = NULL;
1374
684fc892 1375 assert_se(mkdir_safe(tempdir, 0755, getuid(), getgid()) >= 0);
927be00c
RC
1376 assert_se(touch(name) >= 0);
1377
1378 assert_se(symlink(name, name_alias) >= 0);
1379 assert_se(readlink_and_make_absolute(name_alias, &r) >= 0);
1380 assert_se(streq(r, name));
1381 free(r);
1382 assert_se(unlink(name_alias) >= 0);
1383
1384 assert_se(chdir(tempdir) >= 0);
1385 assert_se(symlink(name2, name_alias) >= 0);
1386 assert_se(readlink_and_make_absolute(name_alias, &r) >= 0);
1387 assert_se(streq(r, name));
1388 free(r);
1389 assert_se(unlink(name_alias) >= 0);
1390
c6878637 1391 assert_se(rm_rf(tempdir, REMOVE_ROOT|REMOVE_PHYSICAL) >= 0);
927be00c
RC
1392}
1393
927be00c
RC
1394static void test_ignore_signals(void) {
1395 assert_se(ignore_signals(SIGINT, -1) >= 0);
1396 assert_se(kill(getpid(), SIGINT) >= 0);
1397 assert_se(ignore_signals(SIGUSR1, SIGUSR2, SIGTERM, SIGPIPE, -1) >= 0);
1398 assert_se(kill(getpid(), SIGUSR1) >= 0);
1399 assert_se(kill(getpid(), SIGUSR2) >= 0);
1400 assert_se(kill(getpid(), SIGTERM) >= 0);
1401 assert_se(kill(getpid(), SIGPIPE) >= 0);
1402 assert_se(default_signals(SIGINT, SIGUSR1, SIGUSR2, SIGTERM, SIGPIPE, -1) >= 0);
1403}
1404
1405static void test_strshorten(void) {
1406 char s[] = "foobar";
1407
1408 assert_se(strlen(strshorten(s, 6)) == 6);
1409 assert_se(strlen(strshorten(s, 12)) == 6);
1410 assert_se(strlen(strshorten(s, 2)) == 2);
1411 assert_se(strlen(strshorten(s, 0)) == 0);
1412}
1413
63c372cb 1414static void test_strjoina(void) {
8085f163
DR
1415 char *actual;
1416
63c372cb 1417 actual = strjoina("", "foo", "bar");
8085f163
DR
1418 assert_se(streq(actual, "foobar"));
1419
63c372cb 1420 actual = strjoina("foo", "bar", "baz");
8085f163
DR
1421 assert_se(streq(actual, "foobarbaz"));
1422
63c372cb 1423 actual = strjoina("foo", "", "bar", "baz");
8085f163 1424 assert_se(streq(actual, "foobarbaz"));
63c372cb
LP
1425
1426 actual = strjoina("foo");
1427 assert_se(streq(actual, "foo"));
1428
1429 actual = strjoina(NULL);
1430 assert_se(streq(actual, ""));
1431
1432 actual = strjoina(NULL, "foo");
1433 assert_se(streq(actual, ""));
1434
1435 actual = strjoina("foo", NULL, "bar");
1436 assert_se(streq(actual, "foo"));
8085f163
DR
1437}
1438
8852362b
RC
1439static void test_is_symlink(void) {
1440 char name[] = "/tmp/test-is_symlink.XXXXXX";
1441 char name_link[] = "/tmp/test-is_symlink.link";
1442 _cleanup_close_ int fd = -1;
1443
1444 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1445 assert_se(fd >= 0);
1446 assert_se(symlink(name, name_link) >= 0);
1447
1448 assert_se(is_symlink(name) == 0);
1449 assert_se(is_symlink(name_link) == 1);
1450 assert_se(is_symlink("/a/file/which/does/not/exist/i/guess") < 0);
1451
1452
1453 unlink(name);
1454 unlink(name_link);
1455}
1456
8852362b
RC
1457static void test_search_and_fopen(void) {
1458 const char *dirs[] = {"/tmp/foo/bar", "/tmp", NULL};
1459 char name[] = "/tmp/test-search_and_fopen.XXXXXX";
1460 int fd = -1;
1461 int r;
1462 FILE *f;
1463
1464 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1465 assert_se(fd >= 0);
1466 close(fd);
1467
1468 r = search_and_fopen(basename(name), "r", NULL, dirs, &f);
1469 assert_se(r >= 0);
1470 fclose(f);
1471
1472 r = search_and_fopen(name, "r", NULL, dirs, &f);
1473 assert_se(r >= 0);
1474 fclose(f);
1475
1476 r = search_and_fopen(basename(name), "r", "/", dirs, &f);
1477 assert_se(r >= 0);
1478 fclose(f);
1479
1480 r = search_and_fopen("/a/file/which/does/not/exist/i/guess", "r", NULL, dirs, &f);
1481 assert_se(r < 0);
1482 r = search_and_fopen("afilewhichdoesnotexistiguess", "r", NULL, dirs, &f);
1483 assert_se(r < 0);
1484
1485 r = unlink(name);
1486 assert_se(r == 0);
1487
1488 r = search_and_fopen(basename(name), "r", NULL, dirs, &f);
1489 assert_se(r < 0);
1490}
1491
1492
1493static void test_search_and_fopen_nulstr(void) {
1494 const char dirs[] = "/tmp/foo/bar\0/tmp\0";
1495 char name[] = "/tmp/test-search_and_fopen.XXXXXX";
1496 int fd = -1;
1497 int r;
1498 FILE *f;
1499
1500 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1501 assert_se(fd >= 0);
1502 close(fd);
1503
1504 r = search_and_fopen_nulstr(basename(name), "r", NULL, dirs, &f);
1505 assert_se(r >= 0);
1506 fclose(f);
1507
1508 r = search_and_fopen_nulstr(name, "r", NULL, dirs, &f);
1509 assert_se(r >= 0);
1510 fclose(f);
1511
1512 r = search_and_fopen_nulstr("/a/file/which/does/not/exist/i/guess", "r", NULL, dirs, &f);
1513 assert_se(r < 0);
1514 r = search_and_fopen_nulstr("afilewhichdoesnotexistiguess", "r", NULL, dirs, &f);
1515 assert_se(r < 0);
1516
1517 r = unlink(name);
1518 assert_se(r == 0);
1519
1520 r = search_and_fopen_nulstr(basename(name), "r", NULL, dirs, &f);
1521 assert_se(r < 0);
1522}
1523
1524static void test_glob_exists(void) {
1525 char name[] = "/tmp/test-glob_exists.XXXXXX";
1526 int fd = -1;
1527 int r;
1528
1529 fd = mkostemp_safe(name, O_RDWR|O_CLOEXEC);
1530 assert_se(fd >= 0);
1531 close(fd);
1532
1533 r = glob_exists("/tmp/test-glob_exists*");
1534 assert_se(r == 1);
1535
1536 r = unlink(name);
1537 assert_se(r == 0);
1538 r = glob_exists("/tmp/test-glob_exists*");
1539 assert_se(r == 0);
1540}
1541
1542static void test_execute_directory(void) {
aac7766c
ZJS
1543 char template_lo[] = "/tmp/test-readlink_and_make_absolute-lo.XXXXXXX";
1544 char template_hi[] = "/tmp/test-readlink_and_make_absolute-hi.XXXXXXX";
76f282c6 1545 const char * dirs[] = {template_hi, template_lo, NULL};
aac7766c
ZJS
1546 const char *name, *name2, *name3, *overridden, *override, *masked, *mask;
1547
1548 assert_se(mkdtemp(template_lo));
1549 assert_se(mkdtemp(template_hi));
1550
63c372cb
LP
1551 name = strjoina(template_lo, "/script");
1552 name2 = strjoina(template_hi, "/script2");
1553 name3 = strjoina(template_lo, "/useless");
1554 overridden = strjoina(template_lo, "/overridden");
1555 override = strjoina(template_hi, "/overridden");
1556 masked = strjoina(template_lo, "/masked");
1557 mask = strjoina(template_hi, "/masked");
e801700e 1558
4c1fc3e4
DM
1559 assert_se(write_string_file(name, "#!/bin/sh\necho 'Executing '$0\ntouch $(dirname $0)/it_works", WRITE_STRING_FILE_CREATE) == 0);
1560 assert_se(write_string_file(name2, "#!/bin/sh\necho 'Executing '$0\ntouch $(dirname $0)/it_works2", WRITE_STRING_FILE_CREATE) == 0);
1561 assert_se(write_string_file(overridden, "#!/bin/sh\necho 'Executing '$0\ntouch $(dirname $0)/failed", WRITE_STRING_FILE_CREATE) == 0);
1562 assert_se(write_string_file(override, "#!/bin/sh\necho 'Executing '$0", WRITE_STRING_FILE_CREATE) == 0);
1563 assert_se(write_string_file(masked, "#!/bin/sh\necho 'Executing '$0\ntouch $(dirname $0)/failed", WRITE_STRING_FILE_CREATE) == 0);
aac7766c 1564 assert_se(symlink("/dev/null", mask) == 0);
8852362b
RC
1565 assert_se(chmod(name, 0755) == 0);
1566 assert_se(chmod(name2, 0755) == 0);
aac7766c
ZJS
1567 assert_se(chmod(overridden, 0755) == 0);
1568 assert_se(chmod(override, 0755) == 0);
1569 assert_se(chmod(masked, 0755) == 0);
8852362b
RC
1570 assert_se(touch(name3) >= 0);
1571
e801700e 1572 execute_directories(dirs, DEFAULT_TIMEOUT_USEC, NULL);
aac7766c 1573
0c0cdb06 1574 assert_se(chdir(template_lo) == 0);
e801700e 1575 assert_se(access("it_works", F_OK) >= 0);
aac7766c
ZJS
1576 assert_se(access("failed", F_OK) < 0);
1577
0c0cdb06 1578 assert_se(chdir(template_hi) == 0);
e801700e 1579 assert_se(access("it_works2", F_OK) >= 0);
aac7766c 1580 assert_se(access("failed", F_OK) < 0);
8852362b 1581
c6878637
LP
1582 (void) rm_rf(template_lo, REMOVE_ROOT|REMOVE_PHYSICAL);
1583 (void) rm_rf(template_hi, REMOVE_ROOT|REMOVE_PHYSICAL);
8852362b
RC
1584}
1585
68685607 1586static void test_extract_first_word(void) {
7629889c
LP
1587 const char *p, *original;
1588 char *t;
1589
1590 p = original = "foobar waldo";
68685607 1591 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
7629889c
LP
1592 assert_se(streq(t, "foobar"));
1593 free(t);
1594 assert_se(p == original + 7);
1595
68685607 1596 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
7629889c
LP
1597 assert_se(streq(t, "waldo"));
1598 free(t);
4b1c1753 1599 assert_se(isempty(p));
7629889c 1600
68685607 1601 assert_se(extract_first_word(&p, &t, NULL, 0) == 0);
7629889c 1602 assert_se(!t);
4b1c1753 1603 assert_se(isempty(p));
7629889c
LP
1604
1605 p = original = "\"foobar\" \'waldo\'";
68685607 1606 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
12ba2c44 1607 assert_se(streq(t, "\"foobar\""));
7629889c
LP
1608 free(t);
1609 assert_se(p == original + 9);
1610
68685607 1611 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
12ba2c44
RM
1612 assert_se(streq(t, "\'waldo\'"));
1613 free(t);
1614 assert_se(isempty(p));
1615
1616 assert_se(extract_first_word(&p, &t, NULL, 0) == 0);
1617 assert_se(!t);
1618 assert_se(isempty(p));
1619
1620 p = original = "\"foobar\" \'waldo\'";
1621 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) > 0);
1622 assert_se(streq(t, "foobar"));
1623 free(t);
1624 assert_se(p == original + 9);
1625
1626 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) > 0);
7629889c
LP
1627 assert_se(streq(t, "waldo"));
1628 free(t);
4b1c1753 1629 assert_se(isempty(p));
7629889c 1630
68685607 1631 assert_se(extract_first_word(&p, &t, NULL, 0) == 0);
7629889c 1632 assert_se(!t);
4b1c1753 1633 assert_se(isempty(p));
7629889c
LP
1634
1635 p = original = "\"";
12ba2c44
RM
1636 assert_se(extract_first_word(&p, &t, NULL, 0) == 1);
1637 assert_se(streq(t, "\""));
21e5a0be 1638 free(t);
12ba2c44
RM
1639 assert_se(isempty(p));
1640
1641 p = original = "\"";
1642 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) == -EINVAL);
7629889c
LP
1643 assert_se(p == original + 1);
1644
1645 p = original = "\'";
12ba2c44
RM
1646 assert_se(extract_first_word(&p, &t, NULL, 0) == 1);
1647 assert_se(streq(t, "\'"));
21e5a0be 1648 free(t);
12ba2c44
RM
1649 assert_se(isempty(p));
1650
1651 p = original = "\'";
1652 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) == -EINVAL);
7629889c
LP
1653 assert_se(p == original + 1);
1654
f32d2db1 1655 p = original = "\'fooo";
12ba2c44
RM
1656 assert_se(extract_first_word(&p, &t, NULL, 0) == 1);
1657 assert_se(streq(t, "\'fooo"));
21e5a0be 1658 free(t);
12ba2c44
RM
1659 assert_se(isempty(p));
1660
1661 p = original = "\'fooo";
1662 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) == -EINVAL);
f32d2db1
LP
1663 assert_se(p == original + 5);
1664
1665 p = original = "\'fooo";
12ba2c44 1666 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_RELAX) > 0);
f32d2db1 1667 assert_se(streq(t, "fooo"));
e1ba963f 1668 free(t);
4b1c1753 1669 assert_se(isempty(p));
f32d2db1 1670
9e44f56b
EV
1671 p = original = "\"fooo";
1672 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_RELAX) > 0);
1673 assert_se(streq(t, "fooo"));
1674 free(t);
1675 assert_se(isempty(p));
1676
7629889c 1677 p = original = "yay\'foo\'bar";
68685607 1678 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
12ba2c44
RM
1679 assert_se(streq(t, "yay\'foo\'bar"));
1680 free(t);
1681 assert_se(isempty(p));
1682
1683 p = original = "yay\'foo\'bar";
1684 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) > 0);
7629889c
LP
1685 assert_se(streq(t, "yayfoobar"));
1686 free(t);
4b1c1753 1687 assert_se(isempty(p));
7629889c
LP
1688
1689 p = original = " foobar ";
68685607 1690 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
7629889c
LP
1691 assert_se(streq(t, "foobar"));
1692 free(t);
4b1c1753 1693 assert_se(isempty(p));
4034a06d
LP
1694
1695 p = original = " foo\\ba\\x6ar ";
68685607 1696 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE) > 0);
4034a06d
LP
1697 assert_se(streq(t, "foo\ba\x6ar"));
1698 free(t);
4b1c1753 1699 assert_se(isempty(p));
4034a06d
LP
1700
1701 p = original = " foo\\ba\\x6ar ";
68685607 1702 assert_se(extract_first_word(&p, &t, NULL, 0) > 0);
4034a06d
LP
1703 assert_se(streq(t, "foobax6ar"));
1704 free(t);
4b1c1753 1705 assert_se(isempty(p));
8ebac1f9
LP
1706
1707 p = original = " f\\u00f6o \"pi\\U0001F4A9le\" ";
68685607 1708 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE) > 0);
8ebac1f9
LP
1709 assert_se(streq(t, "föo"));
1710 free(t);
1711 assert_se(p == original + 13);
1712
12ba2c44 1713 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE) > 0);
8ebac1f9
LP
1714 assert_se(streq(t, "pi\360\237\222\251le"));
1715 free(t);
4b1c1753 1716 assert_se(isempty(p));
d6293c07
FB
1717
1718 p = original = "fooo\\";
68685607 1719 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_RELAX) > 0);
d6293c07
FB
1720 assert_se(streq(t, "fooo"));
1721 free(t);
4b1c1753 1722 assert_se(isempty(p));
d6293c07
FB
1723
1724 p = original = "fooo\\";
68685607 1725 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE_RELAX) > 0);
d6293c07
FB
1726 assert_se(streq(t, "fooo\\"));
1727 free(t);
4b1c1753 1728 assert_se(isempty(p));
d6293c07
FB
1729
1730 p = original = "fooo\\";
68685607 1731 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE_RELAX|EXTRACT_RELAX) > 0);
d6293c07
FB
1732 assert_se(streq(t, "fooo\\"));
1733 free(t);
4b1c1753 1734 assert_se(isempty(p));
d6293c07
FB
1735
1736 p = original = "fooo\\";
68685607 1737 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE|EXTRACT_CUNESCAPE_RELAX) > 0);
d6293c07
FB
1738 assert_se(streq(t, "fooo\\"));
1739 free(t);
4b1c1753 1740 assert_se(isempty(p));
d6293c07
FB
1741
1742 p = original = "\"foo\\";
68685607 1743 assert_se(extract_first_word(&p, &t, NULL, 0) == -EINVAL);
d6293c07
FB
1744 assert_se(p == original + 5);
1745
1746 p = original = "\"foo\\";
12ba2c44 1747 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_RELAX) > 0);
d6293c07
FB
1748 assert_se(streq(t, "foo"));
1749 free(t);
4b1c1753 1750 assert_se(isempty(p));
d6293c07 1751
68685607
RM
1752 p = original = "foo::bar";
1753 assert_se(extract_first_word(&p, &t, ":", 0) == 1);
1754 assert_se(streq(t, "foo"));
1755 free(t);
1756 assert_se(p == original + 5);
1757
1758 assert_se(extract_first_word(&p, &t, ":", 0) == 1);
1759 assert_se(streq(t, "bar"));
1760 free(t);
1761 assert_se(isempty(p));
1762
1763 assert_se(extract_first_word(&p, &t, ":", 0) == 0);
1764 assert_se(!t);
1765 assert_se(isempty(p));
1766
1767 p = original = "foo\\:bar::waldo";
1768 assert_se(extract_first_word(&p, &t, ":", 0) == 1);
1769 assert_se(streq(t, "foo:bar"));
1770 free(t);
1771 assert_se(p == original + 10);
1772
1773 assert_se(extract_first_word(&p, &t, ":", 0) == 1);
1774 assert_se(streq(t, "waldo"));
1775 free(t);
1776 assert_se(isempty(p));
1777
1778 assert_se(extract_first_word(&p, &t, ":", 0) == 0);
1779 assert_se(!t);
1780 assert_se(isempty(p));
1781
d6293c07 1782 p = original = "\"foo\\";
12ba2c44 1783 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE_RELAX) == -EINVAL);
d6293c07
FB
1784 assert_se(p == original + 5);
1785
1786 p = original = "\"foo\\";
12ba2c44 1787 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE_RELAX|EXTRACT_RELAX) > 0);
d6293c07
FB
1788 assert_se(streq(t, "foo\\"));
1789 free(t);
4b1c1753 1790 assert_se(isempty(p));
d6293c07
FB
1791
1792 p = original = "\"foo\\";
12ba2c44 1793 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE|EXTRACT_CUNESCAPE_RELAX|EXTRACT_RELAX) > 0);
d6293c07
FB
1794 assert_se(streq(t, "foo\\"));
1795 free(t);
4b1c1753 1796 assert_se(isempty(p));
d6293c07
FB
1797
1798 p = original = "fooo\\ bar quux";
68685607 1799 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_RELAX) > 0);
d6293c07
FB
1800 assert_se(streq(t, "fooo bar"));
1801 free(t);
1802 assert_se(p == original + 10);
1803
1804 p = original = "fooo\\ bar quux";
68685607 1805 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE_RELAX) > 0);
d6293c07
FB
1806 assert_se(streq(t, "fooo bar"));
1807 free(t);
1808 assert_se(p == original + 10);
1809
1810 p = original = "fooo\\ bar quux";
68685607 1811 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE_RELAX|EXTRACT_RELAX) > 0);
d6293c07
FB
1812 assert_se(streq(t, "fooo bar"));
1813 free(t);
1814 assert_se(p == original + 10);
1815
1816 p = original = "fooo\\ bar quux";
68685607 1817 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE) == -EINVAL);
d6293c07
FB
1818 assert_se(p == original + 5);
1819
1820 p = original = "fooo\\ bar quux";
68685607 1821 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE|EXTRACT_CUNESCAPE_RELAX) > 0);
d6293c07
FB
1822 assert_se(streq(t, "fooo\\ bar"));
1823 free(t);
1824 assert_se(p == original + 10);
1825
1826 p = original = "\\w+@\\K[\\d.]+";
68685607 1827 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE) == -EINVAL);
d6293c07
FB
1828 assert_se(p == original + 1);
1829
1830 p = original = "\\w+@\\K[\\d.]+";
68685607 1831 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE|EXTRACT_CUNESCAPE_RELAX) > 0);
d6293c07
FB
1832 assert_se(streq(t, "\\w+@\\K[\\d.]+"));
1833 free(t);
4b1c1753 1834 assert_se(isempty(p));
d6293c07
FB
1835
1836 p = original = "\\w+\\b";
68685607 1837 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_CUNESCAPE|EXTRACT_CUNESCAPE_RELAX) > 0);
d6293c07
FB
1838 assert_se(streq(t, "\\w+\b"));
1839 free(t);
4b1c1753 1840 assert_se(isempty(p));
14e685c2
RM
1841
1842 p = original = "-N ''";
12ba2c44 1843 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) > 0);
14e685c2
RM
1844 assert_se(streq(t, "-N"));
1845 free(t);
1846 assert_se(p == original + 3);
1847
12ba2c44 1848 assert_se(extract_first_word(&p, &t, NULL, EXTRACT_QUOTES) > 0);
14e685c2
RM
1849 assert_se(streq(t, ""));
1850 free(t);
4b1c1753 1851 assert_se(isempty(p));
206644ae
RM
1852
1853 p = original = ":foo\\:bar::waldo:";
1854 assert_se(extract_first_word(&p, &t, ":", EXTRACT_DONT_COALESCE_SEPARATORS) == 1);
1855 assert_se(t);
1856 assert_se(streq(t, ""));
1857 free(t);
1858 assert_se(p == original + 1);
1859
1860 assert_se(extract_first_word(&p, &t, ":", EXTRACT_DONT_COALESCE_SEPARATORS) == 1);
1861 assert_se(streq(t, "foo:bar"));
1862 free(t);
1863 assert_se(p == original + 10);
1864
1865 assert_se(extract_first_word(&p, &t, ":", EXTRACT_DONT_COALESCE_SEPARATORS) == 1);
1866 assert_se(t);
1867 assert_se(streq(t, ""));
1868 free(t);
1869 assert_se(p == original + 11);
1870
1871 assert_se(extract_first_word(&p, &t, ":", EXTRACT_DONT_COALESCE_SEPARATORS) == 1);
1872 assert_se(streq(t, "waldo"));
1873 free(t);
1874 assert_se(p == original + 17);
1875
1876 assert_se(extract_first_word(&p, &t, ":", EXTRACT_DONT_COALESCE_SEPARATORS) == 1);
1877 assert_se(streq(t, ""));
1878 free(t);
1879 assert_se(p == NULL);
1880
1881 assert_se(extract_first_word(&p, &t, ":", EXTRACT_DONT_COALESCE_SEPARATORS) == 0);
1882 assert_se(!t);
1883 assert_se(!p);
7629889c
LP
1884}
1885
68685607 1886static void test_extract_first_word_and_warn(void) {
b59292b2
FB
1887 const char *p, *original;
1888 char *t;
1889
1890 p = original = "foobar waldo";
68685607 1891 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) > 0);
b59292b2
FB
1892 assert_se(streq(t, "foobar"));
1893 free(t);
1894 assert_se(p == original + 7);
1895
68685607 1896 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) > 0);
b59292b2
FB
1897 assert_se(streq(t, "waldo"));
1898 free(t);
4b1c1753 1899 assert_se(isempty(p));
b59292b2 1900
68685607 1901 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) == 0);
b59292b2 1902 assert_se(!t);
4b1c1753 1903 assert_se(isempty(p));
b59292b2
FB
1904
1905 p = original = "\"foobar\" \'waldo\'";
12ba2c44 1906 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES, NULL, "fake", 1, original) > 0);
b59292b2
FB
1907 assert_se(streq(t, "foobar"));
1908 free(t);
1909 assert_se(p == original + 9);
1910
12ba2c44 1911 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES, NULL, "fake", 1, original) > 0);
b59292b2
FB
1912 assert_se(streq(t, "waldo"));
1913 free(t);
4b1c1753 1914 assert_se(isempty(p));
b59292b2 1915
68685607 1916 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) == 0);
b59292b2 1917 assert_se(!t);
4b1c1753 1918 assert_se(isempty(p));
b59292b2
FB
1919
1920 p = original = "\"";
12ba2c44 1921 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES, NULL, "fake", 1, original) == -EINVAL);
b59292b2
FB
1922 assert_se(p == original + 1);
1923
1924 p = original = "\'";
12ba2c44 1925 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES, NULL, "fake", 1, original) == -EINVAL);
b59292b2
FB
1926 assert_se(p == original + 1);
1927
1928 p = original = "\'fooo";
12ba2c44 1929 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES, NULL, "fake", 1, original) == -EINVAL);
b59292b2
FB
1930 assert_se(p == original + 5);
1931
1932 p = original = "\'fooo";
12ba2c44 1933 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_RELAX, NULL, "fake", 1, original) > 0);
b59292b2
FB
1934 assert_se(streq(t, "fooo"));
1935 free(t);
4b1c1753 1936 assert_se(isempty(p));
b59292b2
FB
1937
1938 p = original = " foo\\ba\\x6ar ";
68685607 1939 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
1940 assert_se(streq(t, "foo\ba\x6ar"));
1941 free(t);
4b1c1753 1942 assert_se(isempty(p));
b59292b2
FB
1943
1944 p = original = " foo\\ba\\x6ar ";
68685607 1945 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) > 0);
b59292b2
FB
1946 assert_se(streq(t, "foobax6ar"));
1947 free(t);
4b1c1753 1948 assert_se(isempty(p));
b59292b2
FB
1949
1950 p = original = " f\\u00f6o \"pi\\U0001F4A9le\" ";
68685607 1951 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
1952 assert_se(streq(t, "föo"));
1953 free(t);
1954 assert_se(p == original + 13);
1955
12ba2c44 1956 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
1957 assert_se(streq(t, "pi\360\237\222\251le"));
1958 free(t);
4b1c1753 1959 assert_se(isempty(p));
b59292b2
FB
1960
1961 p = original = "fooo\\";
68685607 1962 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_RELAX, NULL, "fake", 1, original) > 0);
b59292b2
FB
1963 assert_se(streq(t, "fooo"));
1964 free(t);
4b1c1753 1965 assert_se(isempty(p));
b59292b2
FB
1966
1967 p = original = "fooo\\";
68685607 1968 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) > 0);
b59292b2
FB
1969 assert_se(streq(t, "fooo\\"));
1970 free(t);
4b1c1753 1971 assert_se(isempty(p));
b59292b2
FB
1972
1973 p = original = "fooo\\";
68685607 1974 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
1975 assert_se(streq(t, "fooo\\"));
1976 free(t);
4b1c1753 1977 assert_se(isempty(p));
b59292b2
FB
1978
1979 p = original = "\"foo\\";
12ba2c44 1980 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES, NULL, "fake", 1, original) == -EINVAL);
b59292b2
FB
1981 assert_se(p == original + 5);
1982
1983 p = original = "\"foo\\";
12ba2c44 1984 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_RELAX, NULL, "fake", 1, original) > 0);
b59292b2
FB
1985 assert_se(streq(t, "foo"));
1986 free(t);
4b1c1753 1987 assert_se(isempty(p));
b59292b2
FB
1988
1989 p = original = "\"foo\\";
12ba2c44 1990 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE, NULL, "fake", 1, original) == -EINVAL);
b59292b2
FB
1991 assert_se(p == original + 5);
1992
1993 p = original = "\"foo\\";
12ba2c44 1994 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_QUOTES|EXTRACT_CUNESCAPE|EXTRACT_RELAX, NULL, "fake", 1, original) > 0);
b59292b2
FB
1995 assert_se(streq(t, "foo"));
1996 free(t);
4b1c1753 1997 assert_se(isempty(p));
b59292b2
FB
1998
1999 p = original = "fooo\\ bar quux";
68685607 2000 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_RELAX, NULL, "fake", 1, original) > 0);
b59292b2
FB
2001 assert_se(streq(t, "fooo bar"));
2002 free(t);
2003 assert_se(p == original + 10);
2004
2005 p = original = "fooo\\ bar quux";
68685607 2006 assert_se(extract_first_word_and_warn(&p, &t, NULL, 0, NULL, "fake", 1, original) > 0);
b59292b2
FB
2007 assert_se(streq(t, "fooo bar"));
2008 free(t);
2009 assert_se(p == original + 10);
2010
2011 p = original = "fooo\\ bar quux";
68685607 2012 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
2013 assert_se(streq(t, "fooo\\ bar"));
2014 free(t);
2015 assert_se(p == original + 10);
2016
2017 p = original = "\\w+@\\K[\\d.]+";
68685607 2018 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
2019 assert_se(streq(t, "\\w+@\\K[\\d.]+"));
2020 free(t);
4b1c1753 2021 assert_se(isempty(p));
b59292b2
FB
2022
2023 p = original = "\\w+\\b";
68685607 2024 assert_se(extract_first_word_and_warn(&p, &t, NULL, EXTRACT_CUNESCAPE, NULL, "fake", 1, original) > 0);
b59292b2
FB
2025 assert_se(streq(t, "\\w+\b"));
2026 free(t);
4b1c1753 2027 assert_se(isempty(p));
b59292b2
FB
2028}
2029
68685607 2030static void test_extract_many_words(void) {
7629889c
LP
2031 const char *p, *original;
2032 char *a, *b, *c;
2033
2034 p = original = "foobar waldi piep";
68685607 2035 assert_se(extract_many_words(&p, NULL, 0, &a, &b, &c, NULL) == 3);
4b1c1753 2036 assert_se(isempty(p));
7629889c
LP
2037 assert_se(streq_ptr(a, "foobar"));
2038 assert_se(streq_ptr(b, "waldi"));
2039 assert_se(streq_ptr(c, "piep"));
2040 free(a);
2041 free(b);
2042 free(c);
2043
2044 p = original = "'foobar' wa\"ld\"i ";
68685607 2045 assert_se(extract_many_words(&p, NULL, 0, &a, &b, &c, NULL) == 2);
4b1c1753 2046 assert_se(isempty(p));
12ba2c44
RM
2047 assert_se(streq_ptr(a, "'foobar'"));
2048 assert_se(streq_ptr(b, "wa\"ld\"i"));
2049 assert_se(streq_ptr(c, NULL));
2050 free(a);
2051 free(b);
2052
2053 p = original = "'foobar' wa\"ld\"i ";
2054 assert_se(extract_many_words(&p, NULL, EXTRACT_QUOTES, &a, &b, &c, NULL) == 2);
2055 assert_se(isempty(p));
7629889c
LP
2056 assert_se(streq_ptr(a, "foobar"));
2057 assert_se(streq_ptr(b, "waldi"));
2058 assert_se(streq_ptr(c, NULL));
2059 free(a);
2060 free(b);
2061
2062 p = original = "";
68685607 2063 assert_se(extract_many_words(&p, NULL, 0, &a, &b, &c, NULL) == 0);
4b1c1753 2064 assert_se(isempty(p));
7629889c
LP
2065 assert_se(streq_ptr(a, NULL));
2066 assert_se(streq_ptr(b, NULL));
2067 assert_se(streq_ptr(c, NULL));
2068
2069 p = original = " ";
68685607 2070 assert_se(extract_many_words(&p, NULL, 0, &a, &b, &c, NULL) == 0);
4b1c1753 2071 assert_se(isempty(p));
7629889c
LP
2072 assert_se(streq_ptr(a, NULL));
2073 assert_se(streq_ptr(b, NULL));
2074 assert_se(streq_ptr(c, NULL));
2075
2076 p = original = "foobar";
68685607 2077 assert_se(extract_many_words(&p, NULL, 0, NULL) == 0);
7629889c
LP
2078 assert_se(p == original);
2079
2080 p = original = "foobar waldi";
68685607 2081 assert_se(extract_many_words(&p, NULL, 0, &a, NULL) == 1);
7629889c
LP
2082 assert_se(p == original+7);
2083 assert_se(streq_ptr(a, "foobar"));
eee84633 2084 free(a);
7629889c
LP
2085
2086 p = original = " foobar ";
68685607 2087 assert_se(extract_many_words(&p, NULL, 0, &a, NULL) == 1);
4b1c1753 2088 assert_se(isempty(p));
7629889c 2089 assert_se(streq_ptr(a, "foobar"));
eee84633 2090 free(a);
7629889c
LP
2091}
2092
f32d2db1
LP
2093static int parse_item(const char *key, const char *value) {
2094 assert_se(key);
2095
2096 log_info("kernel cmdline option <%s> = <%s>", key, strna(value));
2097 return 0;
2098}
2099
2100static void test_parse_proc_cmdline(void) {
2101 assert_se(parse_proc_cmdline(parse_item) >= 0);
2102}
2103
ee05e779
ZJS
2104static void test_raw_clone(void) {
2105 pid_t parent, pid, pid2;
2106
2107 parent = getpid();
2108 log_info("before clone: getpid()→"PID_FMT, parent);
2109 assert_se(raw_getpid() == parent);
2110
2111 pid = raw_clone(0, NULL);
e50221bf 2112 assert_se(pid >= 0);
ee05e779
ZJS
2113
2114 pid2 = raw_getpid();
2115 log_info("raw_clone: "PID_FMT" getpid()→"PID_FMT" raw_getpid()→"PID_FMT,
2116 pid, getpid(), pid2);
0289a5bc 2117 if (pid == 0) {
e50221bf 2118 assert_se(pid2 != parent);
0289a5bc
FB
2119 _exit(EXIT_SUCCESS);
2120 } else {
2121 int status;
2122
e50221bf 2123 assert_se(pid2 == parent);
0289a5bc
FB
2124 waitpid(pid, &status, __WCLONE);
2125 assert_se(WIFEXITED(status) && WEXITSTATUS(status) == EXIT_SUCCESS);
2126 }
ee05e779
ZJS
2127}
2128
f7ad54a3
LP
2129static void test_same_fd(void) {
2130 _cleanup_close_pair_ int p[2] = { -1, -1 };
2131 _cleanup_close_ int a = -1, b = -1, c = -1;
2132
2133 assert_se(pipe2(p, O_CLOEXEC) >= 0);
2134 assert_se((a = dup(p[0])) >= 0);
2135 assert_se((b = open("/dev/null", O_RDONLY|O_CLOEXEC)) >= 0);
2136 assert_se((c = dup(a)) >= 0);
2137
2138 assert_se(same_fd(p[0], p[0]) > 0);
2139 assert_se(same_fd(p[1], p[1]) > 0);
2140 assert_se(same_fd(a, a) > 0);
2141 assert_se(same_fd(b, b) > 0);
2142
2143 assert_se(same_fd(a, p[0]) > 0);
2144 assert_se(same_fd(p[0], a) > 0);
2145 assert_se(same_fd(c, p[0]) > 0);
2146 assert_se(same_fd(p[0], c) > 0);
2147 assert_se(same_fd(a, c) > 0);
2148 assert_se(same_fd(c, a) > 0);
2149
2150 assert_se(same_fd(p[0], p[1]) == 0);
2151 assert_se(same_fd(p[1], p[0]) == 0);
2152 assert_se(same_fd(p[0], b) == 0);
2153 assert_se(same_fd(b, p[0]) == 0);
2154 assert_se(same_fd(p[1], a) == 0);
2155 assert_se(same_fd(a, p[1]) == 0);
2156 assert_se(same_fd(p[1], b) == 0);
2157 assert_se(same_fd(b, p[1]) == 0);
2158
2159 assert_se(same_fd(a, b) == 0);
2160 assert_se(same_fd(b, a) == 0);
2161}
2162
8cb4ab00
LP
2163static void test_uid_ptr(void) {
2164
2165 assert_se(UID_TO_PTR(0) != NULL);
2166 assert_se(UID_TO_PTR(1000) != NULL);
2167
2168 assert_se(PTR_TO_UID(UID_TO_PTR(0)) == 0);
2169 assert_se(PTR_TO_UID(UID_TO_PTR(1000)) == 1000);
2170}
2171
ff6a7460
LP
2172static void test_sparse_write_one(int fd, const char *buffer, size_t n) {
2173 char check[n];
2174
2175 assert_se(lseek(fd, 0, SEEK_SET) == 0);
2176 assert_se(ftruncate(fd, 0) >= 0);
2177 assert_se(sparse_write(fd, buffer, n, 4) == (ssize_t) n);
2178
2179 assert_se(lseek(fd, 0, SEEK_CUR) == (off_t) n);
2180 assert_se(ftruncate(fd, n) >= 0);
2181
2182 assert_se(lseek(fd, 0, SEEK_SET) == 0);
2183 assert_se(read(fd, check, n) == (ssize_t) n);
2184
2185 assert_se(memcmp(buffer, check, n) == 0);
2186}
2187
2188static void test_sparse_write(void) {
2189 const char test_a[] = "test";
2190 const char test_b[] = "\0\0\0\0test\0\0\0\0";
2191 const char test_c[] = "\0\0test\0\0\0\0";
2192 const char test_d[] = "\0\0test\0\0\0test\0\0\0\0test\0\0\0\0\0test\0\0\0test\0\0\0\0test\0\0\0\0\0\0\0\0";
2193 const char test_e[] = "test\0\0\0\0test";
2194 _cleanup_close_ int fd = -1;
2195 char fn[] = "/tmp/sparseXXXXXX";
2196
2197 fd = mkostemp(fn, O_CLOEXEC);
2198 assert_se(fd >= 0);
2199 unlink(fn);
2200
2201 test_sparse_write_one(fd, test_a, sizeof(test_a));
2202 test_sparse_write_one(fd, test_b, sizeof(test_b));
2203 test_sparse_write_one(fd, test_c, sizeof(test_c));
2204 test_sparse_write_one(fd, test_d, sizeof(test_d));
2205 test_sparse_write_one(fd, test_e, sizeof(test_e));
2206}
2207
61ee6939
RM
2208static void test_shell_escape_one(const char *s, const char *bad, const char *expected) {
2209 _cleanup_free_ char *r;
2210
2211 assert_se(r = shell_escape(s, bad));
2212 assert_se(streq_ptr(r, expected));
2213}
2214
2215static void test_shell_escape(void) {
2216 test_shell_escape_one("", "", "");
2217 test_shell_escape_one("\\", "", "\\\\");
2218 test_shell_escape_one("foobar", "", "foobar");
2219 test_shell_escape_one("foobar", "o", "f\\o\\obar");
2220 test_shell_escape_one("foo:bar,baz", ",:", "foo\\:bar\\,baz");
2221}
2222
019c7fba
LP
2223static void test_shell_maybe_quote_one(const char *s, const char *expected) {
2224 _cleanup_free_ char *r;
2225
2226 assert_se(r = shell_maybe_quote(s));
2227 assert_se(streq(r, expected));
2228}
2229
2230static void test_shell_maybe_quote(void) {
2231
2232 test_shell_maybe_quote_one("", "");
2233 test_shell_maybe_quote_one("\\", "\"\\\\\"");
2234 test_shell_maybe_quote_one("\"", "\"\\\"\"");
2235 test_shell_maybe_quote_one("foobar", "foobar");
2236 test_shell_maybe_quote_one("foo bar", "\"foo bar\"");
2237 test_shell_maybe_quote_one("foo \"bar\" waldo", "\"foo \\\"bar\\\" waldo\"");
2238 test_shell_maybe_quote_one("foo$bar", "\"foo\\$bar\"");
2239}
2240
2ff7b0a5
LP
2241static void test_parse_mode(void) {
2242 mode_t m;
2243
2244 assert_se(parse_mode("-1", &m) < 0);
2245 assert_se(parse_mode("", &m) < 0);
2246 assert_se(parse_mode("888", &m) < 0);
2247 assert_se(parse_mode("77777", &m) < 0);
2248
2249 assert_se(parse_mode("544", &m) >= 0 && m == 0544);
2250 assert_se(parse_mode("777", &m) >= 0 && m == 0777);
2251 assert_se(parse_mode("7777", &m) >= 0 && m == 07777);
2252 assert_se(parse_mode("0", &m) >= 0 && m == 0);
2253}
2254
14bcf25c
LP
2255static void test_tempfn(void) {
2256 char *ret = NULL, *p;
2257
2258 assert_se(tempfn_xxxxxx("/foo/bar/waldo", NULL, &ret) >= 0);
2259 assert_se(streq_ptr(ret, "/foo/bar/.#waldoXXXXXX"));
2260 free(ret);
2261
2262 assert_se(tempfn_xxxxxx("/foo/bar/waldo", "[miau]", &ret) >= 0);
2263 assert_se(streq_ptr(ret, "/foo/bar/.#[miau]waldoXXXXXX"));
2264 free(ret);
2265
2266 assert_se(tempfn_random("/foo/bar/waldo", NULL, &ret) >= 0);
2267 assert_se(p = startswith(ret, "/foo/bar/.#waldo"));
2268 assert_se(strlen(p) == 16);
2269 assert_se(in_charset(p, "0123456789abcdef"));
2270 free(ret);
2271
2272 assert_se(tempfn_random("/foo/bar/waldo", "[wuff]", &ret) >= 0);
2273 assert_se(p = startswith(ret, "/foo/bar/.#[wuff]waldo"));
2274 assert_se(strlen(p) == 16);
2275 assert_se(in_charset(p, "0123456789abcdef"));
2276 free(ret);
2277
2278 assert_se(tempfn_random_child("/foo/bar/waldo", NULL, &ret) >= 0);
2279 assert_se(p = startswith(ret, "/foo/bar/waldo/.#"));
2280 assert_se(strlen(p) == 16);
2281 assert_se(in_charset(p, "0123456789abcdef"));
2282 free(ret);
2283
2284 assert_se(tempfn_random_child("/foo/bar/waldo", "[kikiriki]", &ret) >= 0);
2285 assert_se(p = startswith(ret, "/foo/bar/waldo/.#[kikiriki]"));
2286 assert_se(strlen(p) == 16);
2287 assert_se(in_charset(p, "0123456789abcdef"));
2288 free(ret);
2289}
2290
c030a850
NK
2291static void test_strcmp_ptr(void) {
2292 assert_se(strcmp_ptr(NULL, NULL) == 0);
2293 assert_se(strcmp_ptr("", NULL) > 0);
2294 assert_se(strcmp_ptr("foo", NULL) > 0);
2295 assert_se(strcmp_ptr(NULL, "") < 0);
2296 assert_se(strcmp_ptr(NULL, "bar") < 0);
2297 assert_se(strcmp_ptr("foo", "bar") > 0);
2298 assert_se(strcmp_ptr("bar", "baz") < 0);
2299 assert_se(strcmp_ptr("foo", "foo") == 0);
2300 assert_se(strcmp_ptr("", "") == 0);
2301}
2302
df241a67
LP
2303static void test_fgetxattrat_fake(void) {
2304 char t[] = "/var/tmp/xattrtestXXXXXX";
2305 _cleanup_close_ int fd = -1;
2306 const char *x;
2307 char v[3] = {};
2308 int r;
2309
2310 assert_se(mkdtemp(t));
2311 x = strjoina(t, "/test");
2312 assert_se(touch(x) >= 0);
2313
2314 r = setxattr(x, "user.foo", "bar", 3, 0);
2315 if (r < 0 && errno == EOPNOTSUPP) /* no xattrs supported on /var/tmp... */
2316 goto cleanup;
2317 assert_se(r >= 0);
2318
2319 fd = open(t, O_RDONLY|O_DIRECTORY|O_CLOEXEC|O_NOCTTY);
2320 assert_se(fd >= 0);
2321
2322 assert_se(fgetxattrat_fake(fd, "test", "user.foo", v, 3, 0) >= 0);
2323 assert_se(memcmp(v, "bar", 3) == 0);
2324
2325 safe_close(fd);
2326 fd = open("/", O_RDONLY|O_DIRECTORY|O_CLOEXEC|O_NOCTTY);
2327 assert_se(fd >= 0);
2328 assert_se(fgetxattrat_fake(fd, "usr", "user.idontexist", v, 3, 0) == -ENODATA);
2329
2330cleanup:
2331 assert_se(unlink(x) >= 0);
2332 assert_se(rmdir(t) >= 0);
2333}
2334
539ad707 2335int main(int argc, char *argv[]) {
9480794b
ZJS
2336 log_parse_environment();
2337 log_open();
2338
539ad707 2339 test_streq_ptr();
625e870b 2340 test_align_power2();
7242d742 2341 test_max();
fb835651 2342 test_container_of();
95d78c7e 2343 test_alloca();
180a60bc 2344 test_div_round_up();
539ad707 2345 test_first_word();
dbd73f9e 2346 test_close_many();
8354c34e 2347 test_parse_boolean();
8d99e5f5
TA
2348 test_parse_pid();
2349 test_parse_uid();
ff9265d0
DM
2350 test_safe_atou16();
2351 test_safe_atoi16();
8d99e5f5
TA
2352 test_safe_atolli();
2353 test_safe_atod();
dbd73f9e 2354 test_strappend();
1ef04f0b
TA
2355 test_strstrip();
2356 test_delete_chars();
2357 test_in_charset();
44f4c86c
DB
2358 test_hexchar();
2359 test_unhexchar();
919a7f5f
TG
2360 test_base32hexchar();
2361 test_unbase32hexchar();
13a5d76b
TG
2362 test_base64char();
2363 test_unbase64char();
44f4c86c
DB
2364 test_octchar();
2365 test_unoctchar();
2366 test_decchar();
2367 test_undecchar();
30494563 2368 test_unhexmem();
919a7f5f
TG
2369 test_base32hexmem();
2370 test_unbase32hexmem();
13a5d76b
TG
2371 test_base64mem();
2372 test_unbase64mem();
b4ecc959
TA
2373 test_cescape();
2374 test_cunescape();
1ef04f0b 2375 test_foreach_word();
539ad707 2376 test_foreach_word_quoted();
0d585d82 2377 test_memdup_multiply();
144e51ec 2378 test_u64log2();
2a371001 2379 test_protect_errno();
5556b5fe 2380 test_parse_size();
5f05235f 2381 test_parse_cpu_set();
59f448cf 2382 test_config_parse_iec_uint64();
b4ecc959
TA
2383 test_strextend();
2384 test_strrep();
d4ac85c6 2385 test_split_pair();
22f5f628 2386 test_fstab_node_to_udev_node();
893fa014 2387 test_get_files_in_directory();
cabb7806 2388 test_in_set();
87b02843 2389 test_writing_tmpfile();
29bfbcd6 2390 test_hexdump();
8fe90522 2391 test_log2i();
c4a7b2c5 2392 test_foreach_string();
ae6c3cc0 2393 test_filename_is_valid();
1cb1767a 2394 test_string_has_cc();
927be00c
RC
2395 test_ascii_strlower();
2396 test_files_same();
2397 test_is_valid_documentation_url();
2398 test_file_in_same_dir();
2399 test_endswith();
ff9265d0 2400 test_endswith_no_case();
927be00c
RC
2401 test_close_nointr();
2402 test_unlink_noerrno();
2403 test_readlink_and_make_absolute();
927be00c
RC
2404 test_ignore_signals();
2405 test_strshorten();
63c372cb 2406 test_strjoina();
8852362b 2407 test_is_symlink();
8852362b
RC
2408 test_search_and_fopen();
2409 test_search_and_fopen_nulstr();
2410 test_glob_exists();
2411 test_execute_directory();
68685607
RM
2412 test_extract_first_word();
2413 test_extract_first_word_and_warn();
2414 test_extract_many_words();
f32d2db1 2415 test_parse_proc_cmdline();
ee05e779 2416 test_raw_clone();
f7ad54a3 2417 test_same_fd();
8cb4ab00 2418 test_uid_ptr();
ff6a7460 2419 test_sparse_write();
61ee6939 2420 test_shell_escape();
019c7fba 2421 test_shell_maybe_quote();
2ff7b0a5 2422 test_parse_mode();
14bcf25c 2423 test_tempfn();
c030a850 2424 test_strcmp_ptr();
df241a67 2425 test_fgetxattrat_fake();
539ad707
TA
2426
2427 return 0;
2428}