Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/contrib/atf/atf-c/macros_test.c
39534 views
1
/* Copyright (c) 2008 The NetBSD Foundation, Inc.
2
* All rights reserved.
3
*
4
* Redistribution and use in source and binary forms, with or without
5
* modification, are permitted provided that the following conditions
6
* are met:
7
* 1. Redistributions of source code must retain the above copyright
8
* notice, this list of conditions and the following disclaimer.
9
* 2. Redistributions in binary form must reproduce the above copyright
10
* notice, this list of conditions and the following disclaimer in the
11
* documentation and/or other materials provided with the distribution.
12
*
13
* THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND
14
* CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
15
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
16
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17
* IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS BE LIABLE FOR ANY
18
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
20
* GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
22
* IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
23
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
24
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
25
26
#include "atf-c/macros.h"
27
28
#include <sys/types.h>
29
#include <sys/wait.h>
30
31
#include <errno.h>
32
#include <fcntl.h>
33
#include <stdarg.h>
34
#include <stdbool.h>
35
#include <stdio.h>
36
#include <stdlib.h>
37
#include <string.h>
38
#include <unistd.h>
39
40
#include <atf-c.h>
41
42
#include "atf-c/detail/fs.h"
43
#include "atf-c/detail/process.h"
44
#include "atf-c/detail/test_helpers.h"
45
#include "atf-c/detail/text.h"
46
47
/* ---------------------------------------------------------------------
48
* Auxiliary functions.
49
* --------------------------------------------------------------------- */
50
51
static
52
void
53
create_ctl_file(const char *name)
54
{
55
atf_fs_path_t p;
56
57
RE(atf_fs_path_init_fmt(&p, "%s", name));
58
ATF_REQUIRE(open(atf_fs_path_cstring(&p),
59
O_CREAT | O_WRONLY | O_TRUNC, 0644) != -1);
60
atf_fs_path_fini(&p);
61
}
62
63
static
64
bool
65
exists(const char *p)
66
{
67
bool b;
68
atf_fs_path_t pp;
69
70
RE(atf_fs_path_init_fmt(&pp, "%s", p));
71
RE(atf_fs_exists(&pp, &b));
72
atf_fs_path_fini(&pp);
73
74
return b;
75
}
76
77
static
78
void
79
init_and_run_h_tc(const char *name, void (*head)(atf_tc_t *),
80
void (*body)(const atf_tc_t *))
81
{
82
atf_tc_t tc;
83
const char *const config[] = { NULL };
84
85
RE(atf_tc_init(&tc, name, head, body, NULL, config));
86
run_h_tc(&tc, "output", "error", "result");
87
atf_tc_fini(&tc);
88
}
89
90
/* ---------------------------------------------------------------------
91
* Helper test cases.
92
* --------------------------------------------------------------------- */
93
94
#define H_DEF(id, macro) \
95
ATF_TC_HEAD(h_ ## id, tc) \
96
{ \
97
atf_tc_set_md_var(tc, "descr", "Helper test case"); \
98
} \
99
ATF_TC_BODY(h_ ## id, tc) \
100
{ \
101
create_ctl_file("before"); \
102
macro; \
103
create_ctl_file("after"); \
104
}
105
106
#define H_CHECK_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_check_ ## id)
107
#define H_CHECK_BODY_NAME(id) ATF_TC_BODY_NAME(h_check_ ## id)
108
#define H_CHECK(id, condition) \
109
H_DEF(check_ ## id, ATF_CHECK(condition))
110
111
#define H_CHECK_MSG_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_check_msg_ ## id)
112
#define H_CHECK_MSG_BODY_NAME(id) ATF_TC_BODY_NAME(h_check_msg_ ## id)
113
#define H_CHECK_MSG(id, condition, msg) \
114
H_DEF(check_msg_ ## id, ATF_CHECK_MSG(condition, msg))
115
116
#define H_CHECK_EQ_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_check_eq_ ## id)
117
#define H_CHECK_EQ_BODY_NAME(id) ATF_TC_BODY_NAME(h_check_eq_ ## id)
118
#define H_CHECK_EQ(id, v1, v2) \
119
H_DEF(check_eq_ ## id, ATF_CHECK_EQ(v1, v2))
120
121
#define H_CHECK_STREQ_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_check_streq_ ## id)
122
#define H_CHECK_STREQ_BODY_NAME(id) ATF_TC_BODY_NAME(h_check_streq_ ## id)
123
#define H_CHECK_STREQ(id, v1, v2) \
124
H_DEF(check_streq_ ## id, ATF_CHECK_STREQ(v1, v2))
125
126
#define H_CHECK_MATCH_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_check_match_ ## id)
127
#define H_CHECK_MATCH_BODY_NAME(id) ATF_TC_BODY_NAME(h_check_match_ ## id)
128
#define H_CHECK_MATCH(id, v1, v2) \
129
H_DEF(check_match_ ## id, ATF_CHECK_MATCH(v1, v2))
130
131
#define H_CHECK_EQ_MSG_HEAD_NAME(id) \
132
ATF_TC_HEAD_NAME(h_check_eq_msg_ ## id)
133
#define H_CHECK_EQ_MSG_BODY_NAME(id) \
134
ATF_TC_BODY_NAME(h_check_eq_msg_ ## id)
135
#define H_CHECK_EQ_MSG(id, v1, v2, msg) \
136
H_DEF(check_eq_msg_ ## id, ATF_CHECK_EQ_MSG(v1, v2, msg))
137
138
#define H_CHECK_STREQ_MSG_HEAD_NAME(id) \
139
ATF_TC_HEAD_NAME(h_check_streq_msg_ ## id)
140
#define H_CHECK_STREQ_MSG_BODY_NAME(id) \
141
ATF_TC_BODY_NAME(h_check_streq_msg_ ## id)
142
#define H_CHECK_STREQ_MSG(id, v1, v2, msg) \
143
H_DEF(check_streq_msg_ ## id, ATF_CHECK_STREQ_MSG(v1, v2, msg))
144
145
#define H_CHECK_MATCH_MSG_HEAD_NAME(id) \
146
ATF_TC_HEAD_NAME(h_check_match_msg_ ## id)
147
#define H_CHECK_MATCH_MSG_BODY_NAME(id) \
148
ATF_TC_BODY_NAME(h_check_match_msg_ ## id)
149
#define H_CHECK_MATCH_MSG(id, v1, v2, msg) \
150
H_DEF(check_match_msg_ ## id, ATF_CHECK_MATCH_MSG(v1, v2, msg))
151
152
#define H_CHECK_ERRNO_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_check_errno_ ## id)
153
#define H_CHECK_ERRNO_BODY_NAME(id) ATF_TC_BODY_NAME(h_check_errno_ ## id)
154
#define H_CHECK_ERRNO(id, exp_errno, bool_expr) \
155
H_DEF(check_errno_ ## id, ATF_CHECK_ERRNO(exp_errno, bool_expr))
156
157
#define H_REQUIRE_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_require_ ## id)
158
#define H_REQUIRE_BODY_NAME(id) ATF_TC_BODY_NAME(h_require_ ## id)
159
#define H_REQUIRE(id, condition) \
160
H_DEF(require_ ## id, ATF_REQUIRE(condition))
161
162
#define H_REQUIRE_MSG_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_require_msg_ ## id)
163
#define H_REQUIRE_MSG_BODY_NAME(id) ATF_TC_BODY_NAME(h_require_msg_ ## id)
164
#define H_REQUIRE_MSG(id, condition, msg) \
165
H_DEF(require_msg_ ## id, ATF_REQUIRE_MSG(condition, msg))
166
167
#define H_REQUIRE_EQ_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_require_eq_ ## id)
168
#define H_REQUIRE_EQ_BODY_NAME(id) ATF_TC_BODY_NAME(h_require_eq_ ## id)
169
#define H_REQUIRE_EQ(id, v1, v2) \
170
H_DEF(require_eq_ ## id, ATF_REQUIRE_EQ(v1, v2))
171
172
#define H_REQUIRE_STREQ_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_require_streq_ ## id)
173
#define H_REQUIRE_STREQ_BODY_NAME(id) ATF_TC_BODY_NAME(h_require_streq_ ## id)
174
#define H_REQUIRE_STREQ(id, v1, v2) \
175
H_DEF(require_streq_ ## id, ATF_REQUIRE_STREQ(v1, v2))
176
177
#define H_REQUIRE_MATCH_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_require_match_ ## id)
178
#define H_REQUIRE_MATCH_BODY_NAME(id) ATF_TC_BODY_NAME(h_require_match_ ## id)
179
#define H_REQUIRE_MATCH(id, v1, v2) \
180
H_DEF(require_match_ ## id, ATF_REQUIRE_MATCH(v1, v2))
181
182
#define H_REQUIRE_EQ_MSG_HEAD_NAME(id) \
183
ATF_TC_HEAD_NAME(h_require_eq_msg_ ## id)
184
#define H_REQUIRE_EQ_MSG_BODY_NAME(id) \
185
ATF_TC_BODY_NAME(h_require_eq_msg_ ## id)
186
#define H_REQUIRE_EQ_MSG(id, v1, v2, msg) \
187
H_DEF(require_eq_msg_ ## id, ATF_REQUIRE_EQ_MSG(v1, v2, msg))
188
189
#define H_REQUIRE_STREQ_MSG_HEAD_NAME(id) \
190
ATF_TC_HEAD_NAME(h_require_streq_msg_ ## id)
191
#define H_REQUIRE_STREQ_MSG_BODY_NAME(id) \
192
ATF_TC_BODY_NAME(h_require_streq_msg_ ## id)
193
#define H_REQUIRE_STREQ_MSG(id, v1, v2, msg) \
194
H_DEF(require_streq_msg_ ## id, ATF_REQUIRE_STREQ_MSG(v1, v2, msg))
195
196
#define H_REQUIRE_MATCH_MSG_HEAD_NAME(id) \
197
ATF_TC_HEAD_NAME(h_require_match_msg_ ## id)
198
#define H_REQUIRE_MATCH_MSG_BODY_NAME(id) \
199
ATF_TC_BODY_NAME(h_require_match_msg_ ## id)
200
#define H_REQUIRE_MATCH_MSG(id, v1, v2, msg) \
201
H_DEF(require_match_msg_ ## id, ATF_REQUIRE_MATCH_MSG(v1, v2, msg))
202
203
#define H_REQUIRE_ERRNO_HEAD_NAME(id) ATF_TC_HEAD_NAME(h_require_errno_ ## id)
204
#define H_REQUIRE_ERRNO_BODY_NAME(id) ATF_TC_BODY_NAME(h_require_errno_ ## id)
205
#define H_REQUIRE_ERRNO(id, exp_errno, bool_expr) \
206
H_DEF(require_errno_ ## id, ATF_REQUIRE_ERRNO(exp_errno, bool_expr))
207
208
/* ---------------------------------------------------------------------
209
* Test cases for the ATF_{CHECK,REQUIRE}_ERRNO macros.
210
* --------------------------------------------------------------------- */
211
212
static int
213
errno_fail_stub(const int raised_errno)
214
{
215
errno = raised_errno;
216
return -1;
217
}
218
219
static int
220
errno_ok_stub(void)
221
{
222
return 0;
223
}
224
225
H_CHECK_ERRNO(no_error, -1, errno_ok_stub() == -1);
226
H_CHECK_ERRNO(errno_ok, 2, errno_fail_stub(2) == -1);
227
H_CHECK_ERRNO(errno_fail, 3, errno_fail_stub(4) == -1);
228
229
H_REQUIRE_ERRNO(no_error, -1, errno_ok_stub() == -1);
230
H_REQUIRE_ERRNO(errno_ok, 2, errno_fail_stub(2) == -1);
231
H_REQUIRE_ERRNO(errno_fail, 3, errno_fail_stub(4) == -1);
232
233
ATF_TC(check_errno);
234
ATF_TC_HEAD(check_errno, tc)
235
{
236
atf_tc_set_md_var(tc, "descr", "Tests the ATF_CHECK_ERRNO macro");
237
}
238
ATF_TC_BODY(check_errno, tc)
239
{
240
struct test {
241
void (*head)(atf_tc_t *);
242
void (*body)(const atf_tc_t *);
243
bool ok;
244
const char *exp_regex;
245
} *t, tests[] = {
246
{ H_CHECK_ERRNO_HEAD_NAME(no_error),
247
H_CHECK_ERRNO_BODY_NAME(no_error),
248
false, "Expected true value in errno_ok_stub\\(\\) == -1" },
249
{ H_CHECK_ERRNO_HEAD_NAME(errno_ok),
250
H_CHECK_ERRNO_BODY_NAME(errno_ok),
251
true, NULL },
252
{ H_CHECK_ERRNO_HEAD_NAME(errno_fail),
253
H_CHECK_ERRNO_BODY_NAME(errno_fail),
254
false, "Expected errno 3, got 4, in errno_fail_stub\\(4\\) == -1" },
255
{ NULL, NULL, false, NULL }
256
};
257
258
for (t = &tests[0]; t->head != NULL; t++) {
259
init_and_run_h_tc("h_check_errno", t->head, t->body);
260
261
ATF_REQUIRE(exists("before"));
262
ATF_REQUIRE(exists("after"));
263
264
if (t->ok) {
265
ATF_REQUIRE(atf_utils_grep_file("^passed", "result"));
266
} else {
267
ATF_REQUIRE(atf_utils_grep_file("^failed", "result"));
268
ATF_REQUIRE(atf_utils_grep_file(
269
"macros_test.c:[0-9]+: %s$", "error", t->exp_regex));
270
}
271
272
ATF_REQUIRE(unlink("before") != -1);
273
ATF_REQUIRE(unlink("after") != -1);
274
}
275
}
276
277
ATF_TC(require_errno);
278
ATF_TC_HEAD(require_errno, tc)
279
{
280
atf_tc_set_md_var(tc, "descr", "Tests the ATF_REQUIRE_ERRNO macro");
281
}
282
ATF_TC_BODY(require_errno, tc)
283
{
284
struct test {
285
void (*head)(atf_tc_t *);
286
void (*body)(const atf_tc_t *);
287
bool ok;
288
const char *exp_regex;
289
} *t, tests[] = {
290
{ H_REQUIRE_ERRNO_HEAD_NAME(no_error),
291
H_REQUIRE_ERRNO_BODY_NAME(no_error),
292
false, "Expected true value in errno_ok_stub\\(\\) == -1" },
293
{ H_REQUIRE_ERRNO_HEAD_NAME(errno_ok),
294
H_REQUIRE_ERRNO_BODY_NAME(errno_ok),
295
true, NULL },
296
{ H_REQUIRE_ERRNO_HEAD_NAME(errno_fail),
297
H_REQUIRE_ERRNO_BODY_NAME(errno_fail),
298
false, "Expected errno 3, got 4, in errno_fail_stub\\(4\\) == -1" },
299
{ NULL, NULL, false, NULL }
300
};
301
302
for (t = &tests[0]; t->head != NULL; t++) {
303
init_and_run_h_tc("h_require_errno", t->head, t->body);
304
305
ATF_REQUIRE(exists("before"));
306
if (t->ok) {
307
ATF_REQUIRE(atf_utils_grep_file("^passed", "result"));
308
ATF_REQUIRE(exists("after"));
309
} else {
310
ATF_REQUIRE(atf_utils_grep_file(
311
"^failed: .*macros_test.c:[0-9]+: %s$", "result",
312
t->exp_regex));
313
ATF_REQUIRE(!exists("after"));
314
}
315
316
ATF_REQUIRE(unlink("before") != -1);
317
if (t->ok)
318
ATF_REQUIRE(unlink("after") != -1);
319
}
320
}
321
322
/* ---------------------------------------------------------------------
323
* Test cases for the ATF_CHECK and ATF_CHECK_MSG macros.
324
* --------------------------------------------------------------------- */
325
326
H_CHECK(0, 0);
327
H_CHECK(1, 1);
328
H_CHECK_MSG(0, 0, "expected a false value");
329
H_CHECK_MSG(1, 1, "expected a true value");
330
331
ATF_TC(check);
332
ATF_TC_HEAD(check, tc)
333
{
334
atf_tc_set_md_var(tc, "descr", "Tests the ATF_CHECK and "
335
"ATF_CHECK_MSG macros");
336
}
337
ATF_TC_BODY(check, tc)
338
{
339
struct test {
340
void (*head)(atf_tc_t *);
341
void (*body)(const atf_tc_t *);
342
bool value;
343
const char *msg;
344
bool ok;
345
} *t, tests[] = {
346
{ H_CHECK_HEAD_NAME(0), H_CHECK_BODY_NAME(0), 0,
347
"0 not met", false },
348
{ H_CHECK_HEAD_NAME(1), H_CHECK_BODY_NAME(1), 1,
349
"1 not met", true },
350
{ H_CHECK_MSG_HEAD_NAME(0), H_CHECK_MSG_BODY_NAME(0), 0,
351
"expected a false value", false },
352
{ H_CHECK_MSG_HEAD_NAME(1), H_CHECK_MSG_BODY_NAME(1), 1,
353
"expected a true value", true },
354
{ NULL, NULL, false, NULL, false }
355
};
356
357
for (t = &tests[0]; t->head != NULL; t++) {
358
printf("Checking with a %d value\n", t->value);
359
360
init_and_run_h_tc("h_check", t->head, t->body);
361
362
ATF_REQUIRE(exists("before"));
363
ATF_REQUIRE(exists("after"));
364
365
if (t->ok) {
366
ATF_REQUIRE(atf_utils_grep_file("^passed", "result"));
367
} else {
368
ATF_REQUIRE(atf_utils_grep_file("^failed", "result"));
369
ATF_REQUIRE(atf_utils_grep_file("Check failed: .*"
370
"macros_test.c:[0-9]+: %s$", "error", t->msg));
371
}
372
373
ATF_REQUIRE(unlink("before") != -1);
374
ATF_REQUIRE(unlink("after") != -1);
375
}
376
}
377
378
/* ---------------------------------------------------------------------
379
* Test cases for the ATF_CHECK_*EQ_ macros.
380
* --------------------------------------------------------------------- */
381
382
struct check_eq_test {
383
void (*head)(atf_tc_t *);
384
void (*body)(const atf_tc_t *);
385
const char *v1;
386
const char *v2;
387
const char *msg;
388
bool ok;
389
};
390
391
static
392
void
393
do_check_eq_tests(const struct check_eq_test *tests)
394
{
395
const struct check_eq_test *t;
396
397
for (t = &tests[0]; t->head != NULL; t++) {
398
printf("Checking with %s, %s and expecting %s\n", t->v1, t->v2,
399
t->ok ? "true" : "false");
400
401
init_and_run_h_tc("h_check", t->head, t->body);
402
403
ATF_CHECK(exists("before"));
404
ATF_CHECK(exists("after"));
405
406
if (t->ok) {
407
ATF_REQUIRE(atf_utils_grep_file("^passed", "result"));
408
} else {
409
ATF_REQUIRE(atf_utils_grep_file("^failed", "result"));
410
ATF_CHECK(atf_utils_grep_file("Check failed: .*"
411
"macros_test.c:[0-9]+: %s$", "error", t->msg));
412
}
413
414
ATF_CHECK(unlink("before") != -1);
415
ATF_CHECK(unlink("after") != -1);
416
}
417
}
418
419
H_CHECK_EQ(1_1, 1, 1);
420
H_CHECK_EQ(1_2, 1, 2);
421
H_CHECK_EQ(2_1, 2, 1);
422
H_CHECK_EQ(2_2, 2, 2);
423
H_CHECK_EQ_MSG(1_1, 1, 1, "1 does not match 1");
424
H_CHECK_EQ_MSG(1_2, 1, 2, "1 does not match 2");
425
H_CHECK_EQ_MSG(2_1, 2, 1, "2 does not match 1");
426
H_CHECK_EQ_MSG(2_2, 2, 2, "2 does not match 2");
427
428
ATF_TC(check_eq);
429
ATF_TC_HEAD(check_eq, tc)
430
{
431
atf_tc_set_md_var(tc, "descr", "Tests the ATF_CHECK_EQ and "
432
"ATF_CHECK_EQ_MSG macros");
433
}
434
ATF_TC_BODY(check_eq, tc)
435
{
436
struct check_eq_test tests[] = {
437
{ H_CHECK_EQ_HEAD_NAME(1_1), H_CHECK_EQ_BODY_NAME(1_1),
438
"1", "1", "1 != 1", true },
439
{ H_CHECK_EQ_HEAD_NAME(1_2), H_CHECK_EQ_BODY_NAME(1_2),
440
"1", "2", "1 != 2", false },
441
{ H_CHECK_EQ_HEAD_NAME(2_1), H_CHECK_EQ_BODY_NAME(2_1),
442
"2", "1", "2 != 1", false },
443
{ H_CHECK_EQ_HEAD_NAME(2_2), H_CHECK_EQ_BODY_NAME(2_2),
444
"2", "2", "2 != 2", true },
445
{ H_CHECK_EQ_MSG_HEAD_NAME(1_1), H_CHECK_EQ_MSG_BODY_NAME(1_1),
446
"1", "1", "1 != 1: 1 does not match 1", true },
447
{ H_CHECK_EQ_MSG_HEAD_NAME(1_2), H_CHECK_EQ_MSG_BODY_NAME(1_2),
448
"1", "2", "1 != 2: 1 does not match 2", false },
449
{ H_CHECK_EQ_MSG_HEAD_NAME(2_1), H_CHECK_EQ_MSG_BODY_NAME(2_1),
450
"2", "1", "2 != 1: 2 does not match 1", false },
451
{ H_CHECK_EQ_MSG_HEAD_NAME(2_2), H_CHECK_EQ_MSG_BODY_NAME(2_2),
452
"2", "2", "2 != 2: 2 does not match 2", true },
453
{ NULL, NULL, 0, 0, "", false }
454
};
455
do_check_eq_tests(tests);
456
}
457
458
H_CHECK_STREQ(1_1, "1", "1");
459
H_CHECK_STREQ(1_2, "1", "2");
460
H_CHECK_STREQ(2_1, "2", "1");
461
H_CHECK_STREQ(2_2, "2", "2");
462
H_CHECK_STREQ_MSG(1_1, "1", "1", "1 does not match 1");
463
H_CHECK_STREQ_MSG(1_2, "1", "2", "1 does not match 2");
464
H_CHECK_STREQ_MSG(2_1, "2", "1", "2 does not match 1");
465
H_CHECK_STREQ_MSG(2_2, "2", "2", "2 does not match 2");
466
#define CHECK_STREQ_VAR1 "5"
467
#define CHECK_STREQ_VAR2 "9"
468
const char *check_streq_var1 = CHECK_STREQ_VAR1;
469
const char *check_streq_var2 = CHECK_STREQ_VAR2;
470
H_CHECK_STREQ(vars, check_streq_var1, check_streq_var2);
471
472
ATF_TC(check_streq);
473
ATF_TC_HEAD(check_streq, tc)
474
{
475
atf_tc_set_md_var(tc, "descr", "Tests the ATF_CHECK_STREQ and "
476
"ATF_CHECK_STREQ_MSG macros");
477
}
478
ATF_TC_BODY(check_streq, tc)
479
{
480
struct check_eq_test tests[] = {
481
{ H_CHECK_STREQ_HEAD_NAME(1_1), H_CHECK_STREQ_BODY_NAME(1_1),
482
"1", "1", "\"1\" != \"1\" \\(1 != 1\\)", true },
483
{ H_CHECK_STREQ_HEAD_NAME(1_2), H_CHECK_STREQ_BODY_NAME(1_2),
484
"1", "2", "\"1\" != \"2\" \\(1 != 2\\)", false },
485
{ H_CHECK_STREQ_HEAD_NAME(2_1), H_CHECK_STREQ_BODY_NAME(2_1),
486
"2", "1", "\"2\" != \"1\" \\(2 != 1\\)", false },
487
{ H_CHECK_STREQ_HEAD_NAME(2_2), H_CHECK_STREQ_BODY_NAME(2_2),
488
"2", "2", "\"2\" != \"2\" \\(2 != 2\\)", true },
489
{ H_CHECK_STREQ_MSG_HEAD_NAME(1_1),
490
H_CHECK_STREQ_MSG_BODY_NAME(1_1),
491
"1", "1", "\"1\" != \"1\" \\(1 != 1\\): 1 does not match 1", true },
492
{ H_CHECK_STREQ_MSG_HEAD_NAME(1_2),
493
H_CHECK_STREQ_MSG_BODY_NAME(1_2),
494
"1", "2", "\"1\" != \"2\" \\(1 != 2\\): 1 does not match 2", false },
495
{ H_CHECK_STREQ_MSG_HEAD_NAME(2_1),
496
H_CHECK_STREQ_MSG_BODY_NAME(2_1),
497
"2", "1", "\"2\" != \"1\" \\(2 != 1\\): 2 does not match 1", false },
498
{ H_CHECK_STREQ_MSG_HEAD_NAME(2_2),
499
H_CHECK_STREQ_MSG_BODY_NAME(2_2),
500
"2", "2", "\"2\" != \"2\" \\(2 != 2\\): 2 does not match 2", true },
501
{ H_CHECK_STREQ_HEAD_NAME(vars), H_CHECK_STREQ_BODY_NAME(vars),
502
check_streq_var1, check_streq_var2,
503
"check_streq_var1 != check_streq_var2 \\("
504
CHECK_STREQ_VAR1 " != " CHECK_STREQ_VAR2 "\\)", false },
505
{ NULL, NULL, 0, 0, "", false }
506
};
507
do_check_eq_tests(tests);
508
}
509
510
/* ---------------------------------------------------------------------
511
* Test cases for the ATF_CHECK_MATCH and ATF_CHECK_MATCH_MSG macros.
512
* --------------------------------------------------------------------- */
513
514
H_CHECK_MATCH(yes, "hello [a-z]+", "abc hello world");
515
H_CHECK_MATCH(no, "hello [a-z]+", "abc hello WORLD");
516
H_CHECK_MATCH_MSG(yes, "hello [a-z]+", "abc hello world", "lowercase");
517
H_CHECK_MATCH_MSG(no, "hello [a-z]+", "abc hello WORLD", "uppercase");
518
519
ATF_TC(check_match);
520
ATF_TC_HEAD(check_match, tc)
521
{
522
atf_tc_set_md_var(tc, "descr", "Tests the ATF_CHECK_MATCH and "
523
"ATF_CHECK_MATCH_MSG macros");
524
}
525
ATF_TC_BODY(check_match, tc)
526
{
527
struct check_eq_test tests[] = {
528
{ H_CHECK_MATCH_HEAD_NAME(yes), H_CHECK_MATCH_BODY_NAME(yes),
529
"hello [a-z]+", "abc hello world", "", true },
530
{ H_CHECK_MATCH_HEAD_NAME(no), H_CHECK_MATCH_BODY_NAME(no),
531
"hello [a-z]+", "abc hello WORLD",
532
"'hello \\[a-z\\]\\+' not matched in 'abc hello WORLD'", false },
533
{ H_CHECK_MATCH_MSG_HEAD_NAME(yes), H_CHECK_MATCH_MSG_BODY_NAME(yes),
534
"hello [a-z]+", "abc hello world", "", true },
535
{ H_CHECK_MATCH_MSG_HEAD_NAME(no), H_CHECK_MATCH_MSG_BODY_NAME(no),
536
"hello [a-z]+", "abc hello WORLD",
537
"'hello \\[a-z\\]\\+' not matched in 'abc hello WORLD': uppercase",
538
false },
539
{ NULL, NULL, 0, 0, "", false }
540
};
541
do_check_eq_tests(tests);
542
}
543
544
/* ---------------------------------------------------------------------
545
* Test cases for the ATF_REQUIRE and ATF_REQUIRE_MSG macros.
546
* --------------------------------------------------------------------- */
547
548
H_REQUIRE(0, 0);
549
H_REQUIRE(1, 1);
550
H_REQUIRE_MSG(0, 0, "expected a false value");
551
H_REQUIRE_MSG(1, 1, "expected a true value");
552
553
ATF_TC(require);
554
ATF_TC_HEAD(require, tc)
555
{
556
atf_tc_set_md_var(tc, "descr", "Tests the ATF_REQUIRE and "
557
"ATF_REQUIRE_MSG macros");
558
}
559
ATF_TC_BODY(require, tc)
560
{
561
struct test {
562
void (*head)(atf_tc_t *);
563
void (*body)(const atf_tc_t *);
564
bool value;
565
const char *msg;
566
bool ok;
567
} *t, tests[] = {
568
{ H_REQUIRE_HEAD_NAME(0), H_REQUIRE_BODY_NAME(0), 0,
569
"0 not met", false },
570
{ H_REQUIRE_HEAD_NAME(1), H_REQUIRE_BODY_NAME(1), 1,
571
"1 not met", true },
572
{ H_REQUIRE_MSG_HEAD_NAME(0), H_REQUIRE_MSG_BODY_NAME(0), 0,
573
"expected a false value", false },
574
{ H_REQUIRE_MSG_HEAD_NAME(1), H_REQUIRE_MSG_BODY_NAME(1), 1,
575
"expected a true value", true },
576
{ NULL, NULL, false, NULL, false }
577
};
578
579
for (t = &tests[0]; t->head != NULL; t++) {
580
printf("Checking with a %d value\n", t->value);
581
582
init_and_run_h_tc("h_require", t->head, t->body);
583
584
ATF_REQUIRE(exists("before"));
585
if (t->ok) {
586
ATF_REQUIRE(atf_utils_grep_file("^passed", "result"));
587
ATF_REQUIRE(exists("after"));
588
} else {
589
ATF_REQUIRE(atf_utils_grep_file(
590
"^failed: .*macros_test.c:[0-9]+: %s$", "result", t->msg));
591
ATF_REQUIRE(!exists("after"));
592
}
593
594
ATF_REQUIRE(unlink("before") != -1);
595
if (t->ok)
596
ATF_REQUIRE(unlink("after") != -1);
597
}
598
}
599
600
/* ---------------------------------------------------------------------
601
* Test cases for the ATF_REQUIRE_*EQ_ macros.
602
* --------------------------------------------------------------------- */
603
604
struct require_eq_test {
605
void (*head)(atf_tc_t *);
606
void (*body)(const atf_tc_t *);
607
const char *v1;
608
const char *v2;
609
const char *msg;
610
bool ok;
611
};
612
613
static
614
void
615
do_require_eq_tests(const struct require_eq_test *tests)
616
{
617
const struct require_eq_test *t;
618
619
for (t = &tests[0]; t->head != NULL; t++) {
620
printf("Checking with %s, %s and expecting %s\n", t->v1, t->v2,
621
t->ok ? "true" : "false");
622
623
init_and_run_h_tc("h_require", t->head, t->body);
624
625
ATF_REQUIRE(exists("before"));
626
if (t->ok) {
627
ATF_REQUIRE(atf_utils_grep_file("^passed", "result"));
628
ATF_REQUIRE(exists("after"));
629
} else {
630
ATF_REQUIRE(atf_utils_grep_file("^failed: .*macros_test.c"
631
":[0-9]+: %s$", "result", t->msg));
632
ATF_REQUIRE(!exists("after"));
633
}
634
635
ATF_REQUIRE(unlink("before") != -1);
636
if (t->ok)
637
ATF_REQUIRE(unlink("after") != -1);
638
}
639
}
640
641
H_REQUIRE_EQ(1_1, 1, 1);
642
H_REQUIRE_EQ(1_2, 1, 2);
643
H_REQUIRE_EQ(2_1, 2, 1);
644
H_REQUIRE_EQ(2_2, 2, 2);
645
H_REQUIRE_EQ_MSG(1_1, 1, 1, "1 does not match 1");
646
H_REQUIRE_EQ_MSG(1_2, 1, 2, "1 does not match 2");
647
H_REQUIRE_EQ_MSG(2_1, 2, 1, "2 does not match 1");
648
H_REQUIRE_EQ_MSG(2_2, 2, 2, "2 does not match 2");
649
650
ATF_TC(require_eq);
651
ATF_TC_HEAD(require_eq, tc)
652
{
653
atf_tc_set_md_var(tc, "descr", "Tests the ATF_REQUIRE_EQ and "
654
"ATF_REQUIRE_EQ_MSG macros");
655
}
656
ATF_TC_BODY(require_eq, tc)
657
{
658
struct require_eq_test tests[] = {
659
{ H_REQUIRE_EQ_HEAD_NAME(1_1), H_REQUIRE_EQ_BODY_NAME(1_1),
660
"1", "1", "1 != 1", true },
661
{ H_REQUIRE_EQ_HEAD_NAME(1_2), H_REQUIRE_EQ_BODY_NAME(1_2),
662
"1", "2", "1 != 2", false },
663
{ H_REQUIRE_EQ_HEAD_NAME(2_1), H_REQUIRE_EQ_BODY_NAME(2_1),
664
"2", "1", "2 != 1", false },
665
{ H_REQUIRE_EQ_HEAD_NAME(2_2), H_REQUIRE_EQ_BODY_NAME(2_2),
666
"2", "2", "2 != 2", true },
667
{ H_REQUIRE_EQ_MSG_HEAD_NAME(1_1), H_REQUIRE_EQ_MSG_BODY_NAME(1_1),
668
"1", "1", "1 != 1: 1 does not match 1", true },
669
{ H_REQUIRE_EQ_MSG_HEAD_NAME(1_2), H_REQUIRE_EQ_MSG_BODY_NAME(1_2),
670
"1", "2", "1 != 2: 1 does not match 2", false },
671
{ H_REQUIRE_EQ_MSG_HEAD_NAME(2_1), H_REQUIRE_EQ_MSG_BODY_NAME(2_1),
672
"2", "1", "2 != 1: 2 does not match 1", false },
673
{ H_REQUIRE_EQ_MSG_HEAD_NAME(2_2), H_REQUIRE_EQ_MSG_BODY_NAME(2_2),
674
"2", "2", "2 != 2: 2 does not match 2", true },
675
{ NULL, NULL, 0, 0, "", false }
676
};
677
do_require_eq_tests(tests);
678
}
679
680
H_REQUIRE_STREQ(1_1, "1", "1");
681
H_REQUIRE_STREQ(1_2, "1", "2");
682
H_REQUIRE_STREQ(2_1, "2", "1");
683
H_REQUIRE_STREQ(2_2, "2", "2");
684
H_REQUIRE_STREQ_MSG(1_1, "1", "1", "1 does not match 1");
685
H_REQUIRE_STREQ_MSG(1_2, "1", "2", "1 does not match 2");
686
H_REQUIRE_STREQ_MSG(2_1, "2", "1", "2 does not match 1");
687
H_REQUIRE_STREQ_MSG(2_2, "2", "2", "2 does not match 2");
688
#define REQUIRE_STREQ_VAR1 "5"
689
#define REQUIRE_STREQ_VAR2 "9"
690
const char *require_streq_var1 = REQUIRE_STREQ_VAR1;
691
const char *require_streq_var2 = REQUIRE_STREQ_VAR2;
692
H_REQUIRE_STREQ(vars, require_streq_var1, require_streq_var2);
693
694
ATF_TC(require_streq);
695
ATF_TC_HEAD(require_streq, tc)
696
{
697
atf_tc_set_md_var(tc, "descr", "Tests the ATF_REQUIRE_STREQ and "
698
"ATF_REQUIRE_STREQ_MSG macros");
699
}
700
ATF_TC_BODY(require_streq, tc)
701
{
702
struct require_eq_test tests[] = {
703
{ H_REQUIRE_STREQ_HEAD_NAME(1_1), H_REQUIRE_STREQ_BODY_NAME(1_1),
704
"1", "1", "\"1\" != \"1\" \\(1 != 1\\)", true },
705
{ H_REQUIRE_STREQ_HEAD_NAME(1_2), H_REQUIRE_STREQ_BODY_NAME(1_2),
706
"1", "2", "\"1\" != \"2\" \\(1 != 2\\)", false },
707
{ H_REQUIRE_STREQ_HEAD_NAME(2_1), H_REQUIRE_STREQ_BODY_NAME(2_1),
708
"2", "1", "\"2\" != \"1\" \\(2 != 1\\)", false },
709
{ H_REQUIRE_STREQ_HEAD_NAME(2_2), H_REQUIRE_STREQ_BODY_NAME(2_2),
710
"2", "2", "\"2\" != \"2\" \\(2 != 2\\)", true },
711
{ H_REQUIRE_STREQ_MSG_HEAD_NAME(1_1),
712
H_REQUIRE_STREQ_MSG_BODY_NAME(1_1),
713
"1", "1", "\"1\" != \"1\" \\(1 != 1\\): 1 does not match 1", true },
714
{ H_REQUIRE_STREQ_MSG_HEAD_NAME(1_2),
715
H_REQUIRE_STREQ_MSG_BODY_NAME(1_2),
716
"1", "2", "\"1\" != \"2\" \\(1 != 2\\): 1 does not match 2", false },
717
{ H_REQUIRE_STREQ_MSG_HEAD_NAME(2_1),
718
H_REQUIRE_STREQ_MSG_BODY_NAME(2_1),
719
"2", "1", "\"2\" != \"1\" \\(2 != 1\\): 2 does not match 1", false },
720
{ H_REQUIRE_STREQ_MSG_HEAD_NAME(2_2),
721
H_REQUIRE_STREQ_MSG_BODY_NAME(2_2),
722
"2", "2", "\"2\" != \"2\" \\(2 != 2\\): 2 does not match 2", true },
723
{ H_REQUIRE_STREQ_HEAD_NAME(vars), H_REQUIRE_STREQ_BODY_NAME(vars),
724
require_streq_var1, require_streq_var2,
725
"require_streq_var1 != require_streq_var2 \\("
726
REQUIRE_STREQ_VAR1 " != " REQUIRE_STREQ_VAR2 "\\)", false },
727
{ NULL, NULL, 0, 0, "", false }
728
};
729
do_require_eq_tests(tests);
730
}
731
732
/* ---------------------------------------------------------------------
733
* Test cases for the ATF_REQUIRE_MATCH and ATF_REQUIRE_MATCH_MSG macros.
734
* --------------------------------------------------------------------- */
735
736
H_REQUIRE_MATCH(yes, "hello [a-z]+", "abc hello world");
737
H_REQUIRE_MATCH(no, "hello [a-z]+", "abc hello WORLD");
738
H_REQUIRE_MATCH_MSG(yes, "hello [a-z]+", "abc hello world", "lowercase");
739
H_REQUIRE_MATCH_MSG(no, "hello [a-z]+", "abc hello WORLD", "uppercase");
740
741
ATF_TC(require_match);
742
ATF_TC_HEAD(require_match, tc)
743
{
744
atf_tc_set_md_var(tc, "descr", "Tests the ATF_REQUIRE_MATCH and "
745
"ATF_REQUIRE_MATCH_MSG macros");
746
}
747
ATF_TC_BODY(require_match, tc)
748
{
749
struct require_eq_test tests[] = {
750
{ H_REQUIRE_MATCH_HEAD_NAME(yes), H_REQUIRE_MATCH_BODY_NAME(yes),
751
"hello [a-z]+", "abc hello world", "", true },
752
{ H_REQUIRE_MATCH_HEAD_NAME(no), H_REQUIRE_MATCH_BODY_NAME(no),
753
"hello [a-z]+", "abc hello WORLD",
754
"'hello \\[a-z\\]\\+' not matched in 'abc hello WORLD'", false },
755
{ H_REQUIRE_MATCH_MSG_HEAD_NAME(yes),
756
H_REQUIRE_MATCH_MSG_BODY_NAME(yes),
757
"hello [a-z]+", "abc hello world", "", true },
758
{ H_REQUIRE_MATCH_MSG_HEAD_NAME(no), H_REQUIRE_MATCH_MSG_BODY_NAME(no),
759
"hello [a-z]+", "abc hello WORLD",
760
"'hello \\[a-z\\]\\+' not matched in 'abc hello WORLD': uppercase",
761
false },
762
{ NULL, NULL, 0, 0, "", false }
763
};
764
do_require_eq_tests(tests);
765
}
766
767
/* ---------------------------------------------------------------------
768
* Miscellaneous test cases covering several macros.
769
* --------------------------------------------------------------------- */
770
771
static
772
bool
773
aux_bool(const char *fmt ATF_DEFS_ATTRIBUTE_UNUSED)
774
{
775
return false;
776
}
777
778
static
779
const char *
780
aux_str(const char *fmt ATF_DEFS_ATTRIBUTE_UNUSED)
781
{
782
return "foo";
783
}
784
785
H_CHECK(msg, aux_bool("%d"));
786
H_REQUIRE(msg, aux_bool("%d"));
787
H_CHECK_STREQ(msg, aux_str("%d"), "");
788
H_REQUIRE_STREQ(msg, aux_str("%d"), "");
789
790
ATF_TC(msg_embedded_fmt);
791
ATF_TC_HEAD(msg_embedded_fmt, tc)
792
{
793
atf_tc_set_md_var(tc, "descr", "Tests that format strings passed "
794
"as part of the automatically-generated messages "
795
"do not get expanded");
796
}
797
ATF_TC_BODY(msg_embedded_fmt, tc)
798
{
799
struct test {
800
void (*head)(atf_tc_t *);
801
void (*body)(const atf_tc_t *);
802
bool fatal;
803
const char *msg;
804
} *t, tests[] = {
805
{ H_CHECK_HEAD_NAME(msg), H_CHECK_BODY_NAME(msg), false,
806
"aux_bool\\(\"%d\"\\) not met" },
807
{ H_REQUIRE_HEAD_NAME(msg), H_REQUIRE_BODY_NAME(msg), true,
808
"aux_bool\\(\"%d\"\\) not met" },
809
{ H_CHECK_STREQ_HEAD_NAME(msg), H_CHECK_STREQ_BODY_NAME(msg), false,
810
"aux_str\\(\"%d\"\\) != \"\" \\(foo != \\)" },
811
{ H_REQUIRE_STREQ_HEAD_NAME(msg), H_REQUIRE_STREQ_BODY_NAME(msg), true,
812
"aux_str\\(\"%d\"\\) != \"\" \\(foo != \\)" },
813
{ NULL, NULL, false, NULL }
814
};
815
816
for (t = &tests[0]; t->head != NULL; t++) {
817
printf("Checking with an expected '%s' message\n", t->msg);
818
819
init_and_run_h_tc("h_check", t->head, t->body);
820
821
if (t->fatal) {
822
bool matched =
823
atf_utils_grep_file(
824
"^failed: .*macros_test.c:[0-9]+: %s$", "result", t->msg);
825
ATF_CHECK_MSG(matched, "couldn't find error string in result");
826
} else {
827
bool matched = atf_utils_grep_file("Check failed: .*"
828
"macros_test.c:[0-9]+: %s$", "error", t->msg);
829
ATF_CHECK_MSG(matched, "couldn't find error string in output");
830
}
831
}
832
}
833
834
/* ---------------------------------------------------------------------
835
* Tests cases for the header file.
836
* --------------------------------------------------------------------- */
837
838
BUILD_TC(use, "macros_h_test.c",
839
"Tests that the macros provided by the atf-c/macros.h file "
840
"do not cause syntax errors when used",
841
"Build of macros_h_test.c failed; some macros in atf-c/macros.h "
842
"are broken");
843
844
ATF_TC(detect_unused_tests);
845
ATF_TC_HEAD(detect_unused_tests, tc)
846
{
847
atf_tc_set_md_var(tc, "descr",
848
"Tests that defining an unused test case raises a "
849
"warning (and thus an error)");
850
}
851
ATF_TC_BODY(detect_unused_tests, tc)
852
{
853
const char* validate_compiler =
854
"struct test_struct { int dummy; };\n"
855
"#define define_unused static struct test_struct unused\n"
856
"define_unused;\n";
857
858
atf_utils_create_file("compiler_test.c", "%s", validate_compiler);
859
if (build_check_c_o("compiler_test.c"))
860
atf_tc_expect_fail("Compiler does not raise a warning on an unused "
861
"static global variable declared by a macro");
862
863
if (build_check_c_o_srcdir(tc, "unused_test.c"))
864
atf_tc_fail("Build of unused_test.c passed; unused test cases are "
865
"not properly detected");
866
}
867
868
/* ---------------------------------------------------------------------
869
* Main.
870
* --------------------------------------------------------------------- */
871
872
ATF_TP_ADD_TCS(tp)
873
{
874
ATF_TP_ADD_TC(tp, check);
875
ATF_TP_ADD_TC(tp, check_eq);
876
ATF_TP_ADD_TC(tp, check_streq);
877
ATF_TP_ADD_TC(tp, check_errno);
878
ATF_TP_ADD_TC(tp, check_match);
879
880
ATF_TP_ADD_TC(tp, require);
881
ATF_TP_ADD_TC(tp, require_eq);
882
ATF_TP_ADD_TC(tp, require_streq);
883
ATF_TP_ADD_TC(tp, require_errno);
884
ATF_TP_ADD_TC(tp, require_match);
885
886
ATF_TP_ADD_TC(tp, msg_embedded_fmt);
887
888
/* Add the test cases for the header file. */
889
ATF_TP_ADD_TC(tp, use);
890
ATF_TP_ADD_TC(tp, detect_unused_tests);
891
892
return atf_no_error();
893
}
894
895