t_ptrace_wait.c revision 1.112
1/* $NetBSD: t_ptrace_wait.c,v 1.112 2019/04/25 11:45:12 kamil Exp $ */ 2 3/*- 4 * Copyright (c) 2016, 2017, 2018, 2019 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 CONTRIBUTORS 17 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 18 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 19 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 20 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 26 * POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29#include <sys/cdefs.h> 30__RCSID("$NetBSD: t_ptrace_wait.c,v 1.112 2019/04/25 11:45:12 kamil Exp $"); 31 32#include <sys/param.h> 33#include <sys/types.h> 34#include <sys/mman.h> 35#include <sys/ptrace.h> 36#include <sys/resource.h> 37#include <sys/stat.h> 38#include <sys/syscall.h> 39#include <sys/sysctl.h> 40#include <sys/wait.h> 41#include <machine/reg.h> 42#include <elf.h> 43#include <err.h> 44#include <errno.h> 45#include <lwp.h> 46#include <pthread.h> 47#include <sched.h> 48#include <signal.h> 49#include <stdint.h> 50#include <stdio.h> 51#include <stdlib.h> 52#include <strings.h> 53#include <time.h> 54#include <unistd.h> 55 56#include <atf-c.h> 57 58#include "h_macros.h" 59 60#include "t_ptrace_wait.h" 61#include "msg.h" 62 63#define PARENT_TO_CHILD(info, fds, msg) \ 64 SYSCALL_REQUIRE(msg_write_child(info " to child " # fds, &fds, &msg, \ 65 sizeof(msg)) == 0) 66 67#define CHILD_FROM_PARENT(info, fds, msg) \ 68 FORKEE_ASSERT(msg_read_parent(info " from parent " # fds, &fds, &msg, \ 69 sizeof(msg)) == 0) 70 71#define CHILD_TO_PARENT(info, fds, msg) \ 72 FORKEE_ASSERT(msg_write_parent(info " to parent " # fds, &fds, &msg, \ 73 sizeof(msg)) == 0) 74 75#define PARENT_FROM_CHILD(info, fds, msg) \ 76 SYSCALL_REQUIRE(msg_read_child(info " from parent " # fds, &fds, &msg, \ 77 sizeof(msg)) == 0) 78 79#define SYSCALL_REQUIRE(expr) ATF_REQUIRE_MSG(expr, "%s: %s", # expr, \ 80 strerror(errno)) 81#define SYSCALL_REQUIRE_ERRNO(res, exp) ATF_REQUIRE_MSG(res == exp, \ 82 "%d(%s) != %d", res, strerror(res), exp) 83 84static int debug = 0; 85 86#define DPRINTF(a, ...) do \ 87 if (debug) printf(a, ##__VA_ARGS__); \ 88 while (/*CONSTCOND*/0) 89 90#ifndef TEST_VFORK_ENABLED 91#define TEST_VFORK_ENABLED 0 92#endif 93 94/// ---------------------------------------------------------------------------- 95 96static void 97traceme_raise(int sigval) 98{ 99 const int exitval = 5; 100 pid_t child, wpid; 101#if defined(TWAIT_HAVE_STATUS) 102 int status; 103#endif 104 105 struct ptrace_siginfo info; 106 memset(&info, 0, sizeof(info)); 107 108 DPRINTF("Before forking process PID=%d\n", getpid()); 109 SYSCALL_REQUIRE((child = fork()) != -1); 110 if (child == 0) { 111 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 112 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 113 114 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 115 FORKEE_ASSERT(raise(sigval) == 0); 116 117 switch (sigval) { 118 case SIGKILL: 119 /* NOTREACHED */ 120 FORKEE_ASSERTX(0 && "This shall not be reached"); 121 __unreachable(); 122 default: 123 DPRINTF("Before exiting of the child process\n"); 124 _exit(exitval); 125 } 126 } 127 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 128 129 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 130 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 131 132 switch (sigval) { 133 case SIGKILL: 134 validate_status_signaled(status, sigval, 0); 135 break; 136 default: 137 validate_status_stopped(status, sigval); 138 139 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 140 "child\n"); 141 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, 142 sizeof(info)) != -1); 143 144 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 145 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 146 "si_errno=%#x\n", 147 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 148 info.psi_siginfo.si_errno); 149 150 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 151 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 152 153 DPRINTF("Before resuming the child process where it left off " 154 "and without signal to be sent\n"); 155 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 156 157 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 158 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 159 child); 160 break; 161 } 162 163 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 164 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 165} 166 167#define TRACEME_RAISE(test, sig) \ 168ATF_TC(test); \ 169ATF_TC_HEAD(test, tc) \ 170{ \ 171 atf_tc_set_md_var(tc, "descr", \ 172 "Verify " #sig " followed by _exit(2) in a child"); \ 173} \ 174 \ 175ATF_TC_BODY(test, tc) \ 176{ \ 177 \ 178 traceme_raise(sig); \ 179} 180 181TRACEME_RAISE(traceme_raise1, SIGKILL) /* non-maskable */ 182TRACEME_RAISE(traceme_raise2, SIGSTOP) /* non-maskable */ 183TRACEME_RAISE(traceme_raise3, SIGABRT) /* regular abort trap */ 184TRACEME_RAISE(traceme_raise4, SIGHUP) /* hangup */ 185TRACEME_RAISE(traceme_raise5, SIGCONT) /* continued? */ 186TRACEME_RAISE(traceme_raise6, SIGTRAP) /* crash signal */ 187TRACEME_RAISE(traceme_raise7, SIGBUS) /* crash signal */ 188TRACEME_RAISE(traceme_raise8, SIGILL) /* crash signal */ 189TRACEME_RAISE(traceme_raise9, SIGFPE) /* crash signal */ 190TRACEME_RAISE(traceme_raise10, SIGSEGV) /* crash signal */ 191 192/// ---------------------------------------------------------------------------- 193 194static void 195traceme_raisesignal_ignored(int sigignored) 196{ 197 const int exitval = 5; 198 const int sigval = SIGSTOP; 199 pid_t child, wpid; 200 struct sigaction sa; 201#if defined(TWAIT_HAVE_STATUS) 202 int status; 203#endif 204 struct ptrace_siginfo info; 205 206 memset(&info, 0, sizeof(info)); 207 208 DPRINTF("Before forking process PID=%d\n", getpid()); 209 SYSCALL_REQUIRE((child = fork()) != -1); 210 if (child == 0) { 211 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 212 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 213 214 memset(&sa, 0, sizeof(sa)); 215 sa.sa_handler = SIG_IGN; 216 sigemptyset(&sa.sa_mask); 217 FORKEE_ASSERT(sigaction(sigignored, &sa, NULL) != -1); 218 219 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 220 FORKEE_ASSERT(raise(sigval) == 0); 221 222 DPRINTF("Before raising %s from child\n", 223 strsignal(sigignored)); 224 FORKEE_ASSERT(raise(sigignored) == 0); 225 226 DPRINTF("Before exiting of the child process\n"); 227 _exit(exitval); 228 } 229 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 230 231 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 232 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 233 234 validate_status_stopped(status, sigval); 235 236 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 237 SYSCALL_REQUIRE( 238 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 239 240 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 241 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 242 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 243 info.psi_siginfo.si_errno); 244 245 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 246 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 247 248 DPRINTF("Before resuming the child process where it left off and " 249 "without signal to be sent\n"); 250 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 251 252 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 253 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 254 255 validate_status_stopped(status, sigignored); 256 257 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 258 SYSCALL_REQUIRE( 259 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 260 261 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 262 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 263 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 264 info.psi_siginfo.si_errno); 265 266 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigignored); 267 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 268 269 DPRINTF("Before resuming the child process where it left off and " 270 "without signal to be sent\n"); 271 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 272 273 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 274 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 275 276 validate_status_exited(status, exitval); 277 278 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 279 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 280} 281 282#define TRACEME_RAISESIGNAL_IGNORED(test, sig) \ 283ATF_TC(test); \ 284ATF_TC_HEAD(test, tc) \ 285{ \ 286 atf_tc_set_md_var(tc, "descr", \ 287 "Verify that ignoring (with SIG_IGN) " #sig " in tracee " \ 288 "does not stop tracer from catching this raised signal"); \ 289} \ 290 \ 291ATF_TC_BODY(test, tc) \ 292{ \ 293 \ 294 traceme_raisesignal_ignored(sig); \ 295} 296 297// A signal handler for SIGKILL and SIGSTOP cannot be ignored. 298TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored1, SIGABRT) /* abort */ 299TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored2, SIGHUP) /* hangup */ 300TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored3, SIGCONT) /* cont. */ 301TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored4, SIGTRAP) /* crash */ 302TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored5, SIGBUS) /* crash */ 303TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored6, SIGILL) /* crash */ 304TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored7, SIGFPE) /* crash */ 305TRACEME_RAISESIGNAL_IGNORED(traceme_raisesignal_ignored8, SIGSEGV) /* crash */ 306 307/// ---------------------------------------------------------------------------- 308 309static void 310traceme_raisesignal_masked(int sigmasked) 311{ 312 const int exitval = 5; 313 const int sigval = SIGSTOP; 314 pid_t child, wpid; 315#if defined(TWAIT_HAVE_STATUS) 316 int status; 317#endif 318 sigset_t intmask; 319 struct ptrace_siginfo info; 320 321 memset(&info, 0, sizeof(info)); 322 323 DPRINTF("Before forking process PID=%d\n", getpid()); 324 SYSCALL_REQUIRE((child = fork()) != -1); 325 if (child == 0) { 326 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 327 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 328 329 sigemptyset(&intmask); 330 sigaddset(&intmask, sigmasked); 331 sigprocmask(SIG_BLOCK, &intmask, NULL); 332 333 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 334 FORKEE_ASSERT(raise(sigval) == 0); 335 336 DPRINTF("Before raising %s breakpoint from child\n", 337 strsignal(sigmasked)); 338 FORKEE_ASSERT(raise(sigmasked) == 0); 339 340 DPRINTF("Before exiting of the child process\n"); 341 _exit(exitval); 342 } 343 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 344 345 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 346 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 347 348 validate_status_stopped(status, sigval); 349 350 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 351 SYSCALL_REQUIRE( 352 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 353 354 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 355 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 356 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 357 info.psi_siginfo.si_errno); 358 359 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 360 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 361 362 DPRINTF("Before resuming the child process where it left off and " 363 "without signal to be sent\n"); 364 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 365 366 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 367 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 368 369 validate_status_exited(status, exitval); 370 371 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 372 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 373} 374 375#define TRACEME_RAISESIGNAL_MASKED(test, sig) \ 376ATF_TC(test); \ 377ATF_TC_HEAD(test, tc) \ 378{ \ 379 atf_tc_set_md_var(tc, "descr", \ 380 "Verify that masking (with SIG_BLOCK) " #sig " in tracee " \ 381 "stops tracer from catching this raised signal"); \ 382} \ 383 \ 384ATF_TC_BODY(test, tc) \ 385{ \ 386 \ 387 traceme_raisesignal_masked(sig); \ 388} 389 390// A signal handler for SIGKILL and SIGSTOP cannot be masked. 391TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked1, SIGABRT) /* abort trap */ 392TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked2, SIGHUP) /* hangup */ 393TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked3, SIGCONT) /* continued? */ 394TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked4, SIGTRAP) /* crash sig. */ 395TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked5, SIGBUS) /* crash sig. */ 396TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked6, SIGILL) /* crash sig. */ 397TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked7, SIGFPE) /* crash sig. */ 398TRACEME_RAISESIGNAL_MASKED(traceme_raisesignal_masked8, SIGSEGV) /* crash sig. */ 399 400/// ---------------------------------------------------------------------------- 401 402static void 403traceme_crash(int sig) 404{ 405 pid_t child, wpid; 406#if defined(TWAIT_HAVE_STATUS) 407 int status; 408#endif 409 struct ptrace_siginfo info; 410 411#ifndef PTRACE_ILLEGAL_ASM 412 if (sig == SIGILL) 413 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 414#endif 415 416 memset(&info, 0, sizeof(info)); 417 418 DPRINTF("Before forking process PID=%d\n", getpid()); 419 SYSCALL_REQUIRE((child = fork()) != -1); 420 if (child == 0) { 421 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 422 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 423 424 DPRINTF("Before executing a trap\n"); 425 switch (sig) { 426 case SIGTRAP: 427 trigger_trap(); 428 break; 429 case SIGSEGV: 430 trigger_segv(); 431 break; 432 case SIGILL: 433 trigger_ill(); 434 break; 435 case SIGFPE: 436 trigger_fpe(); 437 break; 438 case SIGBUS: 439 trigger_bus(); 440 break; 441 default: 442 /* NOTREACHED */ 443 FORKEE_ASSERTX(0 && "This shall not be reached"); 444 } 445 446 /* NOTREACHED */ 447 FORKEE_ASSERTX(0 && "This shall not be reached"); 448 } 449 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 450 451 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 452 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 453 454 validate_status_stopped(status, sig); 455 456 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 457 SYSCALL_REQUIRE( 458 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 459 460 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 461 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 462 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 463 info.psi_siginfo.si_errno); 464 465 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sig); 466 switch (sig) { 467 case SIGTRAP: 468 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_BRKPT); 469 break; 470 case SIGSEGV: 471 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SEGV_MAPERR); 472 break; 473 case SIGILL: 474 ATF_REQUIRE(info.psi_siginfo.si_code >= 0 && 475 info.psi_siginfo.si_code <= ILL_BADSTK); 476 break; 477 case SIGFPE: 478 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, FPE_INTDIV); 479 break; 480 case SIGBUS: 481 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, BUS_ADRERR); 482 break; 483 } 484 485 SYSCALL_REQUIRE(ptrace(PT_KILL, child, NULL, 0) != -1); 486 487 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 488 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 489 490 validate_status_signaled(status, SIGKILL, 0); 491 492 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 493 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 494} 495 496#define TRACEME_CRASH(test, sig) \ 497ATF_TC(test); \ 498ATF_TC_HEAD(test, tc) \ 499{ \ 500 atf_tc_set_md_var(tc, "descr", \ 501 "Verify crash signal " #sig " in a child after PT_TRACE_ME"); \ 502} \ 503 \ 504ATF_TC_BODY(test, tc) \ 505{ \ 506 \ 507 traceme_crash(sig); \ 508} 509 510TRACEME_CRASH(traceme_crash_trap, SIGTRAP) 511TRACEME_CRASH(traceme_crash_segv, SIGSEGV) 512TRACEME_CRASH(traceme_crash_ill, SIGILL) 513TRACEME_CRASH(traceme_crash_fpe, SIGFPE) 514TRACEME_CRASH(traceme_crash_bus, SIGBUS) 515 516/// ---------------------------------------------------------------------------- 517 518static void 519traceme_signalmasked_crash(int sig) 520{ 521 const int sigval = SIGSTOP; 522 pid_t child, wpid; 523#if defined(TWAIT_HAVE_STATUS) 524 int status; 525#endif 526 struct ptrace_siginfo info; 527 sigset_t intmask; 528 struct kinfo_proc2 kp; 529 size_t len = sizeof(kp); 530 531 int name[6]; 532 const size_t namelen = __arraycount(name); 533 ki_sigset_t kp_sigmask; 534 535#ifndef PTRACE_ILLEGAL_ASM 536 if (sig == SIGILL) 537 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 538#endif 539 540 memset(&info, 0, sizeof(info)); 541 542 DPRINTF("Before forking process PID=%d\n", getpid()); 543 SYSCALL_REQUIRE((child = fork()) != -1); 544 if (child == 0) { 545 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 546 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 547 548 sigemptyset(&intmask); 549 sigaddset(&intmask, sig); 550 sigprocmask(SIG_BLOCK, &intmask, NULL); 551 552 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 553 FORKEE_ASSERT(raise(sigval) == 0); 554 555 DPRINTF("Before executing a trap\n"); 556 switch (sig) { 557 case SIGTRAP: 558 trigger_trap(); 559 break; 560 case SIGSEGV: 561 trigger_segv(); 562 break; 563 case SIGILL: 564 trigger_ill(); 565 break; 566 case SIGFPE: 567 trigger_fpe(); 568 break; 569 case SIGBUS: 570 trigger_bus(); 571 break; 572 default: 573 /* NOTREACHED */ 574 FORKEE_ASSERTX(0 && "This shall not be reached"); 575 } 576 577 /* NOTREACHED */ 578 FORKEE_ASSERTX(0 && "This shall not be reached"); 579 } 580 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 581 582 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 583 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 584 585 validate_status_stopped(status, sigval); 586 587 name[0] = CTL_KERN, 588 name[1] = KERN_PROC2, 589 name[2] = KERN_PROC_PID; 590 name[3] = child; 591 name[4] = sizeof(kp); 592 name[5] = 1; 593 594 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 595 596 kp_sigmask = kp.p_sigmask; 597 598 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 599 SYSCALL_REQUIRE( 600 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 601 602 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 603 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 604 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 605 info.psi_siginfo.si_errno); 606 607 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 608 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 609 610 DPRINTF("Before resuming the child process where it left off and " 611 "without signal to be sent\n"); 612 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 613 614 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 615 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 616 617 validate_status_stopped(status, sig); 618 619 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 620 SYSCALL_REQUIRE( 621 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 622 623 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 624 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 625 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 626 info.psi_siginfo.si_errno); 627 628 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 629 630 DPRINTF("kp_sigmask=" 631 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 632 kp_sigmask.__bits[0], kp_sigmask.__bits[1], kp_sigmask.__bits[2], 633 kp_sigmask.__bits[3]); 634 635 DPRINTF("kp.p_sigmask=" 636 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 637 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 638 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 639 640 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, sizeof(kp_sigmask))); 641 642 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sig); 643 switch (sig) { 644 case SIGTRAP: 645 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_BRKPT); 646 break; 647 case SIGSEGV: 648 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SEGV_MAPERR); 649 break; 650 case SIGILL: 651 ATF_REQUIRE(info.psi_siginfo.si_code >= 0 && 652 info.psi_siginfo.si_code <= ILL_BADSTK); 653 break; 654 case SIGFPE: 655 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, FPE_INTDIV); 656 break; 657 case SIGBUS: 658 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, BUS_ADRERR); 659 break; 660 } 661 662 SYSCALL_REQUIRE(ptrace(PT_KILL, child, NULL, 0) != -1); 663 664 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 665 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 666 667 validate_status_signaled(status, SIGKILL, 0); 668 669 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 670 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 671} 672 673#define TRACEME_SIGNALMASKED_CRASH(test, sig) \ 674ATF_TC(test); \ 675ATF_TC_HEAD(test, tc) \ 676{ \ 677 atf_tc_set_md_var(tc, "descr", \ 678 "Verify masked crash signal " #sig " in a child after " \ 679 "PT_TRACE_ME is delivered to its tracer"); \ 680} \ 681 \ 682ATF_TC_BODY(test, tc) \ 683{ \ 684 \ 685 traceme_signalmasked_crash(sig); \ 686} 687 688TRACEME_SIGNALMASKED_CRASH(traceme_signalmasked_crash_trap, SIGTRAP) 689TRACEME_SIGNALMASKED_CRASH(traceme_signalmasked_crash_segv, SIGSEGV) 690TRACEME_SIGNALMASKED_CRASH(traceme_signalmasked_crash_ill, SIGILL) 691TRACEME_SIGNALMASKED_CRASH(traceme_signalmasked_crash_fpe, SIGFPE) 692TRACEME_SIGNALMASKED_CRASH(traceme_signalmasked_crash_bus, SIGBUS) 693 694/// ---------------------------------------------------------------------------- 695 696static void 697traceme_signalignored_crash(int sig) 698{ 699 const int sigval = SIGSTOP; 700 pid_t child, wpid; 701#if defined(TWAIT_HAVE_STATUS) 702 int status; 703#endif 704 struct sigaction sa; 705 struct ptrace_siginfo info; 706 struct kinfo_proc2 kp; 707 size_t len = sizeof(kp); 708 709 int name[6]; 710 const size_t namelen = __arraycount(name); 711 ki_sigset_t kp_sigignore; 712 713#ifndef PTRACE_ILLEGAL_ASM 714 if (sig == SIGILL) 715 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 716#endif 717 718 memset(&info, 0, sizeof(info)); 719 720 DPRINTF("Before forking process PID=%d\n", getpid()); 721 SYSCALL_REQUIRE((child = fork()) != -1); 722 if (child == 0) { 723 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 724 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 725 726 memset(&sa, 0, sizeof(sa)); 727 sa.sa_handler = SIG_IGN; 728 sigemptyset(&sa.sa_mask); 729 730 FORKEE_ASSERT(sigaction(sig, &sa, NULL) != -1); 731 732 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 733 FORKEE_ASSERT(raise(sigval) == 0); 734 735 DPRINTF("Before executing a trap\n"); 736 switch (sig) { 737 case SIGTRAP: 738 trigger_trap(); 739 break; 740 case SIGSEGV: 741 trigger_segv(); 742 break; 743 case SIGILL: 744 trigger_ill(); 745 break; 746 case SIGFPE: 747 trigger_fpe(); 748 break; 749 case SIGBUS: 750 trigger_bus(); 751 break; 752 default: 753 /* NOTREACHED */ 754 FORKEE_ASSERTX(0 && "This shall not be reached"); 755 } 756 757 /* NOTREACHED */ 758 FORKEE_ASSERTX(0 && "This shall not be reached"); 759 } 760 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 761 762 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 763 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 764 765 validate_status_stopped(status, sigval); 766 767 name[0] = CTL_KERN, 768 name[1] = KERN_PROC2, 769 name[2] = KERN_PROC_PID; 770 name[3] = child; 771 name[4] = sizeof(kp); 772 name[5] = 1; 773 774 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 775 776 kp_sigignore = kp.p_sigignore; 777 778 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 779 SYSCALL_REQUIRE( 780 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 781 782 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 783 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 784 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 785 info.psi_siginfo.si_errno); 786 787 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 788 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 789 790 DPRINTF("Before resuming the child process where it left off and " 791 "without signal to be sent\n"); 792 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 793 794 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 795 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 796 797 validate_status_stopped(status, sig); 798 799 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 800 SYSCALL_REQUIRE( 801 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 802 803 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 804 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 805 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 806 info.psi_siginfo.si_errno); 807 808 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 809 810 DPRINTF("kp_sigignore=" 811 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 812 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 813 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 814 815 DPRINTF("kp.p_sigignore=" 816 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 817 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 818 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 819 820 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, sizeof(kp_sigignore))); 821 822 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sig); 823 switch (sig) { 824 case SIGTRAP: 825 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_BRKPT); 826 break; 827 case SIGSEGV: 828 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SEGV_MAPERR); 829 break; 830 case SIGILL: 831 ATF_REQUIRE(info.psi_siginfo.si_code >= 0 && 832 info.psi_siginfo.si_code <= ILL_BADSTK); 833 break; 834 case SIGFPE: 835 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, FPE_INTDIV); 836 break; 837 case SIGBUS: 838 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, BUS_ADRERR); 839 break; 840 } 841 842 SYSCALL_REQUIRE(ptrace(PT_KILL, child, NULL, 0) != -1); 843 844 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 845 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 846 847 validate_status_signaled(status, SIGKILL, 0); 848 849 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 850 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 851} 852 853#define TRACEME_SIGNALIGNORED_CRASH(test, sig) \ 854ATF_TC(test); \ 855ATF_TC_HEAD(test, tc) \ 856{ \ 857 atf_tc_set_md_var(tc, "descr", \ 858 "Verify ignored crash signal " #sig " in a child after " \ 859 "PT_TRACE_ME is delivered to its tracer"); \ 860} \ 861 \ 862ATF_TC_BODY(test, tc) \ 863{ \ 864 \ 865 traceme_signalignored_crash(sig); \ 866} 867 868TRACEME_SIGNALIGNORED_CRASH(traceme_signalignored_crash_trap, SIGTRAP) 869TRACEME_SIGNALIGNORED_CRASH(traceme_signalignored_crash_segv, SIGSEGV) 870TRACEME_SIGNALIGNORED_CRASH(traceme_signalignored_crash_ill, SIGILL) 871TRACEME_SIGNALIGNORED_CRASH(traceme_signalignored_crash_fpe, SIGFPE) 872TRACEME_SIGNALIGNORED_CRASH(traceme_signalignored_crash_bus, SIGBUS) 873 874/// ---------------------------------------------------------------------------- 875 876static void 877traceme_sendsignal_handle(int sigsent, void (*sah)(int a), int *traceme_caught) 878{ 879 const int exitval = 5; 880 const int sigval = SIGSTOP; 881 pid_t child, wpid; 882 struct sigaction sa; 883#if defined(TWAIT_HAVE_STATUS) 884 int status; 885#endif 886 struct ptrace_siginfo info; 887 888 memset(&info, 0, sizeof(info)); 889 890 DPRINTF("Before forking process PID=%d\n", getpid()); 891 SYSCALL_REQUIRE((child = fork()) != -1); 892 if (child == 0) { 893 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 894 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 895 896 sa.sa_handler = sah; 897 sa.sa_flags = SA_SIGINFO; 898 sigemptyset(&sa.sa_mask); 899 900 FORKEE_ASSERT(sigaction(sigsent, &sa, NULL) != -1); 901 902 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 903 FORKEE_ASSERT(raise(sigval) == 0); 904 905 FORKEE_ASSERT_EQ(*traceme_caught, 1); 906 907 DPRINTF("Before exiting of the child process\n"); 908 _exit(exitval); 909 } 910 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 911 912 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 913 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 914 915 validate_status_stopped(status, sigval); 916 917 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 918 SYSCALL_REQUIRE( 919 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 920 921 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 922 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 923 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 924 info.psi_siginfo.si_errno); 925 926 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 927 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 928 929 DPRINTF("Before resuming the child process where it left off and with " 930 "signal %s to be sent\n", strsignal(sigsent)); 931 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 932 933 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 934 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 935 936 validate_status_exited(status, exitval); 937 938 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 939 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 940} 941 942#define TRACEME_SENDSIGNAL_HANDLE(test, sig) \ 943ATF_TC(test); \ 944ATF_TC_HEAD(test, tc) \ 945{ \ 946 atf_tc_set_md_var(tc, "descr", \ 947 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 948 "handled correctly and caught by a signal handler"); \ 949} \ 950 \ 951static int test##_caught = 0; \ 952 \ 953static void \ 954test##_sighandler(int arg) \ 955{ \ 956 FORKEE_ASSERT_EQ(arg, sig); \ 957 \ 958 ++ test##_caught; \ 959} \ 960 \ 961ATF_TC_BODY(test, tc) \ 962{ \ 963 \ 964 traceme_sendsignal_handle(sig, test##_sighandler, & test##_caught); \ 965} 966 967// A signal handler for SIGKILL and SIGSTOP cannot be registered. 968TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle1, SIGABRT) /* abort trap */ 969TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle2, SIGHUP) /* hangup */ 970TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle3, SIGCONT) /* continued? */ 971TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle4, SIGTRAP) /* crash sig. */ 972TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle5, SIGBUS) /* crash sig. */ 973TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle6, SIGILL) /* crash sig. */ 974TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle7, SIGFPE) /* crash sig. */ 975TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle8, SIGSEGV) /* crash sig. */ 976 977/// ---------------------------------------------------------------------------- 978 979static void 980traceme_sendsignal_masked(int sigsent) 981{ 982 const int exitval = 5; 983 const int sigval = SIGSTOP; 984 pid_t child, wpid; 985 sigset_t set; 986#if defined(TWAIT_HAVE_STATUS) 987 int status; 988#endif 989 struct ptrace_siginfo info; 990 991 memset(&info, 0, sizeof(info)); 992 993 DPRINTF("Before forking process PID=%d\n", getpid()); 994 SYSCALL_REQUIRE((child = fork()) != -1); 995 if (child == 0) { 996 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 997 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 998 999 sigemptyset(&set); 1000 sigaddset(&set, sigsent); 1001 FORKEE_ASSERT(sigprocmask(SIG_BLOCK, &set, NULL) != -1); 1002 1003 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1004 FORKEE_ASSERT(raise(sigval) == 0); 1005 1006 _exit(exitval); 1007 } 1008 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1009 1010 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1011 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1012 1013 validate_status_stopped(status, sigval); 1014 1015 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 1016 SYSCALL_REQUIRE( 1017 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 1018 1019 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 1020 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 1021 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 1022 info.psi_siginfo.si_errno); 1023 1024 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 1025 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 1026 1027 DPRINTF("Before resuming the child process where it left off and with " 1028 "signal %s to be sent\n", strsignal(sigsent)); 1029 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 1030 1031 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1032 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1033 1034 validate_status_exited(status, exitval); 1035 1036 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 1037 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1038} 1039 1040#define TRACEME_SENDSIGNAL_MASKED(test, sig) \ 1041ATF_TC(test); \ 1042ATF_TC_HEAD(test, tc) \ 1043{ \ 1044 atf_tc_set_md_var(tc, "descr", \ 1045 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 1046 "handled correctly and the signal is masked by SIG_BLOCK"); \ 1047} \ 1048 \ 1049ATF_TC_BODY(test, tc) \ 1050{ \ 1051 \ 1052 traceme_sendsignal_masked(sig); \ 1053} 1054 1055// A signal handler for SIGKILL and SIGSTOP cannot be masked. 1056TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked1, SIGABRT) /* abort trap */ 1057TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked2, SIGHUP) /* hangup */ 1058TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked3, SIGCONT) /* continued? */ 1059TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked4, SIGTRAP) /* crash sig. */ 1060TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked5, SIGBUS) /* crash sig. */ 1061TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked6, SIGILL) /* crash sig. */ 1062TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked7, SIGFPE) /* crash sig. */ 1063TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked8, SIGSEGV) /* crash sig. */ 1064 1065/// ---------------------------------------------------------------------------- 1066 1067static void 1068traceme_sendsignal_ignored(int sigsent) 1069{ 1070 const int exitval = 5; 1071 const int sigval = SIGSTOP; 1072 pid_t child, wpid; 1073 struct sigaction sa; 1074#if defined(TWAIT_HAVE_STATUS) 1075 int status; 1076#endif 1077 struct ptrace_siginfo info; 1078 1079 memset(&info, 0, sizeof(info)); 1080 1081 DPRINTF("Before forking process PID=%d\n", getpid()); 1082 SYSCALL_REQUIRE((child = fork()) != -1); 1083 if (child == 0) { 1084 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1085 1086 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1087 1088 memset(&sa, 0, sizeof(sa)); 1089 sa.sa_handler = SIG_IGN; 1090 sigemptyset(&sa.sa_mask); 1091 FORKEE_ASSERT(sigaction(sigsent, &sa, NULL) != -1); 1092 1093 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1094 FORKEE_ASSERT(raise(sigval) == 0); 1095 1096 _exit(exitval); 1097 } 1098 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1099 1100 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1101 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1102 1103 validate_status_stopped(status, sigval); 1104 1105 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 1106 SYSCALL_REQUIRE( 1107 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 1108 1109 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 1110 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 1111 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 1112 info.psi_siginfo.si_errno); 1113 1114 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 1115 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 1116 1117 DPRINTF("Before resuming the child process where it left off and with " 1118 "signal %s to be sent\n", strsignal(sigsent)); 1119 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 1120 1121 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1122 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1123 1124 validate_status_exited(status, exitval); 1125 1126 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 1127 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1128} 1129 1130#define TRACEME_SENDSIGNAL_IGNORED(test, sig) \ 1131ATF_TC(test); \ 1132ATF_TC_HEAD(test, tc) \ 1133{ \ 1134 atf_tc_set_md_var(tc, "descr", \ 1135 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 1136 "handled correctly and the signal is masked by SIG_IGN"); \ 1137} \ 1138 \ 1139ATF_TC_BODY(test, tc) \ 1140{ \ 1141 \ 1142 traceme_sendsignal_ignored(sig); \ 1143} 1144 1145// A signal handler for SIGKILL and SIGSTOP cannot be ignored. 1146TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored1, SIGABRT) /* abort */ 1147TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored2, SIGHUP) /* hangup */ 1148TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored3, SIGCONT) /* continued */ 1149TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored4, SIGTRAP) /* crash s. */ 1150TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored5, SIGBUS) /* crash s. */ 1151TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored6, SIGILL) /* crash s. */ 1152TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored7, SIGFPE) /* crash s. */ 1153TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored8, SIGSEGV) /* crash s. */ 1154 1155/// ---------------------------------------------------------------------------- 1156 1157static void 1158traceme_sendsignal_simple(int sigsent) 1159{ 1160 const int sigval = SIGSTOP; 1161 int exitval = 0; 1162 pid_t child, wpid; 1163#if defined(TWAIT_HAVE_STATUS) 1164 int status; 1165 int expect_core; 1166 1167 switch (sigsent) { 1168 case SIGABRT: 1169 case SIGTRAP: 1170 case SIGBUS: 1171 case SIGILL: 1172 case SIGFPE: 1173 case SIGSEGV: 1174 expect_core = 1; 1175 break; 1176 default: 1177 expect_core = 0; 1178 break; 1179 } 1180#endif 1181 struct ptrace_siginfo info; 1182 1183 memset(&info, 0, sizeof(info)); 1184 1185 DPRINTF("Before forking process PID=%d\n", getpid()); 1186 SYSCALL_REQUIRE((child = fork()) != -1); 1187 if (child == 0) { 1188 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1189 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1190 1191 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1192 FORKEE_ASSERT(raise(sigval) == 0); 1193 1194 switch (sigsent) { 1195 case SIGCONT: 1196 case SIGSTOP: 1197 _exit(exitval); 1198 default: 1199 /* NOTREACHED */ 1200 FORKEE_ASSERTX(0 && "This shall not be reached"); 1201 } 1202 } 1203 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1204 1205 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1206 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1207 1208 validate_status_stopped(status, sigval); 1209 1210 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 1211 SYSCALL_REQUIRE( 1212 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 1213 1214 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 1215 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 1216 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 1217 info.psi_siginfo.si_errno); 1218 1219 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 1220 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 1221 1222 DPRINTF("Before resuming the child process where it left off and with " 1223 "signal %s to be sent\n", strsignal(sigsent)); 1224 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 1225 1226 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1227 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1228 1229 switch (sigsent) { 1230 case SIGSTOP: 1231 validate_status_stopped(status, sigsent); 1232 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 1233 "child\n"); 1234 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, 1235 sizeof(info)) != -1); 1236 1237 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 1238 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 1239 "si_errno=%#x\n", 1240 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 1241 info.psi_siginfo.si_errno); 1242 1243 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 1244 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 1245 1246 DPRINTF("Before resuming the child process where it left off " 1247 "and with signal %s to be sent\n", strsignal(sigsent)); 1248 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 1249 1250 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1251 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 1252 child); 1253 /* FALLTHROUGH */ 1254 case SIGCONT: 1255 validate_status_exited(status, exitval); 1256 break; 1257 default: 1258 validate_status_signaled(status, sigsent, expect_core); 1259 break; 1260 } 1261 1262 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 1263 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1264} 1265 1266#define TRACEME_SENDSIGNAL_SIMPLE(test, sig) \ 1267ATF_TC(test); \ 1268ATF_TC_HEAD(test, tc) \ 1269{ \ 1270 atf_tc_set_md_var(tc, "descr", \ 1271 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 1272 "handled correctly in a child without a signal handler"); \ 1273} \ 1274 \ 1275ATF_TC_BODY(test, tc) \ 1276{ \ 1277 \ 1278 traceme_sendsignal_simple(sig); \ 1279} 1280 1281TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple1, SIGKILL) /* non-maskable*/ 1282TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple2, SIGSTOP) /* non-maskable*/ 1283TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple3, SIGABRT) /* abort trap */ 1284TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple4, SIGHUP) /* hangup */ 1285TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple5, SIGCONT) /* continued? */ 1286TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple6, SIGTRAP) /* crash sig. */ 1287TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple7, SIGBUS) /* crash sig. */ 1288TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple8, SIGILL) /* crash sig. */ 1289TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple9, SIGFPE) /* crash sig. */ 1290TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple10, SIGSEGV) /* crash sig. */ 1291 1292/// ---------------------------------------------------------------------------- 1293 1294ATF_TC(traceme_pid1_parent); 1295ATF_TC_HEAD(traceme_pid1_parent, tc) 1296{ 1297 atf_tc_set_md_var(tc, "descr", 1298 "Verify that PT_TRACE_ME is not allowed when our parent is PID1"); 1299} 1300 1301ATF_TC_BODY(traceme_pid1_parent, tc) 1302{ 1303 struct msg_fds parent_child; 1304 int exitval_child1 = 1, exitval_child2 = 2; 1305 pid_t child1, child2, wpid; 1306 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1307#if defined(TWAIT_HAVE_STATUS) 1308 int status; 1309#endif 1310 1311 SYSCALL_REQUIRE(msg_open(&parent_child) == 0); 1312 1313 DPRINTF("Before forking process PID=%d\n", getpid()); 1314 SYSCALL_REQUIRE((child1 = fork()) != -1); 1315 if (child1 == 0) { 1316 DPRINTF("Before forking process PID=%d\n", getpid()); 1317 SYSCALL_REQUIRE((child2 = fork()) != -1); 1318 if (child2 != 0) { 1319 DPRINTF("Parent process PID=%d, child2's PID=%d\n", 1320 getpid(), child2); 1321 _exit(exitval_child1); 1322 } 1323 CHILD_FROM_PARENT("exit child1", parent_child, msg); 1324 1325 DPRINTF("Assert that our parent is PID1 (initproc)\n"); 1326 FORKEE_ASSERT_EQ(getppid(), 1); 1327 1328 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1329 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) == -1); 1330 SYSCALL_REQUIRE_ERRNO(errno, EPERM); 1331 1332 CHILD_TO_PARENT("child2 exiting", parent_child, msg); 1333 1334 _exit(exitval_child2); 1335 } 1336 DPRINTF("Parent process PID=%d, child1's PID=%d\n", getpid(), child1); 1337 1338 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1339 TWAIT_REQUIRE_SUCCESS( 1340 wpid = TWAIT_GENERIC(child1, &status, WEXITED), child1); 1341 1342 validate_status_exited(status, exitval_child1); 1343 1344 DPRINTF("Notify that child1 is dead\n"); 1345 PARENT_TO_CHILD("exit child1", parent_child, msg); 1346 1347 DPRINTF("Wait for exiting of child2\n"); 1348 PARENT_FROM_CHILD("child2 exiting", parent_child, msg); 1349} 1350 1351/// ---------------------------------------------------------------------------- 1352 1353static void 1354traceme_vfork_raise(int sigval) 1355{ 1356 const int exitval = 5, exitval_watcher = 10; 1357 pid_t child, parent, watcher, wpid; 1358 int rv; 1359#if defined(TWAIT_HAVE_STATUS) 1360 int status; 1361 1362 /* volatile workarounds GCC -Werror=clobbered */ 1363 volatile int expect_core; 1364 1365 switch (sigval) { 1366 case SIGABRT: 1367 case SIGTRAP: 1368 case SIGBUS: 1369 case SIGILL: 1370 case SIGFPE: 1371 case SIGSEGV: 1372 expect_core = 1; 1373 break; 1374 default: 1375 expect_core = 0; 1376 break; 1377 } 1378#endif 1379 1380 /* 1381 * Spawn a dedicated thread to watch for a stopped child and emit 1382 * the SIGKILL signal to it. 1383 * 1384 * vfork(2) might clobber watcher, this means that it's safer and 1385 * simpler to reparent this process to initproc and forget about it. 1386 */ 1387 if (sigval == SIGSTOP) { 1388 parent = getpid(); 1389 1390 watcher = fork(); 1391 ATF_REQUIRE(watcher != 1); 1392 if (watcher == 0) { 1393 /* Double fork(2) trick to reparent to initproc */ 1394 watcher = fork(); 1395 FORKEE_ASSERT_NEQ(watcher, -1); 1396 if (watcher != 0) 1397 _exit(exitval_watcher); 1398 1399 child = await_stopped_child(parent); 1400 1401 errno = 0; 1402 rv = kill(child, SIGKILL); 1403 FORKEE_ASSERT_EQ(rv, 0); 1404 FORKEE_ASSERT_EQ(errno, 0); 1405 1406 /* This exit value will be collected by initproc */ 1407 _exit(0); 1408 } 1409 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1410 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(watcher, &status, 0), 1411 watcher); 1412 1413 validate_status_exited(status, exitval_watcher); 1414 1415 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1416 TWAIT_REQUIRE_FAILURE(ECHILD, 1417 wpid = TWAIT_GENERIC(watcher, &status, 0)); 1418 } 1419 1420 DPRINTF("Before forking process PID=%d\n", getpid()); 1421 SYSCALL_REQUIRE((child = vfork()) != -1); 1422 if (child == 0) { 1423 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1424 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1425 1426 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1427 FORKEE_ASSERT(raise(sigval) == 0); 1428 1429 switch (sigval) { 1430 case SIGSTOP: 1431 case SIGKILL: 1432 case SIGABRT: 1433 case SIGHUP: 1434 case SIGTRAP: 1435 case SIGBUS: 1436 case SIGILL: 1437 case SIGFPE: 1438 case SIGSEGV: 1439 /* NOTREACHED */ 1440 FORKEE_ASSERTX(0 && "This shall not be reached"); 1441 __unreachable(); 1442 default: 1443 DPRINTF("Before exiting of the child process\n"); 1444 _exit(exitval); 1445 } 1446 } 1447 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1448 1449 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1450 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1451 1452 switch (sigval) { 1453 case SIGKILL: 1454 case SIGABRT: 1455 case SIGHUP: 1456 case SIGTRAP: 1457 case SIGBUS: 1458 case SIGILL: 1459 case SIGFPE: 1460 case SIGSEGV: 1461 validate_status_signaled(status, sigval, expect_core); 1462 break; 1463 case SIGSTOP: 1464 validate_status_signaled(status, SIGKILL, 0); 1465 break; 1466 case SIGCONT: 1467 case SIGTSTP: 1468 case SIGTTIN: 1469 case SIGTTOU: 1470 validate_status_exited(status, exitval); 1471 break; 1472 default: 1473 /* NOTREACHED */ 1474 ATF_REQUIRE(0 && "NOT IMPLEMENTED"); 1475 break; 1476 } 1477 1478 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1479 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1480} 1481 1482#define TRACEME_VFORK_RAISE(test, sig) \ 1483ATF_TC(test); \ 1484ATF_TC_HEAD(test, tc) \ 1485{ \ 1486 atf_tc_set_md_var(tc, "descr", \ 1487 "Verify PT_TRACE_ME followed by raise of " #sig " in a " \ 1488 "vfork(2)ed child"); \ 1489} \ 1490 \ 1491ATF_TC_BODY(test, tc) \ 1492{ \ 1493 \ 1494 traceme_vfork_raise(sig); \ 1495} 1496 1497TRACEME_VFORK_RAISE(traceme_vfork_raise1, SIGKILL) /* non-maskable */ 1498TRACEME_VFORK_RAISE(traceme_vfork_raise2, SIGSTOP) /* non-maskable */ 1499TRACEME_VFORK_RAISE(traceme_vfork_raise3, SIGTSTP) /* ignored in vfork(2) */ 1500TRACEME_VFORK_RAISE(traceme_vfork_raise4, SIGTTIN) /* ignored in vfork(2) */ 1501TRACEME_VFORK_RAISE(traceme_vfork_raise5, SIGTTOU) /* ignored in vfork(2) */ 1502TRACEME_VFORK_RAISE(traceme_vfork_raise6, SIGABRT) /* regular abort trap */ 1503TRACEME_VFORK_RAISE(traceme_vfork_raise7, SIGHUP) /* hangup */ 1504TRACEME_VFORK_RAISE(traceme_vfork_raise8, SIGCONT) /* continued? */ 1505TRACEME_VFORK_RAISE(traceme_vfork_raise9, SIGTRAP) /* crash signal */ 1506TRACEME_VFORK_RAISE(traceme_vfork_raise10, SIGBUS) /* crash signal */ 1507TRACEME_VFORK_RAISE(traceme_vfork_raise11, SIGILL) /* crash signal */ 1508TRACEME_VFORK_RAISE(traceme_vfork_raise12, SIGFPE) /* crash signal */ 1509TRACEME_VFORK_RAISE(traceme_vfork_raise13, SIGSEGV) /* crash signal */ 1510 1511/// ---------------------------------------------------------------------------- 1512 1513static void 1514traceme_vfork_crash(int sig) 1515{ 1516 pid_t child, wpid; 1517#if defined(TWAIT_HAVE_STATUS) 1518 int status; 1519#endif 1520 1521#ifndef PTRACE_ILLEGAL_ASM 1522 if (sig == SIGILL) 1523 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 1524#endif 1525 1526 DPRINTF("Before forking process PID=%d\n", getpid()); 1527 SYSCALL_REQUIRE((child = vfork()) != -1); 1528 if (child == 0) { 1529 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1530 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1531 1532 DPRINTF("Before executing a trap\n"); 1533 switch (sig) { 1534 case SIGTRAP: 1535 trigger_trap(); 1536 break; 1537 case SIGSEGV: 1538 trigger_segv(); 1539 break; 1540 case SIGILL: 1541 trigger_ill(); 1542 break; 1543 case SIGFPE: 1544 trigger_fpe(); 1545 break; 1546 case SIGBUS: 1547 trigger_bus(); 1548 break; 1549 default: 1550 /* NOTREACHED */ 1551 FORKEE_ASSERTX(0 && "This shall not be reached"); 1552 } 1553 1554 /* NOTREACHED */ 1555 FORKEE_ASSERTX(0 && "This shall not be reached"); 1556 } 1557 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1558 1559 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1560 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1561 1562 validate_status_signaled(status, sig, 1); 1563 1564 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1565 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1566} 1567 1568#define TRACEME_VFORK_CRASH(test, sig) \ 1569ATF_TC(test); \ 1570ATF_TC_HEAD(test, tc) \ 1571{ \ 1572 atf_tc_set_md_var(tc, "descr", \ 1573 "Verify PT_TRACE_ME followed by a crash signal " #sig " in a " \ 1574 "vfork(2)ed child"); \ 1575} \ 1576 \ 1577ATF_TC_BODY(test, tc) \ 1578{ \ 1579 \ 1580 traceme_vfork_crash(sig); \ 1581} 1582 1583TRACEME_VFORK_CRASH(traceme_vfork_crash_trap, SIGTRAP) 1584TRACEME_VFORK_CRASH(traceme_vfork_crash_segv, SIGSEGV) 1585TRACEME_VFORK_CRASH(traceme_vfork_crash_ill, SIGILL) 1586TRACEME_VFORK_CRASH(traceme_vfork_crash_fpe, SIGFPE) 1587TRACEME_VFORK_CRASH(traceme_vfork_crash_bus, SIGBUS) 1588 1589/// ---------------------------------------------------------------------------- 1590 1591static void 1592traceme_vfork_signalmasked_crash(int sig) 1593{ 1594 pid_t child, wpid; 1595#if defined(TWAIT_HAVE_STATUS) 1596 int status; 1597#endif 1598 sigset_t intmask; 1599 1600#ifndef PTRACE_ILLEGAL_ASM 1601 if (sig == SIGILL) 1602 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 1603#endif 1604 1605 DPRINTF("Before forking process PID=%d\n", getpid()); 1606 SYSCALL_REQUIRE((child = vfork()) != -1); 1607 if (child == 0) { 1608 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1609 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1610 1611 sigemptyset(&intmask); 1612 sigaddset(&intmask, sig); 1613 sigprocmask(SIG_BLOCK, &intmask, NULL); 1614 1615 DPRINTF("Before executing a trap\n"); 1616 switch (sig) { 1617 case SIGTRAP: 1618 trigger_trap(); 1619 break; 1620 case SIGSEGV: 1621 trigger_segv(); 1622 break; 1623 case SIGILL: 1624 trigger_ill(); 1625 break; 1626 case SIGFPE: 1627 trigger_fpe(); 1628 break; 1629 case SIGBUS: 1630 trigger_bus(); 1631 break; 1632 default: 1633 /* NOTREACHED */ 1634 FORKEE_ASSERTX(0 && "This shall not be reached"); 1635 } 1636 1637 /* NOTREACHED */ 1638 FORKEE_ASSERTX(0 && "This shall not be reached"); 1639 } 1640 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1641 1642 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1643 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1644 1645 validate_status_signaled(status, sig, 1); 1646 1647 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1648 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1649} 1650 1651#define TRACEME_VFORK_SIGNALMASKED_CRASH(test, sig) \ 1652ATF_TC(test); \ 1653ATF_TC_HEAD(test, tc) \ 1654{ \ 1655 atf_tc_set_md_var(tc, "descr", \ 1656 "Verify PT_TRACE_ME followed by a crash signal " #sig " in a " \ 1657 "vfork(2)ed child with a masked signal"); \ 1658} \ 1659 \ 1660ATF_TC_BODY(test, tc) \ 1661{ \ 1662 \ 1663 traceme_vfork_signalmasked_crash(sig); \ 1664} 1665 1666TRACEME_VFORK_SIGNALMASKED_CRASH(traceme_vfork_signalmasked_crash_trap, SIGTRAP) 1667TRACEME_VFORK_SIGNALMASKED_CRASH(traceme_vfork_signalmasked_crash_segv, SIGSEGV) 1668TRACEME_VFORK_SIGNALMASKED_CRASH(traceme_vfork_signalmasked_crash_ill, SIGILL) 1669TRACEME_VFORK_SIGNALMASKED_CRASH(traceme_vfork_signalmasked_crash_fpe, SIGFPE) 1670TRACEME_VFORK_SIGNALMASKED_CRASH(traceme_vfork_signalmasked_crash_bus, SIGBUS) 1671 1672/// ---------------------------------------------------------------------------- 1673 1674static void 1675traceme_vfork_signalignored_crash(int sig) 1676{ 1677 pid_t child, wpid; 1678#if defined(TWAIT_HAVE_STATUS) 1679 int status; 1680#endif 1681 struct sigaction sa; 1682 1683#ifndef PTRACE_ILLEGAL_ASM 1684 if (sig == SIGILL) 1685 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 1686#endif 1687 1688 DPRINTF("Before forking process PID=%d\n", getpid()); 1689 SYSCALL_REQUIRE((child = vfork()) != -1); 1690 if (child == 0) { 1691 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1692 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1693 1694 memset(&sa, 0, sizeof(sa)); 1695 sa.sa_handler = SIG_IGN; 1696 sigemptyset(&sa.sa_mask); 1697 1698 FORKEE_ASSERT(sigaction(sig, &sa, NULL) != -1); 1699 1700 DPRINTF("Before executing a trap\n"); 1701 switch (sig) { 1702 case SIGTRAP: 1703 trigger_trap(); 1704 break; 1705 case SIGSEGV: 1706 trigger_segv(); 1707 break; 1708 case SIGILL: 1709 trigger_ill(); 1710 break; 1711 case SIGFPE: 1712 trigger_fpe(); 1713 break; 1714 case SIGBUS: 1715 trigger_bus(); 1716 break; 1717 default: 1718 /* NOTREACHED */ 1719 FORKEE_ASSERTX(0 && "This shall not be reached"); 1720 } 1721 1722 /* NOTREACHED */ 1723 FORKEE_ASSERTX(0 && "This shall not be reached"); 1724 } 1725 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1726 1727 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1728 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1729 1730 validate_status_signaled(status, sig, 1); 1731 1732 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1733 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1734} 1735 1736#define TRACEME_VFORK_SIGNALIGNORED_CRASH(test, sig) \ 1737ATF_TC(test); \ 1738ATF_TC_HEAD(test, tc) \ 1739{ \ 1740 atf_tc_set_md_var(tc, "descr", \ 1741 "Verify PT_TRACE_ME followed by a crash signal " #sig " in a " \ 1742 "vfork(2)ed child with ignored signal"); \ 1743} \ 1744 \ 1745ATF_TC_BODY(test, tc) \ 1746{ \ 1747 \ 1748 traceme_vfork_signalignored_crash(sig); \ 1749} 1750 1751TRACEME_VFORK_SIGNALIGNORED_CRASH(traceme_vfork_signalignored_crash_trap, 1752 SIGTRAP) 1753TRACEME_VFORK_SIGNALIGNORED_CRASH(traceme_vfork_signalignored_crash_segv, 1754 SIGSEGV) 1755TRACEME_VFORK_SIGNALIGNORED_CRASH(traceme_vfork_signalignored_crash_ill, 1756 SIGILL) 1757TRACEME_VFORK_SIGNALIGNORED_CRASH(traceme_vfork_signalignored_crash_fpe, 1758 SIGFPE) 1759TRACEME_VFORK_SIGNALIGNORED_CRASH(traceme_vfork_signalignored_crash_bus, 1760 SIGBUS) 1761 1762/// ---------------------------------------------------------------------------- 1763 1764static void 1765traceme_vfork_exec(bool masked, bool ignored) 1766{ 1767 const int sigval = SIGTRAP; 1768 pid_t child, wpid; 1769#if defined(TWAIT_HAVE_STATUS) 1770 int status; 1771#endif 1772 struct sigaction sa; 1773 struct ptrace_siginfo info; 1774 sigset_t intmask; 1775 struct kinfo_proc2 kp; 1776 size_t len = sizeof(kp); 1777 1778 int name[6]; 1779 const size_t namelen = __arraycount(name); 1780 ki_sigset_t kp_sigmask; 1781 ki_sigset_t kp_sigignore; 1782 1783 memset(&info, 0, sizeof(info)); 1784 1785 DPRINTF("Before forking process PID=%d\n", getpid()); 1786 SYSCALL_REQUIRE((child = vfork()) != -1); 1787 if (child == 0) { 1788 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1789 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1790 1791 if (masked) { 1792 sigemptyset(&intmask); 1793 sigaddset(&intmask, sigval); 1794 sigprocmask(SIG_BLOCK, &intmask, NULL); 1795 } 1796 1797 if (ignored) { 1798 memset(&sa, 0, sizeof(sa)); 1799 sa.sa_handler = SIG_IGN; 1800 sigemptyset(&sa.sa_mask); 1801 FORKEE_ASSERT(sigaction(sigval, &sa, NULL) != -1); 1802 } 1803 1804 DPRINTF("Before calling execve(2) from child\n"); 1805 execlp("/bin/echo", "/bin/echo", NULL); 1806 1807 /* NOTREACHED */ 1808 FORKEE_ASSERTX(0 && "Not reached"); 1809 } 1810 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1811 1812 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1813 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1814 1815 validate_status_stopped(status, sigval); 1816 1817 name[0] = CTL_KERN, 1818 name[1] = KERN_PROC2, 1819 name[2] = KERN_PROC_PID; 1820 name[3] = getpid(); 1821 name[4] = sizeof(kp); 1822 name[5] = 1; 1823 1824 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 1825 1826 if (masked) 1827 kp_sigmask = kp.p_sigmask; 1828 1829 if (ignored) 1830 kp_sigignore = kp.p_sigignore; 1831 1832 name[3] = getpid(); 1833 1834 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 1835 1836 if (masked) { 1837 DPRINTF("kp_sigmask=" 1838 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 1839 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 1840 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 1841 1842 DPRINTF("kp.p_sigmask=" 1843 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 1844 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 1845 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 1846 1847 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 1848 sizeof(kp_sigmask))); 1849 } 1850 1851 if (ignored) { 1852 DPRINTF("kp_sigignore=" 1853 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 1854 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 1855 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 1856 1857 DPRINTF("kp.p_sigignore=" 1858 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 1859 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 1860 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 1861 1862 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 1863 sizeof(kp_sigignore))); 1864 } 1865 1866 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 1867 SYSCALL_REQUIRE( 1868 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 1869 1870 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 1871 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 1872 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 1873 info.psi_siginfo.si_errno); 1874 1875 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 1876 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_EXEC); 1877 1878 DPRINTF("Before resuming the child process where it left off and " 1879 "without signal to be sent\n"); 1880 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 1881 1882 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1883 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1884 1885 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1886 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1887} 1888 1889#define TRACEME_VFORK_EXEC(test, masked, ignored) \ 1890ATF_TC(test); \ 1891ATF_TC_HEAD(test, tc) \ 1892{ \ 1893 atf_tc_set_md_var(tc, "descr", \ 1894 "Verify PT_TRACE_ME followed by exec(3) in a vfork(2)ed " \ 1895 "child%s%s", masked ? " with masked signal" : "", \ 1896 masked ? " with ignored signal" : ""); \ 1897} \ 1898 \ 1899ATF_TC_BODY(test, tc) \ 1900{ \ 1901 \ 1902 traceme_vfork_exec(masked, ignored); \ 1903} 1904 1905TRACEME_VFORK_EXEC(traceme_vfork_exec, false, false) 1906TRACEME_VFORK_EXEC(traceme_vfork_signalmasked_exec, true, false) 1907TRACEME_VFORK_EXEC(traceme_vfork_signalignored_exec, false, true) 1908 1909/// ---------------------------------------------------------------------------- 1910 1911#if defined(TWAIT_HAVE_PID) 1912static void 1913unrelated_tracer_sees_crash(int sig, bool masked, bool ignored) 1914{ 1915 const int sigval = SIGSTOP; 1916 struct msg_fds parent_tracee, parent_tracer; 1917 const int exitval = 10; 1918 pid_t tracee, tracer, wpid; 1919 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1920#if defined(TWAIT_HAVE_STATUS) 1921 int status; 1922#endif 1923 struct sigaction sa; 1924 struct ptrace_siginfo info; 1925 sigset_t intmask; 1926 struct kinfo_proc2 kp; 1927 size_t len = sizeof(kp); 1928 1929 int name[6]; 1930 const size_t namelen = __arraycount(name); 1931 ki_sigset_t kp_sigmask; 1932 ki_sigset_t kp_sigignore; 1933 1934#ifndef PTRACE_ILLEGAL_ASM 1935 if (sig == SIGILL) 1936 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 1937#endif 1938 1939 memset(&info, 0, sizeof(info)); 1940 1941 DPRINTF("Spawn tracee\n"); 1942 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 1943 tracee = atf_utils_fork(); 1944 if (tracee == 0) { 1945 // Wait for parent to let us crash 1946 CHILD_FROM_PARENT("exit tracee", parent_tracee, msg); 1947 1948 if (masked) { 1949 sigemptyset(&intmask); 1950 sigaddset(&intmask, sig); 1951 sigprocmask(SIG_BLOCK, &intmask, NULL); 1952 } 1953 1954 if (ignored) { 1955 memset(&sa, 0, sizeof(sa)); 1956 sa.sa_handler = SIG_IGN; 1957 sigemptyset(&sa.sa_mask); 1958 FORKEE_ASSERT(sigaction(sig, &sa, NULL) != -1); 1959 } 1960 1961 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1962 FORKEE_ASSERT(raise(sigval) == 0); 1963 1964 DPRINTF("Before executing a trap\n"); 1965 switch (sig) { 1966 case SIGTRAP: 1967 trigger_trap(); 1968 break; 1969 case SIGSEGV: 1970 trigger_segv(); 1971 break; 1972 case SIGILL: 1973 trigger_ill(); 1974 break; 1975 case SIGFPE: 1976 trigger_fpe(); 1977 break; 1978 case SIGBUS: 1979 trigger_bus(); 1980 break; 1981 default: 1982 /* NOTREACHED */ 1983 FORKEE_ASSERTX(0 && "This shall not be reached"); 1984 } 1985 1986 /* NOTREACHED */ 1987 FORKEE_ASSERTX(0 && "This shall not be reached"); 1988 } 1989 1990 DPRINTF("Spawn debugger\n"); 1991 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 1992 tracer = atf_utils_fork(); 1993 if (tracer == 0) { 1994 /* Fork again and drop parent to reattach to PID 1 */ 1995 tracer = atf_utils_fork(); 1996 if (tracer != 0) 1997 _exit(exitval); 1998 1999 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 2000 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 2001 2002 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 2003 FORKEE_REQUIRE_SUCCESS( 2004 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2005 2006 forkee_status_stopped(status, SIGSTOP); 2007 2008 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for the " 2009 "traced process\n"); 2010 SYSCALL_REQUIRE( 2011 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 2012 2013 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 2014 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 2015 "si_errno=%#x\n", info.psi_siginfo.si_signo, 2016 info.psi_siginfo.si_code, info.psi_siginfo.si_errno); 2017 2018 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, SIGSTOP); 2019 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SI_USER); 2020 2021 /* Resume tracee with PT_CONTINUE */ 2022 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 2023 2024 /* Inform parent that tracer has attached to tracee */ 2025 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 2026 2027 /* Wait for parent to tell use that tracee should have exited */ 2028 CHILD_FROM_PARENT("wait for tracee exit", parent_tracer, msg); 2029 2030 /* Wait for tracee and assert that it exited */ 2031 FORKEE_REQUIRE_SUCCESS( 2032 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2033 2034 forkee_status_stopped(status, sigval); 2035 2036 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for the " 2037 "traced process\n"); 2038 SYSCALL_REQUIRE( 2039 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 2040 2041 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 2042 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 2043 "si_errno=%#x\n", info.psi_siginfo.si_signo, 2044 info.psi_siginfo.si_code, info.psi_siginfo.si_errno); 2045 2046 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, sigval); 2047 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SI_LWP); 2048 2049 name[0] = CTL_KERN, 2050 name[1] = KERN_PROC2, 2051 name[2] = KERN_PROC_PID; 2052 name[3] = tracee; 2053 name[4] = sizeof(kp); 2054 name[5] = 1; 2055 2056 FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 2057 2058 if (masked) 2059 kp_sigmask = kp.p_sigmask; 2060 2061 if (ignored) 2062 kp_sigignore = kp.p_sigignore; 2063 2064 /* Resume tracee with PT_CONTINUE */ 2065 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 2066 2067 /* Wait for tracee and assert that it exited */ 2068 FORKEE_REQUIRE_SUCCESS( 2069 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2070 2071 forkee_status_stopped(status, sig); 2072 2073 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for the " 2074 "traced process\n"); 2075 SYSCALL_REQUIRE( 2076 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 2077 2078 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 2079 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 2080 "si_errno=%#x\n", info.psi_siginfo.si_signo, 2081 info.psi_siginfo.si_code, info.psi_siginfo.si_errno); 2082 2083 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, sig); 2084 2085 FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 2086 2087 if (masked) { 2088 DPRINTF("kp_sigmask=" 2089 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 2090 PRIx32 "\n", 2091 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 2092 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 2093 2094 DPRINTF("kp.p_sigmask=" 2095 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 2096 PRIx32 "\n", 2097 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 2098 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 2099 2100 FORKEE_ASSERTX(!memcmp(&kp_sigmask, &kp.p_sigmask, 2101 sizeof(kp_sigmask))); 2102 } 2103 2104 if (ignored) { 2105 DPRINTF("kp_sigignore=" 2106 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 2107 PRIx32 "\n", 2108 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 2109 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 2110 2111 DPRINTF("kp.p_sigignore=" 2112 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 2113 PRIx32 "\n", 2114 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 2115 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 2116 2117 FORKEE_ASSERTX(!memcmp(&kp_sigignore, &kp.p_sigignore, 2118 sizeof(kp_sigignore))); 2119 } 2120 2121 switch (sig) { 2122 case SIGTRAP: 2123 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, TRAP_BRKPT); 2124 break; 2125 case SIGSEGV: 2126 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SEGV_MAPERR); 2127 break; 2128 case SIGILL: 2129 FORKEE_ASSERT(info.psi_siginfo.si_code >= 0 && 2130 info.psi_siginfo.si_code <= ILL_BADSTK); 2131 break; 2132 case SIGFPE: 2133 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, FPE_INTDIV); 2134 break; 2135 case SIGBUS: 2136 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, BUS_ADRERR); 2137 break; 2138 } 2139 2140 FORKEE_ASSERT(ptrace(PT_KILL, tracee, NULL, 0) != -1); 2141 DPRINTF("Before calling %s() for the tracee\n", TWAIT_FNAME); 2142 FORKEE_REQUIRE_SUCCESS( 2143 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2144 2145 forkee_status_signaled(status, SIGKILL, 0); 2146 2147 /* Inform parent that tracer is exiting normally */ 2148 CHILD_TO_PARENT("tracer done", parent_tracer, msg); 2149 2150 DPRINTF("Before exiting of the tracer process\n"); 2151 _exit(0 /* collect by initproc */); 2152 } 2153 2154 DPRINTF("Wait for the tracer process (direct child) to exit " 2155 "calling %s()\n", TWAIT_FNAME); 2156 TWAIT_REQUIRE_SUCCESS( 2157 wpid = TWAIT_GENERIC(tracer, &status, 0), tracer); 2158 2159 validate_status_exited(status, exitval); 2160 2161 DPRINTF("Wait for the non-exited tracee process with %s()\n", 2162 TWAIT_FNAME); 2163 TWAIT_REQUIRE_SUCCESS( 2164 wpid = TWAIT_GENERIC(tracee, NULL, WNOHANG), 0); 2165 2166 DPRINTF("Wait for the tracer to attach to the tracee\n"); 2167 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 2168 2169 DPRINTF("Resume the tracee and let it crash\n"); 2170 PARENT_TO_CHILD("exit tracee", parent_tracee, msg); 2171 2172 DPRINTF("Resume the tracer and let it detect crashed tracee\n"); 2173 PARENT_TO_CHILD("Message 2", parent_tracer, msg); 2174 2175 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 2176 TWAIT_FNAME); 2177 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2178 2179 validate_status_signaled(status, SIGKILL, 0); 2180 2181 DPRINTF("Await normal exit of tracer\n"); 2182 PARENT_FROM_CHILD("tracer done", parent_tracer, msg); 2183 2184 msg_close(&parent_tracer); 2185 msg_close(&parent_tracee); 2186} 2187 2188#define UNRELATED_TRACER_SEES_CRASH(test, sig) \ 2189ATF_TC(test); \ 2190ATF_TC_HEAD(test, tc) \ 2191{ \ 2192 atf_tc_set_md_var(tc, "descr", \ 2193 "Assert that an unrelated tracer sees crash signal from " \ 2194 "the debuggee"); \ 2195} \ 2196 \ 2197ATF_TC_BODY(test, tc) \ 2198{ \ 2199 \ 2200 unrelated_tracer_sees_crash(sig, false, false); \ 2201} 2202 2203UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_trap, SIGTRAP) 2204UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_segv, SIGSEGV) 2205UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_ill, SIGILL) 2206UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_fpe, SIGFPE) 2207UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_bus, SIGBUS) 2208 2209#define UNRELATED_TRACER_SEES_SIGNALMASKED_CRASH(test, sig) \ 2210ATF_TC(test); \ 2211ATF_TC_HEAD(test, tc) \ 2212{ \ 2213 atf_tc_set_md_var(tc, "descr", \ 2214 "Assert that an unrelated tracer sees crash signal from " \ 2215 "the debuggee with masked signal"); \ 2216} \ 2217 \ 2218ATF_TC_BODY(test, tc) \ 2219{ \ 2220 \ 2221 unrelated_tracer_sees_crash(sig, true, false); \ 2222} 2223 2224UNRELATED_TRACER_SEES_SIGNALMASKED_CRASH( 2225 unrelated_tracer_sees_signalmasked_crash_trap, SIGTRAP) 2226UNRELATED_TRACER_SEES_SIGNALMASKED_CRASH( 2227 unrelated_tracer_sees_signalmasked_crash_segv, SIGSEGV) 2228UNRELATED_TRACER_SEES_SIGNALMASKED_CRASH( 2229 unrelated_tracer_sees_signalmasked_crash_ill, SIGILL) 2230UNRELATED_TRACER_SEES_SIGNALMASKED_CRASH( 2231 unrelated_tracer_sees_signalmasked_crash_fpe, SIGFPE) 2232UNRELATED_TRACER_SEES_SIGNALMASKED_CRASH( 2233 unrelated_tracer_sees_signalmasked_crash_bus, SIGBUS) 2234 2235#define UNRELATED_TRACER_SEES_SIGNALIGNORED_CRASH(test, sig) \ 2236ATF_TC(test); \ 2237ATF_TC_HEAD(test, tc) \ 2238{ \ 2239 atf_tc_set_md_var(tc, "descr", \ 2240 "Assert that an unrelated tracer sees crash signal from " \ 2241 "the debuggee with signal ignored"); \ 2242} \ 2243 \ 2244ATF_TC_BODY(test, tc) \ 2245{ \ 2246 \ 2247 unrelated_tracer_sees_crash(sig, false, true); \ 2248} 2249 2250UNRELATED_TRACER_SEES_SIGNALIGNORED_CRASH( 2251 unrelated_tracer_sees_signalignored_crash_trap, SIGTRAP) 2252UNRELATED_TRACER_SEES_SIGNALIGNORED_CRASH( 2253 unrelated_tracer_sees_signalignored_crash_segv, SIGSEGV) 2254UNRELATED_TRACER_SEES_SIGNALIGNORED_CRASH( 2255 unrelated_tracer_sees_signalignored_crash_ill, SIGILL) 2256UNRELATED_TRACER_SEES_SIGNALIGNORED_CRASH( 2257 unrelated_tracer_sees_signalignored_crash_fpe, SIGFPE) 2258UNRELATED_TRACER_SEES_SIGNALIGNORED_CRASH( 2259 unrelated_tracer_sees_signalignored_crash_bus, SIGBUS) 2260#endif 2261 2262/// ---------------------------------------------------------------------------- 2263 2264#if defined(TWAIT_HAVE_PID) 2265static void 2266tracer_sees_terminaton_before_the_parent_raw(bool notimeout, bool unrelated, 2267 bool stopped) 2268{ 2269 /* 2270 * notimeout - disable timeout in await zombie function 2271 * unrelated - attach from unrelated tracer reparented to initproc 2272 * stopped - attach to a stopped process 2273 */ 2274 2275 struct msg_fds parent_tracee, parent_tracer; 2276 const int exitval_tracee = 5; 2277 const int exitval_tracer = 10; 2278 pid_t tracee, tracer, wpid; 2279 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 2280#if defined(TWAIT_HAVE_STATUS) 2281 int status; 2282#endif 2283 2284 /* 2285 * Only a subset of options are supported. 2286 */ 2287 ATF_REQUIRE((!notimeout && !unrelated && !stopped) || 2288 (!notimeout && unrelated && !stopped) || 2289 (notimeout && !unrelated && !stopped) || 2290 (!notimeout && unrelated && stopped)); 2291 2292 DPRINTF("Spawn tracee\n"); 2293 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 2294 tracee = atf_utils_fork(); 2295 if (tracee == 0) { 2296 if (stopped) { 2297 DPRINTF("Stop self PID %d\n", getpid()); 2298 raise(SIGSTOP); 2299 } 2300 2301 // Wait for parent to let us exit 2302 CHILD_FROM_PARENT("exit tracee", parent_tracee, msg); 2303 _exit(exitval_tracee); 2304 } 2305 2306 DPRINTF("Spawn debugger\n"); 2307 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 2308 tracer = atf_utils_fork(); 2309 if (tracer == 0) { 2310 if(unrelated) { 2311 /* Fork again and drop parent to reattach to PID 1 */ 2312 tracer = atf_utils_fork(); 2313 if (tracer != 0) 2314 _exit(exitval_tracer); 2315 } 2316 2317 if (stopped) { 2318 DPRINTF("Await for a stopped parent PID %d\n", tracee); 2319 await_stopped(tracee); 2320 } 2321 2322 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 2323 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 2324 2325 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 2326 FORKEE_REQUIRE_SUCCESS( 2327 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2328 2329 forkee_status_stopped(status, SIGSTOP); 2330 2331 /* Resume tracee with PT_CONTINUE */ 2332 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 2333 2334 /* Inform parent that tracer has attached to tracee */ 2335 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 2336 2337 /* Wait for parent to tell use that tracee should have exited */ 2338 CHILD_FROM_PARENT("wait for tracee exit", parent_tracer, msg); 2339 2340 /* Wait for tracee and assert that it exited */ 2341 FORKEE_REQUIRE_SUCCESS( 2342 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2343 2344 forkee_status_exited(status, exitval_tracee); 2345 DPRINTF("Tracee %d exited with %d\n", tracee, exitval_tracee); 2346 2347 DPRINTF("Before exiting of the tracer process\n"); 2348 _exit(unrelated ? 0 /* collect by initproc */ : exitval_tracer); 2349 } 2350 2351 if (unrelated) { 2352 DPRINTF("Wait for the tracer process (direct child) to exit " 2353 "calling %s()\n", TWAIT_FNAME); 2354 TWAIT_REQUIRE_SUCCESS( 2355 wpid = TWAIT_GENERIC(tracer, &status, 0), tracer); 2356 2357 validate_status_exited(status, exitval_tracer); 2358 2359 DPRINTF("Wait for the non-exited tracee process with %s()\n", 2360 TWAIT_FNAME); 2361 TWAIT_REQUIRE_SUCCESS( 2362 wpid = TWAIT_GENERIC(tracee, NULL, WNOHANG), 0); 2363 } 2364 2365 DPRINTF("Wait for the tracer to attach to the tracee\n"); 2366 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 2367 2368 DPRINTF("Resume the tracee and let it exit\n"); 2369 PARENT_TO_CHILD("exit tracee", parent_tracee, msg); 2370 2371 DPRINTF("Detect that tracee is zombie\n"); 2372 if (notimeout) 2373 await_zombie_raw(tracee, 0); 2374 else 2375 await_zombie(tracee); 2376 2377 DPRINTF("Assert that there is no status about tracee %d - " 2378 "Tracer must detect zombie first - calling %s()\n", tracee, 2379 TWAIT_FNAME); 2380 TWAIT_REQUIRE_SUCCESS( 2381 wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 0); 2382 2383 if (unrelated) { 2384 DPRINTF("Resume the tracer and let it detect exited tracee\n"); 2385 PARENT_TO_CHILD("Message 2", parent_tracer, msg); 2386 } else { 2387 DPRINTF("Tell the tracer child should have exited\n"); 2388 PARENT_TO_CHILD("wait for tracee exit", parent_tracer, msg); 2389 DPRINTF("Wait for tracer to finish its job and exit - calling " 2390 "%s()\n", TWAIT_FNAME); 2391 2392 DPRINTF("Wait from tracer child to complete waiting for " 2393 "tracee\n"); 2394 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracer, &status, 0), 2395 tracer); 2396 2397 validate_status_exited(status, exitval_tracer); 2398 } 2399 2400 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 2401 TWAIT_FNAME); 2402 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2403 2404 validate_status_exited(status, exitval_tracee); 2405 2406 msg_close(&parent_tracer); 2407 msg_close(&parent_tracee); 2408} 2409 2410ATF_TC(tracer_sees_terminaton_before_the_parent); 2411ATF_TC_HEAD(tracer_sees_terminaton_before_the_parent, tc) 2412{ 2413 atf_tc_set_md_var(tc, "descr", 2414 "Assert that tracer sees process termination before the parent"); 2415} 2416 2417ATF_TC_BODY(tracer_sees_terminaton_before_the_parent, tc) 2418{ 2419 2420 tracer_sees_terminaton_before_the_parent_raw(false, false, false); 2421} 2422 2423ATF_TC(tracer_sysctl_lookup_without_duplicates); 2424ATF_TC_HEAD(tracer_sysctl_lookup_without_duplicates, tc) 2425{ 2426 atf_tc_set_md_var(tc, "descr", 2427 "Assert that await_zombie() in attach1 always finds a single " 2428 "process and no other error is reported"); 2429} 2430 2431ATF_TC_BODY(tracer_sysctl_lookup_without_duplicates, tc) 2432{ 2433 time_t start, end; 2434 double diff; 2435 unsigned long N = 0; 2436 2437 /* 2438 * Reuse this test with tracer_sees_terminaton_before_the_parent_raw(). 2439 * This test body isn't specific to this race, however it's just good 2440 * enough for this purposes, no need to invent a dedicated code flow. 2441 */ 2442 2443 start = time(NULL); 2444 while (true) { 2445 DPRINTF("Step: %lu\n", N); 2446 tracer_sees_terminaton_before_the_parent_raw(true, false, 2447 false); 2448 end = time(NULL); 2449 diff = difftime(end, start); 2450 if (diff >= 5.0) 2451 break; 2452 ++N; 2453 } 2454 DPRINTF("Iterations: %lu\n", N); 2455} 2456 2457ATF_TC(unrelated_tracer_sees_terminaton_before_the_parent); 2458ATF_TC_HEAD(unrelated_tracer_sees_terminaton_before_the_parent, tc) 2459{ 2460 atf_tc_set_md_var(tc, "descr", 2461 "Assert that tracer sees process termination before the parent"); 2462} 2463 2464ATF_TC_BODY(unrelated_tracer_sees_terminaton_before_the_parent, tc) 2465{ 2466 2467 tracer_sees_terminaton_before_the_parent_raw(false, true, false); 2468} 2469 2470ATF_TC(tracer_attach_to_unrelated_stopped_process); 2471ATF_TC_HEAD(tracer_attach_to_unrelated_stopped_process, tc) 2472{ 2473 atf_tc_set_md_var(tc, "descr", 2474 "Assert that tracer can attach to an unrelated stopped process"); 2475} 2476 2477ATF_TC_BODY(tracer_attach_to_unrelated_stopped_process, tc) 2478{ 2479 2480 tracer_sees_terminaton_before_the_parent_raw(false, true, true); 2481} 2482#endif 2483 2484/// ---------------------------------------------------------------------------- 2485 2486static void 2487parent_attach_to_its_child(bool stopped) 2488{ 2489 struct msg_fds parent_tracee; 2490 const int exitval_tracee = 5; 2491 pid_t tracee, wpid; 2492 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 2493#if defined(TWAIT_HAVE_STATUS) 2494 int status; 2495#endif 2496 2497 DPRINTF("Spawn tracee\n"); 2498 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 2499 tracee = atf_utils_fork(); 2500 if (tracee == 0) { 2501 CHILD_FROM_PARENT("Message 1", parent_tracee, msg); 2502 DPRINTF("Parent should now attach to tracee\n"); 2503 2504 if (stopped) { 2505 DPRINTF("Stop self PID %d\n", getpid()); 2506 SYSCALL_REQUIRE(raise(SIGSTOP) != -1); 2507 } 2508 2509 CHILD_FROM_PARENT("Message 2", parent_tracee, msg); 2510 /* Wait for message from the parent */ 2511 _exit(exitval_tracee); 2512 } 2513 PARENT_TO_CHILD("Message 1", parent_tracee, msg); 2514 2515 if (stopped) { 2516 DPRINTF("Await for a stopped tracee PID %d\n", tracee); 2517 await_stopped(tracee); 2518 } 2519 2520 DPRINTF("Before calling PT_ATTACH for tracee %d\n", tracee); 2521 SYSCALL_REQUIRE(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 2522 2523 DPRINTF("Wait for the stopped tracee process with %s()\n", 2524 TWAIT_FNAME); 2525 TWAIT_REQUIRE_SUCCESS( 2526 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2527 2528 validate_status_stopped(status, SIGSTOP); 2529 2530 DPRINTF("Resume tracee with PT_CONTINUE\n"); 2531 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 2532 2533 DPRINTF("Let the tracee exit now\n"); 2534 PARENT_TO_CHILD("Message 2", parent_tracee, msg); 2535 2536 DPRINTF("Wait for tracee to exit with %s()\n", TWAIT_FNAME); 2537 TWAIT_REQUIRE_SUCCESS( 2538 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2539 2540 validate_status_exited(status, exitval_tracee); 2541 2542 DPRINTF("Before calling %s() for tracee\n", TWAIT_FNAME); 2543 TWAIT_REQUIRE_FAILURE(ECHILD, 2544 wpid = TWAIT_GENERIC(tracee, &status, 0)); 2545 2546 msg_close(&parent_tracee); 2547} 2548 2549ATF_TC(parent_attach_to_its_child); 2550ATF_TC_HEAD(parent_attach_to_its_child, tc) 2551{ 2552 atf_tc_set_md_var(tc, "descr", 2553 "Assert that tracer parent can PT_ATTACH to its child"); 2554} 2555 2556ATF_TC_BODY(parent_attach_to_its_child, tc) 2557{ 2558 2559 parent_attach_to_its_child(false); 2560} 2561 2562ATF_TC(parent_attach_to_its_stopped_child); 2563ATF_TC_HEAD(parent_attach_to_its_stopped_child, tc) 2564{ 2565 atf_tc_set_md_var(tc, "descr", 2566 "Assert that tracer parent can PT_ATTACH to its stopped child"); 2567} 2568 2569ATF_TC_BODY(parent_attach_to_its_stopped_child, tc) 2570{ 2571 2572 parent_attach_to_its_child(true); 2573} 2574 2575/// ---------------------------------------------------------------------------- 2576 2577static void 2578child_attach_to_its_parent(bool stopped) 2579{ 2580 struct msg_fds parent_tracee; 2581 const int exitval_tracer = 5; 2582 pid_t tracer, wpid; 2583 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 2584#if defined(TWAIT_HAVE_STATUS) 2585 int status; 2586#endif 2587 2588 DPRINTF("Spawn tracer\n"); 2589 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 2590 tracer = atf_utils_fork(); 2591 if (tracer == 0) { 2592 /* Wait for message from the parent */ 2593 CHILD_FROM_PARENT("Message 1", parent_tracee, msg); 2594 2595 if (stopped) { 2596 DPRINTF("Await for a stopped parent PID %d\n", 2597 getppid()); 2598 await_stopped(getppid()); 2599 } 2600 2601 DPRINTF("Attach to parent PID %d with PT_ATTACH from child\n", 2602 getppid()); 2603 FORKEE_ASSERT(ptrace(PT_ATTACH, getppid(), NULL, 0) != -1); 2604 2605 DPRINTF("Wait for the stopped parent process with %s()\n", 2606 TWAIT_FNAME); 2607 FORKEE_REQUIRE_SUCCESS( 2608 wpid = TWAIT_GENERIC(getppid(), &status, 0), getppid()); 2609 2610 forkee_status_stopped(status, SIGSTOP); 2611 2612 DPRINTF("Resume parent with PT_DETACH\n"); 2613 FORKEE_ASSERT(ptrace(PT_DETACH, getppid(), (void *)1, 0) 2614 != -1); 2615 2616 /* Tell parent we are ready */ 2617 CHILD_TO_PARENT("Message 1", parent_tracee, msg); 2618 2619 _exit(exitval_tracer); 2620 } 2621 2622 DPRINTF("Wait for the tracer to become ready\n"); 2623 PARENT_TO_CHILD("Message 1", parent_tracee, msg); 2624 2625 if (stopped) { 2626 DPRINTF("Stop self PID %d\n", getpid()); 2627 SYSCALL_REQUIRE(raise(SIGSTOP) != -1); 2628 } 2629 2630 DPRINTF("Allow the tracer to exit now\n"); 2631 PARENT_FROM_CHILD("Message 1", parent_tracee, msg); 2632 2633 DPRINTF("Wait for tracer to exit with %s()\n", TWAIT_FNAME); 2634 TWAIT_REQUIRE_SUCCESS( 2635 wpid = TWAIT_GENERIC(tracer, &status, 0), tracer); 2636 2637 validate_status_exited(status, exitval_tracer); 2638 2639 DPRINTF("Before calling %s() for tracer\n", TWAIT_FNAME); 2640 TWAIT_REQUIRE_FAILURE(ECHILD, 2641 wpid = TWAIT_GENERIC(tracer, &status, 0)); 2642 2643 msg_close(&parent_tracee); 2644} 2645 2646ATF_TC(child_attach_to_its_parent); 2647ATF_TC_HEAD(child_attach_to_its_parent, tc) 2648{ 2649 atf_tc_set_md_var(tc, "descr", 2650 "Assert that tracer child can PT_ATTACH to its parent"); 2651} 2652 2653ATF_TC_BODY(child_attach_to_its_parent, tc) 2654{ 2655 2656 child_attach_to_its_parent(false); 2657} 2658 2659ATF_TC(child_attach_to_its_stopped_parent); 2660ATF_TC_HEAD(child_attach_to_its_stopped_parent, tc) 2661{ 2662 atf_tc_set_md_var(tc, "descr", 2663 "Assert that tracer child can PT_ATTACH to its stopped parent"); 2664} 2665 2666ATF_TC_BODY(child_attach_to_its_stopped_parent, tc) 2667{ 2668 /* 2669 * The ATF framework (atf-run) does not tolerate raise(SIGSTOP), as 2670 * this causes a pipe (established from atf-run) to be broken. 2671 * atf-run uses this mechanism to monitor whether a test is alive. 2672 * 2673 * As a workaround spawn this test as a subprocess. 2674 */ 2675 2676 const int exitval = 15; 2677 pid_t child, wpid; 2678#if defined(TWAIT_HAVE_STATUS) 2679 int status; 2680#endif 2681 2682 SYSCALL_REQUIRE((child = fork()) != -1); 2683 if (child == 0) { 2684 child_attach_to_its_parent(true); 2685 _exit(exitval); 2686 } else { 2687 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2688 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2689 2690 validate_status_exited(status, exitval); 2691 2692 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 2693 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2694 } 2695} 2696 2697/// ---------------------------------------------------------------------------- 2698 2699#if defined(TWAIT_HAVE_PID) 2700 2701enum tracee_sees_its_original_parent_type { 2702 TRACEE_SEES_ITS_ORIGINAL_PARENT_GETPPID, 2703 TRACEE_SEES_ITS_ORIGINAL_PARENT_SYSCTL_KINFO_PROC2, 2704 TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS 2705}; 2706 2707static void 2708tracee_sees_its_original_parent(enum tracee_sees_its_original_parent_type type) 2709{ 2710 struct msg_fds parent_tracer, parent_tracee; 2711 const int exitval_tracee = 5; 2712 const int exitval_tracer = 10; 2713 pid_t parent, tracee, tracer, wpid; 2714 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 2715#if defined(TWAIT_HAVE_STATUS) 2716 int status; 2717#endif 2718 /* sysctl(3) - kinfo_proc2 */ 2719 int name[CTL_MAXNAME]; 2720 struct kinfo_proc2 kp; 2721 size_t len = sizeof(kp); 2722 unsigned int namelen; 2723 2724 /* procfs - status */ 2725 FILE *fp; 2726 struct stat st; 2727 const char *fname = "/proc/curproc/status"; 2728 char s_executable[MAXPATHLEN]; 2729 int s_pid, s_ppid; 2730 int rv; 2731 2732 if (type == TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS) { 2733 SYSCALL_REQUIRE( 2734 (rv = stat(fname, &st)) == 0 || (errno == ENOENT)); 2735 if (rv != 0) 2736 atf_tc_skip("/proc/curproc/status not found"); 2737 } 2738 2739 DPRINTF("Spawn tracee\n"); 2740 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 2741 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 2742 tracee = atf_utils_fork(); 2743 if (tracee == 0) { 2744 parent = getppid(); 2745 2746 /* Emit message to the parent */ 2747 CHILD_TO_PARENT("tracee ready", parent_tracee, msg); 2748 CHILD_FROM_PARENT("exit tracee", parent_tracee, msg); 2749 2750 switch (type) { 2751 case TRACEE_SEES_ITS_ORIGINAL_PARENT_GETPPID: 2752 FORKEE_ASSERT_EQ(parent, getppid()); 2753 break; 2754 case TRACEE_SEES_ITS_ORIGINAL_PARENT_SYSCTL_KINFO_PROC2: 2755 namelen = 0; 2756 name[namelen++] = CTL_KERN; 2757 name[namelen++] = KERN_PROC2; 2758 name[namelen++] = KERN_PROC_PID; 2759 name[namelen++] = getpid(); 2760 name[namelen++] = len; 2761 name[namelen++] = 1; 2762 2763 FORKEE_ASSERT_EQ( 2764 sysctl(name, namelen, &kp, &len, NULL, 0), 0); 2765 FORKEE_ASSERT_EQ(parent, kp.p_ppid); 2766 break; 2767 case TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS: 2768 /* 2769 * Format: 2770 * EXECUTABLE PID PPID ... 2771 */ 2772 FORKEE_ASSERT((fp = fopen(fname, "r")) != NULL); 2773 fscanf(fp, "%s %d %d", s_executable, &s_pid, &s_ppid); 2774 FORKEE_ASSERT_EQ(fclose(fp), 0); 2775 FORKEE_ASSERT_EQ(parent, s_ppid); 2776 break; 2777 } 2778 2779 _exit(exitval_tracee); 2780 } 2781 DPRINTF("Wait for child to record its parent identifier (pid)\n"); 2782 PARENT_FROM_CHILD("tracee ready", parent_tracee, msg); 2783 2784 DPRINTF("Spawn debugger\n"); 2785 tracer = atf_utils_fork(); 2786 if (tracer == 0) { 2787 /* No IPC to communicate with the child */ 2788 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 2789 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 2790 2791 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 2792 FORKEE_REQUIRE_SUCCESS( 2793 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2794 2795 forkee_status_stopped(status, SIGSTOP); 2796 2797 /* Resume tracee with PT_CONTINUE */ 2798 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 2799 2800 /* Inform parent that tracer has attached to tracee */ 2801 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 2802 2803 /* Wait for parent to tell use that tracee should have exited */ 2804 CHILD_FROM_PARENT("wait for tracee exit", parent_tracer, msg); 2805 2806 /* Wait for tracee and assert that it exited */ 2807 FORKEE_REQUIRE_SUCCESS( 2808 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 2809 2810 forkee_status_exited(status, exitval_tracee); 2811 2812 DPRINTF("Before exiting of the tracer process\n"); 2813 _exit(exitval_tracer); 2814 } 2815 2816 DPRINTF("Wait for the tracer to attach to the tracee\n"); 2817 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 2818 2819 DPRINTF("Resume the tracee and let it exit\n"); 2820 PARENT_TO_CHILD("exit tracee", parent_tracee, msg); 2821 2822 DPRINTF("Detect that tracee is zombie\n"); 2823 await_zombie(tracee); 2824 2825 DPRINTF("Assert that there is no status about tracee - " 2826 "Tracer must detect zombie first - calling %s()\n", TWAIT_FNAME); 2827 TWAIT_REQUIRE_SUCCESS( 2828 wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 0); 2829 2830 DPRINTF("Tell the tracer child should have exited\n"); 2831 PARENT_TO_CHILD("wait for tracee exit", parent_tracer, msg); 2832 2833 DPRINTF("Wait from tracer child to complete waiting for tracee\n"); 2834 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracer, &status, 0), 2835 tracer); 2836 2837 validate_status_exited(status, exitval_tracer); 2838 2839 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 2840 TWAIT_FNAME); 2841 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 2842 tracee); 2843 2844 validate_status_exited(status, exitval_tracee); 2845 2846 msg_close(&parent_tracer); 2847 msg_close(&parent_tracee); 2848} 2849 2850#define TRACEE_SEES_ITS_ORIGINAL_PARENT(test, type, descr) \ 2851ATF_TC(test); \ 2852ATF_TC_HEAD(test, tc) \ 2853{ \ 2854 atf_tc_set_md_var(tc, "descr", \ 2855 "Assert that tracee sees its original parent when being traced " \ 2856 "(check " descr ")"); \ 2857} \ 2858 \ 2859ATF_TC_BODY(test, tc) \ 2860{ \ 2861 \ 2862 tracee_sees_its_original_parent(type); \ 2863} 2864 2865TRACEE_SEES_ITS_ORIGINAL_PARENT( 2866 tracee_sees_its_original_parent_getppid, 2867 TRACEE_SEES_ITS_ORIGINAL_PARENT_GETPPID, 2868 "getppid(2)"); 2869TRACEE_SEES_ITS_ORIGINAL_PARENT( 2870 tracee_sees_its_original_parent_sysctl_kinfo_proc2, 2871 TRACEE_SEES_ITS_ORIGINAL_PARENT_SYSCTL_KINFO_PROC2, 2872 "sysctl(3) and kinfo_proc2"); 2873TRACEE_SEES_ITS_ORIGINAL_PARENT( 2874 tracee_sees_its_original_parent_procfs_status, 2875 TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS, 2876 "the status file in procfs"); 2877#endif 2878 2879/// ---------------------------------------------------------------------------- 2880 2881static void 2882eventmask_preserved(int event) 2883{ 2884 const int exitval = 5; 2885 const int sigval = SIGSTOP; 2886 pid_t child, wpid; 2887#if defined(TWAIT_HAVE_STATUS) 2888 int status; 2889#endif 2890 ptrace_event_t set_event, get_event; 2891 const int len = sizeof(ptrace_event_t); 2892 2893 DPRINTF("Before forking process PID=%d\n", getpid()); 2894 SYSCALL_REQUIRE((child = fork()) != -1); 2895 if (child == 0) { 2896 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2897 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2898 2899 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2900 FORKEE_ASSERT(raise(sigval) == 0); 2901 2902 DPRINTF("Before exiting of the child process\n"); 2903 _exit(exitval); 2904 } 2905 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2906 2907 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2908 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2909 2910 validate_status_stopped(status, sigval); 2911 2912 set_event.pe_set_event = event; 2913 SYSCALL_REQUIRE( 2914 ptrace(PT_SET_EVENT_MASK, child, &set_event, len) != -1); 2915 SYSCALL_REQUIRE( 2916 ptrace(PT_GET_EVENT_MASK, child, &get_event, len) != -1); 2917 ATF_REQUIRE(memcmp(&set_event, &get_event, len) == 0); 2918 2919 DPRINTF("Before resuming the child process where it left off and " 2920 "without signal to be sent\n"); 2921 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2922 2923 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2924 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2925 2926 validate_status_exited(status, exitval); 2927 2928 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2929 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2930} 2931 2932#define EVENTMASK_PRESERVED(test, event) \ 2933ATF_TC(test); \ 2934ATF_TC_HEAD(test, tc) \ 2935{ \ 2936 atf_tc_set_md_var(tc, "descr", \ 2937 "Verify that eventmask " #event " is preserved"); \ 2938} \ 2939 \ 2940ATF_TC_BODY(test, tc) \ 2941{ \ 2942 \ 2943 eventmask_preserved(event); \ 2944} 2945 2946EVENTMASK_PRESERVED(eventmask_preserved_empty, 0) 2947EVENTMASK_PRESERVED(eventmask_preserved_fork, PTRACE_FORK) 2948EVENTMASK_PRESERVED(eventmask_preserved_vfork, PTRACE_VFORK) 2949EVENTMASK_PRESERVED(eventmask_preserved_vfork_done, PTRACE_VFORK_DONE) 2950EVENTMASK_PRESERVED(eventmask_preserved_lwp_create, PTRACE_LWP_CREATE) 2951EVENTMASK_PRESERVED(eventmask_preserved_lwp_exit, PTRACE_LWP_EXIT) 2952 2953/// ---------------------------------------------------------------------------- 2954 2955static void 2956fork_body(pid_t (*fn)(void), bool trackfork, bool trackvfork, 2957 bool trackvforkdone) 2958{ 2959 const int exitval = 5; 2960 const int exitval2 = 15; 2961 const int sigval = SIGSTOP; 2962 pid_t child, child2 = 0, wpid; 2963#if defined(TWAIT_HAVE_STATUS) 2964 int status; 2965#endif 2966 ptrace_state_t state; 2967 const int slen = sizeof(state); 2968 ptrace_event_t event; 2969 const int elen = sizeof(event); 2970 2971 DPRINTF("Before forking process PID=%d\n", getpid()); 2972 SYSCALL_REQUIRE((child = fork()) != -1); 2973 if (child == 0) { 2974 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2975 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2976 2977 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2978 FORKEE_ASSERT(raise(sigval) == 0); 2979 2980 FORKEE_ASSERT((child2 = (fn)()) != -1); 2981 2982 if (child2 == 0) 2983 _exit(exitval2); 2984 2985 FORKEE_REQUIRE_SUCCESS 2986 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 2987 2988 forkee_status_exited(status, exitval2); 2989 2990 DPRINTF("Before exiting of the child process\n"); 2991 _exit(exitval); 2992 } 2993 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2994 2995 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2996 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2997 2998 validate_status_stopped(status, sigval); 2999 3000 DPRINTF("Set 0%s%s%s in EVENT_MASK for the child %d\n", 3001 trackfork ? "|PTRACE_FORK" : "", 3002 trackvfork ? "|PTRACE_VFORK" : "", 3003 trackvforkdone ? "|PTRACE_VFORK_DONE" : "", child); 3004 event.pe_set_event = 0; 3005 if (trackfork) 3006 event.pe_set_event |= PTRACE_FORK; 3007 if (trackvfork) 3008 event.pe_set_event |= PTRACE_VFORK; 3009 if (trackvforkdone) 3010 event.pe_set_event |= PTRACE_VFORK_DONE; 3011 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 3012 3013 DPRINTF("Before resuming the child process where it left off and " 3014 "without signal to be sent\n"); 3015 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3016 3017#if defined(TWAIT_HAVE_PID) 3018 if ((trackfork && fn == fork) || (trackvfork && fn == vfork)) { 3019 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 3020 child); 3021 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 3022 child); 3023 3024 validate_status_stopped(status, SIGTRAP); 3025 3026 SYSCALL_REQUIRE( 3027 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 3028 if (trackfork && fn == fork) { 3029 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 3030 PTRACE_FORK); 3031 } 3032 if (trackvfork && fn == vfork) { 3033 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 3034 PTRACE_VFORK); 3035 } 3036 3037 child2 = state.pe_other_pid; 3038 DPRINTF("Reported ptrace event with forkee %d\n", child2); 3039 3040 DPRINTF("Before calling %s() for the forkee %d of the child " 3041 "%d\n", TWAIT_FNAME, child2, child); 3042 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 3043 child2); 3044 3045 validate_status_stopped(status, SIGTRAP); 3046 3047 SYSCALL_REQUIRE( 3048 ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 3049 if (trackfork && fn == fork) { 3050 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 3051 PTRACE_FORK); 3052 } 3053 if (trackvfork && fn == vfork) { 3054 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 3055 PTRACE_VFORK); 3056 } 3057 3058 ATF_REQUIRE_EQ(state.pe_other_pid, child); 3059 3060 DPRINTF("Before resuming the forkee process where it left off " 3061 "and without signal to be sent\n"); 3062 SYSCALL_REQUIRE( 3063 ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 3064 3065 DPRINTF("Before resuming the child process where it left off " 3066 "and without signal to be sent\n"); 3067 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3068 } 3069#endif 3070 3071 if (trackvforkdone && fn == vfork) { 3072 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 3073 child); 3074 TWAIT_REQUIRE_SUCCESS( 3075 wpid = TWAIT_GENERIC(child, &status, 0), child); 3076 3077 validate_status_stopped(status, SIGTRAP); 3078 3079 SYSCALL_REQUIRE( 3080 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 3081 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE); 3082 3083 child2 = state.pe_other_pid; 3084 DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n", 3085 child2); 3086 3087 DPRINTF("Before resuming the child process where it left off " 3088 "and without signal to be sent\n"); 3089 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3090 } 3091 3092#if defined(TWAIT_HAVE_PID) 3093 if ((trackfork && fn == fork) || (trackvfork && fn == vfork)) { 3094 DPRINTF("Before calling %s() for the forkee - expected exited" 3095 "\n", TWAIT_FNAME); 3096 TWAIT_REQUIRE_SUCCESS( 3097 wpid = TWAIT_GENERIC(child2, &status, 0), child2); 3098 3099 validate_status_exited(status, exitval2); 3100 3101 DPRINTF("Before calling %s() for the forkee - expected no " 3102 "process\n", TWAIT_FNAME); 3103 TWAIT_REQUIRE_FAILURE(ECHILD, 3104 wpid = TWAIT_GENERIC(child2, &status, 0)); 3105 } 3106#endif 3107 3108 DPRINTF("Before calling %s() for the child - expected stopped " 3109 "SIGCHLD\n", TWAIT_FNAME); 3110 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3111 3112 validate_status_stopped(status, SIGCHLD); 3113 3114 DPRINTF("Before resuming the child process where it left off and " 3115 "without signal to be sent\n"); 3116 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3117 3118 DPRINTF("Before calling %s() for the child - expected exited\n", 3119 TWAIT_FNAME); 3120 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3121 3122 validate_status_exited(status, exitval); 3123 3124 DPRINTF("Before calling %s() for the child - expected no process\n", 3125 TWAIT_FNAME); 3126 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3127} 3128 3129#define FORK_TEST(name,fun,tfork,tvfork,tvforkdone) \ 3130ATF_TC(name); \ 3131ATF_TC_HEAD(name, tc) \ 3132{ \ 3133 atf_tc_set_md_var(tc, "descr", "Verify " #fun "(2) " \ 3134 "called with 0%s%s%s in EVENT_MASK", \ 3135 tfork ? "|PTRACE_FORK" : "", \ 3136 tvfork ? "|PTRACE_VFORK" : "", \ 3137 tvforkdone ? "|PTRACE_VFORK_DONE" : ""); \ 3138} \ 3139 \ 3140ATF_TC_BODY(name, tc) \ 3141{ \ 3142 \ 3143 fork_body(fun, tfork, tvfork, tvforkdone); \ 3144} 3145 3146FORK_TEST(fork1, fork, false, false, false) 3147#if defined(TWAIT_HAVE_PID) 3148FORK_TEST(fork2, fork, true, false, false) 3149FORK_TEST(fork3, fork, false, true, false) 3150FORK_TEST(fork4, fork, true, true, false) 3151#endif 3152FORK_TEST(fork5, fork, false, false, true) 3153#if defined(TWAIT_HAVE_PID) 3154FORK_TEST(fork6, fork, true, false, true) 3155FORK_TEST(fork7, fork, false, true, true) 3156FORK_TEST(fork8, fork, true, true, true) 3157#endif 3158 3159#if TEST_VFORK_ENABLED 3160FORK_TEST(vfork1, vfork, false, false, false) 3161#if defined(TWAIT_HAVE_PID) 3162FORK_TEST(vfork2, vfork, true, false, false) 3163FORK_TEST(vfork3, vfork, false, true, false) 3164FORK_TEST(vfork4, vfork, true, true, false) 3165#endif 3166FORK_TEST(vfork5, vfork, false, false, true) 3167#if defined(TWAIT_HAVE_PID) 3168FORK_TEST(vfork6, vfork, true, false, true) 3169FORK_TEST(vfork7, vfork, false, true, true) 3170FORK_TEST(vfork8, vfork, true, true, true) 3171#endif 3172#endif 3173 3174/// ---------------------------------------------------------------------------- 3175 3176#if TEST_VFORK_ENABLED 3177static void 3178traceme_vfork_fork_body(pid_t (*fn)(void)) 3179{ 3180 const int exitval = 5; 3181 const int exitval2 = 15; 3182 pid_t child, child2 = 0, wpid; 3183#if defined(TWAIT_HAVE_STATUS) 3184 int status; 3185#endif 3186 3187 DPRINTF("Before forking process PID=%d\n", getpid()); 3188 SYSCALL_REQUIRE((child = vfork()) != -1); 3189 if (child == 0) { 3190 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3191 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3192 3193 FORKEE_ASSERT((child2 = (fn)()) != -1); 3194 3195 if (child2 == 0) 3196 _exit(exitval2); 3197 3198 FORKEE_REQUIRE_SUCCESS 3199 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 3200 3201 forkee_status_exited(status, exitval2); 3202 3203 DPRINTF("Before exiting of the child process\n"); 3204 _exit(exitval); 3205 } 3206 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3207 3208 DPRINTF("Before calling %s() for the child - expected exited\n", 3209 TWAIT_FNAME); 3210 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3211 3212 validate_status_exited(status, exitval); 3213 3214 DPRINTF("Before calling %s() for the child - expected no process\n", 3215 TWAIT_FNAME); 3216 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3217} 3218 3219#define TRACEME_VFORK_FORK_TEST(name,fun) \ 3220ATF_TC(name); \ 3221ATF_TC_HEAD(name, tc) \ 3222{ \ 3223 atf_tc_set_md_var(tc, "descr", "Verify " #fun "(2) " \ 3224 "called from vfork(2)ed child"); \ 3225} \ 3226 \ 3227ATF_TC_BODY(name, tc) \ 3228{ \ 3229 \ 3230 traceme_vfork_fork_body(fun); \ 3231} 3232 3233TRACEME_VFORK_FORK_TEST(traceme_vfork_fork, fork) 3234TRACEME_VFORK_FORK_TEST(traceme_vfork_vfork, vfork) 3235#endif 3236 3237/// ---------------------------------------------------------------------------- 3238 3239enum bytes_transfer_type { 3240 BYTES_TRANSFER_DATA, 3241 BYTES_TRANSFER_DATAIO, 3242 BYTES_TRANSFER_TEXT, 3243 BYTES_TRANSFER_TEXTIO, 3244 BYTES_TRANSFER_AUXV 3245}; 3246 3247static int __used 3248bytes_transfer_dummy(int a, int b, int c, int d) 3249{ 3250 int e, f, g, h; 3251 3252 a *= 4; 3253 b += 3; 3254 c -= 2; 3255 d /= 1; 3256 3257 e = strtol("10", NULL, 10); 3258 f = strtol("20", NULL, 10); 3259 g = strtol("30", NULL, 10); 3260 h = strtol("40", NULL, 10); 3261 3262 return (a + b * c - d) + (e * f - g / h); 3263} 3264 3265static void 3266bytes_transfer(int operation, size_t size, enum bytes_transfer_type type) 3267{ 3268 const int exitval = 5; 3269 const int sigval = SIGSTOP; 3270 pid_t child, wpid; 3271 bool skip = false; 3272 3273 int lookup_me = 0; 3274 uint8_t lookup_me8 = 0; 3275 uint16_t lookup_me16 = 0; 3276 uint32_t lookup_me32 = 0; 3277 uint64_t lookup_me64 = 0; 3278 3279 int magic = 0x13579246; 3280 uint8_t magic8 = 0xab; 3281 uint16_t magic16 = 0x1234; 3282 uint32_t magic32 = 0x98765432; 3283 uint64_t magic64 = 0xabcdef0123456789; 3284 3285 struct ptrace_io_desc io; 3286#if defined(TWAIT_HAVE_STATUS) 3287 int status; 3288#endif 3289 /* 513 is just enough, for the purposes of ATF it's good enough */ 3290 AuxInfo ai[513], *aip; 3291 3292 ATF_REQUIRE(size < sizeof(ai)); 3293 3294 /* Prepare variables for .TEXT transfers */ 3295 switch (type) { 3296 case BYTES_TRANSFER_TEXT: 3297 memcpy(&magic, bytes_transfer_dummy, sizeof(magic)); 3298 break; 3299 case BYTES_TRANSFER_TEXTIO: 3300 switch (size) { 3301 case 8: 3302 memcpy(&magic8, bytes_transfer_dummy, sizeof(magic8)); 3303 break; 3304 case 16: 3305 memcpy(&magic16, bytes_transfer_dummy, sizeof(magic16)); 3306 break; 3307 case 32: 3308 memcpy(&magic32, bytes_transfer_dummy, sizeof(magic32)); 3309 break; 3310 case 64: 3311 memcpy(&magic64, bytes_transfer_dummy, sizeof(magic64)); 3312 break; 3313 } 3314 break; 3315 default: 3316 break; 3317 } 3318 3319 /* Prepare variables for PIOD and AUXV transfers */ 3320 switch (type) { 3321 case BYTES_TRANSFER_TEXTIO: 3322 case BYTES_TRANSFER_DATAIO: 3323 io.piod_op = operation; 3324 switch (size) { 3325 case 8: 3326 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 3327 (void *)bytes_transfer_dummy : 3328 &lookup_me8; 3329 io.piod_addr = &lookup_me8; 3330 io.piod_len = sizeof(lookup_me8); 3331 break; 3332 case 16: 3333 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 3334 (void *)bytes_transfer_dummy : 3335 &lookup_me16; 3336 io.piod_addr = &lookup_me16; 3337 io.piod_len = sizeof(lookup_me16); 3338 break; 3339 case 32: 3340 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 3341 (void *)bytes_transfer_dummy : 3342 &lookup_me32; 3343 io.piod_addr = &lookup_me32; 3344 io.piod_len = sizeof(lookup_me32); 3345 break; 3346 case 64: 3347 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 3348 (void *)bytes_transfer_dummy : 3349 &lookup_me64; 3350 io.piod_addr = &lookup_me64; 3351 io.piod_len = sizeof(lookup_me64); 3352 break; 3353 default: 3354 break; 3355 } 3356 break; 3357 case BYTES_TRANSFER_AUXV: 3358 io.piod_op = operation; 3359 io.piod_offs = 0; 3360 io.piod_addr = ai; 3361 io.piod_len = size; 3362 break; 3363 default: 3364 break; 3365 } 3366 3367 DPRINTF("Before forking process PID=%d\n", getpid()); 3368 SYSCALL_REQUIRE((child = fork()) != -1); 3369 if (child == 0) { 3370 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3371 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3372 3373 switch (type) { 3374 case BYTES_TRANSFER_DATA: 3375 switch (operation) { 3376 case PT_READ_D: 3377 case PT_READ_I: 3378 lookup_me = magic; 3379 break; 3380 default: 3381 break; 3382 } 3383 break; 3384 case BYTES_TRANSFER_DATAIO: 3385 switch (operation) { 3386 case PIOD_READ_D: 3387 case PIOD_READ_I: 3388 switch (size) { 3389 case 8: 3390 lookup_me8 = magic8; 3391 break; 3392 case 16: 3393 lookup_me16 = magic16; 3394 break; 3395 case 32: 3396 lookup_me32 = magic32; 3397 break; 3398 case 64: 3399 lookup_me64 = magic64; 3400 break; 3401 default: 3402 break; 3403 } 3404 break; 3405 default: 3406 break; 3407 } 3408 default: 3409 break; 3410 } 3411 3412 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3413 FORKEE_ASSERT(raise(sigval) == 0); 3414 3415 /* Handle PIOD and PT separately as operation values overlap */ 3416 switch (type) { 3417 case BYTES_TRANSFER_DATA: 3418 switch (operation) { 3419 case PT_WRITE_D: 3420 case PT_WRITE_I: 3421 FORKEE_ASSERT_EQ(lookup_me, magic); 3422 break; 3423 default: 3424 break; 3425 } 3426 break; 3427 case BYTES_TRANSFER_DATAIO: 3428 switch (operation) { 3429 case PIOD_WRITE_D: 3430 case PIOD_WRITE_I: 3431 switch (size) { 3432 case 8: 3433 FORKEE_ASSERT_EQ(lookup_me8, magic8); 3434 break; 3435 case 16: 3436 FORKEE_ASSERT_EQ(lookup_me16, magic16); 3437 break; 3438 case 32: 3439 FORKEE_ASSERT_EQ(lookup_me32, magic32); 3440 break; 3441 case 64: 3442 FORKEE_ASSERT_EQ(lookup_me64, magic64); 3443 break; 3444 default: 3445 break; 3446 } 3447 break; 3448 default: 3449 break; 3450 } 3451 break; 3452 case BYTES_TRANSFER_TEXT: 3453 FORKEE_ASSERT(memcmp(&magic, bytes_transfer_dummy, 3454 sizeof(magic)) == 0); 3455 break; 3456 case BYTES_TRANSFER_TEXTIO: 3457 switch (size) { 3458 case 8: 3459 FORKEE_ASSERT(memcmp(&magic8, 3460 bytes_transfer_dummy, 3461 sizeof(magic8)) == 0); 3462 break; 3463 case 16: 3464 FORKEE_ASSERT(memcmp(&magic16, 3465 bytes_transfer_dummy, 3466 sizeof(magic16)) == 0); 3467 break; 3468 case 32: 3469 FORKEE_ASSERT(memcmp(&magic32, 3470 bytes_transfer_dummy, 3471 sizeof(magic32)) == 0); 3472 break; 3473 case 64: 3474 FORKEE_ASSERT(memcmp(&magic64, 3475 bytes_transfer_dummy, 3476 sizeof(magic64)) == 0); 3477 break; 3478 } 3479 break; 3480 default: 3481 break; 3482 } 3483 3484 DPRINTF("Before exiting of the child process\n"); 3485 _exit(exitval); 3486 } 3487 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3488 3489 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3490 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3491 3492 validate_status_stopped(status, sigval); 3493 3494 /* Check PaX MPROTECT */ 3495 if (!can_we_write_to_text(child)) { 3496 switch (type) { 3497 case BYTES_TRANSFER_TEXTIO: 3498 switch (operation) { 3499 case PIOD_WRITE_D: 3500 case PIOD_WRITE_I: 3501 skip = true; 3502 break; 3503 default: 3504 break; 3505 } 3506 break; 3507 case BYTES_TRANSFER_TEXT: 3508 switch (operation) { 3509 case PT_WRITE_D: 3510 case PT_WRITE_I: 3511 skip = true; 3512 break; 3513 default: 3514 break; 3515 } 3516 break; 3517 default: 3518 break; 3519 } 3520 } 3521 3522 /* Bailout cleanly killing the child process */ 3523 if (skip) { 3524 SYSCALL_REQUIRE(ptrace(PT_KILL, child, (void *)1, 0) != -1); 3525 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3526 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 3527 child); 3528 3529 validate_status_signaled(status, SIGKILL, 0); 3530 3531 atf_tc_skip("PaX MPROTECT setup prevents writes to .text"); 3532 } 3533 3534 DPRINTF("Calling operation to transfer bytes between child=%d and " 3535 "parent=%d\n", child, getpid()); 3536 3537 switch (type) { 3538 case BYTES_TRANSFER_TEXTIO: 3539 case BYTES_TRANSFER_DATAIO: 3540 case BYTES_TRANSFER_AUXV: 3541 switch (operation) { 3542 case PIOD_WRITE_D: 3543 case PIOD_WRITE_I: 3544 switch (size) { 3545 case 8: 3546 lookup_me8 = magic8; 3547 break; 3548 case 16: 3549 lookup_me16 = magic16; 3550 break; 3551 case 32: 3552 lookup_me32 = magic32; 3553 break; 3554 case 64: 3555 lookup_me64 = magic64; 3556 break; 3557 default: 3558 break; 3559 } 3560 break; 3561 default: 3562 break; 3563 } 3564 SYSCALL_REQUIRE(ptrace(PT_IO, child, &io, 0) != -1); 3565 switch (operation) { 3566 case PIOD_READ_D: 3567 case PIOD_READ_I: 3568 switch (size) { 3569 case 8: 3570 ATF_REQUIRE_EQ(lookup_me8, magic8); 3571 break; 3572 case 16: 3573 ATF_REQUIRE_EQ(lookup_me16, magic16); 3574 break; 3575 case 32: 3576 ATF_REQUIRE_EQ(lookup_me32, magic32); 3577 break; 3578 case 64: 3579 ATF_REQUIRE_EQ(lookup_me64, magic64); 3580 break; 3581 default: 3582 break; 3583 } 3584 break; 3585 case PIOD_READ_AUXV: 3586 DPRINTF("Asserting that AUXV length (%zu) is > 0\n", 3587 io.piod_len); 3588 ATF_REQUIRE(io.piod_len > 0); 3589 for (aip = ai; aip->a_type != AT_NULL; aip++) 3590 DPRINTF("a_type=%#llx a_v=%#llx\n", 3591 (long long int)aip->a_type, 3592 (long long int)aip->a_v); 3593 break; 3594 default: 3595 break; 3596 } 3597 break; 3598 case BYTES_TRANSFER_TEXT: 3599 switch (operation) { 3600 case PT_READ_D: 3601 case PT_READ_I: 3602 errno = 0; 3603 lookup_me = ptrace(operation, child, 3604 bytes_transfer_dummy, 0); 3605 ATF_REQUIRE_EQ(lookup_me, magic); 3606 SYSCALL_REQUIRE_ERRNO(errno, 0); 3607 break; 3608 case PT_WRITE_D: 3609 case PT_WRITE_I: 3610 SYSCALL_REQUIRE(ptrace(operation, child, 3611 bytes_transfer_dummy, magic) 3612 != -1); 3613 break; 3614 default: 3615 break; 3616 } 3617 break; 3618 case BYTES_TRANSFER_DATA: 3619 switch (operation) { 3620 case PT_READ_D: 3621 case PT_READ_I: 3622 errno = 0; 3623 lookup_me = ptrace(operation, child, &lookup_me, 0); 3624 ATF_REQUIRE_EQ(lookup_me, magic); 3625 SYSCALL_REQUIRE_ERRNO(errno, 0); 3626 break; 3627 case PT_WRITE_D: 3628 case PT_WRITE_I: 3629 lookup_me = magic; 3630 SYSCALL_REQUIRE(ptrace(operation, child, &lookup_me, 3631 magic) != -1); 3632 break; 3633 default: 3634 break; 3635 } 3636 break; 3637 default: 3638 break; 3639 } 3640 3641 DPRINTF("Before resuming the child process where it left off and " 3642 "without signal to be sent\n"); 3643 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3644 3645 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3646 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3647 3648 validate_status_exited(status, exitval); 3649 3650 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3651 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3652} 3653 3654#define BYTES_TRANSFER(test, operation, size, type) \ 3655ATF_TC(test); \ 3656ATF_TC_HEAD(test, tc) \ 3657{ \ 3658 atf_tc_set_md_var(tc, "descr", \ 3659 "Verify bytes transfer operation" #operation " and size " #size \ 3660 " of type " #type); \ 3661} \ 3662 \ 3663ATF_TC_BODY(test, tc) \ 3664{ \ 3665 \ 3666 bytes_transfer(operation, size, BYTES_TRANSFER_##type); \ 3667} 3668 3669// DATA 3670 3671BYTES_TRANSFER(bytes_transfer_piod_read_d_8, PIOD_READ_D, 8, DATAIO) 3672BYTES_TRANSFER(bytes_transfer_piod_read_d_16, PIOD_READ_D, 16, DATAIO) 3673BYTES_TRANSFER(bytes_transfer_piod_read_d_32, PIOD_READ_D, 32, DATAIO) 3674BYTES_TRANSFER(bytes_transfer_piod_read_d_64, PIOD_READ_D, 64, DATAIO) 3675 3676BYTES_TRANSFER(bytes_transfer_piod_read_i_8, PIOD_READ_I, 8, DATAIO) 3677BYTES_TRANSFER(bytes_transfer_piod_read_i_16, PIOD_READ_I, 16, DATAIO) 3678BYTES_TRANSFER(bytes_transfer_piod_read_i_32, PIOD_READ_I, 32, DATAIO) 3679BYTES_TRANSFER(bytes_transfer_piod_read_i_64, PIOD_READ_I, 64, DATAIO) 3680 3681BYTES_TRANSFER(bytes_transfer_piod_write_d_8, PIOD_WRITE_D, 8, DATAIO) 3682BYTES_TRANSFER(bytes_transfer_piod_write_d_16, PIOD_WRITE_D, 16, DATAIO) 3683BYTES_TRANSFER(bytes_transfer_piod_write_d_32, PIOD_WRITE_D, 32, DATAIO) 3684BYTES_TRANSFER(bytes_transfer_piod_write_d_64, PIOD_WRITE_D, 64, DATAIO) 3685 3686BYTES_TRANSFER(bytes_transfer_piod_write_i_8, PIOD_WRITE_I, 8, DATAIO) 3687BYTES_TRANSFER(bytes_transfer_piod_write_i_16, PIOD_WRITE_I, 16, DATAIO) 3688BYTES_TRANSFER(bytes_transfer_piod_write_i_32, PIOD_WRITE_I, 32, DATAIO) 3689BYTES_TRANSFER(bytes_transfer_piod_write_i_64, PIOD_WRITE_I, 64, DATAIO) 3690 3691BYTES_TRANSFER(bytes_transfer_read_d, PT_READ_D, 32, DATA) 3692BYTES_TRANSFER(bytes_transfer_read_i, PT_READ_I, 32, DATA) 3693BYTES_TRANSFER(bytes_transfer_write_d, PT_WRITE_D, 32, DATA) 3694BYTES_TRANSFER(bytes_transfer_write_i, PT_WRITE_I, 32, DATA) 3695 3696// TEXT 3697 3698BYTES_TRANSFER(bytes_transfer_piod_read_d_8_text, PIOD_READ_D, 8, TEXTIO) 3699BYTES_TRANSFER(bytes_transfer_piod_read_d_16_text, PIOD_READ_D, 16, TEXTIO) 3700BYTES_TRANSFER(bytes_transfer_piod_read_d_32_text, PIOD_READ_D, 32, TEXTIO) 3701BYTES_TRANSFER(bytes_transfer_piod_read_d_64_text, PIOD_READ_D, 64, TEXTIO) 3702 3703BYTES_TRANSFER(bytes_transfer_piod_read_i_8_text, PIOD_READ_I, 8, TEXTIO) 3704BYTES_TRANSFER(bytes_transfer_piod_read_i_16_text, PIOD_READ_I, 16, TEXTIO) 3705BYTES_TRANSFER(bytes_transfer_piod_read_i_32_text, PIOD_READ_I, 32, TEXTIO) 3706BYTES_TRANSFER(bytes_transfer_piod_read_i_64_text, PIOD_READ_I, 64, TEXTIO) 3707 3708BYTES_TRANSFER(bytes_transfer_piod_write_d_8_text, PIOD_WRITE_D, 8, TEXTIO) 3709BYTES_TRANSFER(bytes_transfer_piod_write_d_16_text, PIOD_WRITE_D, 16, TEXTIO) 3710BYTES_TRANSFER(bytes_transfer_piod_write_d_32_text, PIOD_WRITE_D, 32, TEXTIO) 3711BYTES_TRANSFER(bytes_transfer_piod_write_d_64_text, PIOD_WRITE_D, 64, TEXTIO) 3712 3713BYTES_TRANSFER(bytes_transfer_piod_write_i_8_text, PIOD_WRITE_I, 8, TEXTIO) 3714BYTES_TRANSFER(bytes_transfer_piod_write_i_16_text, PIOD_WRITE_I, 16, TEXTIO) 3715BYTES_TRANSFER(bytes_transfer_piod_write_i_32_text, PIOD_WRITE_I, 32, TEXTIO) 3716BYTES_TRANSFER(bytes_transfer_piod_write_i_64_text, PIOD_WRITE_I, 64, TEXTIO) 3717 3718BYTES_TRANSFER(bytes_transfer_read_d_text, PT_READ_D, 32, TEXT) 3719BYTES_TRANSFER(bytes_transfer_read_i_text, PT_READ_I, 32, TEXT) 3720BYTES_TRANSFER(bytes_transfer_write_d_text, PT_WRITE_D, 32, TEXT) 3721BYTES_TRANSFER(bytes_transfer_write_i_text, PT_WRITE_I, 32, TEXT) 3722 3723// AUXV 3724 3725BYTES_TRANSFER(bytes_transfer_piod_read_auxv, PIOD_READ_AUXV, 4096, AUXV) 3726 3727/// ---------------------------------------------------------------------------- 3728 3729static void 3730bytes_transfer_alignment(const char *operation) 3731{ 3732 const int exitval = 5; 3733 const int sigval = SIGSTOP; 3734 pid_t child, wpid; 3735#if defined(TWAIT_HAVE_STATUS) 3736 int status; 3737#endif 3738 char *buffer; 3739 int vector; 3740 size_t len; 3741 size_t i; 3742 int op; 3743 3744 struct ptrace_io_desc io; 3745 struct ptrace_siginfo info; 3746 3747 memset(&io, 0, sizeof(io)); 3748 memset(&info, 0, sizeof(info)); 3749 3750 /* Testing misaligned byte transfer crossing page boundaries */ 3751 len = sysconf(_SC_PAGESIZE) * 2; 3752 buffer = malloc(len); 3753 ATF_REQUIRE(buffer != NULL); 3754 3755 /* Initialize the buffer with random data */ 3756 for (i = 0; i < len; i++) 3757 buffer[i] = i & 0xff; 3758 3759 DPRINTF("Before forking process PID=%d\n", getpid()); 3760 SYSCALL_REQUIRE((child = fork()) != -1); 3761 if (child == 0) { 3762 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3763 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3764 3765 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3766 FORKEE_ASSERT(raise(sigval) == 0); 3767 3768 DPRINTF("Before exiting of the child process\n"); 3769 _exit(exitval); 3770 } 3771 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3772 3773 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3774 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3775 3776 validate_status_stopped(status, sigval); 3777 3778 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 3779 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) 3780 != -1); 3781 3782 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 3783 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 3784 "si_errno=%#x\n", 3785 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 3786 info.psi_siginfo.si_errno); 3787 3788 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 3789 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 3790 3791 if (strcmp(operation, "PT_READ_I") == 0 || 3792 strcmp(operation, "PT_READ_D") == 0) { 3793 if (strcmp(operation, "PT_READ_I")) 3794 op = PT_READ_I; 3795 else 3796 op = PT_READ_D; 3797 3798 for (i = 0; i <= (len - sizeof(int)); i++) { 3799 errno = 0; 3800 vector = ptrace(op, child, buffer + i, 0); 3801 ATF_REQUIRE_EQ(errno, 0); 3802 ATF_REQUIRE(!memcmp(&vector, buffer + i, sizeof(int))); 3803 } 3804 } else if (strcmp(operation, "PT_WRITE_I") == 0 || 3805 strcmp(operation, "PT_WRITE_D") == 0) { 3806 if (strcmp(operation, "PT_WRITE_I")) 3807 op = PT_WRITE_I; 3808 else 3809 op = PT_WRITE_D; 3810 3811 for (i = 0; i <= (len - sizeof(int)); i++) { 3812 memcpy(&vector, buffer + i, sizeof(int)); 3813 SYSCALL_REQUIRE(ptrace(op, child, buffer + 1, vector) 3814 != -1); 3815 } 3816 } else if (strcmp(operation, "PIOD_READ_I") == 0 || 3817 strcmp(operation, "PIOD_READ_D") == 0) { 3818 if (strcmp(operation, "PIOD_READ_I")) 3819 op = PIOD_READ_I; 3820 else 3821 op = PIOD_READ_D; 3822 3823 io.piod_op = op; 3824 io.piod_addr = &vector; 3825 io.piod_len = sizeof(int); 3826 3827 for (i = 0; i <= (len - sizeof(int)); i++) { 3828 io.piod_offs = buffer + i; 3829 3830 SYSCALL_REQUIRE(ptrace(PT_IO, child, &io, sizeof(io)) 3831 != -1); 3832 ATF_REQUIRE(!memcmp(&vector, buffer + i, sizeof(int))); 3833 } 3834 } else if (strcmp(operation, "PIOD_WRITE_I") == 0 || 3835 strcmp(operation, "PIOD_WRITE_D") == 0) { 3836 if (strcmp(operation, "PIOD_WRITE_I")) 3837 op = PIOD_WRITE_I; 3838 else 3839 op = PIOD_WRITE_D; 3840 3841 io.piod_op = op; 3842 io.piod_addr = &vector; 3843 io.piod_len = sizeof(int); 3844 3845 for (i = 0; i <= (len - sizeof(int)); i++) { 3846 io.piod_offs = buffer + i; 3847 3848 SYSCALL_REQUIRE(ptrace(PT_IO, child, &io, sizeof(io)) 3849 != -1); 3850 } 3851 } else if (strcmp(operation, "PIOD_READ_AUXV") == 0) { 3852 io.piod_op = PIOD_READ_AUXV; 3853 io.piod_addr = &vector; 3854 io.piod_len = sizeof(int); 3855 3856 errno = 0; 3857 i = 0; 3858 /* Read the whole AUXV vector, it has no clear length */ 3859 while (errno != EIO) { 3860 io.piod_offs = (void *)(intptr_t)i; 3861 SYSCALL_REQUIRE(ptrace(PT_IO, child, &io, sizeof(io)) 3862 != -1 || (errno == EIO && i > 0)); 3863 ++i; 3864 } 3865 } 3866 3867 DPRINTF("Before resuming the child process where it left off " 3868 "and without signal to be sent\n"); 3869 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3870 3871 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3872 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 3873 child); 3874 3875 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3876 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3877} 3878 3879#define BYTES_TRANSFER_ALIGNMENT(test, operation) \ 3880ATF_TC(test); \ 3881ATF_TC_HEAD(test, tc) \ 3882{ \ 3883 atf_tc_set_md_var(tc, "descr", \ 3884 "Verify bytes transfer for potentially misaligned " \ 3885 "operation " operation); \ 3886} \ 3887 \ 3888ATF_TC_BODY(test, tc) \ 3889{ \ 3890 \ 3891 bytes_transfer_alignment(operation); \ 3892} 3893 3894BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_pt_read_i, "PT_READ_I") 3895BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_pt_read_d, "PT_READ_D") 3896BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_pt_write_i, "PT_WRITE_I") 3897BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_pt_write_d, "PT_WRITE_D") 3898 3899BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_piod_read_i, "PIOD_READ_I") 3900BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_piod_read_d, "PIOD_READ_D") 3901BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_piod_write_i, "PIOD_WRITE_I") 3902BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_piod_write_d, "PIOD_WRITE_D") 3903 3904BYTES_TRANSFER_ALIGNMENT(bytes_transfer_alignment_piod_read_auxv, "PIOD_READ_AUXV") 3905 3906/// ---------------------------------------------------------------------------- 3907 3908#if defined(HAVE_GPREGS) || defined(HAVE_FPREGS) 3909static void 3910access_regs(const char *regset, const char *aux) 3911{ 3912 const int exitval = 5; 3913 const int sigval = SIGSTOP; 3914 pid_t child, wpid; 3915#if defined(TWAIT_HAVE_STATUS) 3916 int status; 3917#endif 3918#if defined(HAVE_GPREGS) 3919 struct reg gpr; 3920 register_t rgstr; 3921#endif 3922#if defined(HAVE_FPREGS) 3923 struct fpreg fpr; 3924#endif 3925 3926#if !defined(HAVE_GPREGS) 3927 if (strcmp(regset, "regs") == 0) 3928 atf_tc_fail("Impossible test scenario!"); 3929#endif 3930 3931#if !defined(HAVE_FPREGS) 3932 if (strcmp(regset, "fpregs") == 0) 3933 atf_tc_fail("Impossible test scenario!"); 3934#endif 3935 3936 DPRINTF("Before forking process PID=%d\n", getpid()); 3937 SYSCALL_REQUIRE((child = fork()) != -1); 3938 if (child == 0) { 3939 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3940 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3941 3942 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3943 FORKEE_ASSERT(raise(sigval) == 0); 3944 3945 DPRINTF("Before exiting of the child process\n"); 3946 _exit(exitval); 3947 } 3948 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3949 3950 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3951 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3952 3953 validate_status_stopped(status, sigval); 3954 3955#if defined(HAVE_GPREGS) 3956 if (strcmp(regset, "regs") == 0) { 3957 DPRINTF("Call GETREGS for the child process\n"); 3958 SYSCALL_REQUIRE(ptrace(PT_GETREGS, child, &gpr, 0) != -1); 3959 3960 if (strcmp(aux, "none") == 0) { 3961 DPRINTF("Retrieved registers\n"); 3962 } else if (strcmp(aux, "pc") == 0) { 3963 rgstr = PTRACE_REG_PC(&gpr); 3964 DPRINTF("Retrieved %" PRIxREGISTER "\n", rgstr); 3965 } else if (strcmp(aux, "set_pc") == 0) { 3966 rgstr = PTRACE_REG_PC(&gpr); 3967 PTRACE_REG_SET_PC(&gpr, rgstr); 3968 } else if (strcmp(aux, "sp") == 0) { 3969 rgstr = PTRACE_REG_SP(&gpr); 3970 DPRINTF("Retrieved %" PRIxREGISTER "\n", rgstr); 3971 } else if (strcmp(aux, "intrv") == 0) { 3972 rgstr = PTRACE_REG_INTRV(&gpr); 3973 DPRINTF("Retrieved %" PRIxREGISTER "\n", rgstr); 3974 } else if (strcmp(aux, "setregs") == 0) { 3975 DPRINTF("Call SETREGS for the child process\n"); 3976 SYSCALL_REQUIRE( 3977 ptrace(PT_GETREGS, child, &gpr, 0) != -1); 3978 } 3979 } 3980#endif 3981 3982#if defined(HAVE_FPREGS) 3983 if (strcmp(regset, "fpregs") == 0) { 3984 DPRINTF("Call GETFPREGS for the child process\n"); 3985 SYSCALL_REQUIRE(ptrace(PT_GETFPREGS, child, &fpr, 0) != -1); 3986 3987 if (strcmp(aux, "getfpregs") == 0) { 3988 DPRINTF("Retrieved FP registers\n"); 3989 } else if (strcmp(aux, "setfpregs") == 0) { 3990 DPRINTF("Call SETFPREGS for the child\n"); 3991 SYSCALL_REQUIRE( 3992 ptrace(PT_SETFPREGS, child, &fpr, 0) != -1); 3993 } 3994 } 3995#endif 3996 3997 DPRINTF("Before resuming the child process where it left off and " 3998 "without signal to be sent\n"); 3999 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4000 4001 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4002 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4003 4004 validate_status_exited(status, exitval); 4005 4006 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4007 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4008} 4009 4010#define ACCESS_REGS(test, regset, aux) \ 4011ATF_TC(test); \ 4012ATF_TC_HEAD(test, tc) \ 4013{ \ 4014 atf_tc_set_md_var(tc, "descr", \ 4015 "Verify " regset " with auxiliary operation: " aux); \ 4016} \ 4017 \ 4018ATF_TC_BODY(test, tc) \ 4019{ \ 4020 \ 4021 access_regs(regset, aux); \ 4022} 4023#endif 4024 4025#if defined(HAVE_GPREGS) 4026ACCESS_REGS(access_regs1, "regs", "none") 4027ACCESS_REGS(access_regs2, "regs", "pc") 4028ACCESS_REGS(access_regs3, "regs", "set_pc") 4029ACCESS_REGS(access_regs4, "regs", "sp") 4030ACCESS_REGS(access_regs5, "regs", "intrv") 4031ACCESS_REGS(access_regs6, "regs", "setregs") 4032#endif 4033#if defined(HAVE_FPREGS) 4034ACCESS_REGS(access_fpregs1, "fpregs", "getfpregs") 4035ACCESS_REGS(access_fpregs2, "fpregs", "setfpregs") 4036#endif 4037 4038/// ---------------------------------------------------------------------------- 4039 4040#if defined(PT_STEP) 4041static void 4042ptrace_step(int N, int setstep, bool masked, bool ignored) 4043{ 4044 const int exitval = 5; 4045 const int sigval = SIGSTOP; 4046 pid_t child, wpid; 4047#if defined(TWAIT_HAVE_STATUS) 4048 int status; 4049#endif 4050 int happy; 4051 struct sigaction sa; 4052 struct ptrace_siginfo info; 4053 sigset_t intmask; 4054 struct kinfo_proc2 kp; 4055 size_t len = sizeof(kp); 4056 4057 int name[6]; 4058 const size_t namelen = __arraycount(name); 4059 ki_sigset_t kp_sigmask; 4060 ki_sigset_t kp_sigignore; 4061 4062#if defined(__arm__) 4063 /* PT_STEP not supported on arm 32-bit */ 4064 atf_tc_expect_fail("PR kern/52119"); 4065#endif 4066 4067 DPRINTF("Before forking process PID=%d\n", getpid()); 4068 SYSCALL_REQUIRE((child = fork()) != -1); 4069 if (child == 0) { 4070 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4071 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4072 4073 if (masked) { 4074 sigemptyset(&intmask); 4075 sigaddset(&intmask, SIGTRAP); 4076 sigprocmask(SIG_BLOCK, &intmask, NULL); 4077 } 4078 4079 if (ignored) { 4080 memset(&sa, 0, sizeof(sa)); 4081 sa.sa_handler = SIG_IGN; 4082 sigemptyset(&sa.sa_mask); 4083 FORKEE_ASSERT(sigaction(SIGTRAP, &sa, NULL) != -1); 4084 } 4085 4086 happy = check_happy(999); 4087 4088 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4089 FORKEE_ASSERT(raise(sigval) == 0); 4090 4091 FORKEE_ASSERT_EQ(happy, check_happy(999)); 4092 4093 DPRINTF("Before exiting of the child process\n"); 4094 _exit(exitval); 4095 } 4096 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4097 4098 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4099 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4100 4101 validate_status_stopped(status, sigval); 4102 4103 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 4104 SYSCALL_REQUIRE( 4105 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4106 4107 DPRINTF("Before checking siginfo_t\n"); 4108 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 4109 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 4110 4111 name[0] = CTL_KERN, 4112 name[1] = KERN_PROC2, 4113 name[2] = KERN_PROC_PID; 4114 name[3] = child; 4115 name[4] = sizeof(kp); 4116 name[5] = 1; 4117 4118 FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 4119 4120 if (masked) 4121 kp_sigmask = kp.p_sigmask; 4122 4123 if (ignored) 4124 kp_sigignore = kp.p_sigignore; 4125 4126 while (N --> 0) { 4127 if (setstep) { 4128 DPRINTF("Before resuming the child process where it " 4129 "left off and without signal to be sent (use " 4130 "PT_SETSTEP and PT_CONTINUE)\n"); 4131 SYSCALL_REQUIRE(ptrace(PT_SETSTEP, child, 0, 0) != -1); 4132 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) 4133 != -1); 4134 } else { 4135 DPRINTF("Before resuming the child process where it " 4136 "left off and without signal to be sent (use " 4137 "PT_STEP)\n"); 4138 SYSCALL_REQUIRE(ptrace(PT_STEP, child, (void *)1, 0) 4139 != -1); 4140 } 4141 4142 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4143 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 4144 child); 4145 4146 validate_status_stopped(status, SIGTRAP); 4147 4148 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 4149 SYSCALL_REQUIRE( 4150 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4151 4152 DPRINTF("Before checking siginfo_t\n"); 4153 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 4154 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_TRACE); 4155 4156 if (setstep) { 4157 SYSCALL_REQUIRE(ptrace(PT_CLEARSTEP, child, 0, 0) != -1); 4158 } 4159 4160 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 4161 4162 if (masked) { 4163 DPRINTF("kp_sigmask=" 4164 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 4165 PRIx32 "\n", 4166 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 4167 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 4168 4169 DPRINTF("kp.p_sigmask=" 4170 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 4171 PRIx32 "\n", 4172 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 4173 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 4174 4175 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 4176 sizeof(kp_sigmask))); 4177 } 4178 4179 if (ignored) { 4180 DPRINTF("kp_sigignore=" 4181 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 4182 PRIx32 "\n", 4183 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 4184 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 4185 4186 DPRINTF("kp.p_sigignore=" 4187 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 4188 PRIx32 "\n", 4189 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 4190 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 4191 4192 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 4193 sizeof(kp_sigignore))); 4194 } 4195 } 4196 4197 DPRINTF("Before resuming the child process where it left off and " 4198 "without signal to be sent\n"); 4199 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4200 4201 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4202 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4203 4204 validate_status_exited(status, exitval); 4205 4206 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4207 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4208} 4209 4210#define PTRACE_STEP(test, N, setstep) \ 4211ATF_TC(test); \ 4212ATF_TC_HEAD(test, tc) \ 4213{ \ 4214 atf_tc_set_md_var(tc, "descr", \ 4215 "Verify " #N " (PT_SETSTEP set to: " #setstep ")"); \ 4216} \ 4217 \ 4218ATF_TC_BODY(test, tc) \ 4219{ \ 4220 \ 4221 ptrace_step(N, setstep, false, false); \ 4222} 4223 4224PTRACE_STEP(step1, 1, 0) 4225PTRACE_STEP(step2, 2, 0) 4226PTRACE_STEP(step3, 3, 0) 4227PTRACE_STEP(step4, 4, 0) 4228PTRACE_STEP(setstep1, 1, 1) 4229PTRACE_STEP(setstep2, 2, 1) 4230PTRACE_STEP(setstep3, 3, 1) 4231PTRACE_STEP(setstep4, 4, 1) 4232 4233ATF_TC(step_signalmasked); 4234ATF_TC_HEAD(step_signalmasked, tc) 4235{ 4236 atf_tc_set_md_var(tc, "descr", "Verify PT_STEP with masked SIGTRAP"); 4237} 4238 4239ATF_TC_BODY(step_signalmasked, tc) 4240{ 4241 4242 ptrace_step(1, 0, true, false); 4243} 4244 4245ATF_TC(step_signalignored); 4246ATF_TC_HEAD(step_signalignored, tc) 4247{ 4248 atf_tc_set_md_var(tc, "descr", "Verify PT_STEP with ignored SIGTRAP"); 4249} 4250 4251ATF_TC_BODY(step_signalignored, tc) 4252{ 4253 4254 ptrace_step(1, 0, false, true); 4255} 4256#endif 4257 4258/// ---------------------------------------------------------------------------- 4259 4260static void 4261ptrace_kill(const char *type) 4262{ 4263 const int sigval = SIGSTOP; 4264 pid_t child, wpid; 4265#if defined(TWAIT_HAVE_STATUS) 4266 int status; 4267#endif 4268 4269 DPRINTF("Before forking process PID=%d\n", getpid()); 4270 SYSCALL_REQUIRE((child = fork()) != -1); 4271 if (child == 0) { 4272 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4273 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4274 4275 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4276 FORKEE_ASSERT(raise(sigval) == 0); 4277 4278 /* NOTREACHED */ 4279 FORKEE_ASSERTX(0 && 4280 "Child should be terminated by a signal from its parent"); 4281 } 4282 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4283 4284 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4285 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4286 4287 validate_status_stopped(status, sigval); 4288 4289 DPRINTF("Before killing the child process with %s\n", type); 4290 if (strcmp(type, "ptrace(PT_KILL)") == 0) { 4291 SYSCALL_REQUIRE(ptrace(PT_KILL, child, (void*)1, 0) != -1); 4292 } else if (strcmp(type, "kill(SIGKILL)") == 0) { 4293 kill(child, SIGKILL); 4294 } else if (strcmp(type, "killpg(SIGKILL)") == 0) { 4295 setpgid(child, 0); 4296 killpg(getpgid(child), SIGKILL); 4297 } 4298 4299 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4300 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4301 4302 validate_status_signaled(status, SIGKILL, 0); 4303 4304 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4305 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4306} 4307 4308#define PTRACE_KILL(test, type) \ 4309ATF_TC(test); \ 4310ATF_TC_HEAD(test, tc) \ 4311{ \ 4312 atf_tc_set_md_var(tc, "descr", \ 4313 "Verify killing the child with " type); \ 4314} \ 4315 \ 4316ATF_TC_BODY(test, tc) \ 4317{ \ 4318 \ 4319 ptrace_kill(type); \ 4320} 4321 4322// PT_CONTINUE with SIGKILL is covered by traceme_sendsignal_simple1 4323PTRACE_KILL(kill1, "ptrace(PT_KILL)") 4324PTRACE_KILL(kill2, "kill(SIGKILL)") 4325PTRACE_KILL(kill3, "killpg(SIGKILL)") 4326 4327/// ---------------------------------------------------------------------------- 4328 4329static void 4330traceme_lwpinfo(const int threads) 4331{ 4332 const int sigval = SIGSTOP; 4333 const int sigval2 = SIGINT; 4334 pid_t child, wpid; 4335#if defined(TWAIT_HAVE_STATUS) 4336 int status; 4337#endif 4338 struct ptrace_lwpinfo lwp = {0, 0}; 4339 struct ptrace_siginfo info; 4340 4341 /* Maximum number of supported threads in this test */ 4342 pthread_t t[3]; 4343 int n, rv; 4344 4345 ATF_REQUIRE((int)__arraycount(t) >= threads); 4346 4347 DPRINTF("Before forking process PID=%d\n", getpid()); 4348 SYSCALL_REQUIRE((child = fork()) != -1); 4349 if (child == 0) { 4350 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4351 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4352 4353 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4354 FORKEE_ASSERT(raise(sigval) == 0); 4355 4356 for (n = 0; n < threads; n++) { 4357 rv = pthread_create(&t[n], NULL, infinite_thread, NULL); 4358 FORKEE_ASSERT(rv == 0); 4359 } 4360 4361 DPRINTF("Before raising %s from child\n", strsignal(sigval2)); 4362 FORKEE_ASSERT(raise(sigval2) == 0); 4363 4364 /* NOTREACHED */ 4365 FORKEE_ASSERTX(0 && "Not reached"); 4366 } 4367 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4368 4369 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4370 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4371 4372 validate_status_stopped(status, sigval); 4373 4374 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 4375 SYSCALL_REQUIRE( 4376 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4377 4378 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4379 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 4380 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4381 info.psi_siginfo.si_errno); 4382 4383 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 4384 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 4385 4386 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 4387 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 4388 4389 DPRINTF("Assert that there exists a single thread only\n"); 4390 ATF_REQUIRE(lwp.pl_lwpid > 0); 4391 4392 DPRINTF("Assert that lwp thread %d received event PL_EVENT_SIGNAL\n", 4393 lwp.pl_lwpid); 4394 FORKEE_ASSERT_EQ(lwp.pl_event, PL_EVENT_SIGNAL); 4395 4396 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 4397 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 4398 4399 DPRINTF("Assert that there exists a single thread only\n"); 4400 ATF_REQUIRE_EQ(lwp.pl_lwpid, 0); 4401 4402 DPRINTF("Before resuming the child process where it left off and " 4403 "without signal to be sent\n"); 4404 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4405 4406 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4407 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4408 4409 validate_status_stopped(status, sigval2); 4410 4411 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 4412 SYSCALL_REQUIRE( 4413 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4414 4415 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4416 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 4417 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4418 info.psi_siginfo.si_errno); 4419 4420 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval2); 4421 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 4422 4423 memset(&lwp, 0, sizeof(lwp)); 4424 4425 for (n = 0; n <= threads; n++) { 4426 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 4427 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 4428 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 4429 4430 DPRINTF("Assert that the thread exists\n"); 4431 ATF_REQUIRE(lwp.pl_lwpid > 0); 4432 4433 DPRINTF("Assert that lwp thread %d received expected event\n", 4434 lwp.pl_lwpid); 4435 FORKEE_ASSERT_EQ(lwp.pl_event, info.psi_lwpid == lwp.pl_lwpid ? 4436 PL_EVENT_SIGNAL : PL_EVENT_NONE); 4437 } 4438 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 4439 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 4440 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 4441 4442 DPRINTF("Assert that there are no more threads\n"); 4443 ATF_REQUIRE_EQ(lwp.pl_lwpid, 0); 4444 4445 DPRINTF("Before resuming the child process where it left off and " 4446 "without signal to be sent\n"); 4447 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, SIGKILL) != -1); 4448 4449 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4450 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4451 4452 validate_status_signaled(status, SIGKILL, 0); 4453 4454 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4455 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4456} 4457 4458#define TRACEME_LWPINFO(test, threads) \ 4459ATF_TC(test); \ 4460ATF_TC_HEAD(test, tc) \ 4461{ \ 4462 atf_tc_set_md_var(tc, "descr", \ 4463 "Verify LWPINFO with the child with " #threads \ 4464 " spawned extra threads"); \ 4465} \ 4466 \ 4467ATF_TC_BODY(test, tc) \ 4468{ \ 4469 \ 4470 traceme_lwpinfo(threads); \ 4471} 4472 4473TRACEME_LWPINFO(traceme_lwpinfo0, 0) 4474TRACEME_LWPINFO(traceme_lwpinfo1, 1) 4475TRACEME_LWPINFO(traceme_lwpinfo2, 2) 4476TRACEME_LWPINFO(traceme_lwpinfo3, 3) 4477 4478/// ---------------------------------------------------------------------------- 4479 4480#if defined(TWAIT_HAVE_PID) 4481static void 4482attach_lwpinfo(const int threads) 4483{ 4484 const int sigval = SIGINT; 4485 struct msg_fds parent_tracee, parent_tracer; 4486 const int exitval_tracer = 10; 4487 pid_t tracee, tracer, wpid; 4488 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 4489#if defined(TWAIT_HAVE_STATUS) 4490 int status; 4491#endif 4492 struct ptrace_lwpinfo lwp = {0, 0}; 4493 struct ptrace_siginfo info; 4494 4495 /* Maximum number of supported threads in this test */ 4496 pthread_t t[3]; 4497 int n, rv; 4498 4499 DPRINTF("Spawn tracee\n"); 4500 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 4501 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 4502 tracee = atf_utils_fork(); 4503 if (tracee == 0) { 4504 /* Wait for message from the parent */ 4505 CHILD_TO_PARENT("tracee ready", parent_tracee, msg); 4506 4507 CHILD_FROM_PARENT("spawn threads", parent_tracee, msg); 4508 4509 for (n = 0; n < threads; n++) { 4510 rv = pthread_create(&t[n], NULL, infinite_thread, NULL); 4511 FORKEE_ASSERT(rv == 0); 4512 } 4513 4514 CHILD_TO_PARENT("tracee exit", parent_tracee, msg); 4515 4516 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4517 FORKEE_ASSERT(raise(sigval) == 0); 4518 4519 /* NOTREACHED */ 4520 FORKEE_ASSERTX(0 && "Not reached"); 4521 } 4522 PARENT_FROM_CHILD("tracee ready", parent_tracee, msg); 4523 4524 DPRINTF("Spawn debugger\n"); 4525 tracer = atf_utils_fork(); 4526 if (tracer == 0) { 4527 /* No IPC to communicate with the child */ 4528 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 4529 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 4530 4531 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 4532 FORKEE_REQUIRE_SUCCESS( 4533 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 4534 4535 forkee_status_stopped(status, SIGSTOP); 4536 4537 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 4538 "tracee"); 4539 FORKEE_ASSERT( 4540 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 4541 4542 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4543 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 4544 "si_errno=%#x\n", 4545 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4546 info.psi_siginfo.si_errno); 4547 4548 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, SIGSTOP); 4549 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SI_USER); 4550 4551 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 4552 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, sizeof(lwp)) 4553 != -1); 4554 4555 DPRINTF("Assert that there exists a thread\n"); 4556 FORKEE_ASSERTX(lwp.pl_lwpid > 0); 4557 4558 DPRINTF("Assert that lwp thread %d received event " 4559 "PL_EVENT_SIGNAL\n", lwp.pl_lwpid); 4560 FORKEE_ASSERT_EQ(lwp.pl_event, PL_EVENT_SIGNAL); 4561 4562 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for " 4563 "tracee\n"); 4564 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, sizeof(lwp)) 4565 != -1); 4566 4567 DPRINTF("Assert that there are no more lwp threads in " 4568 "tracee\n"); 4569 FORKEE_ASSERT_EQ(lwp.pl_lwpid, 0); 4570 4571 /* Resume tracee with PT_CONTINUE */ 4572 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 4573 4574 /* Inform parent that tracer has attached to tracee */ 4575 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 4576 4577 /* Wait for parent */ 4578 CHILD_FROM_PARENT("tracer wait", parent_tracer, msg); 4579 4580 /* Wait for tracee and assert that it raised a signal */ 4581 FORKEE_REQUIRE_SUCCESS( 4582 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 4583 4584 forkee_status_stopped(status, SIGINT); 4585 4586 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 4587 "child"); 4588 FORKEE_ASSERT( 4589 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 4590 4591 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4592 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 4593 "si_errno=%#x\n", 4594 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4595 info.psi_siginfo.si_errno); 4596 4597 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, sigval); 4598 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SI_LWP); 4599 4600 memset(&lwp, 0, sizeof(lwp)); 4601 4602 for (n = 0; n <= threads; n++) { 4603 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for " 4604 "child\n"); 4605 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, 4606 sizeof(lwp)) != -1); 4607 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 4608 4609 DPRINTF("Assert that the thread exists\n"); 4610 FORKEE_ASSERT(lwp.pl_lwpid > 0); 4611 4612 DPRINTF("Assert that lwp thread %d received expected " 4613 "event\n", lwp.pl_lwpid); 4614 FORKEE_ASSERT_EQ(lwp.pl_event, 4615 info.psi_lwpid == lwp.pl_lwpid ? 4616 PL_EVENT_SIGNAL : PL_EVENT_NONE); 4617 } 4618 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for " 4619 "tracee\n"); 4620 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, sizeof(lwp)) 4621 != -1); 4622 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 4623 4624 DPRINTF("Assert that there are no more threads\n"); 4625 FORKEE_ASSERT_EQ(lwp.pl_lwpid, 0); 4626 4627 DPRINTF("Before resuming the child process where it left off " 4628 "and without signal to be sent\n"); 4629 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, SIGKILL) 4630 != -1); 4631 4632 /* Wait for tracee and assert that it exited */ 4633 FORKEE_REQUIRE_SUCCESS( 4634 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 4635 4636 forkee_status_signaled(status, SIGKILL, 0); 4637 4638 DPRINTF("Before exiting of the tracer process\n"); 4639 _exit(exitval_tracer); 4640 } 4641 4642 DPRINTF("Wait for the tracer to attach to the tracee\n"); 4643 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 4644 4645 DPRINTF("Resume the tracee and spawn threads\n"); 4646 PARENT_TO_CHILD("spawn threads", parent_tracee, msg); 4647 4648 DPRINTF("Resume the tracee and let it exit\n"); 4649 PARENT_FROM_CHILD("tracee exit", parent_tracee, msg); 4650 4651 DPRINTF("Resume the tracer and let it detect multiple threads\n"); 4652 PARENT_TO_CHILD("tracer wait", parent_tracer, msg); 4653 4654 DPRINTF("Wait for tracer to finish its job and exit - calling %s()\n", 4655 TWAIT_FNAME); 4656 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracer, &status, 0), 4657 tracer); 4658 4659 validate_status_exited(status, exitval_tracer); 4660 4661 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 4662 TWAIT_FNAME); 4663 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 4664 tracee); 4665 4666 validate_status_signaled(status, SIGKILL, 0); 4667 4668 msg_close(&parent_tracer); 4669 msg_close(&parent_tracee); 4670} 4671 4672#define ATTACH_LWPINFO(test, threads) \ 4673ATF_TC(test); \ 4674ATF_TC_HEAD(test, tc) \ 4675{ \ 4676 atf_tc_set_md_var(tc, "descr", \ 4677 "Verify LWPINFO with the child with " #threads \ 4678 " spawned extra threads (tracer is not the original " \ 4679 "parent)"); \ 4680} \ 4681 \ 4682ATF_TC_BODY(test, tc) \ 4683{ \ 4684 \ 4685 attach_lwpinfo(threads); \ 4686} 4687 4688ATTACH_LWPINFO(attach_lwpinfo0, 0) 4689ATTACH_LWPINFO(attach_lwpinfo1, 1) 4690ATTACH_LWPINFO(attach_lwpinfo2, 2) 4691ATTACH_LWPINFO(attach_lwpinfo3, 3) 4692#endif 4693 4694/// ---------------------------------------------------------------------------- 4695 4696static void 4697ptrace_siginfo(bool faked, void (*sah)(int a, siginfo_t *b, void *c), int *signal_caught) 4698{ 4699 const int exitval = 5; 4700 const int sigval = SIGINT; 4701 const int sigfaked = SIGTRAP; 4702 const int sicodefaked = TRAP_BRKPT; 4703 pid_t child, wpid; 4704 struct sigaction sa; 4705#if defined(TWAIT_HAVE_STATUS) 4706 int status; 4707#endif 4708 struct ptrace_siginfo info; 4709 memset(&info, 0, sizeof(info)); 4710 4711 DPRINTF("Before forking process PID=%d\n", getpid()); 4712 SYSCALL_REQUIRE((child = fork()) != -1); 4713 if (child == 0) { 4714 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4715 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4716 4717 sa.sa_sigaction = sah; 4718 sa.sa_flags = SA_SIGINFO; 4719 sigemptyset(&sa.sa_mask); 4720 4721 FORKEE_ASSERT(sigaction(faked ? sigfaked : sigval, &sa, NULL) 4722 != -1); 4723 4724 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4725 FORKEE_ASSERT(raise(sigval) == 0); 4726 4727 FORKEE_ASSERT_EQ(*signal_caught, 1); 4728 4729 DPRINTF("Before exiting of the child process\n"); 4730 _exit(exitval); 4731 } 4732 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4733 4734 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4735 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4736 4737 validate_status_stopped(status, sigval); 4738 4739 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 4740 SYSCALL_REQUIRE( 4741 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4742 4743 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4744 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 4745 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4746 info.psi_siginfo.si_errno); 4747 4748 if (faked) { 4749 DPRINTF("Before setting new faked signal to signo=%d " 4750 "si_code=%d\n", sigfaked, sicodefaked); 4751 info.psi_siginfo.si_signo = sigfaked; 4752 info.psi_siginfo.si_code = sicodefaked; 4753 } 4754 4755 DPRINTF("Before calling ptrace(2) with PT_SET_SIGINFO for child\n"); 4756 SYSCALL_REQUIRE( 4757 ptrace(PT_SET_SIGINFO, child, &info, sizeof(info)) != -1); 4758 4759 if (faked) { 4760 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 4761 "child\n"); 4762 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, 4763 sizeof(info)) != -1); 4764 4765 DPRINTF("Before checking siginfo_t\n"); 4766 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigfaked); 4767 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, sicodefaked); 4768 } 4769 4770 DPRINTF("Before resuming the child process where it left off and " 4771 "without signal to be sent\n"); 4772 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 4773 faked ? sigfaked : sigval) != -1); 4774 4775 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4776 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4777 4778 validate_status_exited(status, exitval); 4779 4780 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4781 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4782} 4783 4784#define PTRACE_SIGINFO(test, faked) \ 4785ATF_TC(test); \ 4786ATF_TC_HEAD(test, tc) \ 4787{ \ 4788 atf_tc_set_md_var(tc, "descr", \ 4789 "Verify basic PT_GET_SIGINFO and PT_SET_SIGINFO calls" \ 4790 "with%s setting signal to new value", faked ? "" : "out"); \ 4791} \ 4792 \ 4793static int test##_caught = 0; \ 4794 \ 4795static void \ 4796test##_sighandler(int sig, siginfo_t *info, void *ctx) \ 4797{ \ 4798 if (faked) { \ 4799 FORKEE_ASSERT_EQ(sig, SIGTRAP); \ 4800 FORKEE_ASSERT_EQ(info->si_signo, SIGTRAP); \ 4801 FORKEE_ASSERT_EQ(info->si_code, TRAP_BRKPT); \ 4802 } else { \ 4803 FORKEE_ASSERT_EQ(sig, SIGINT); \ 4804 FORKEE_ASSERT_EQ(info->si_signo, SIGINT); \ 4805 FORKEE_ASSERT_EQ(info->si_code, SI_LWP); \ 4806 } \ 4807 \ 4808 ++ test##_caught; \ 4809} \ 4810 \ 4811ATF_TC_BODY(test, tc) \ 4812{ \ 4813 \ 4814 ptrace_siginfo(faked, test##_sighandler, & test##_caught); \ 4815} 4816 4817PTRACE_SIGINFO(siginfo_set_unmodified, false) 4818PTRACE_SIGINFO(siginfo_set_faked, true) 4819 4820/// ---------------------------------------------------------------------------- 4821 4822static void 4823traceme_exec(bool masked, bool ignored) 4824{ 4825 const int sigval = SIGTRAP; 4826 pid_t child, wpid; 4827#if defined(TWAIT_HAVE_STATUS) 4828 int status; 4829#endif 4830 struct sigaction sa; 4831 struct ptrace_siginfo info; 4832 sigset_t intmask; 4833 struct kinfo_proc2 kp; 4834 size_t len = sizeof(kp); 4835 4836 int name[6]; 4837 const size_t namelen = __arraycount(name); 4838 ki_sigset_t kp_sigmask; 4839 ki_sigset_t kp_sigignore; 4840 4841 memset(&info, 0, sizeof(info)); 4842 4843 DPRINTF("Before forking process PID=%d\n", getpid()); 4844 SYSCALL_REQUIRE((child = fork()) != -1); 4845 if (child == 0) { 4846 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4847 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4848 4849 if (masked) { 4850 sigemptyset(&intmask); 4851 sigaddset(&intmask, sigval); 4852 sigprocmask(SIG_BLOCK, &intmask, NULL); 4853 } 4854 4855 if (ignored) { 4856 memset(&sa, 0, sizeof(sa)); 4857 sa.sa_handler = SIG_IGN; 4858 sigemptyset(&sa.sa_mask); 4859 FORKEE_ASSERT(sigaction(sigval, &sa, NULL) != -1); 4860 } 4861 4862 DPRINTF("Before calling execve(2) from child\n"); 4863 execlp("/bin/echo", "/bin/echo", NULL); 4864 4865 FORKEE_ASSERT(0 && "Not reached"); 4866 } 4867 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4868 4869 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4870 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4871 4872 validate_status_stopped(status, sigval); 4873 4874 name[0] = CTL_KERN, 4875 name[1] = KERN_PROC2, 4876 name[2] = KERN_PROC_PID; 4877 name[3] = getpid(); 4878 name[4] = sizeof(kp); 4879 name[5] = 1; 4880 4881 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 4882 4883 if (masked) 4884 kp_sigmask = kp.p_sigmask; 4885 4886 if (ignored) 4887 kp_sigignore = kp.p_sigignore; 4888 4889 name[3] = getpid(); 4890 4891 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 4892 4893 if (masked) { 4894 DPRINTF("kp_sigmask=" 4895 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 4896 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 4897 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 4898 4899 DPRINTF("kp.p_sigmask=" 4900 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 4901 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 4902 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 4903 4904 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 4905 sizeof(kp_sigmask))); 4906 } 4907 4908 if (ignored) { 4909 DPRINTF("kp_sigignore=" 4910 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 4911 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 4912 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 4913 4914 DPRINTF("kp.p_sigignore=" 4915 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" PRIx32"\n", 4916 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 4917 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 4918 4919 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 4920 sizeof(kp_sigignore))); 4921 } 4922 4923 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 4924 SYSCALL_REQUIRE( 4925 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4926 4927 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4928 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 4929 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4930 info.psi_siginfo.si_errno); 4931 4932 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 4933 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_EXEC); 4934 4935 DPRINTF("Before resuming the child process where it left off and " 4936 "without signal to be sent\n"); 4937 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4938 4939 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4940 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4941 4942 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4943 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4944} 4945 4946#define TRACEME_EXEC(test, masked, ignored) \ 4947ATF_TC(test); \ 4948ATF_TC_HEAD(test, tc) \ 4949{ \ 4950 atf_tc_set_md_var(tc, "descr", \ 4951 "Detect SIGTRAP TRAP_EXEC from " \ 4952 "child%s%s", masked ? " with masked signal" : "", \ 4953 masked ? " with ignored signal" : ""); \ 4954} \ 4955 \ 4956ATF_TC_BODY(test, tc) \ 4957{ \ 4958 \ 4959 traceme_exec(masked, ignored); \ 4960} 4961 4962TRACEME_EXEC(traceme_exec, false, false) 4963TRACEME_EXEC(traceme_signalmasked_exec, true, false) 4964TRACEME_EXEC(traceme_signalignored_exec, false, true) 4965 4966/// ---------------------------------------------------------------------------- 4967 4968static volatile int done; 4969 4970static void * 4971trace_threads_cb(void *arg __unused) 4972{ 4973 4974 done++; 4975 4976 while (done < 3) 4977 continue; 4978 4979 return NULL; 4980} 4981 4982static void 4983trace_threads(bool trace_create, bool trace_exit) 4984{ 4985 const int sigval = SIGSTOP; 4986 pid_t child, wpid; 4987#if defined(TWAIT_HAVE_STATUS) 4988 int status; 4989#endif 4990 ptrace_state_t state; 4991 const int slen = sizeof(state); 4992 ptrace_event_t event; 4993 const int elen = sizeof(event); 4994 struct ptrace_siginfo info; 4995 4996 pthread_t t[3]; 4997 int rv; 4998 size_t n; 4999 lwpid_t lid; 5000 5001 /* Track created and exited threads */ 5002 bool traced_lwps[__arraycount(t)]; 5003 5004 atf_tc_skip("PR kern/51995"); 5005 5006 DPRINTF("Before forking process PID=%d\n", getpid()); 5007 SYSCALL_REQUIRE((child = fork()) != -1); 5008 if (child == 0) { 5009 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5010 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5011 5012 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5013 FORKEE_ASSERT(raise(sigval) == 0); 5014 5015 for (n = 0; n < __arraycount(t); n++) { 5016 rv = pthread_create(&t[n], NULL, trace_threads_cb, 5017 NULL); 5018 FORKEE_ASSERT(rv == 0); 5019 } 5020 5021 for (n = 0; n < __arraycount(t); n++) { 5022 rv = pthread_join(t[n], NULL); 5023 FORKEE_ASSERT(rv == 0); 5024 } 5025 5026 /* 5027 * There is race between _exit() and pthread_join() detaching 5028 * a thread. For simplicity kill the process after detecting 5029 * LWP events. 5030 */ 5031 while (true) 5032 continue; 5033 5034 FORKEE_ASSERT(0 && "Not reached"); 5035 } 5036 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5037 5038 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5039 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5040 5041 validate_status_stopped(status, sigval); 5042 5043 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 5044 SYSCALL_REQUIRE( 5045 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 5046 5047 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 5048 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 5049 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 5050 info.psi_siginfo.si_errno); 5051 5052 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 5053 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 5054 5055 DPRINTF("Set LWP event mask for the child %d\n", child); 5056 memset(&event, 0, sizeof(event)); 5057 if (trace_create) 5058 event.pe_set_event |= PTRACE_LWP_CREATE; 5059 if (trace_exit) 5060 event.pe_set_event |= PTRACE_LWP_EXIT; 5061 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 5062 5063 DPRINTF("Before resuming the child process where it left off and " 5064 "without signal to be sent\n"); 5065 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5066 5067 memset(traced_lwps, 0, sizeof(traced_lwps)); 5068 5069 for (n = 0; n < (trace_create ? __arraycount(t) : 0); n++) { 5070 DPRINTF("Before calling %s() for the child - expected stopped " 5071 "SIGTRAP\n", TWAIT_FNAME); 5072 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 5073 child); 5074 5075 validate_status_stopped(status, SIGTRAP); 5076 5077 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 5078 "child\n"); 5079 SYSCALL_REQUIRE( 5080 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 5081 5082 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 5083 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 5084 "si_errno=%#x\n", 5085 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 5086 info.psi_siginfo.si_errno); 5087 5088 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 5089 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_LWP); 5090 5091 SYSCALL_REQUIRE( 5092 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 5093 5094 ATF_REQUIRE_EQ_MSG(state.pe_report_event, PTRACE_LWP_CREATE, 5095 "%d != %d", state.pe_report_event, PTRACE_LWP_CREATE); 5096 5097 lid = state.pe_lwp; 5098 DPRINTF("Reported PTRACE_LWP_CREATE event with lid %d\n", lid); 5099 5100 traced_lwps[lid - 1] = true; 5101 5102 DPRINTF("Before resuming the child process where it left off " 5103 "and without signal to be sent\n"); 5104 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5105 } 5106 5107 for (n = 0; n < (trace_exit ? __arraycount(t) : 0); n++) { 5108 DPRINTF("Before calling %s() for the child - expected stopped " 5109 "SIGTRAP\n", TWAIT_FNAME); 5110 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 5111 child); 5112 5113 validate_status_stopped(status, SIGTRAP); 5114 5115 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 5116 "child\n"); 5117 SYSCALL_REQUIRE( 5118 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 5119 5120 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 5121 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 5122 "si_errno=%#x\n", 5123 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 5124 info.psi_siginfo.si_errno); 5125 5126 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 5127 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_LWP); 5128 5129 SYSCALL_REQUIRE( 5130 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 5131 5132 ATF_REQUIRE_EQ_MSG(state.pe_report_event, PTRACE_LWP_EXIT, 5133 "%d != %d", state.pe_report_event, PTRACE_LWP_EXIT); 5134 5135 lid = state.pe_lwp; 5136 DPRINTF("Reported PTRACE_LWP_EXIT event with lid %d\n", lid); 5137 5138 if (trace_create) { 5139 ATF_REQUIRE(traced_lwps[lid - 1] == true); 5140 traced_lwps[lid - 1] = false; 5141 } 5142 5143 DPRINTF("Before resuming the child process where it left off " 5144 "and without signal to be sent\n"); 5145 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5146 } 5147 5148 kill(child, SIGKILL); 5149 5150 DPRINTF("Before calling %s() for the child - expected exited\n", 5151 TWAIT_FNAME); 5152 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5153 5154 validate_status_signaled(status, SIGKILL, 0); 5155 5156 DPRINTF("Before calling %s() for the child - expected no process\n", 5157 TWAIT_FNAME); 5158 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5159} 5160 5161#define TRACE_THREADS(test, trace_create, trace_exit) \ 5162ATF_TC(test); \ 5163ATF_TC_HEAD(test, tc) \ 5164{ \ 5165 atf_tc_set_md_var(tc, "descr", \ 5166 "Verify spawning threads with%s tracing LWP create and" \ 5167 "with%s tracing LWP exit", trace_create ? "" : "out", \ 5168 trace_exit ? "" : "out"); \ 5169} \ 5170 \ 5171ATF_TC_BODY(test, tc) \ 5172{ \ 5173 \ 5174 trace_threads(trace_create, trace_exit); \ 5175} 5176 5177TRACE_THREADS(trace_thread1, false, false) 5178TRACE_THREADS(trace_thread2, false, true) 5179TRACE_THREADS(trace_thread3, true, false) 5180TRACE_THREADS(trace_thread4, true, true) 5181 5182/// ---------------------------------------------------------------------------- 5183 5184ATF_TC(signal_mask_unrelated); 5185ATF_TC_HEAD(signal_mask_unrelated, tc) 5186{ 5187 atf_tc_set_md_var(tc, "descr", 5188 "Verify that masking single unrelated signal does not stop tracer " 5189 "from catching other signals"); 5190} 5191 5192ATF_TC_BODY(signal_mask_unrelated, tc) 5193{ 5194 const int exitval = 5; 5195 const int sigval = SIGSTOP; 5196 const int sigmasked = SIGTRAP; 5197 const int signotmasked = SIGINT; 5198 pid_t child, wpid; 5199#if defined(TWAIT_HAVE_STATUS) 5200 int status; 5201#endif 5202 sigset_t intmask; 5203 5204 DPRINTF("Before forking process PID=%d\n", getpid()); 5205 SYSCALL_REQUIRE((child = fork()) != -1); 5206 if (child == 0) { 5207 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5208 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5209 5210 sigemptyset(&intmask); 5211 sigaddset(&intmask, sigmasked); 5212 sigprocmask(SIG_BLOCK, &intmask, NULL); 5213 5214 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5215 FORKEE_ASSERT(raise(sigval) == 0); 5216 5217 DPRINTF("Before raising %s from child\n", 5218 strsignal(signotmasked)); 5219 FORKEE_ASSERT(raise(signotmasked) == 0); 5220 5221 DPRINTF("Before exiting of the child process\n"); 5222 _exit(exitval); 5223 } 5224 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5225 5226 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5227 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5228 5229 validate_status_stopped(status, sigval); 5230 5231 DPRINTF("Before resuming the child process where it left off and " 5232 "without signal to be sent\n"); 5233 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5234 5235 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5236 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5237 5238 validate_status_stopped(status, signotmasked); 5239 5240 DPRINTF("Before resuming the child process where it left off and " 5241 "without signal to be sent\n"); 5242 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5243 5244 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5245 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5246 5247 validate_status_exited(status, exitval); 5248 5249 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5250 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5251} 5252 5253/// ---------------------------------------------------------------------------- 5254 5255#if defined(TWAIT_HAVE_PID) 5256static void 5257fork2_body(bool trackfork, bool trackvfork, bool trackvforkdone, bool masked, 5258 bool ignored) 5259{ 5260 const int exitval = 5; 5261 const int exitval2 = 15; 5262 const int sigval = SIGSTOP; 5263 pid_t child, child2 = 0, wpid; 5264#if defined(TWAIT_HAVE_STATUS) 5265 int status; 5266#endif 5267 ptrace_state_t state; 5268 const int slen = sizeof(state); 5269 ptrace_event_t event; 5270 const int elen = sizeof(event); 5271 pid_t (*fn)(void); 5272 struct sigaction sa; 5273 struct ptrace_siginfo info; 5274 sigset_t intmask; 5275 struct kinfo_proc2 kp; 5276 size_t len = sizeof(kp); 5277 5278 int name[6]; 5279 const size_t namelen = __arraycount(name); 5280 ki_sigset_t kp_sigmask; 5281 ki_sigset_t kp_sigignore; 5282 5283 if (trackfork) 5284 fn = fork; 5285 if (trackvfork || trackvforkdone) 5286 fn = vfork; 5287 5288 DPRINTF("Before forking process PID=%d\n", getpid()); 5289 SYSCALL_REQUIRE((child = fork()) != -1); 5290 if (child == 0) { 5291 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5292 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5293 5294 if (masked) { 5295 sigemptyset(&intmask); 5296 sigaddset(&intmask, SIGTRAP); 5297 sigprocmask(SIG_BLOCK, &intmask, NULL); 5298 } 5299 5300 if (ignored) { 5301 memset(&sa, 0, sizeof(sa)); 5302 sa.sa_handler = SIG_IGN; 5303 sigemptyset(&sa.sa_mask); 5304 FORKEE_ASSERT(sigaction(SIGTRAP, &sa, NULL) != -1); 5305 } 5306 5307 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5308 FORKEE_ASSERT(raise(sigval) == 0); 5309 5310 FORKEE_ASSERT((child2 = (fn)()) != -1); 5311 5312 if (child2 == 0) 5313 _exit(exitval2); 5314 5315 FORKEE_REQUIRE_SUCCESS 5316 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 5317 5318 forkee_status_exited(status, exitval2); 5319 5320 DPRINTF("Before exiting of the child process\n"); 5321 _exit(exitval); 5322 } 5323 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5324 5325 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5326 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5327 5328 validate_status_stopped(status, sigval); 5329 5330 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 5331 SYSCALL_REQUIRE( 5332 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 5333 5334 DPRINTF("Before checking siginfo_t\n"); 5335 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 5336 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 5337 5338 name[0] = CTL_KERN, 5339 name[1] = KERN_PROC2, 5340 name[2] = KERN_PROC_PID; 5341 name[3] = child; 5342 name[4] = sizeof(kp); 5343 name[5] = 1; 5344 5345 FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 5346 5347 if (masked) 5348 kp_sigmask = kp.p_sigmask; 5349 5350 if (ignored) 5351 kp_sigignore = kp.p_sigignore; 5352 5353 DPRINTF("Set 0%s%s%s in EVENT_MASK for the child %d\n", 5354 trackfork ? "|PTRACE_FORK" : "", 5355 trackvfork ? "|PTRACE_VFORK" : "", 5356 trackvforkdone ? "|PTRACE_VFORK_DONE" : "", child); 5357 event.pe_set_event = 0; 5358 if (trackfork) 5359 event.pe_set_event |= PTRACE_FORK; 5360 if (trackvfork) 5361 event.pe_set_event |= PTRACE_VFORK; 5362 if (trackvforkdone) 5363 event.pe_set_event |= PTRACE_VFORK_DONE; 5364 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 5365 5366 DPRINTF("Before resuming the child process where it left off and " 5367 "without signal to be sent\n"); 5368 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5369 5370 if (trackfork || trackvfork) { 5371 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 5372 child); 5373 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 5374 child); 5375 5376 validate_status_stopped(status, SIGTRAP); 5377 5378 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 5379 5380 if (masked) { 5381 DPRINTF("kp_sigmask=" 5382 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5383 PRIx32 "\n", 5384 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 5385 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 5386 5387 DPRINTF("kp.p_sigmask=" 5388 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5389 PRIx32 "\n", 5390 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 5391 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 5392 5393 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 5394 sizeof(kp_sigmask))); 5395 } 5396 5397 if (ignored) { 5398 DPRINTF("kp_sigignore=" 5399 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5400 PRIx32 "\n", 5401 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 5402 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 5403 5404 DPRINTF("kp.p_sigignore=" 5405 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5406 PRIx32 "\n", 5407 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 5408 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 5409 5410 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 5411 sizeof(kp_sigignore))); 5412 } 5413 5414 SYSCALL_REQUIRE( 5415 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 5416 if (trackfork) { 5417 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 5418 PTRACE_FORK); 5419 } 5420 if (trackvfork) { 5421 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 5422 PTRACE_VFORK); 5423 } 5424 5425 child2 = state.pe_other_pid; 5426 DPRINTF("Reported ptrace event with forkee %d\n", child2); 5427 5428 DPRINTF("Before calling %s() for the forkee %d of the child " 5429 "%d\n", TWAIT_FNAME, child2, child); 5430 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 5431 child2); 5432 5433 validate_status_stopped(status, SIGTRAP); 5434 5435 name[3] = child2; 5436 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 5437 5438 if (masked) { 5439 DPRINTF("kp_sigmask=" 5440 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5441 PRIx32 "\n", 5442 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 5443 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 5444 5445 DPRINTF("kp.p_sigmask=" 5446 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5447 PRIx32 "\n", 5448 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 5449 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 5450 5451 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 5452 sizeof(kp_sigmask))); 5453 } 5454 5455 if (ignored) { 5456 DPRINTF("kp_sigignore=" 5457 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5458 PRIx32 "\n", 5459 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 5460 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 5461 5462 DPRINTF("kp.p_sigignore=" 5463 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5464 PRIx32 "\n", 5465 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 5466 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 5467 5468 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 5469 sizeof(kp_sigignore))); 5470 } 5471 5472 SYSCALL_REQUIRE( 5473 ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 5474 if (trackfork) { 5475 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 5476 PTRACE_FORK); 5477 } 5478 if (trackvfork) { 5479 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 5480 PTRACE_VFORK); 5481 } 5482 5483 ATF_REQUIRE_EQ(state.pe_other_pid, child); 5484 5485 DPRINTF("Before resuming the forkee process where it left off " 5486 "and without signal to be sent\n"); 5487 SYSCALL_REQUIRE( 5488 ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 5489 5490 DPRINTF("Before resuming the child process where it left off " 5491 "and without signal to be sent\n"); 5492 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5493 } 5494 5495 if (trackvforkdone) { 5496 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 5497 child); 5498 TWAIT_REQUIRE_SUCCESS( 5499 wpid = TWAIT_GENERIC(child, &status, 0), child); 5500 5501 validate_status_stopped(status, SIGTRAP); 5502 5503 name[3] = child; 5504 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 5505 5506 /* 5507 * SIGCHLD is now pending in the signal queue and 5508 * the kernel presents it to userland as a masked signal. 5509 */ 5510 sigdelset((sigset_t *)&kp.p_sigmask, SIGCHLD); 5511 5512 if (masked) { 5513 DPRINTF("kp_sigmask=" 5514 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5515 PRIx32 "\n", 5516 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 5517 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 5518 5519 DPRINTF("kp.p_sigmask=" 5520 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5521 PRIx32 "\n", 5522 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 5523 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 5524 5525 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 5526 sizeof(kp_sigmask))); 5527 } 5528 5529 if (ignored) { 5530 DPRINTF("kp_sigignore=" 5531 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5532 PRIx32 "\n", 5533 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 5534 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 5535 5536 DPRINTF("kp.p_sigignore=" 5537 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 5538 PRIx32 "\n", 5539 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 5540 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 5541 5542 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 5543 sizeof(kp_sigignore))); 5544 } 5545 5546 SYSCALL_REQUIRE( 5547 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 5548 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE); 5549 5550 child2 = state.pe_other_pid; 5551 DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n", 5552 child2); 5553 5554 DPRINTF("Before resuming the child process where it left off " 5555 "and without signal to be sent\n"); 5556 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5557 } 5558 5559 if (trackfork || trackvfork) { 5560 DPRINTF("Before calling %s() for the forkee - expected exited" 5561 "\n", TWAIT_FNAME); 5562 TWAIT_REQUIRE_SUCCESS( 5563 wpid = TWAIT_GENERIC(child2, &status, 0), child2); 5564 5565 validate_status_exited(status, exitval2); 5566 5567 DPRINTF("Before calling %s() for the forkee - expected no " 5568 "process\n", TWAIT_FNAME); 5569 TWAIT_REQUIRE_FAILURE(ECHILD, 5570 wpid = TWAIT_GENERIC(child2, &status, 0)); 5571 } 5572 5573 DPRINTF("Before calling %s() for the child - expected stopped " 5574 "SIGCHLD\n", TWAIT_FNAME); 5575 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5576 5577 validate_status_stopped(status, SIGCHLD); 5578 5579 DPRINTF("Before resuming the child process where it left off and " 5580 "without signal to be sent\n"); 5581 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5582 5583 DPRINTF("Before calling %s() for the child - expected exited\n", 5584 TWAIT_FNAME); 5585 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5586 5587 validate_status_exited(status, exitval); 5588 5589 DPRINTF("Before calling %s() for the child - expected no process\n", 5590 TWAIT_FNAME); 5591 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5592} 5593 5594#define FORK2_TEST(name,trackfork,trackvfork,trackvforkdone, \ 5595 masked,ignored) \ 5596ATF_TC(name); \ 5597ATF_TC_HEAD(name, tc) \ 5598{ \ 5599 atf_tc_set_md_var(tc, "descr", "Verify that %s%s%s is caught " \ 5600 "regardless of signal %s%s", \ 5601 trackfork ? "PTRACE_FORK" : "", \ 5602 trackvfork ? "PTRACE_VFORK" : "", \ 5603 trackvforkdone ? "PTRACE_VFORK_DONE" : "", \ 5604 masked ? "masked" : "", ignored ? "ignored" : ""); \ 5605} \ 5606 \ 5607ATF_TC_BODY(name, tc) \ 5608{ \ 5609 \ 5610 fork2_body(trackfork, trackvfork, trackvforkdone, masked, \ 5611 ignored); \ 5612} 5613 5614FORK2_TEST(fork_singalmasked, true, false, false, true, false) 5615FORK2_TEST(fork_singalignored, true, false, false, false, true) 5616#if TEST_VFORK_ENABLED 5617FORK2_TEST(vfork_singalmasked, false, true, false, true, false) 5618FORK2_TEST(vfork_singalignored, false, true, false, false, true) 5619FORK2_TEST(vforkdone_singalmasked, false, false, true, true, false) 5620FORK2_TEST(vforkdone_singalignored, false, false, true, false, true) 5621#endif 5622#endif 5623 5624/// ---------------------------------------------------------------------------- 5625 5626volatile lwpid_t the_lwp_id = 0; 5627 5628static void 5629lwp_main_func(void *arg) 5630{ 5631 the_lwp_id = _lwp_self(); 5632 _lwp_exit(); 5633} 5634 5635ATF_TC(signal9); 5636ATF_TC_HEAD(signal9, tc) 5637{ 5638 atf_tc_set_md_var(tc, "descr", 5639 "Verify that masking SIGTRAP in tracee does not stop tracer from " 5640 "catching PTRACE_LWP_CREATE breakpoint"); 5641} 5642 5643ATF_TC_BODY(signal9, tc) 5644{ 5645 const int exitval = 5; 5646 const int sigval = SIGSTOP; 5647 const int sigmasked = SIGTRAP; 5648 pid_t child, wpid; 5649#if defined(TWAIT_HAVE_STATUS) 5650 int status; 5651#endif 5652 sigset_t intmask; 5653 ptrace_state_t state; 5654 const int slen = sizeof(state); 5655 ptrace_event_t event; 5656 const int elen = sizeof(event); 5657 ucontext_t uc; 5658 lwpid_t lid; 5659 static const size_t ssize = 16*1024; 5660 void *stack; 5661 5662 atf_tc_expect_fail("PR kern/51918"); 5663 5664 DPRINTF("Before forking process PID=%d\n", getpid()); 5665 SYSCALL_REQUIRE((child = fork()) != -1); 5666 if (child == 0) { 5667 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5668 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5669 5670 sigemptyset(&intmask); 5671 sigaddset(&intmask, sigmasked); 5672 sigprocmask(SIG_BLOCK, &intmask, NULL); 5673 5674 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5675 FORKEE_ASSERT(raise(sigval) == 0); 5676 5677 DPRINTF("Before allocating memory for stack in child\n"); 5678 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 5679 5680 DPRINTF("Before making context for new lwp in child\n"); 5681 _lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize); 5682 5683 DPRINTF("Before creating new in child\n"); 5684 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 5685 5686 DPRINTF("Before waiting for lwp %d to exit\n", lid); 5687 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 5688 5689 DPRINTF("Before verifying that reported %d and running lid %d " 5690 "are the same\n", lid, the_lwp_id); 5691 FORKEE_ASSERT_EQ(lid, the_lwp_id); 5692 5693 DPRINTF("Before exiting of the child process\n"); 5694 _exit(exitval); 5695 } 5696 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5697 5698 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5699 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5700 5701 validate_status_stopped(status, sigval); 5702 5703 DPRINTF("Set empty EVENT_MASK for the child %d\n", child); 5704 event.pe_set_event = PTRACE_LWP_CREATE; 5705 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 5706 5707 DPRINTF("Before resuming the child process where it left off and " 5708 "without signal to be sent\n"); 5709 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5710 5711 DPRINTF("Before calling %s() for the child - expected stopped " 5712 "SIGTRAP\n", TWAIT_FNAME); 5713 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5714 5715 validate_status_stopped(status, sigmasked); 5716 5717 SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 5718 5719 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_CREATE); 5720 5721 lid = state.pe_lwp; 5722 DPRINTF("Reported PTRACE_LWP_CREATE event with lid %d\n", lid); 5723 5724 DPRINTF("Before resuming the child process where it left off and " 5725 "without signal to be sent\n"); 5726 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5727 5728 DPRINTF("Before calling %s() for the child - expected exited\n", 5729 TWAIT_FNAME); 5730 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5731 5732 validate_status_exited(status, exitval); 5733 5734 DPRINTF("Before calling %s() for the child - expected no process\n", 5735 TWAIT_FNAME); 5736 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5737} 5738 5739ATF_TC(signal10); 5740ATF_TC_HEAD(signal10, tc) 5741{ 5742 atf_tc_set_md_var(tc, "descr", 5743 "Verify that masking SIGTRAP in tracee does not stop tracer from " 5744 "catching PTRACE_LWP_EXIT breakpoint"); 5745} 5746 5747ATF_TC_BODY(signal10, tc) 5748{ 5749 const int exitval = 5; 5750 const int sigval = SIGSTOP; 5751 const int sigmasked = SIGTRAP; 5752 pid_t child, wpid; 5753#if defined(TWAIT_HAVE_STATUS) 5754 int status; 5755#endif 5756 sigset_t intmask; 5757 ptrace_state_t state; 5758 const int slen = sizeof(state); 5759 ptrace_event_t event; 5760 const int elen = sizeof(event); 5761 ucontext_t uc; 5762 lwpid_t lid; 5763 static const size_t ssize = 16*1024; 5764 void *stack; 5765 5766 atf_tc_expect_fail("PR kern/51918"); 5767 5768 DPRINTF("Before forking process PID=%d\n", getpid()); 5769 SYSCALL_REQUIRE((child = fork()) != -1); 5770 if (child == 0) { 5771 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5772 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5773 5774 sigemptyset(&intmask); 5775 sigaddset(&intmask, sigmasked); 5776 sigprocmask(SIG_BLOCK, &intmask, NULL); 5777 5778 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5779 FORKEE_ASSERT(raise(sigval) == 0); 5780 5781 DPRINTF("Before allocating memory for stack in child\n"); 5782 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 5783 5784 DPRINTF("Before making context for new lwp in child\n"); 5785 _lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize); 5786 5787 DPRINTF("Before creating new in child\n"); 5788 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 5789 5790 DPRINTF("Before waiting for lwp %d to exit\n", lid); 5791 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 5792 5793 DPRINTF("Before verifying that reported %d and running lid %d " 5794 "are the same\n", lid, the_lwp_id); 5795 FORKEE_ASSERT_EQ(lid, the_lwp_id); 5796 5797 DPRINTF("Before exiting of the child process\n"); 5798 _exit(exitval); 5799 } 5800 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5801 5802 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5803 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5804 5805 validate_status_stopped(status, sigval); 5806 5807 DPRINTF("Set empty EVENT_MASK for the child %d\n", child); 5808 event.pe_set_event = PTRACE_LWP_EXIT; 5809 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 5810 5811 DPRINTF("Before resuming the child process where it left off and " 5812 "without signal to be sent\n"); 5813 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5814 5815 DPRINTF("Before calling %s() for the child - expected stopped " 5816 "SIGTRAP\n", TWAIT_FNAME); 5817 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5818 5819 validate_status_stopped(status, sigmasked); 5820 5821 SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 5822 5823 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_EXIT); 5824 5825 lid = state.pe_lwp; 5826 DPRINTF("Reported PTRACE_LWP_EXIT event with lid %d\n", lid); 5827 5828 DPRINTF("Before resuming the child process where it left off and " 5829 "without signal to be sent\n"); 5830 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5831 5832 DPRINTF("Before calling %s() for the child - expected exited\n", 5833 TWAIT_FNAME); 5834 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5835 5836 validate_status_exited(status, exitval); 5837 5838 DPRINTF("Before calling %s() for the child - expected no process\n", 5839 TWAIT_FNAME); 5840 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5841} 5842 5843static void 5844lwp_main_stop(void *arg) 5845{ 5846 the_lwp_id = _lwp_self(); 5847 5848 raise(SIGTRAP); 5849 5850 _lwp_exit(); 5851} 5852 5853ATF_TC(suspend1); 5854ATF_TC_HEAD(suspend1, tc) 5855{ 5856 atf_tc_set_md_var(tc, "descr", 5857 "Verify that a thread can be suspended by a debugger and later " 5858 "resumed by a tracee"); 5859} 5860 5861ATF_TC_BODY(suspend1, tc) 5862{ 5863 const int exitval = 5; 5864 const int sigval = SIGSTOP; 5865 pid_t child, wpid; 5866#if defined(TWAIT_HAVE_STATUS) 5867 int status; 5868#endif 5869 ucontext_t uc; 5870 lwpid_t lid; 5871 static const size_t ssize = 16*1024; 5872 void *stack; 5873 struct ptrace_lwpinfo pl; 5874 struct ptrace_siginfo psi; 5875 volatile int go = 0; 5876 5877 // Feature pending for refactoring 5878 atf_tc_expect_fail("PR kern/51995"); 5879 5880 // Hangs with qemu 5881 ATF_REQUIRE(0 && "In order to get reliable failure, abort"); 5882 5883 DPRINTF("Before forking process PID=%d\n", getpid()); 5884 SYSCALL_REQUIRE((child = fork()) != -1); 5885 if (child == 0) { 5886 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5887 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5888 5889 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5890 FORKEE_ASSERT(raise(sigval) == 0); 5891 5892 DPRINTF("Before allocating memory for stack in child\n"); 5893 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 5894 5895 DPRINTF("Before making context for new lwp in child\n"); 5896 _lwp_makecontext(&uc, lwp_main_stop, NULL, NULL, stack, ssize); 5897 5898 DPRINTF("Before creating new in child\n"); 5899 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 5900 5901 while (go == 0) 5902 continue; 5903 5904 raise(SIGINT); 5905 5906 FORKEE_ASSERT(_lwp_continue(lid) == 0); 5907 5908 DPRINTF("Before waiting for lwp %d to exit\n", lid); 5909 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 5910 5911 DPRINTF("Before verifying that reported %d and running lid %d " 5912 "are the same\n", lid, the_lwp_id); 5913 FORKEE_ASSERT_EQ(lid, the_lwp_id); 5914 5915 DPRINTF("Before exiting of the child process\n"); 5916 _exit(exitval); 5917 } 5918 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5919 5920 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5921 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5922 5923 validate_status_stopped(status, sigval); 5924 5925 DPRINTF("Before resuming the child process where it left off and " 5926 "without signal to be sent\n"); 5927 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5928 5929 DPRINTF("Before calling %s() for the child - expected stopped " 5930 "SIGTRAP\n", TWAIT_FNAME); 5931 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5932 5933 validate_status_stopped(status, SIGTRAP); 5934 5935 DPRINTF("Before reading siginfo and lwpid_t\n"); 5936 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1); 5937 5938 DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid); 5939 SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1); 5940 5941 DPRINTF("Write new go to tracee (PID=%d) from tracer (PID=%d)\n", 5942 child, getpid()); 5943 SYSCALL_REQUIRE(ptrace(PT_WRITE_D, child, __UNVOLATILE(&go), 1) != -1); 5944 5945 DPRINTF("Before resuming the child process where it left off and " 5946 "without signal to be sent\n"); 5947 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5948 5949 DPRINTF("Before calling %s() for the child - expected stopped " 5950 "SIGINT\n", TWAIT_FNAME); 5951 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5952 5953 validate_status_stopped(status, SIGINT); 5954 5955 pl.pl_lwpid = 0; 5956 5957 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 5958 while (pl.pl_lwpid != 0) { 5959 5960 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 5961 switch (pl.pl_lwpid) { 5962 case 1: 5963 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SIGNAL); 5964 break; 5965 case 2: 5966 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SUSPENDED); 5967 break; 5968 } 5969 } 5970 5971 DPRINTF("Before resuming the child process where it left off and " 5972 "without signal to be sent\n"); 5973 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5974 5975 DPRINTF("Before calling %s() for the child - expected exited\n", 5976 TWAIT_FNAME); 5977 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5978 5979 validate_status_exited(status, exitval); 5980 5981 DPRINTF("Before calling %s() for the child - expected no process\n", 5982 TWAIT_FNAME); 5983 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5984} 5985 5986ATF_TC(suspend2); 5987ATF_TC_HEAD(suspend2, tc) 5988{ 5989 atf_tc_set_md_var(tc, "descr", 5990 "Verify that the while the only thread within a process is " 5991 "suspended, the whole process cannot be unstopped"); 5992} 5993 5994ATF_TC_BODY(suspend2, tc) 5995{ 5996 const int exitval = 5; 5997 const int sigval = SIGSTOP; 5998 pid_t child, wpid; 5999#if defined(TWAIT_HAVE_STATUS) 6000 int status; 6001#endif 6002 struct ptrace_siginfo psi; 6003 6004 // Feature pending for refactoring 6005 atf_tc_expect_fail("PR kern/51995"); 6006 6007 // Hangs with qemu 6008 ATF_REQUIRE(0 && "In order to get reliable failure, abort"); 6009 6010 DPRINTF("Before forking process PID=%d\n", getpid()); 6011 SYSCALL_REQUIRE((child = fork()) != -1); 6012 if (child == 0) { 6013 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 6014 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 6015 6016 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 6017 FORKEE_ASSERT(raise(sigval) == 0); 6018 6019 DPRINTF("Before exiting of the child process\n"); 6020 _exit(exitval); 6021 } 6022 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 6023 6024 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6025 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6026 6027 validate_status_stopped(status, sigval); 6028 6029 DPRINTF("Before reading siginfo and lwpid_t\n"); 6030 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1); 6031 6032 DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid); 6033 SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1); 6034 6035 DPRINTF("Before resuming the child process where it left off and " 6036 "without signal to be sent\n"); 6037 ATF_REQUIRE_ERRNO(EDEADLK, 6038 ptrace(PT_CONTINUE, child, (void *)1, 0) == -1); 6039 6040 DPRINTF("Before resuming LWP %d\n", psi.psi_lwpid); 6041 SYSCALL_REQUIRE(ptrace(PT_RESUME, child, NULL, psi.psi_lwpid) != -1); 6042 6043 DPRINTF("Before resuming the child process where it left off and " 6044 "without signal to be sent\n"); 6045 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6046 6047 DPRINTF("Before calling %s() for the child - expected exited\n", 6048 TWAIT_FNAME); 6049 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6050 6051 validate_status_exited(status, exitval); 6052 6053 DPRINTF("Before calling %s() for the child - expected no process\n", 6054 TWAIT_FNAME); 6055 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 6056} 6057 6058ATF_TC(resume1); 6059ATF_TC_HEAD(resume1, tc) 6060{ 6061 atf_tc_set_md_var(tc, "timeout", "5"); 6062 atf_tc_set_md_var(tc, "descr", 6063 "Verify that a thread can be suspended by a debugger and later " 6064 "resumed by the debugger"); 6065} 6066 6067ATF_TC_BODY(resume1, tc) 6068{ 6069 struct msg_fds fds; 6070 const int exitval = 5; 6071 const int sigval = SIGSTOP; 6072 pid_t child, wpid; 6073 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 6074#if defined(TWAIT_HAVE_STATUS) 6075 int status; 6076#endif 6077 ucontext_t uc; 6078 lwpid_t lid; 6079 static const size_t ssize = 16*1024; 6080 void *stack; 6081 struct ptrace_lwpinfo pl; 6082 struct ptrace_siginfo psi; 6083 6084 // Feature pending for refactoring 6085 atf_tc_expect_fail("PR kern/51995"); 6086 6087 // Hangs with qemu 6088 ATF_REQUIRE(0 && "In order to get reliable failure, abort"); 6089 6090 SYSCALL_REQUIRE(msg_open(&fds) == 0); 6091 6092 DPRINTF("Before forking process PID=%d\n", getpid()); 6093 SYSCALL_REQUIRE((child = fork()) != -1); 6094 if (child == 0) { 6095 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 6096 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 6097 6098 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 6099 FORKEE_ASSERT(raise(sigval) == 0); 6100 6101 DPRINTF("Before allocating memory for stack in child\n"); 6102 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 6103 6104 DPRINTF("Before making context for new lwp in child\n"); 6105 _lwp_makecontext(&uc, lwp_main_stop, NULL, NULL, stack, ssize); 6106 6107 DPRINTF("Before creating new in child\n"); 6108 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 6109 6110 CHILD_TO_PARENT("Message", fds, msg); 6111 6112 raise(SIGINT); 6113 6114 DPRINTF("Before waiting for lwp %d to exit\n", lid); 6115 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 6116 6117 DPRINTF("Before verifying that reported %d and running lid %d " 6118 "are the same\n", lid, the_lwp_id); 6119 FORKEE_ASSERT_EQ(lid, the_lwp_id); 6120 6121 DPRINTF("Before exiting of the child process\n"); 6122 _exit(exitval); 6123 } 6124 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 6125 6126 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6127 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6128 6129 validate_status_stopped(status, sigval); 6130 6131 DPRINTF("Before resuming the child process where it left off and " 6132 "without signal to be sent\n"); 6133 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6134 6135 DPRINTF("Before calling %s() for the child - expected stopped " 6136 "SIGTRAP\n", TWAIT_FNAME); 6137 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6138 6139 validate_status_stopped(status, SIGTRAP); 6140 6141 DPRINTF("Before reading siginfo and lwpid_t\n"); 6142 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1); 6143 6144 DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid); 6145 SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1); 6146 6147 PARENT_FROM_CHILD("Message", fds, msg); 6148 6149 DPRINTF("Before resuming the child process where it left off and " 6150 "without signal to be sent\n"); 6151 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6152 6153 DPRINTF("Before calling %s() for the child - expected stopped " 6154 "SIGINT\n", TWAIT_FNAME); 6155 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6156 6157 validate_status_stopped(status, SIGINT); 6158 6159 pl.pl_lwpid = 0; 6160 6161 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 6162 while (pl.pl_lwpid != 0) { 6163 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 6164 switch (pl.pl_lwpid) { 6165 case 1: 6166 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SIGNAL); 6167 break; 6168 case 2: 6169 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SUSPENDED); 6170 break; 6171 } 6172 } 6173 6174 DPRINTF("Before resuming LWP %d\n", psi.psi_lwpid); 6175 SYSCALL_REQUIRE(ptrace(PT_RESUME, child, NULL, psi.psi_lwpid) != -1); 6176 6177 DPRINTF("Before resuming the child process where it left off and " 6178 "without signal to be sent\n"); 6179 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6180 6181 DPRINTF("Before calling %s() for the child - expected exited\n", 6182 TWAIT_FNAME); 6183 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6184 6185 validate_status_exited(status, exitval); 6186 6187 DPRINTF("Before calling %s() for the child - expected no process\n", 6188 TWAIT_FNAME); 6189 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 6190 6191 msg_close(&fds); 6192 6193 DPRINTF("XXX: Test worked this time but for consistency timeout it\n"); 6194 sleep(10); 6195} 6196 6197ATF_TC(syscall1); 6198ATF_TC_HEAD(syscall1, tc) 6199{ 6200 atf_tc_set_md_var(tc, "descr", 6201 "Verify that getpid(2) can be traced with PT_SYSCALL"); 6202} 6203 6204ATF_TC_BODY(syscall1, tc) 6205{ 6206 const int exitval = 5; 6207 const int sigval = SIGSTOP; 6208 pid_t child, wpid; 6209#if defined(TWAIT_HAVE_STATUS) 6210 int status; 6211#endif 6212 struct ptrace_siginfo info; 6213 memset(&info, 0, sizeof(info)); 6214 6215 DPRINTF("Before forking process PID=%d\n", getpid()); 6216 SYSCALL_REQUIRE((child = fork()) != -1); 6217 if (child == 0) { 6218 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 6219 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 6220 6221 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 6222 FORKEE_ASSERT(raise(sigval) == 0); 6223 6224 syscall(SYS_getpid); 6225 6226 DPRINTF("Before exiting of the child process\n"); 6227 _exit(exitval); 6228 } 6229 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 6230 6231 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6232 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6233 6234 validate_status_stopped(status, sigval); 6235 6236 DPRINTF("Before resuming the child process where it left off and " 6237 "without signal to be sent\n"); 6238 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 6239 6240 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6241 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6242 6243 validate_status_stopped(status, SIGTRAP); 6244 6245 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 6246 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 6247 6248 DPRINTF("Before checking siginfo_t and lwpid\n"); 6249 ATF_REQUIRE_EQ(info.psi_lwpid, 1); 6250 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 6251 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_SCE); 6252 6253 DPRINTF("Before resuming the child process where it left off and " 6254 "without signal to be sent\n"); 6255 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 6256 6257 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6258 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6259 6260 validate_status_stopped(status, SIGTRAP); 6261 6262 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 6263 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 6264 6265 DPRINTF("Before checking siginfo_t and lwpid\n"); 6266 ATF_REQUIRE_EQ(info.psi_lwpid, 1); 6267 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 6268 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_SCX); 6269 6270 DPRINTF("Before resuming the child process where it left off and " 6271 "without signal to be sent\n"); 6272 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6273 6274 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6275 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6276 6277 validate_status_exited(status, exitval); 6278 6279 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6280 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 6281} 6282 6283ATF_TC(syscallemu1); 6284ATF_TC_HEAD(syscallemu1, tc) 6285{ 6286 atf_tc_set_md_var(tc, "descr", 6287 "Verify that exit(2) can be intercepted with PT_SYSCALLEMU"); 6288} 6289 6290ATF_TC_BODY(syscallemu1, tc) 6291{ 6292 const int exitval = 5; 6293 const int sigval = SIGSTOP; 6294 pid_t child, wpid; 6295#if defined(TWAIT_HAVE_STATUS) 6296 int status; 6297#endif 6298 6299#if defined(__sparc__) && !defined(__sparc64__) 6300 /* syscallemu does not work on sparc (32-bit) */ 6301 atf_tc_expect_fail("PR kern/52166"); 6302#endif 6303 6304 DPRINTF("Before forking process PID=%d\n", getpid()); 6305 SYSCALL_REQUIRE((child = fork()) != -1); 6306 if (child == 0) { 6307 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 6308 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 6309 6310 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 6311 FORKEE_ASSERT(raise(sigval) == 0); 6312 6313 syscall(SYS_exit, 100); 6314 6315 DPRINTF("Before exiting of the child process\n"); 6316 _exit(exitval); 6317 } 6318 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 6319 6320 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6321 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6322 6323 validate_status_stopped(status, sigval); 6324 6325 DPRINTF("Before resuming the child process where it left off and " 6326 "without signal to be sent\n"); 6327 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 6328 6329 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6330 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6331 6332 validate_status_stopped(status, SIGTRAP); 6333 6334 DPRINTF("Set SYSCALLEMU for intercepted syscall\n"); 6335 SYSCALL_REQUIRE(ptrace(PT_SYSCALLEMU, child, (void *)1, 0) != -1); 6336 6337 DPRINTF("Before resuming the child process where it left off and " 6338 "without signal to be sent\n"); 6339 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 6340 6341 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6342 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6343 6344 validate_status_stopped(status, SIGTRAP); 6345 6346 DPRINTF("Before resuming the child process where it left off and " 6347 "without signal to be sent\n"); 6348 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6349 6350 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6351 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6352 6353 validate_status_exited(status, exitval); 6354 6355 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6356 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 6357} 6358 6359/// ---------------------------------------------------------------------------- 6360 6361static void 6362clone_body(int flags, bool trackfork, bool trackvfork, 6363 bool trackvforkdone) 6364{ 6365 const int exitval = 5; 6366 const int exitval2 = 15; 6367 const int sigval = SIGSTOP; 6368 pid_t child, child2 = 0, wpid; 6369#if defined(TWAIT_HAVE_STATUS) 6370 int status; 6371#endif 6372 ptrace_state_t state; 6373 const int slen = sizeof(state); 6374 ptrace_event_t event; 6375 const int elen = sizeof(event); 6376 6377 const size_t stack_size = 1024 * 1024; 6378 void *stack, *stack_base; 6379 6380 stack = malloc(stack_size); 6381 ATF_REQUIRE(stack != NULL); 6382 6383#ifdef __MACHINE_STACK_GROWS_UP 6384 stack_base = stack; 6385#else 6386 stack_base = (char *)stack + stack_size; 6387#endif 6388 6389 DPRINTF("Before forking process PID=%d\n", getpid()); 6390 SYSCALL_REQUIRE((child = fork()) != -1); 6391 if (child == 0) { 6392 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 6393 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 6394 6395 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 6396 FORKEE_ASSERT(raise(sigval) == 0); 6397 6398 SYSCALL_REQUIRE((child2 = __clone(clone_func, stack_base, 6399 flags|SIGCHLD, (void *)(intptr_t)exitval2)) != -1); 6400 6401 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), 6402 child2); 6403 6404 // XXX WALLSIG? 6405 FORKEE_REQUIRE_SUCCESS 6406 (wpid = TWAIT_GENERIC(child2, &status, WALLSIG), child2); 6407 6408 forkee_status_exited(status, exitval2); 6409 6410 DPRINTF("Before exiting of the child process\n"); 6411 _exit(exitval); 6412 } 6413 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 6414 6415 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6416 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6417 6418 validate_status_stopped(status, sigval); 6419 6420 DPRINTF("Set 0%s%s%s in EVENT_MASK for the child %d\n", 6421 trackfork ? "|PTRACE_FORK" : "", 6422 trackvfork ? "|PTRACE_VFORK" : "", 6423 trackvforkdone ? "|PTRACE_VFORK_DONE" : "", child); 6424 event.pe_set_event = 0; 6425 if (trackfork) 6426 event.pe_set_event |= PTRACE_FORK; 6427 if (trackvfork) 6428 event.pe_set_event |= PTRACE_VFORK; 6429 if (trackvforkdone) 6430 event.pe_set_event |= PTRACE_VFORK_DONE; 6431 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 6432 6433 DPRINTF("Before resuming the child process where it left off and " 6434 "without signal to be sent\n"); 6435 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6436 6437#if defined(TWAIT_HAVE_PID) 6438 if ((trackfork && !(flags & CLONE_VFORK)) || 6439 (trackvfork && (flags & CLONE_VFORK))) { 6440 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 6441 child); 6442 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 6443 child); 6444 6445 validate_status_stopped(status, SIGTRAP); 6446 6447 SYSCALL_REQUIRE( 6448 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 6449 if (trackfork && !(flags & CLONE_VFORK)) { 6450 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 6451 PTRACE_FORK); 6452 } 6453 if (trackvfork && (flags & CLONE_VFORK)) { 6454 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 6455 PTRACE_VFORK); 6456 } 6457 6458 child2 = state.pe_other_pid; 6459 DPRINTF("Reported ptrace event with forkee %d\n", child2); 6460 6461 DPRINTF("Before calling %s() for the forkee %d of the child " 6462 "%d\n", TWAIT_FNAME, child2, child); 6463 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 6464 child2); 6465 6466 validate_status_stopped(status, SIGTRAP); 6467 6468 SYSCALL_REQUIRE( 6469 ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 6470 if (trackfork && !(flags & CLONE_VFORK)) { 6471 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 6472 PTRACE_FORK); 6473 } 6474 if (trackvfork && (flags & CLONE_VFORK)) { 6475 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 6476 PTRACE_VFORK); 6477 } 6478 6479 ATF_REQUIRE_EQ(state.pe_other_pid, child); 6480 6481 DPRINTF("Before resuming the forkee process where it left off " 6482 "and without signal to be sent\n"); 6483 SYSCALL_REQUIRE( 6484 ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 6485 6486 DPRINTF("Before resuming the child process where it left off " 6487 "and without signal to be sent\n"); 6488 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6489 } 6490#endif 6491 6492 if (trackvforkdone && (flags & CLONE_VFORK)) { 6493 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 6494 child); 6495 TWAIT_REQUIRE_SUCCESS( 6496 wpid = TWAIT_GENERIC(child, &status, 0), child); 6497 6498 validate_status_stopped(status, SIGTRAP); 6499 6500 SYSCALL_REQUIRE( 6501 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 6502 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE); 6503 6504 child2 = state.pe_other_pid; 6505 DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n", 6506 child2); 6507 6508 DPRINTF("Before resuming the child process where it left off " 6509 "and without signal to be sent\n"); 6510 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6511 } 6512 6513#if defined(TWAIT_HAVE_PID) 6514 if ((trackfork && !(flags & CLONE_VFORK)) || 6515 (trackvfork && (flags & CLONE_VFORK))) { 6516 DPRINTF("Before calling %s() for the forkee - expected exited" 6517 "\n", TWAIT_FNAME); 6518 TWAIT_REQUIRE_SUCCESS( 6519 wpid = TWAIT_GENERIC(child2, &status, 0), child2); 6520 6521 validate_status_exited(status, exitval2); 6522 6523 DPRINTF("Before calling %s() for the forkee - expected no " 6524 "process\n", TWAIT_FNAME); 6525 TWAIT_REQUIRE_FAILURE(ECHILD, 6526 wpid = TWAIT_GENERIC(child2, &status, 0)); 6527 } 6528#endif 6529 6530 DPRINTF("Before calling %s() for the child - expected stopped " 6531 "SIGCHLD\n", TWAIT_FNAME); 6532 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6533 6534 validate_status_stopped(status, SIGCHLD); 6535 6536 DPRINTF("Before resuming the child process where it left off and " 6537 "without signal to be sent\n"); 6538 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6539 6540 DPRINTF("Before calling %s() for the child - expected exited\n", 6541 TWAIT_FNAME); 6542 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6543 6544 validate_status_exited(status, exitval); 6545 6546 DPRINTF("Before calling %s() for the child - expected no process\n", 6547 TWAIT_FNAME); 6548 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 6549} 6550 6551#define CLONE_TEST(name,flags,tfork,tvfork,tvforkdone) \ 6552ATF_TC(name); \ 6553ATF_TC_HEAD(name, tc) \ 6554{ \ 6555 atf_tc_set_md_var(tc, "descr", "Verify clone(%s) " \ 6556 "called with 0%s%s%s in EVENT_MASK", \ 6557 #flags, \ 6558 tfork ? "|PTRACE_FORK" : "", \ 6559 tvfork ? "|PTRACE_VFORK" : "", \ 6560 tvforkdone ? "|PTRACE_VFORK_DONE" : ""); \ 6561} \ 6562 \ 6563ATF_TC_BODY(name, tc) \ 6564{ \ 6565 \ 6566 clone_body(flags, tfork, tvfork, tvforkdone); \ 6567} 6568 6569CLONE_TEST(clone1, 0, false, false, false) 6570#if defined(TWAIT_HAVE_PID) 6571CLONE_TEST(clone2, 0, true, false, false) 6572CLONE_TEST(clone3, 0, false, true, false) 6573CLONE_TEST(clone4, 0, true, true, false) 6574#endif 6575CLONE_TEST(clone5, 0, false, false, true) 6576#if defined(TWAIT_HAVE_PID) 6577CLONE_TEST(clone6, 0, true, false, true) 6578CLONE_TEST(clone7, 0, false, true, true) 6579CLONE_TEST(clone8, 0, true, true, true) 6580#endif 6581 6582CLONE_TEST(clone_vm1, CLONE_VM, false, false, false) 6583#if defined(TWAIT_HAVE_PID) 6584CLONE_TEST(clone_vm2, CLONE_VM, true, false, false) 6585CLONE_TEST(clone_vm3, CLONE_VM, false, true, false) 6586CLONE_TEST(clone_vm4, CLONE_VM, true, true, false) 6587#endif 6588CLONE_TEST(clone_vm5, CLONE_VM, false, false, true) 6589#if defined(TWAIT_HAVE_PID) 6590CLONE_TEST(clone_vm6, CLONE_VM, true, false, true) 6591CLONE_TEST(clone_vm7, CLONE_VM, false, true, true) 6592CLONE_TEST(clone_vm8, CLONE_VM, true, true, true) 6593#endif 6594 6595CLONE_TEST(clone_fs1, CLONE_FS, false, false, false) 6596#if defined(TWAIT_HAVE_PID) 6597CLONE_TEST(clone_fs2, CLONE_FS, true, false, false) 6598CLONE_TEST(clone_fs3, CLONE_FS, false, true, false) 6599CLONE_TEST(clone_fs4, CLONE_FS, true, true, false) 6600#endif 6601CLONE_TEST(clone_fs5, CLONE_FS, false, false, true) 6602#if defined(TWAIT_HAVE_PID) 6603CLONE_TEST(clone_fs6, CLONE_FS, true, false, true) 6604CLONE_TEST(clone_fs7, CLONE_FS, false, true, true) 6605CLONE_TEST(clone_fs8, CLONE_FS, true, true, true) 6606#endif 6607 6608CLONE_TEST(clone_files1, CLONE_FILES, false, false, false) 6609#if defined(TWAIT_HAVE_PID) 6610CLONE_TEST(clone_files2, CLONE_FILES, true, false, false) 6611CLONE_TEST(clone_files3, CLONE_FILES, false, true, false) 6612CLONE_TEST(clone_files4, CLONE_FILES, true, true, false) 6613#endif 6614CLONE_TEST(clone_files5, CLONE_FILES, false, false, true) 6615#if defined(TWAIT_HAVE_PID) 6616CLONE_TEST(clone_files6, CLONE_FILES, true, false, true) 6617CLONE_TEST(clone_files7, CLONE_FILES, false, true, true) 6618CLONE_TEST(clone_files8, CLONE_FILES, true, true, true) 6619#endif 6620 6621//CLONE_TEST(clone_sighand1, CLONE_SIGHAND, false, false, false) 6622#if defined(TWAIT_HAVE_PID) 6623//CLONE_TEST(clone_sighand2, CLONE_SIGHAND, true, false, false) 6624//CLONE_TEST(clone_sighand3, CLONE_SIGHAND, false, true, false) 6625//CLONE_TEST(clone_sighand4, CLONE_SIGHAND, true, true, false) 6626#endif 6627//CLONE_TEST(clone_sighand5, CLONE_SIGHAND, false, false, true) 6628#if defined(TWAIT_HAVE_PID) 6629//CLONE_TEST(clone_sighand6, CLONE_SIGHAND, true, false, true) 6630//CLONE_TEST(clone_sighand7, CLONE_SIGHAND, false, true, true) 6631//CLONE_TEST(clone_sighand8, CLONE_SIGHAND, true, true, true) 6632#endif 6633 6634#if TEST_VFORK_ENABLED 6635CLONE_TEST(clone_vfork1, CLONE_VFORK, false, false, false) 6636#if defined(TWAIT_HAVE_PID) 6637CLONE_TEST(clone_vfork2, CLONE_VFORK, true, false, false) 6638CLONE_TEST(clone_vfork3, CLONE_VFORK, false, true, false) 6639CLONE_TEST(clone_vfork4, CLONE_VFORK, true, true, false) 6640#endif 6641CLONE_TEST(clone_vfork5, CLONE_VFORK, false, false, true) 6642#if defined(TWAIT_HAVE_PID) 6643CLONE_TEST(clone_vfork6, CLONE_VFORK, true, false, true) 6644CLONE_TEST(clone_vfork7, CLONE_VFORK, false, true, true) 6645CLONE_TEST(clone_vfork8, CLONE_VFORK, true, true, true) 6646#endif 6647#endif 6648 6649/// ---------------------------------------------------------------------------- 6650 6651#if defined(TWAIT_HAVE_PID) 6652static void 6653clone_body2(int flags, bool masked, bool ignored) 6654{ 6655 const int exitval = 5; 6656 const int exitval2 = 15; 6657 const int sigval = SIGSTOP; 6658 pid_t child, child2 = 0, wpid; 6659#if defined(TWAIT_HAVE_STATUS) 6660 int status; 6661#endif 6662 ptrace_state_t state; 6663 const int slen = sizeof(state); 6664 ptrace_event_t event; 6665 const int elen = sizeof(event); 6666 struct sigaction sa; 6667 struct ptrace_siginfo info; 6668 sigset_t intmask; 6669 struct kinfo_proc2 kp; 6670 size_t len = sizeof(kp); 6671 6672 int name[6]; 6673 const size_t namelen = __arraycount(name); 6674 ki_sigset_t kp_sigmask; 6675 ki_sigset_t kp_sigignore; 6676 6677 const size_t stack_size = 1024 * 1024; 6678 void *stack, *stack_base; 6679 6680 stack = malloc(stack_size); 6681 ATF_REQUIRE(stack != NULL); 6682 6683#ifdef __MACHINE_STACK_GROWS_UP 6684 stack_base = stack; 6685#else 6686 stack_base = (char *)stack + stack_size; 6687#endif 6688 6689 SYSCALL_REQUIRE((child = fork()) != -1); 6690 if (child == 0) { 6691 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 6692 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 6693 6694 if (masked) { 6695 sigemptyset(&intmask); 6696 sigaddset(&intmask, SIGTRAP); 6697 sigprocmask(SIG_BLOCK, &intmask, NULL); 6698 } 6699 6700 if (ignored) { 6701 memset(&sa, 0, sizeof(sa)); 6702 sa.sa_handler = SIG_IGN; 6703 sigemptyset(&sa.sa_mask); 6704 FORKEE_ASSERT(sigaction(SIGTRAP, &sa, NULL) != -1); 6705 } 6706 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 6707 FORKEE_ASSERT(raise(sigval) == 0); 6708 6709 DPRINTF("Before forking process PID=%d flags=%#x\n", getpid(), 6710 flags); 6711 SYSCALL_REQUIRE((child2 = __clone(clone_func, stack_base, 6712 flags|SIGCHLD, (void *)(intptr_t)exitval2)) != -1); 6713 6714 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), 6715 child2); 6716 6717 // XXX WALLSIG? 6718 FORKEE_REQUIRE_SUCCESS 6719 (wpid = TWAIT_GENERIC(child2, &status, WALLSIG), child2); 6720 6721 forkee_status_exited(status, exitval2); 6722 6723 DPRINTF("Before exiting of the child process\n"); 6724 _exit(exitval); 6725 } 6726 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 6727 6728 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 6729 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6730 6731 validate_status_stopped(status, sigval); 6732 6733 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 6734 SYSCALL_REQUIRE( 6735 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 6736 6737 DPRINTF("Before checking siginfo_t\n"); 6738 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 6739 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 6740 6741 name[0] = CTL_KERN, 6742 name[1] = KERN_PROC2, 6743 name[2] = KERN_PROC_PID; 6744 name[3] = child; 6745 name[4] = sizeof(kp); 6746 name[5] = 1; 6747 6748 FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 6749 6750 if (masked) 6751 kp_sigmask = kp.p_sigmask; 6752 6753 if (ignored) 6754 kp_sigignore = kp.p_sigignore; 6755 6756 DPRINTF("Set PTRACE_FORK | PTRACE_VFORK | PTRACE_VFORK_DONE in " 6757 "EVENT_MASK for the child %d\n", child); 6758 event.pe_set_event = PTRACE_FORK | PTRACE_VFORK | PTRACE_VFORK_DONE; 6759 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 6760 6761 DPRINTF("Before resuming the child process where it left off and " 6762 "without signal to be sent\n"); 6763 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6764 6765 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 6766 child); 6767 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 6768 child); 6769 6770 validate_status_stopped(status, SIGTRAP); 6771 6772 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 6773 6774 if (masked) { 6775 DPRINTF("kp_sigmask=" 6776 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6777 PRIx32 "\n", 6778 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 6779 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 6780 6781 DPRINTF("kp.p_sigmask=" 6782 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6783 PRIx32 "\n", 6784 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 6785 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 6786 6787 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 6788 sizeof(kp_sigmask))); 6789 } 6790 6791 if (ignored) { 6792 DPRINTF("kp_sigignore=" 6793 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6794 PRIx32 "\n", 6795 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 6796 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 6797 6798 DPRINTF("kp.p_sigignore=" 6799 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6800 PRIx32 "\n", 6801 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 6802 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 6803 6804 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 6805 sizeof(kp_sigignore))); 6806 } 6807 6808 SYSCALL_REQUIRE( 6809 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 6810 DPRINTF("state.pe_report_event=%#x pid=%d\n", state.pe_report_event, 6811 child2); 6812 if (!(flags & CLONE_VFORK)) { 6813 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 6814 PTRACE_FORK); 6815 } else { 6816 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 6817 PTRACE_VFORK); 6818 } 6819 6820 child2 = state.pe_other_pid; 6821 DPRINTF("Reported ptrace event with forkee %d\n", child2); 6822 6823 DPRINTF("Before calling %s() for the forkee %d of the child " 6824 "%d\n", TWAIT_FNAME, child2, child); 6825 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 6826 child2); 6827 6828 validate_status_stopped(status, SIGTRAP); 6829 6830 name[3] = child2; 6831 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 6832 6833 if (masked) { 6834 DPRINTF("kp_sigmask=" 6835 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6836 PRIx32 "\n", 6837 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 6838 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 6839 6840 DPRINTF("kp.p_sigmask=" 6841 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6842 PRIx32 "\n", 6843 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 6844 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 6845 6846 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 6847 sizeof(kp_sigmask))); 6848 } 6849 6850 if (ignored) { 6851 DPRINTF("kp_sigignore=" 6852 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6853 PRIx32 "\n", 6854 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 6855 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 6856 6857 DPRINTF("kp.p_sigignore=" 6858 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6859 PRIx32 "\n", 6860 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 6861 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 6862 6863 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 6864 sizeof(kp_sigignore))); 6865 } 6866 6867 SYSCALL_REQUIRE( 6868 ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 6869 if (!(flags & CLONE_VFORK)) { 6870 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 6871 PTRACE_FORK); 6872 } else { 6873 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 6874 PTRACE_VFORK); 6875 } 6876 6877 ATF_REQUIRE_EQ(state.pe_other_pid, child); 6878 6879 DPRINTF("Before resuming the forkee process where it left off " 6880 "and without signal to be sent\n"); 6881 SYSCALL_REQUIRE( 6882 ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 6883 6884 DPRINTF("Before resuming the child process where it left off " 6885 "and without signal to be sent\n"); 6886 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6887 6888 if (flags & CLONE_VFORK) { 6889 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 6890 child); 6891 TWAIT_REQUIRE_SUCCESS( 6892 wpid = TWAIT_GENERIC(child, &status, 0), child); 6893 6894 validate_status_stopped(status, SIGTRAP); 6895 6896 name[3] = child; 6897 ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0); 6898 6899 /* 6900 * SIGCHLD is now pending in the signal queue and 6901 * the kernel presents it to userland as a masked signal. 6902 */ 6903 sigdelset((sigset_t *)&kp.p_sigmask, SIGCHLD); 6904 6905 if (masked) { 6906 DPRINTF("kp_sigmask=" 6907 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6908 PRIx32 "\n", 6909 kp_sigmask.__bits[0], kp_sigmask.__bits[1], 6910 kp_sigmask.__bits[2], kp_sigmask.__bits[3]); 6911 6912 DPRINTF("kp.p_sigmask=" 6913 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6914 PRIx32 "\n", 6915 kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1], 6916 kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]); 6917 6918 ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask, 6919 sizeof(kp_sigmask))); 6920 } 6921 6922 if (ignored) { 6923 DPRINTF("kp_sigignore=" 6924 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6925 PRIx32 "\n", 6926 kp_sigignore.__bits[0], kp_sigignore.__bits[1], 6927 kp_sigignore.__bits[2], kp_sigignore.__bits[3]); 6928 6929 DPRINTF("kp.p_sigignore=" 6930 "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02" 6931 PRIx32 "\n", 6932 kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1], 6933 kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]); 6934 6935 ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore, 6936 sizeof(kp_sigignore))); 6937 } 6938 6939 SYSCALL_REQUIRE( 6940 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 6941 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE); 6942 6943 child2 = state.pe_other_pid; 6944 DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n", 6945 child2); 6946 6947 DPRINTF("Before resuming the child process where it left off " 6948 "and without signal to be sent\n"); 6949 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6950 } 6951 6952 DPRINTF("Before calling %s() for the forkee - expected exited" 6953 "\n", TWAIT_FNAME); 6954 TWAIT_REQUIRE_SUCCESS( 6955 wpid = TWAIT_GENERIC(child2, &status, 0), child2); 6956 6957 validate_status_exited(status, exitval2); 6958 6959 DPRINTF("Before calling %s() for the forkee - expected no " 6960 "process\n", TWAIT_FNAME); 6961 TWAIT_REQUIRE_FAILURE(ECHILD, 6962 wpid = TWAIT_GENERIC(child2, &status, 0)); 6963 6964 DPRINTF("Before calling %s() for the child - expected stopped " 6965 "SIGCHLD\n", TWAIT_FNAME); 6966 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6967 6968 validate_status_stopped(status, SIGCHLD); 6969 6970 DPRINTF("Before resuming the child process where it left off and " 6971 "without signal to be sent\n"); 6972 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 6973 6974 DPRINTF("Before calling %s() for the child - expected exited\n", 6975 TWAIT_FNAME); 6976 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 6977 6978 validate_status_exited(status, exitval); 6979 6980 DPRINTF("Before calling %s() for the child - expected no process\n", 6981 TWAIT_FNAME); 6982 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 6983} 6984 6985#define CLONE_TEST2(name,flags,masked,ignored) \ 6986ATF_TC(name); \ 6987ATF_TC_HEAD(name, tc) \ 6988{ \ 6989 atf_tc_set_md_var(tc, "descr", "Verify that clone(%s) is caught"\ 6990 " regardless of signal %s%s", \ 6991 #flags, masked ? "masked" : "", ignored ? "ignored" : ""); \ 6992} \ 6993 \ 6994ATF_TC_BODY(name, tc) \ 6995{ \ 6996 \ 6997 clone_body2(flags, masked, ignored); \ 6998} 6999 7000CLONE_TEST2(clone_signalignored, 0, true, false) 7001CLONE_TEST2(clone_signalmasked, 0, false, true) 7002CLONE_TEST2(clone_vm_signalignored, CLONE_VM, true, false) 7003CLONE_TEST2(clone_vm_signalmasked, CLONE_VM, false, true) 7004CLONE_TEST2(clone_fs_signalignored, CLONE_FS, true, false) 7005CLONE_TEST2(clone_fs_signalmasked, CLONE_FS, false, true) 7006CLONE_TEST2(clone_files_signalignored, CLONE_FILES, true, false) 7007CLONE_TEST2(clone_files_signalmasked, CLONE_FILES, false, true) 7008//CLONE_TEST2(clone_sighand_signalignored, CLONE_SIGHAND, true, false) // XXX 7009//CLONE_TEST2(clone_sighand_signalmasked, CLONE_SIGHAND, false, true) // XXX 7010#if TEST_VFORK_ENABLED 7011CLONE_TEST2(clone_vfork_signalignored, CLONE_VFORK, true, false) 7012CLONE_TEST2(clone_vfork_signalmasked, CLONE_VFORK, false, true) 7013#endif 7014#endif 7015 7016/// ---------------------------------------------------------------------------- 7017 7018#if TEST_VFORK_ENABLED 7019#if defined(TWAIT_HAVE_PID) 7020static void 7021traceme_vfork_clone_body(int flags) 7022{ 7023 const int exitval = 5; 7024 const int exitval2 = 15; 7025 pid_t child, child2 = 0, wpid; 7026#if defined(TWAIT_HAVE_STATUS) 7027 int status; 7028#endif 7029 7030 const size_t stack_size = 1024 * 1024; 7031 void *stack, *stack_base; 7032 7033 stack = malloc(stack_size); 7034 ATF_REQUIRE(stack != NULL); 7035 7036#ifdef __MACHINE_STACK_GROWS_UP 7037 stack_base = stack; 7038#else 7039 stack_base = (char *)stack + stack_size; 7040#endif 7041 7042 SYSCALL_REQUIRE((child = vfork()) != -1); 7043 if (child == 0) { 7044 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 7045 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 7046 7047 DPRINTF("Before forking process PID=%d flags=%#x\n", getpid(), 7048 flags); 7049 SYSCALL_REQUIRE((child2 = __clone(clone_func, stack_base, 7050 flags|SIGCHLD, (void *)(intptr_t)exitval2)) != -1); 7051 7052 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), 7053 child2); 7054 7055 // XXX WALLSIG? 7056 FORKEE_REQUIRE_SUCCESS 7057 (wpid = TWAIT_GENERIC(child2, &status, WALLSIG), child2); 7058 7059 forkee_status_exited(status, exitval2); 7060 7061 DPRINTF("Before exiting of the child process\n"); 7062 _exit(exitval); 7063 } 7064 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 7065 7066 DPRINTF("Before calling %s() for the child - expected exited\n", 7067 TWAIT_FNAME); 7068 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 7069 7070 validate_status_exited(status, exitval); 7071 7072 DPRINTF("Before calling %s() for the child - expected no process\n", 7073 TWAIT_FNAME); 7074 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 7075} 7076 7077#define TRACEME_VFORK_CLONE_TEST(name,flags) \ 7078ATF_TC(name); \ 7079ATF_TC_HEAD(name, tc) \ 7080{ \ 7081 atf_tc_set_md_var(tc, "descr", "Verify that clone(%s) is " \ 7082 "handled correctly with vfork(2)ed tracer", \ 7083 #flags); \ 7084} \ 7085 \ 7086ATF_TC_BODY(name, tc) \ 7087{ \ 7088 \ 7089 traceme_vfork_clone_body(flags); \ 7090} 7091 7092TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone, 0) 7093TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_vm, CLONE_VM) 7094TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_fs, CLONE_FS) 7095TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_files, CLONE_FILES) 7096//TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_sighand, CLONE_SIGHAND) // XXX 7097TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_vfork, CLONE_VFORK) 7098#endif 7099#endif 7100 7101/// ---------------------------------------------------------------------------- 7102 7103#include "t_ptrace_amd64_wait.h" 7104#include "t_ptrace_i386_wait.h" 7105#include "t_ptrace_x86_wait.h" 7106 7107ATF_TP_ADD_TCS(tp) 7108{ 7109 setvbuf(stdout, NULL, _IONBF, 0); 7110 setvbuf(stderr, NULL, _IONBF, 0); 7111 7112 ATF_TP_ADD_TC(tp, traceme_raise1); 7113 ATF_TP_ADD_TC(tp, traceme_raise2); 7114 ATF_TP_ADD_TC(tp, traceme_raise3); 7115 ATF_TP_ADD_TC(tp, traceme_raise4); 7116 ATF_TP_ADD_TC(tp, traceme_raise5); 7117 ATF_TP_ADD_TC(tp, traceme_raise6); 7118 ATF_TP_ADD_TC(tp, traceme_raise7); 7119 ATF_TP_ADD_TC(tp, traceme_raise8); 7120 ATF_TP_ADD_TC(tp, traceme_raise9); 7121 ATF_TP_ADD_TC(tp, traceme_raise10); 7122 7123 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored1); 7124 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored2); 7125 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored3); 7126 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored4); 7127 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored5); 7128 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored6); 7129 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored7); 7130 ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored8); 7131 7132 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked1); 7133 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked2); 7134 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked3); 7135 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked4); 7136 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked5); 7137 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked6); 7138 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked7); 7139 ATF_TP_ADD_TC(tp, traceme_raisesignal_masked8); 7140 7141 ATF_TP_ADD_TC(tp, traceme_crash_trap); 7142 ATF_TP_ADD_TC(tp, traceme_crash_segv); 7143 ATF_TP_ADD_TC(tp, traceme_crash_ill); 7144 ATF_TP_ADD_TC(tp, traceme_crash_fpe); 7145 ATF_TP_ADD_TC(tp, traceme_crash_bus); 7146 7147 ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_trap); 7148 ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_segv); 7149 ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_ill); 7150 ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_fpe); 7151 ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_bus); 7152 7153 ATF_TP_ADD_TC(tp, traceme_signalignored_crash_trap); 7154 ATF_TP_ADD_TC(tp, traceme_signalignored_crash_segv); 7155 ATF_TP_ADD_TC(tp, traceme_signalignored_crash_ill); 7156 ATF_TP_ADD_TC(tp, traceme_signalignored_crash_fpe); 7157 ATF_TP_ADD_TC(tp, traceme_signalignored_crash_bus); 7158 7159 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle1); 7160 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle2); 7161 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle3); 7162 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle4); 7163 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle5); 7164 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle6); 7165 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle7); 7166 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle8); 7167 7168 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked1); 7169 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked2); 7170 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked3); 7171 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked4); 7172 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked5); 7173 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked6); 7174 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked7); 7175 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked8); 7176 7177 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored1); 7178 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored2); 7179 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored3); 7180 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored4); 7181 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored5); 7182 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored6); 7183 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored7); 7184 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored8); 7185 7186 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple1); 7187 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple2); 7188 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple3); 7189 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple4); 7190 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple5); 7191 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple6); 7192 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple7); 7193 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple8); 7194 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple9); 7195 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple10); 7196 7197 ATF_TP_ADD_TC(tp, traceme_pid1_parent); 7198 7199 ATF_TP_ADD_TC(tp, traceme_vfork_raise1); 7200 ATF_TP_ADD_TC(tp, traceme_vfork_raise2); 7201 ATF_TP_ADD_TC(tp, traceme_vfork_raise3); 7202 ATF_TP_ADD_TC(tp, traceme_vfork_raise4); 7203 ATF_TP_ADD_TC(tp, traceme_vfork_raise5); 7204 ATF_TP_ADD_TC(tp, traceme_vfork_raise6); 7205 ATF_TP_ADD_TC(tp, traceme_vfork_raise7); 7206 ATF_TP_ADD_TC(tp, traceme_vfork_raise8); 7207 ATF_TP_ADD_TC(tp, traceme_vfork_raise9); 7208 ATF_TP_ADD_TC(tp, traceme_vfork_raise10); 7209 ATF_TP_ADD_TC(tp, traceme_vfork_raise11); 7210 ATF_TP_ADD_TC(tp, traceme_vfork_raise12); 7211 ATF_TP_ADD_TC(tp, traceme_vfork_raise13); 7212 7213 ATF_TP_ADD_TC(tp, traceme_vfork_crash_trap); 7214 ATF_TP_ADD_TC(tp, traceme_vfork_crash_segv); 7215 ATF_TP_ADD_TC(tp, traceme_vfork_crash_ill); 7216 ATF_TP_ADD_TC(tp, traceme_vfork_crash_fpe); 7217 ATF_TP_ADD_TC(tp, traceme_vfork_crash_bus); 7218 7219 ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_trap); 7220 ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_segv); 7221 ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_ill); 7222 ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_fpe); 7223 ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_bus); 7224 7225 ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_trap); 7226 ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_segv); 7227 ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_ill); 7228 ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_fpe); 7229 ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_bus); 7230 7231 ATF_TP_ADD_TC(tp, traceme_vfork_exec); 7232 ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_exec); 7233 ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_exec); 7234 7235 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_trap); 7236 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_segv); 7237 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_ill); 7238 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_fpe); 7239 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_bus); 7240 7241 ATF_TP_ADD_TC_HAVE_PID(tp, 7242 unrelated_tracer_sees_signalmasked_crash_trap); 7243 ATF_TP_ADD_TC_HAVE_PID(tp, 7244 unrelated_tracer_sees_signalmasked_crash_segv); 7245 ATF_TP_ADD_TC_HAVE_PID(tp, 7246 unrelated_tracer_sees_signalmasked_crash_ill); 7247 ATF_TP_ADD_TC_HAVE_PID(tp, 7248 unrelated_tracer_sees_signalmasked_crash_fpe); 7249 ATF_TP_ADD_TC_HAVE_PID(tp, 7250 unrelated_tracer_sees_signalmasked_crash_bus); 7251 7252 ATF_TP_ADD_TC_HAVE_PID(tp, 7253 unrelated_tracer_sees_signalignored_crash_trap); 7254 ATF_TP_ADD_TC_HAVE_PID(tp, 7255 unrelated_tracer_sees_signalignored_crash_segv); 7256 ATF_TP_ADD_TC_HAVE_PID(tp, 7257 unrelated_tracer_sees_signalignored_crash_ill); 7258 ATF_TP_ADD_TC_HAVE_PID(tp, 7259 unrelated_tracer_sees_signalignored_crash_fpe); 7260 ATF_TP_ADD_TC_HAVE_PID(tp, 7261 unrelated_tracer_sees_signalignored_crash_bus); 7262 7263 ATF_TP_ADD_TC_HAVE_PID(tp, tracer_sees_terminaton_before_the_parent); 7264 ATF_TP_ADD_TC_HAVE_PID(tp, tracer_sysctl_lookup_without_duplicates); 7265 ATF_TP_ADD_TC_HAVE_PID(tp, 7266 unrelated_tracer_sees_terminaton_before_the_parent); 7267 ATF_TP_ADD_TC_HAVE_PID(tp, tracer_attach_to_unrelated_stopped_process); 7268 7269 ATF_TP_ADD_TC(tp, parent_attach_to_its_child); 7270 ATF_TP_ADD_TC(tp, parent_attach_to_its_stopped_child); 7271 7272 ATF_TP_ADD_TC(tp, child_attach_to_its_parent); 7273 ATF_TP_ADD_TC(tp, child_attach_to_its_stopped_parent); 7274 7275 ATF_TP_ADD_TC_HAVE_PID(tp, 7276 tracee_sees_its_original_parent_getppid); 7277 ATF_TP_ADD_TC_HAVE_PID(tp, 7278 tracee_sees_its_original_parent_sysctl_kinfo_proc2); 7279 ATF_TP_ADD_TC_HAVE_PID(tp, 7280 tracee_sees_its_original_parent_procfs_status); 7281 7282 ATF_TP_ADD_TC(tp, eventmask_preserved_empty); 7283 ATF_TP_ADD_TC(tp, eventmask_preserved_fork); 7284 ATF_TP_ADD_TC(tp, eventmask_preserved_vfork); 7285 ATF_TP_ADD_TC(tp, eventmask_preserved_vfork_done); 7286 ATF_TP_ADD_TC(tp, eventmask_preserved_lwp_create); 7287 ATF_TP_ADD_TC(tp, eventmask_preserved_lwp_exit); 7288 7289 ATF_TP_ADD_TC(tp, fork1); 7290 ATF_TP_ADD_TC_HAVE_PID(tp, fork2); 7291 ATF_TP_ADD_TC_HAVE_PID(tp, fork3); 7292 ATF_TP_ADD_TC_HAVE_PID(tp, fork4); 7293 ATF_TP_ADD_TC(tp, fork5); 7294 ATF_TP_ADD_TC_HAVE_PID(tp, fork6); 7295 ATF_TP_ADD_TC_HAVE_PID(tp, fork7); 7296 ATF_TP_ADD_TC_HAVE_PID(tp, fork8); 7297 7298#if TEST_VFORK_ENABLED 7299 ATF_TP_ADD_TC(tp, vfork1); 7300 ATF_TP_ADD_TC_HAVE_PID(tp, vfork2); 7301 ATF_TP_ADD_TC_HAVE_PID(tp, vfork3); 7302 ATF_TP_ADD_TC_HAVE_PID(tp, vfork4); 7303 ATF_TP_ADD_TC(tp, vfork5); 7304 ATF_TP_ADD_TC_HAVE_PID(tp, vfork6); 7305 ATF_TP_ADD_TC_HAVE_PID(tp, vfork7); 7306 ATF_TP_ADD_TC_HAVE_PID(tp, vfork8); 7307 7308 ATF_TP_ADD_TC(tp, traceme_vfork_fork); 7309 ATF_TP_ADD_TC(tp, traceme_vfork_vfork); 7310#endif 7311 7312 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_8); 7313 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_16); 7314 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_32); 7315 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_64); 7316 7317 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_8); 7318 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_16); 7319 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_32); 7320 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_64); 7321 7322 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_8); 7323 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_16); 7324 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_32); 7325 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_64); 7326 7327 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_8); 7328 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_16); 7329 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_32); 7330 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_64); 7331 7332 ATF_TP_ADD_TC(tp, bytes_transfer_read_d); 7333 ATF_TP_ADD_TC(tp, bytes_transfer_read_i); 7334 ATF_TP_ADD_TC(tp, bytes_transfer_write_d); 7335 ATF_TP_ADD_TC(tp, bytes_transfer_write_i); 7336 7337 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_8_text); 7338 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_16_text); 7339 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_32_text); 7340 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_64_text); 7341 7342 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_8_text); 7343 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_16_text); 7344 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_32_text); 7345 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_64_text); 7346 7347 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_8_text); 7348 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_16_text); 7349 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_32_text); 7350 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_64_text); 7351 7352 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_8_text); 7353 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_16_text); 7354 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_32_text); 7355 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_64_text); 7356 7357 ATF_TP_ADD_TC(tp, bytes_transfer_read_d_text); 7358 ATF_TP_ADD_TC(tp, bytes_transfer_read_i_text); 7359 ATF_TP_ADD_TC(tp, bytes_transfer_write_d_text); 7360 ATF_TP_ADD_TC(tp, bytes_transfer_write_i_text); 7361 7362 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_auxv); 7363 7364 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_read_i); 7365 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_read_d); 7366 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_write_i); 7367 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_write_d); 7368 7369 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_read_i); 7370 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_read_d); 7371 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_write_i); 7372 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_write_d); 7373 7374 ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_read_auxv); 7375 7376 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs1); 7377 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs2); 7378 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs3); 7379 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs4); 7380 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs5); 7381 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs6); 7382 7383 ATF_TP_ADD_TC_HAVE_FPREGS(tp, access_fpregs1); 7384 ATF_TP_ADD_TC_HAVE_FPREGS(tp, access_fpregs2); 7385 7386 ATF_TP_ADD_TC_PT_STEP(tp, step1); 7387 ATF_TP_ADD_TC_PT_STEP(tp, step2); 7388 ATF_TP_ADD_TC_PT_STEP(tp, step3); 7389 ATF_TP_ADD_TC_PT_STEP(tp, step4); 7390 7391 ATF_TP_ADD_TC_PT_STEP(tp, setstep1); 7392 ATF_TP_ADD_TC_PT_STEP(tp, setstep2); 7393 ATF_TP_ADD_TC_PT_STEP(tp, setstep3); 7394 ATF_TP_ADD_TC_PT_STEP(tp, setstep4); 7395 7396 ATF_TP_ADD_TC_PT_STEP(tp, step_signalmasked); 7397 ATF_TP_ADD_TC_PT_STEP(tp, step_signalignored); 7398 7399 ATF_TP_ADD_TC(tp, kill1); 7400 ATF_TP_ADD_TC(tp, kill2); 7401 ATF_TP_ADD_TC(tp, kill3); 7402 7403 ATF_TP_ADD_TC(tp, traceme_lwpinfo0); 7404 ATF_TP_ADD_TC(tp, traceme_lwpinfo1); 7405 ATF_TP_ADD_TC(tp, traceme_lwpinfo2); 7406 ATF_TP_ADD_TC(tp, traceme_lwpinfo3); 7407 7408 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo0); 7409 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo1); 7410 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo2); 7411 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo3); 7412 7413 ATF_TP_ADD_TC(tp, siginfo_set_unmodified); 7414 ATF_TP_ADD_TC(tp, siginfo_set_faked); 7415 7416 ATF_TP_ADD_TC(tp, traceme_exec); 7417 ATF_TP_ADD_TC(tp, traceme_signalmasked_exec); 7418 ATF_TP_ADD_TC(tp, traceme_signalignored_exec); 7419 7420 ATF_TP_ADD_TC(tp, trace_thread1); 7421 ATF_TP_ADD_TC(tp, trace_thread2); 7422 ATF_TP_ADD_TC(tp, trace_thread3); 7423 ATF_TP_ADD_TC(tp, trace_thread4); 7424 7425 ATF_TP_ADD_TC(tp, signal_mask_unrelated); 7426 7427 ATF_TP_ADD_TC_HAVE_PID(tp, fork_singalmasked); 7428 ATF_TP_ADD_TC_HAVE_PID(tp, fork_singalignored); 7429#if TEST_VFORK_ENABLED 7430 ATF_TP_ADD_TC_HAVE_PID(tp, vfork_singalmasked); 7431 ATF_TP_ADD_TC_HAVE_PID(tp, vfork_singalignored); 7432 ATF_TP_ADD_TC_HAVE_PID(tp, vforkdone_singalmasked); 7433 ATF_TP_ADD_TC_HAVE_PID(tp, vforkdone_singalignored); 7434#endif 7435 7436 ATF_TP_ADD_TC(tp, signal9); 7437 ATF_TP_ADD_TC(tp, signal10); 7438 7439 ATF_TP_ADD_TC(tp, suspend1); 7440 ATF_TP_ADD_TC(tp, suspend2); 7441 7442 ATF_TP_ADD_TC(tp, resume1); 7443 7444 ATF_TP_ADD_TC(tp, syscall1); 7445 7446 ATF_TP_ADD_TC(tp, syscallemu1); 7447 7448 ATF_TP_ADD_TC(tp, clone1); 7449 ATF_TP_ADD_TC_HAVE_PID(tp, clone2); 7450 ATF_TP_ADD_TC_HAVE_PID(tp, clone3); 7451 ATF_TP_ADD_TC_HAVE_PID(tp, clone4); 7452 ATF_TP_ADD_TC(tp, clone5); 7453 ATF_TP_ADD_TC_HAVE_PID(tp, clone6); 7454 ATF_TP_ADD_TC_HAVE_PID(tp, clone7); 7455 ATF_TP_ADD_TC_HAVE_PID(tp, clone8); 7456 7457 ATF_TP_ADD_TC(tp, clone_vm1); 7458 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm2); 7459 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm3); 7460 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm4); 7461 ATF_TP_ADD_TC(tp, clone_vm5); 7462 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm6); 7463 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm7); 7464 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm8); 7465 7466 ATF_TP_ADD_TC(tp, clone_fs1); 7467 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs2); 7468 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs3); 7469 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs4); 7470 ATF_TP_ADD_TC(tp, clone_fs5); 7471 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs6); 7472 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs7); 7473 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs8); 7474 7475 ATF_TP_ADD_TC(tp, clone_files1); 7476 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files2); 7477 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files3); 7478 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files4); 7479 ATF_TP_ADD_TC(tp, clone_files5); 7480 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files6); 7481 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files7); 7482 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files8); 7483 7484// ATF_TP_ADD_TC(tp, clone_sighand1); // XXX 7485// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand2); // XXX 7486// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand3); // XXX 7487// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand4); // XXX 7488// ATF_TP_ADD_TC(tp, clone_sighand5); // XXX 7489// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand6); // XXX 7490// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand7); // XXX 7491// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand8); // XXX 7492 7493#if TEST_VFORK_ENABLED 7494 ATF_TP_ADD_TC(tp, clone_vfork1); 7495 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork2); 7496 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork3); 7497 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork4); 7498 ATF_TP_ADD_TC(tp, clone_vfork5); 7499 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork6); 7500 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork7); 7501 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork8); 7502#endif 7503 7504 ATF_TP_ADD_TC_HAVE_PID(tp, clone_signalignored); 7505 ATF_TP_ADD_TC_HAVE_PID(tp, clone_signalmasked); 7506 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm_signalignored); 7507 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm_signalmasked); 7508 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs_signalignored); 7509 ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs_signalmasked); 7510 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files_signalignored); 7511 ATF_TP_ADD_TC_HAVE_PID(tp, clone_files_signalmasked); 7512// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand_signalignored); // XXX 7513// ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand_signalmasked); // XXX 7514#if TEST_VFORK_ENABLED 7515 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork_signalignored); 7516 ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork_signalmasked); 7517#endif 7518 7519#if TEST_VFORK_ENABLED 7520 ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone); 7521 ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_vm); 7522 ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_fs); 7523 ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_files); 7524// ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_sighand); // XXX 7525 ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_vfork); 7526#endif 7527 7528 ATF_TP_ADD_TCS_PTRACE_WAIT_AMD64(); 7529 ATF_TP_ADD_TCS_PTRACE_WAIT_I386(); 7530 ATF_TP_ADD_TCS_PTRACE_WAIT_X86(); 7531 7532 return atf_no_error(); 7533} 7534