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