1 /* @generated by `generate-fortify-tests.lua "select"` */ 2 3 #define _FORTIFY_SOURCE 2 4 #define TMPFILE_SIZE (1024 * 32) 5 6 #include <sys/param.h> 7 #include <sys/random.h> 8 #include <sys/resource.h> 9 #include <sys/select.h> 10 #include <sys/socket.h> 11 #include <sys/time.h> 12 #include <sys/uio.h> 13 #include <sys/wait.h> 14 #include <dirent.h> 15 #include <errno.h> 16 #include <fcntl.h> 17 #include <limits.h> 18 #include <poll.h> 19 #include <signal.h> 20 #include <stdio.h> 21 #include <stdlib.h> 22 #include <string.h> 23 #include <strings.h> 24 #include <sysexits.h> 25 #include <unistd.h> 26 #include <wchar.h> 27 #include <atf-c.h> 28 29 static FILE * __unused 30 new_fp(size_t __len) 31 { 32 static char fpbuf[LINE_MAX]; 33 FILE *fp; 34 35 ATF_REQUIRE(__len <= sizeof(fpbuf)); 36 37 memset(fpbuf, 'A', sizeof(fpbuf) - 1); 38 fpbuf[sizeof(fpbuf) - 1] = '\0'; 39 40 fp = fmemopen(fpbuf, sizeof(fpbuf), "rb"); 41 ATF_REQUIRE(fp != NULL); 42 43 return (fp); 44 } 45 46 /* 47 * Create a new symlink to use for readlink(2) style tests, we'll just use a 48 * random target name to have something interesting to look at. 49 */ 50 static const char * __unused 51 new_symlink(size_t __len) 52 { 53 static const char linkname[] = "link"; 54 char target[MAXNAMLEN]; 55 int error; 56 57 ATF_REQUIRE(__len <= sizeof(target)); 58 59 arc4random_buf(target, sizeof(target)); 60 61 error = unlink(linkname); 62 ATF_REQUIRE(error == 0 || errno == ENOENT); 63 64 error = symlink(target, linkname); 65 ATF_REQUIRE(error == 0); 66 67 return (linkname); 68 } 69 70 /* 71 * For our purposes, first descriptor will be the reader; we'll send both 72 * raw data and a control message over it so that the result can be used for 73 * any of our recv*() tests. 74 */ 75 static void __unused 76 new_socket(int sock[2]) 77 { 78 unsigned char ctrl[CMSG_SPACE(sizeof(int))] = { 0 }; 79 static char sockbuf[256]; 80 ssize_t rv; 81 size_t total = 0; 82 struct msghdr hdr = { 0 }; 83 struct cmsghdr *cmsg; 84 int error, fd; 85 86 error = socketpair(AF_UNIX, SOCK_STREAM, 0, sock); 87 ATF_REQUIRE(error == 0); 88 89 while (total != sizeof(sockbuf)) { 90 rv = send(sock[1], &sockbuf[total], sizeof(sockbuf) - total, 0); 91 92 ATF_REQUIRE_MSG(rv > 0, 93 "expected bytes sent, got %zd with %zu left (size %zu, total %zu)", 94 rv, sizeof(sockbuf) - total, sizeof(sockbuf), total); 95 ATF_REQUIRE_MSG(total + (size_t)rv <= sizeof(sockbuf), 96 "%zd exceeds total %zu", rv, sizeof(sockbuf)); 97 total += rv; 98 } 99 100 hdr.msg_control = ctrl; 101 hdr.msg_controllen = sizeof(ctrl); 102 103 cmsg = CMSG_FIRSTHDR(&hdr); 104 cmsg->cmsg_level = SOL_SOCKET; 105 cmsg->cmsg_type = SCM_RIGHTS; 106 cmsg->cmsg_len = CMSG_LEN(sizeof(fd)); 107 fd = STDIN_FILENO; 108 memcpy(CMSG_DATA(cmsg), &fd, sizeof(fd)); 109 110 error = sendmsg(sock[1], &hdr, 0); 111 ATF_REQUIRE(error != -1); 112 } 113 114 /* 115 * Constructs a tmpfile that we can use for testing read(2) and friends. 116 */ 117 static int __unused 118 new_tmpfile(void) 119 { 120 char buf[1024]; 121 ssize_t rv; 122 size_t written; 123 int fd; 124 125 fd = open("tmpfile", O_RDWR | O_CREAT | O_TRUNC, 0644); 126 ATF_REQUIRE(fd >= 0); 127 128 written = 0; 129 while (written < TMPFILE_SIZE) { 130 rv = write(fd, buf, sizeof(buf)); 131 ATF_REQUIRE(rv > 0); 132 133 written += rv; 134 } 135 136 ATF_REQUIRE_EQ(0, lseek(fd, 0, SEEK_SET)); 137 return (fd); 138 } 139 140 static void 141 disable_coredumps(void) 142 { 143 struct rlimit rl = { 0 }; 144 145 if (setrlimit(RLIMIT_CORE, &rl) == -1) 146 _exit(EX_OSERR); 147 } 148 149 /* 150 * Replaces stdin with a file that we can actually read from, for tests where 151 * we want a FILE * or fd that we can get data from. 152 */ 153 static void __unused 154 replace_stdin(void) 155 { 156 int fd; 157 158 fd = new_tmpfile(); 159 160 (void)dup2(fd, STDIN_FILENO); 161 if (fd != STDIN_FILENO) 162 close(fd); 163 } 164 165 ATF_TC_WITHOUT_HEAD(FD_SET_before_end); 166 ATF_TC_BODY(FD_SET_before_end, tc) 167 { 168 #define BUF &__stack.__buf 169 struct { 170 uint8_t padding_l; 171 fd_set __buf; 172 uint8_t padding_r; 173 } __stack; 174 const size_t __bufsz __unused = sizeof(__stack.__buf); 175 const size_t __len = FD_SETSIZE - 1; 176 const size_t __idx __unused = __len - 1; 177 178 FD_SET(__idx, &__stack.__buf); 179 #undef BUF 180 181 } 182 183 ATF_TC_WITHOUT_HEAD(FD_SET_end); 184 ATF_TC_BODY(FD_SET_end, tc) 185 { 186 #define BUF &__stack.__buf 187 struct { 188 uint8_t padding_l; 189 fd_set __buf; 190 uint8_t padding_r; 191 } __stack; 192 const size_t __bufsz __unused = sizeof(__stack.__buf); 193 const size_t __len = FD_SETSIZE; 194 const size_t __idx __unused = __len - 1; 195 196 FD_SET(__idx, &__stack.__buf); 197 #undef BUF 198 199 } 200 201 ATF_TC_WITHOUT_HEAD(FD_SET_after_end); 202 ATF_TC_BODY(FD_SET_after_end, tc) 203 { 204 #define BUF &__stack.__buf 205 struct { 206 uint8_t padding_l; 207 fd_set __buf; 208 uint8_t padding_r; 209 } __stack; 210 const size_t __bufsz __unused = sizeof(__stack.__buf); 211 const size_t __len = FD_SETSIZE + 1; 212 const size_t __idx __unused = __len - 1; 213 pid_t __child; 214 int __status; 215 216 __child = fork(); 217 ATF_REQUIRE(__child >= 0); 218 if (__child > 0) 219 goto monitor; 220 221 /* Child */ 222 disable_coredumps(); 223 FD_SET(__idx, &__stack.__buf); 224 _exit(EX_SOFTWARE); /* Should have aborted. */ 225 226 monitor: 227 while (waitpid(__child, &__status, 0) != __child) { 228 ATF_REQUIRE_EQ(EINTR, errno); 229 } 230 231 if (!WIFSIGNALED(__status)) { 232 switch (WEXITSTATUS(__status)) { 233 case EX_SOFTWARE: 234 atf_tc_fail("FORTIFY_SOURCE failed to abort"); 235 break; 236 case EX_OSERR: 237 atf_tc_fail("setrlimit(2) failed"); 238 break; 239 default: 240 atf_tc_fail("child exited with status %d", 241 WEXITSTATUS(__status)); 242 } 243 } else { 244 ATF_REQUIRE_EQ(SIGABRT, WTERMSIG(__status)); 245 } 246 #undef BUF 247 248 } 249 250 ATF_TC_WITHOUT_HEAD(FD_SET_heap_before_end); 251 ATF_TC_BODY(FD_SET_heap_before_end, tc) 252 { 253 #define BUF __stack.__buf 254 struct { 255 uint8_t padding_l; 256 fd_set * __buf; 257 uint8_t padding_r; 258 } __stack; 259 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 260 const size_t __len = FD_SETSIZE - 1; 261 const size_t __idx __unused = __len - 1; 262 263 __stack.__buf = malloc(__bufsz); 264 265 FD_SET(__idx, __stack.__buf); 266 #undef BUF 267 268 } 269 270 ATF_TC_WITHOUT_HEAD(FD_SET_heap_end); 271 ATF_TC_BODY(FD_SET_heap_end, tc) 272 { 273 #define BUF __stack.__buf 274 struct { 275 uint8_t padding_l; 276 fd_set * __buf; 277 uint8_t padding_r; 278 } __stack; 279 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 280 const size_t __len = FD_SETSIZE; 281 const size_t __idx __unused = __len - 1; 282 283 __stack.__buf = malloc(__bufsz); 284 285 FD_SET(__idx, __stack.__buf); 286 #undef BUF 287 288 } 289 290 ATF_TC_WITHOUT_HEAD(FD_SET_heap_after_end); 291 ATF_TC_BODY(FD_SET_heap_after_end, tc) 292 { 293 #define BUF __stack.__buf 294 struct { 295 uint8_t padding_l; 296 fd_set * __buf; 297 uint8_t padding_r; 298 } __stack; 299 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 300 const size_t __len = FD_SETSIZE + 1; 301 const size_t __idx __unused = __len - 1; 302 pid_t __child; 303 int __status; 304 305 __child = fork(); 306 ATF_REQUIRE(__child >= 0); 307 if (__child > 0) 308 goto monitor; 309 310 /* Child */ 311 disable_coredumps(); 312 __stack.__buf = malloc(__bufsz); 313 314 FD_SET(__idx, __stack.__buf); 315 _exit(EX_SOFTWARE); /* Should have aborted. */ 316 317 monitor: 318 while (waitpid(__child, &__status, 0) != __child) { 319 ATF_REQUIRE_EQ(EINTR, errno); 320 } 321 322 if (!WIFSIGNALED(__status)) { 323 switch (WEXITSTATUS(__status)) { 324 case EX_SOFTWARE: 325 atf_tc_fail("FORTIFY_SOURCE failed to abort"); 326 break; 327 case EX_OSERR: 328 atf_tc_fail("setrlimit(2) failed"); 329 break; 330 default: 331 atf_tc_fail("child exited with status %d", 332 WEXITSTATUS(__status)); 333 } 334 } else { 335 ATF_REQUIRE_EQ(SIGABRT, WTERMSIG(__status)); 336 } 337 #undef BUF 338 339 } 340 341 ATF_TC_WITHOUT_HEAD(FD_CLR_before_end); 342 ATF_TC_BODY(FD_CLR_before_end, tc) 343 { 344 #define BUF &__stack.__buf 345 struct { 346 uint8_t padding_l; 347 fd_set __buf; 348 uint8_t padding_r; 349 } __stack; 350 const size_t __bufsz __unused = sizeof(__stack.__buf); 351 const size_t __len = FD_SETSIZE - 1; 352 const size_t __idx __unused = __len - 1; 353 354 FD_CLR(__idx, &__stack.__buf); 355 #undef BUF 356 357 } 358 359 ATF_TC_WITHOUT_HEAD(FD_CLR_end); 360 ATF_TC_BODY(FD_CLR_end, tc) 361 { 362 #define BUF &__stack.__buf 363 struct { 364 uint8_t padding_l; 365 fd_set __buf; 366 uint8_t padding_r; 367 } __stack; 368 const size_t __bufsz __unused = sizeof(__stack.__buf); 369 const size_t __len = FD_SETSIZE; 370 const size_t __idx __unused = __len - 1; 371 372 FD_CLR(__idx, &__stack.__buf); 373 #undef BUF 374 375 } 376 377 ATF_TC_WITHOUT_HEAD(FD_CLR_after_end); 378 ATF_TC_BODY(FD_CLR_after_end, tc) 379 { 380 #define BUF &__stack.__buf 381 struct { 382 uint8_t padding_l; 383 fd_set __buf; 384 uint8_t padding_r; 385 } __stack; 386 const size_t __bufsz __unused = sizeof(__stack.__buf); 387 const size_t __len = FD_SETSIZE + 1; 388 const size_t __idx __unused = __len - 1; 389 pid_t __child; 390 int __status; 391 392 __child = fork(); 393 ATF_REQUIRE(__child >= 0); 394 if (__child > 0) 395 goto monitor; 396 397 /* Child */ 398 disable_coredumps(); 399 FD_CLR(__idx, &__stack.__buf); 400 _exit(EX_SOFTWARE); /* Should have aborted. */ 401 402 monitor: 403 while (waitpid(__child, &__status, 0) != __child) { 404 ATF_REQUIRE_EQ(EINTR, errno); 405 } 406 407 if (!WIFSIGNALED(__status)) { 408 switch (WEXITSTATUS(__status)) { 409 case EX_SOFTWARE: 410 atf_tc_fail("FORTIFY_SOURCE failed to abort"); 411 break; 412 case EX_OSERR: 413 atf_tc_fail("setrlimit(2) failed"); 414 break; 415 default: 416 atf_tc_fail("child exited with status %d", 417 WEXITSTATUS(__status)); 418 } 419 } else { 420 ATF_REQUIRE_EQ(SIGABRT, WTERMSIG(__status)); 421 } 422 #undef BUF 423 424 } 425 426 ATF_TC_WITHOUT_HEAD(FD_CLR_heap_before_end); 427 ATF_TC_BODY(FD_CLR_heap_before_end, tc) 428 { 429 #define BUF __stack.__buf 430 struct { 431 uint8_t padding_l; 432 fd_set * __buf; 433 uint8_t padding_r; 434 } __stack; 435 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 436 const size_t __len = FD_SETSIZE - 1; 437 const size_t __idx __unused = __len - 1; 438 439 __stack.__buf = malloc(__bufsz); 440 441 FD_CLR(__idx, __stack.__buf); 442 #undef BUF 443 444 } 445 446 ATF_TC_WITHOUT_HEAD(FD_CLR_heap_end); 447 ATF_TC_BODY(FD_CLR_heap_end, tc) 448 { 449 #define BUF __stack.__buf 450 struct { 451 uint8_t padding_l; 452 fd_set * __buf; 453 uint8_t padding_r; 454 } __stack; 455 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 456 const size_t __len = FD_SETSIZE; 457 const size_t __idx __unused = __len - 1; 458 459 __stack.__buf = malloc(__bufsz); 460 461 FD_CLR(__idx, __stack.__buf); 462 #undef BUF 463 464 } 465 466 ATF_TC_WITHOUT_HEAD(FD_CLR_heap_after_end); 467 ATF_TC_BODY(FD_CLR_heap_after_end, tc) 468 { 469 #define BUF __stack.__buf 470 struct { 471 uint8_t padding_l; 472 fd_set * __buf; 473 uint8_t padding_r; 474 } __stack; 475 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 476 const size_t __len = FD_SETSIZE + 1; 477 const size_t __idx __unused = __len - 1; 478 pid_t __child; 479 int __status; 480 481 __child = fork(); 482 ATF_REQUIRE(__child >= 0); 483 if (__child > 0) 484 goto monitor; 485 486 /* Child */ 487 disable_coredumps(); 488 __stack.__buf = malloc(__bufsz); 489 490 FD_CLR(__idx, __stack.__buf); 491 _exit(EX_SOFTWARE); /* Should have aborted. */ 492 493 monitor: 494 while (waitpid(__child, &__status, 0) != __child) { 495 ATF_REQUIRE_EQ(EINTR, errno); 496 } 497 498 if (!WIFSIGNALED(__status)) { 499 switch (WEXITSTATUS(__status)) { 500 case EX_SOFTWARE: 501 atf_tc_fail("FORTIFY_SOURCE failed to abort"); 502 break; 503 case EX_OSERR: 504 atf_tc_fail("setrlimit(2) failed"); 505 break; 506 default: 507 atf_tc_fail("child exited with status %d", 508 WEXITSTATUS(__status)); 509 } 510 } else { 511 ATF_REQUIRE_EQ(SIGABRT, WTERMSIG(__status)); 512 } 513 #undef BUF 514 515 } 516 517 ATF_TC_WITHOUT_HEAD(FD_ISSET_before_end); 518 ATF_TC_BODY(FD_ISSET_before_end, tc) 519 { 520 #define BUF &__stack.__buf 521 struct { 522 uint8_t padding_l; 523 fd_set __buf; 524 uint8_t padding_r; 525 } __stack; 526 const size_t __bufsz __unused = sizeof(__stack.__buf); 527 const size_t __len = FD_SETSIZE - 1; 528 const size_t __idx __unused = __len - 1; 529 530 FD_ISSET(__idx, &__stack.__buf); 531 #undef BUF 532 533 } 534 535 ATF_TC_WITHOUT_HEAD(FD_ISSET_end); 536 ATF_TC_BODY(FD_ISSET_end, tc) 537 { 538 #define BUF &__stack.__buf 539 struct { 540 uint8_t padding_l; 541 fd_set __buf; 542 uint8_t padding_r; 543 } __stack; 544 const size_t __bufsz __unused = sizeof(__stack.__buf); 545 const size_t __len = FD_SETSIZE; 546 const size_t __idx __unused = __len - 1; 547 548 FD_ISSET(__idx, &__stack.__buf); 549 #undef BUF 550 551 } 552 553 ATF_TC_WITHOUT_HEAD(FD_ISSET_after_end); 554 ATF_TC_BODY(FD_ISSET_after_end, tc) 555 { 556 #define BUF &__stack.__buf 557 struct { 558 uint8_t padding_l; 559 fd_set __buf; 560 uint8_t padding_r; 561 } __stack; 562 const size_t __bufsz __unused = sizeof(__stack.__buf); 563 const size_t __len = FD_SETSIZE + 1; 564 const size_t __idx __unused = __len - 1; 565 pid_t __child; 566 int __status; 567 568 __child = fork(); 569 ATF_REQUIRE(__child >= 0); 570 if (__child > 0) 571 goto monitor; 572 573 /* Child */ 574 disable_coredumps(); 575 FD_ISSET(__idx, &__stack.__buf); 576 _exit(EX_SOFTWARE); /* Should have aborted. */ 577 578 monitor: 579 while (waitpid(__child, &__status, 0) != __child) { 580 ATF_REQUIRE_EQ(EINTR, errno); 581 } 582 583 if (!WIFSIGNALED(__status)) { 584 switch (WEXITSTATUS(__status)) { 585 case EX_SOFTWARE: 586 atf_tc_fail("FORTIFY_SOURCE failed to abort"); 587 break; 588 case EX_OSERR: 589 atf_tc_fail("setrlimit(2) failed"); 590 break; 591 default: 592 atf_tc_fail("child exited with status %d", 593 WEXITSTATUS(__status)); 594 } 595 } else { 596 ATF_REQUIRE_EQ(SIGABRT, WTERMSIG(__status)); 597 } 598 #undef BUF 599 600 } 601 602 ATF_TC_WITHOUT_HEAD(FD_ISSET_heap_before_end); 603 ATF_TC_BODY(FD_ISSET_heap_before_end, tc) 604 { 605 #define BUF __stack.__buf 606 struct { 607 uint8_t padding_l; 608 fd_set * __buf; 609 uint8_t padding_r; 610 } __stack; 611 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 612 const size_t __len = FD_SETSIZE - 1; 613 const size_t __idx __unused = __len - 1; 614 615 __stack.__buf = malloc(__bufsz); 616 617 FD_ISSET(__idx, __stack.__buf); 618 #undef BUF 619 620 } 621 622 ATF_TC_WITHOUT_HEAD(FD_ISSET_heap_end); 623 ATF_TC_BODY(FD_ISSET_heap_end, tc) 624 { 625 #define BUF __stack.__buf 626 struct { 627 uint8_t padding_l; 628 fd_set * __buf; 629 uint8_t padding_r; 630 } __stack; 631 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 632 const size_t __len = FD_SETSIZE; 633 const size_t __idx __unused = __len - 1; 634 635 __stack.__buf = malloc(__bufsz); 636 637 FD_ISSET(__idx, __stack.__buf); 638 #undef BUF 639 640 } 641 642 ATF_TC_WITHOUT_HEAD(FD_ISSET_heap_after_end); 643 ATF_TC_BODY(FD_ISSET_heap_after_end, tc) 644 { 645 #define BUF __stack.__buf 646 struct { 647 uint8_t padding_l; 648 fd_set * __buf; 649 uint8_t padding_r; 650 } __stack; 651 const size_t __bufsz __unused = sizeof(*__stack.__buf) * (1); 652 const size_t __len = FD_SETSIZE + 1; 653 const size_t __idx __unused = __len - 1; 654 pid_t __child; 655 int __status; 656 657 __child = fork(); 658 ATF_REQUIRE(__child >= 0); 659 if (__child > 0) 660 goto monitor; 661 662 /* Child */ 663 disable_coredumps(); 664 __stack.__buf = malloc(__bufsz); 665 666 FD_ISSET(__idx, __stack.__buf); 667 _exit(EX_SOFTWARE); /* Should have aborted. */ 668 669 monitor: 670 while (waitpid(__child, &__status, 0) != __child) { 671 ATF_REQUIRE_EQ(EINTR, errno); 672 } 673 674 if (!WIFSIGNALED(__status)) { 675 switch (WEXITSTATUS(__status)) { 676 case EX_SOFTWARE: 677 atf_tc_fail("FORTIFY_SOURCE failed to abort"); 678 break; 679 case EX_OSERR: 680 atf_tc_fail("setrlimit(2) failed"); 681 break; 682 default: 683 atf_tc_fail("child exited with status %d", 684 WEXITSTATUS(__status)); 685 } 686 } else { 687 ATF_REQUIRE_EQ(SIGABRT, WTERMSIG(__status)); 688 } 689 #undef BUF 690 691 } 692 693 ATF_TP_ADD_TCS(tp) 694 { 695 ATF_TP_ADD_TC(tp, FD_SET_before_end); 696 ATF_TP_ADD_TC(tp, FD_SET_end); 697 ATF_TP_ADD_TC(tp, FD_SET_after_end); 698 ATF_TP_ADD_TC(tp, FD_SET_heap_before_end); 699 ATF_TP_ADD_TC(tp, FD_SET_heap_end); 700 ATF_TP_ADD_TC(tp, FD_SET_heap_after_end); 701 ATF_TP_ADD_TC(tp, FD_CLR_before_end); 702 ATF_TP_ADD_TC(tp, FD_CLR_end); 703 ATF_TP_ADD_TC(tp, FD_CLR_after_end); 704 ATF_TP_ADD_TC(tp, FD_CLR_heap_before_end); 705 ATF_TP_ADD_TC(tp, FD_CLR_heap_end); 706 ATF_TP_ADD_TC(tp, FD_CLR_heap_after_end); 707 ATF_TP_ADD_TC(tp, FD_ISSET_before_end); 708 ATF_TP_ADD_TC(tp, FD_ISSET_end); 709 ATF_TP_ADD_TC(tp, FD_ISSET_after_end); 710 ATF_TP_ADD_TC(tp, FD_ISSET_heap_before_end); 711 ATF_TP_ADD_TC(tp, FD_ISSET_heap_end); 712 ATF_TP_ADD_TC(tp, FD_ISSET_heap_after_end); 713 return (atf_no_error()); 714 } 715