t_ptrace_wait.c revision 1.80
1/* $NetBSD: t_ptrace_wait.c,v 1.80 2019/02/11 04:20:06 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.80 2019/02/11 04:20:06 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/// ---------------------------------------------------------------------------- 91 92static void 93traceme_raise(int sigval) 94{ 95 const int exitval = 5; 96 pid_t child, wpid; 97#if defined(TWAIT_HAVE_STATUS) 98 int status; 99#endif 100 101 struct ptrace_siginfo info; 102 memset(&info, 0, sizeof(info)); 103 104 DPRINTF("Before forking process PID=%d\n", getpid()); 105 SYSCALL_REQUIRE((child = fork()) != -1); 106 if (child == 0) { 107 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 108 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 109 110 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 111 FORKEE_ASSERT(raise(sigval) == 0); 112 113 switch (sigval) { 114 case SIGKILL: 115 /* NOTREACHED */ 116 FORKEE_ASSERTX(0 && "This shall not be reached"); 117 __unreachable(); 118 default: 119 DPRINTF("Before exiting of the child process\n"); 120 _exit(exitval); 121 } 122 } 123 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 124 125 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 126 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 127 128 switch (sigval) { 129 case SIGKILL: 130 validate_status_signaled(status, sigval, 0); 131 break; 132 default: 133 validate_status_stopped(status, sigval); 134 135 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 136 "child\n"); 137 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, 138 sizeof(info)) != -1); 139 140 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 141 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 142 "si_errno=%#x\n", 143 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 144 info.psi_siginfo.si_errno); 145 146 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 147 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 148 149 DPRINTF("Before resuming the child process where it left off " 150 "and without signal to be sent\n"); 151 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 152 153 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 154 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 155 child); 156 break; 157 } 158 159 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 160 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 161} 162 163#define TRACEME_RAISE(test, sig) \ 164ATF_TC(test); \ 165ATF_TC_HEAD(test, tc) \ 166{ \ 167 atf_tc_set_md_var(tc, "descr", \ 168 "Verify " #sig " followed by _exit(2) in a child"); \ 169} \ 170 \ 171ATF_TC_BODY(test, tc) \ 172{ \ 173 \ 174 traceme_raise(sig); \ 175} 176 177TRACEME_RAISE(traceme_raise1, SIGKILL) /* non-maskable */ 178TRACEME_RAISE(traceme_raise2, SIGSTOP) /* non-maskable */ 179TRACEME_RAISE(traceme_raise3, SIGABRT) /* regular abort trap */ 180TRACEME_RAISE(traceme_raise4, SIGHUP) /* hangup */ 181TRACEME_RAISE(traceme_raise5, SIGCONT) /* continued? */ 182 183/// ---------------------------------------------------------------------------- 184 185static void 186traceme_crash(int sig) 187{ 188 pid_t child, wpid; 189#if defined(TWAIT_HAVE_STATUS) 190 int status; 191#endif 192 struct ptrace_siginfo info; 193 194#ifndef PTRACE_ILLEGAL_ASM 195 if (sig == SIGILL) 196 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 197#endif 198 199 memset(&info, 0, sizeof(info)); 200 201 DPRINTF("Before forking process PID=%d\n", getpid()); 202 SYSCALL_REQUIRE((child = fork()) != -1); 203 if (child == 0) { 204 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 205 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 206 207 DPRINTF("Before executing a trap\n"); 208 switch (sig) { 209 case SIGTRAP: 210 trigger_trap(); 211 break; 212 case SIGSEGV: 213 trigger_segv(); 214 break; 215 case SIGILL: 216 trigger_ill(); 217 break; 218 case SIGFPE: 219 trigger_fpe(); 220 break; 221 case SIGBUS: 222 trigger_bus(); 223 break; 224 default: 225 /* NOTREACHED */ 226 FORKEE_ASSERTX(0 && "This shall not be reached"); 227 } 228 229 /* NOTREACHED */ 230 FORKEE_ASSERTX(0 && "This shall not be reached"); 231 } 232 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 233 234 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 235 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 236 237 validate_status_stopped(status, sig); 238 239 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 240 SYSCALL_REQUIRE( 241 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 242 243 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 244 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 245 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 246 info.psi_siginfo.si_errno); 247 248 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sig); 249 switch (sig) { 250 case SIGTRAP: 251 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_BRKPT); 252 break; 253 case SIGSEGV: 254 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SEGV_MAPERR); 255 break; 256 case SIGILL: 257 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, ILL_PRVOPC); 258 break; 259 case SIGFPE: 260 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, FPE_INTDIV); 261 break; 262 case SIGBUS: 263 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, BUS_ADRERR); 264 break; 265 } 266 267 SYSCALL_REQUIRE(ptrace(PT_KILL, child, NULL, 0) != -1); 268 269 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 270 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 271 272 validate_status_signaled(status, SIGKILL, 0); 273 274 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 275 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 276} 277 278#define TRACEME_CRASH(test, sig) \ 279ATF_TC(test); \ 280ATF_TC_HEAD(test, tc) \ 281{ \ 282 atf_tc_set_md_var(tc, "descr", \ 283 "Verify crash signal " #sig " in a child after PT_TRACE_ME"); \ 284} \ 285 \ 286ATF_TC_BODY(test, tc) \ 287{ \ 288 \ 289 traceme_crash(sig); \ 290} 291 292TRACEME_CRASH(traceme_crash_trap, SIGTRAP) 293TRACEME_CRASH(traceme_crash_segv, SIGSEGV) 294TRACEME_CRASH(traceme_crash_ill, SIGILL) 295TRACEME_CRASH(traceme_crash_fpe, SIGFPE) 296TRACEME_CRASH(traceme_crash_bus, SIGBUS) 297 298/// ---------------------------------------------------------------------------- 299 300static void 301traceme_sendsignal_handle(int sigsent, void (*sah)(int a), int *traceme_caught) 302{ 303 const int exitval = 5; 304 const int sigval = SIGSTOP; 305 pid_t child, wpid; 306 struct sigaction sa; 307#if defined(TWAIT_HAVE_STATUS) 308 int status; 309#endif 310 struct ptrace_siginfo info; 311 312 memset(&info, 0, sizeof(info)); 313 314 DPRINTF("Before forking process PID=%d\n", getpid()); 315 SYSCALL_REQUIRE((child = fork()) != -1); 316 if (child == 0) { 317 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 318 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 319 320 sa.sa_handler = sah; 321 sa.sa_flags = SA_SIGINFO; 322 sigemptyset(&sa.sa_mask); 323 324 FORKEE_ASSERT(sigaction(sigsent, &sa, NULL) != -1); 325 326 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 327 FORKEE_ASSERT(raise(sigval) == 0); 328 329 FORKEE_ASSERT_EQ(*traceme_caught, 1); 330 331 DPRINTF("Before exiting of the child process\n"); 332 _exit(exitval); 333 } 334 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 335 336 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 337 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 338 339 validate_status_stopped(status, sigval); 340 341 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 342 SYSCALL_REQUIRE( 343 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 344 345 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 346 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 347 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 348 info.psi_siginfo.si_errno); 349 350 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 351 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 352 353 DPRINTF("Before resuming the child process where it left off and with " 354 "signal %s to be sent\n", strsignal(sigsent)); 355 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 356 357 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 358 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 359 360 validate_status_exited(status, exitval); 361 362 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 363 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 364} 365 366#define TRACEME_SENDSIGNAL_HANDLE(test, sig) \ 367ATF_TC(test); \ 368ATF_TC_HEAD(test, tc) \ 369{ \ 370 atf_tc_set_md_var(tc, "descr", \ 371 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 372 "handled correctly and caught by a signal handler"); \ 373} \ 374 \ 375static int test##_caught = 0; \ 376 \ 377static void \ 378test##_sighandler(int arg) \ 379{ \ 380 FORKEE_ASSERT_EQ(arg, sig); \ 381 \ 382 ++ test##_caught; \ 383} \ 384 \ 385ATF_TC_BODY(test, tc) \ 386{ \ 387 \ 388 traceme_sendsignal_handle(sig, test##_sighandler, & test##_caught); \ 389} 390 391// A signal handler for SIGKILL and SIGSTOP cannot be registered. 392TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle1, SIGABRT) /* abort trap */ 393TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle2, SIGHUP) /* hangup */ 394TRACEME_SENDSIGNAL_HANDLE(traceme_sendsignal_handle3, SIGCONT) /* continued? */ 395 396/// ---------------------------------------------------------------------------- 397 398static void 399traceme_sendsignal_masked(int sigsent) 400{ 401 const int exitval = 5; 402 const int sigval = SIGSTOP; 403 pid_t child, wpid; 404 sigset_t set; 405#if defined(TWAIT_HAVE_STATUS) 406 int status; 407#endif 408 struct ptrace_siginfo info; 409 410 memset(&info, 0, sizeof(info)); 411 412 DPRINTF("Before forking process PID=%d\n", getpid()); 413 SYSCALL_REQUIRE((child = fork()) != -1); 414 if (child == 0) { 415 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 416 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 417 418 sigemptyset(&set); 419 sigaddset(&set, sigsent); 420 FORKEE_ASSERT(sigprocmask(SIG_BLOCK, &set, NULL) != -1); 421 422 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 423 FORKEE_ASSERT(raise(sigval) == 0); 424 425 _exit(exitval); 426 } 427 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 428 429 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 430 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 431 432 validate_status_stopped(status, sigval); 433 434 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 435 SYSCALL_REQUIRE( 436 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 437 438 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 439 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 440 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 441 info.psi_siginfo.si_errno); 442 443 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 444 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 445 446 DPRINTF("Before resuming the child process where it left off and with " 447 "signal %s to be sent\n", strsignal(sigsent)); 448 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 449 450 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 451 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 452 453 validate_status_exited(status, exitval); 454 455 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 456 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 457} 458 459#define TRACEME_SENDSIGNAL_MASKED(test, sig) \ 460ATF_TC(test); \ 461ATF_TC_HEAD(test, tc) \ 462{ \ 463 atf_tc_set_md_var(tc, "descr", \ 464 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 465 "handled correctly and the signal is masked by SIG_BLOCK"); \ 466} \ 467 \ 468ATF_TC_BODY(test, tc) \ 469{ \ 470 \ 471 traceme_sendsignal_masked(sig); \ 472} 473 474// A signal handler for SIGKILL and SIGSTOP cannot be masked. 475TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked1, SIGABRT) /* abort trap */ 476TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked2, SIGHUP) /* hangup */ 477TRACEME_SENDSIGNAL_MASKED(traceme_sendsignal_masked3, SIGCONT) /* continued? */ 478 479/// ---------------------------------------------------------------------------- 480 481static void 482traceme_sendsignal_ignored(int sigsent) 483{ 484 const int exitval = 5; 485 const int sigval = SIGSTOP; 486 pid_t child, wpid; 487 struct sigaction sa; 488#if defined(TWAIT_HAVE_STATUS) 489 int status; 490#endif 491 struct ptrace_siginfo info; 492 493 memset(&info, 0, sizeof(info)); 494 495 DPRINTF("Before forking process PID=%d\n", getpid()); 496 SYSCALL_REQUIRE((child = fork()) != -1); 497 if (child == 0) { 498 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 499 500 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 501 502 memset(&sa, 0, sizeof(sa)); 503 sa.sa_handler = SIG_IGN; 504 sigemptyset(&sa.sa_mask); 505 FORKEE_ASSERT(sigaction(sigsent, &sa, NULL) != -1); 506 507 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 508 FORKEE_ASSERT(raise(sigval) == 0); 509 510 _exit(exitval); 511 } 512 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 513 514 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 515 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 516 517 validate_status_stopped(status, sigval); 518 519 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 520 SYSCALL_REQUIRE( 521 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 522 523 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 524 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 525 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 526 info.psi_siginfo.si_errno); 527 528 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 529 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 530 531 DPRINTF("Before resuming the child process where it left off and with " 532 "signal %s to be sent\n", strsignal(sigsent)); 533 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 534 535 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 536 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 537 538 validate_status_exited(status, exitval); 539 540 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 541 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 542} 543 544#define TRACEME_SENDSIGNAL_IGNORED(test, sig) \ 545ATF_TC(test); \ 546ATF_TC_HEAD(test, tc) \ 547{ \ 548 atf_tc_set_md_var(tc, "descr", \ 549 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 550 "handled correctly and the signal is masked by SIG_IGN"); \ 551} \ 552 \ 553ATF_TC_BODY(test, tc) \ 554{ \ 555 \ 556 traceme_sendsignal_ignored(sig); \ 557} 558 559// A signal handler for SIGKILL and SIGSTOP cannot be ignored. 560TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored1, SIGABRT) /* abort */ 561TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored2, SIGHUP) /* hangup */ 562TRACEME_SENDSIGNAL_IGNORED(traceme_sendsignal_ignored3, SIGCONT) /* continued */ 563 564/// ---------------------------------------------------------------------------- 565 566static void 567traceme_sendsignal_simple(int sigsent) 568{ 569 const int sigval = SIGSTOP; 570 int exitval = 0; 571 pid_t child, wpid; 572#if defined(TWAIT_HAVE_STATUS) 573 int status; 574 int expect_core = (sigsent == SIGABRT) ? 1 : 0; 575#endif 576 struct ptrace_siginfo info; 577 578 memset(&info, 0, sizeof(info)); 579 580 DPRINTF("Before forking process PID=%d\n", getpid()); 581 SYSCALL_REQUIRE((child = fork()) != -1); 582 if (child == 0) { 583 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 584 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 585 586 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 587 FORKEE_ASSERT(raise(sigval) == 0); 588 589 switch (sigsent) { 590 case SIGCONT: 591 case SIGSTOP: 592 _exit(exitval); 593 default: 594 /* NOTREACHED */ 595 FORKEE_ASSERTX(0 && "This shall not be reached"); 596 } 597 } 598 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 599 600 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 601 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 602 603 validate_status_stopped(status, sigval); 604 605 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 606 SYSCALL_REQUIRE( 607 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 608 609 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 610 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 611 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 612 info.psi_siginfo.si_errno); 613 614 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 615 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 616 617 DPRINTF("Before resuming the child process where it left off and with " 618 "signal %s to be sent\n", strsignal(sigsent)); 619 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, sigsent) != -1); 620 621 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 622 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 623 624 switch (sigsent) { 625 case SIGSTOP: 626 validate_status_stopped(status, sigsent); 627 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 628 "child\n"); 629 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, 630 sizeof(info)) != -1); 631 632 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 633 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 634 "si_errno=%#x\n", 635 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 636 info.psi_siginfo.si_errno); 637 638 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 639 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 640 641 DPRINTF("Before resuming the child process where it left off " 642 "and with signal %s to be sent\n", strsignal(sigsent)); 643 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 644 645 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 646 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 647 child); 648 /* FALLTHROUGH */ 649 case SIGCONT: 650 validate_status_exited(status, exitval); 651 break; 652 default: 653 validate_status_signaled(status, sigsent, expect_core); 654 break; 655 } 656 657 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 658 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 659} 660 661#define TRACEME_SENDSIGNAL_SIMPLE(test, sig) \ 662ATF_TC(test); \ 663ATF_TC_HEAD(test, tc) \ 664{ \ 665 atf_tc_set_md_var(tc, "descr", \ 666 "Verify that a signal " #sig " emitted by a tracer to a child is " \ 667 "handled correctly in a child without a signal handler"); \ 668} \ 669 \ 670ATF_TC_BODY(test, tc) \ 671{ \ 672 \ 673 traceme_sendsignal_simple(sig); \ 674} 675 676TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple1, SIGKILL) /* non-maskable*/ 677TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple2, SIGSTOP) /* non-maskable*/ 678TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple3, SIGABRT) /* abort trap */ 679TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple4, SIGHUP) /* hangup */ 680TRACEME_SENDSIGNAL_SIMPLE(traceme_sendsignal_simple5, SIGCONT) /* continued? */ 681 682/// ---------------------------------------------------------------------------- 683 684ATF_TC(traceme_pid1_parent); 685ATF_TC_HEAD(traceme_pid1_parent, tc) 686{ 687 atf_tc_set_md_var(tc, "descr", 688 "Verify that PT_TRACE_ME is not allowed when our parent is PID1"); 689} 690 691ATF_TC_BODY(traceme_pid1_parent, tc) 692{ 693 struct msg_fds parent_child; 694 int exitval_child1 = 1, exitval_child2 = 2; 695 pid_t child1, child2, wpid; 696 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 697#if defined(TWAIT_HAVE_STATUS) 698 int status; 699#endif 700 701 SYSCALL_REQUIRE(msg_open(&parent_child) == 0); 702 703 DPRINTF("Before forking process PID=%d\n", getpid()); 704 SYSCALL_REQUIRE((child1 = fork()) != -1); 705 if (child1 == 0) { 706 DPRINTF("Before forking process PID=%d\n", getpid()); 707 SYSCALL_REQUIRE((child2 = fork()) != -1); 708 if (child2 != 0) { 709 DPRINTF("Parent process PID=%d, child2's PID=%d\n", 710 getpid(), child2); 711 _exit(exitval_child1); 712 } 713 CHILD_FROM_PARENT("exit child1", parent_child, msg); 714 715 DPRINTF("Assert that our parent is PID1 (initproc)\n"); 716 FORKEE_ASSERT_EQ(getppid(), 1); 717 718 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 719 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) == -1); 720 SYSCALL_REQUIRE_ERRNO(errno, EPERM); 721 722 CHILD_TO_PARENT("child2 exiting", parent_child, msg); 723 724 _exit(exitval_child2); 725 } 726 DPRINTF("Parent process PID=%d, child1's PID=%d\n", getpid(), child1); 727 728 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 729 TWAIT_REQUIRE_SUCCESS( 730 wpid = TWAIT_GENERIC(child1, &status, WEXITED), child1); 731 732 validate_status_exited(status, exitval_child1); 733 734 DPRINTF("Notify that child1 is dead\n"); 735 PARENT_TO_CHILD("exit child1", parent_child, msg); 736 737 DPRINTF("Wait for exiting of child2\n"); 738 PARENT_FROM_CHILD("child2 exiting", parent_child, msg); 739} 740 741/// ---------------------------------------------------------------------------- 742 743static void 744traceme_vfork_raise(int sigval) 745{ 746 const int exitval = 5, exitval_watcher = 10; 747 pid_t child, parent, watcher, wpid; 748 int rv; 749#if defined(TWAIT_HAVE_STATUS) 750 int status; 751 int expect_core = (sigval == SIGABRT) ? 1 : 0; 752#endif 753 754 /* 755 * Spawn a dedicated thread to watch for a stopped child and emit 756 * the SIGKILL signal to it. 757 * 758 * vfork(2) might clobber watcher, this means that it's safer and 759 * simpler to reparent this process to initproc and forget about it. 760 */ 761 if (sigval == SIGSTOP) { 762 parent = getpid(); 763 764 watcher = fork(); 765 ATF_REQUIRE(watcher != 1); 766 if (watcher == 0) { 767 /* Double fork(2) trick to reparent to initproc */ 768 watcher = fork(); 769 FORKEE_ASSERT_NEQ(watcher, -1); 770 if (watcher != 0) 771 _exit(exitval_watcher); 772 773 child = await_stopped_child(parent); 774 775 errno = 0; 776 rv = kill(child, SIGKILL); 777 FORKEE_ASSERT_EQ(rv, 0); 778 FORKEE_ASSERT_EQ(errno, 0); 779 780 /* This exit value will be collected by initproc */ 781 _exit(0); 782 } 783 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 784 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(watcher, &status, 0), 785 watcher); 786 787 validate_status_exited(status, exitval_watcher); 788 789 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 790 TWAIT_REQUIRE_FAILURE(ECHILD, 791 wpid = TWAIT_GENERIC(watcher, &status, 0)); 792 } 793 794 DPRINTF("Before forking process PID=%d\n", getpid()); 795 SYSCALL_REQUIRE((child = vfork()) != -1); 796 if (child == 0) { 797 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 798 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 799 800 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 801 FORKEE_ASSERT(raise(sigval) == 0); 802 803 switch (sigval) { 804 case SIGSTOP: 805 case SIGKILL: 806 case SIGABRT: 807 case SIGHUP: 808 /* NOTREACHED */ 809 FORKEE_ASSERTX(0 && "This shall not be reached"); 810 __unreachable(); 811 default: 812 DPRINTF("Before exiting of the child process\n"); 813 _exit(exitval); 814 } 815 } 816 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 817 818 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 819 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 820 821 switch (sigval) { 822 case SIGKILL: 823 case SIGABRT: 824 case SIGHUP: 825 validate_status_signaled(status, sigval, expect_core); 826 break; 827 case SIGSTOP: 828 validate_status_signaled(status, SIGKILL, 0); 829 break; 830 case SIGCONT: 831 case SIGTSTP: 832 case SIGTTIN: 833 case SIGTTOU: 834 validate_status_exited(status, exitval); 835 break; 836 default: 837 /* NOTREACHED */ 838 ATF_REQUIRE(0 && "NOT IMPLEMENTED"); 839 break; 840 } 841 842 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 843 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 844} 845 846#define TRACEME_VFORK_RAISE(test, sig) \ 847ATF_TC(test); \ 848ATF_TC_HEAD(test, tc) \ 849{ \ 850 atf_tc_set_md_var(tc, "descr", \ 851 "Verify PT_TRACE_ME followed by raise of " #sig " in a " \ 852 "vfork(2)ed child"); \ 853} \ 854 \ 855ATF_TC_BODY(test, tc) \ 856{ \ 857 \ 858 traceme_vfork_raise(sig); \ 859} 860 861TRACEME_VFORK_RAISE(traceme_vfork_raise1, SIGKILL) /* non-maskable */ 862TRACEME_VFORK_RAISE(traceme_vfork_raise2, SIGSTOP) /* non-maskable */ 863TRACEME_VFORK_RAISE(traceme_vfork_raise3, SIGTSTP) /* ignored in vfork(2) */ 864TRACEME_VFORK_RAISE(traceme_vfork_raise4, SIGTTIN) /* ignored in vfork(2) */ 865TRACEME_VFORK_RAISE(traceme_vfork_raise5, SIGTTOU) /* ignored in vfork(2) */ 866TRACEME_VFORK_RAISE(traceme_vfork_raise6, SIGABRT) /* regular abort trap */ 867TRACEME_VFORK_RAISE(traceme_vfork_raise7, SIGHUP) /* hangup */ 868TRACEME_VFORK_RAISE(traceme_vfork_raise8, SIGCONT) /* continued? */ 869 870/// ---------------------------------------------------------------------------- 871 872static void 873traceme_vfork_crash(int sig) 874{ 875 pid_t child, wpid; 876#if defined(TWAIT_HAVE_STATUS) 877 int status; 878#endif 879 880#ifndef PTRACE_ILLEGAL_ASM 881 if (sig == SIGILL) 882 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 883#endif 884 885 DPRINTF("Before forking process PID=%d\n", getpid()); 886 SYSCALL_REQUIRE((child = vfork()) != -1); 887 if (child == 0) { 888 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 889 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 890 891 DPRINTF("Before executing a trap\n"); 892 switch (sig) { 893 case SIGTRAP: 894 trigger_trap(); 895 break; 896 case SIGSEGV: 897 trigger_segv(); 898 break; 899 case SIGILL: 900 trigger_ill(); 901 break; 902 case SIGFPE: 903 trigger_fpe(); 904 break; 905 case SIGBUS: 906 trigger_bus(); 907 break; 908 default: 909 /* NOTREACHED */ 910 FORKEE_ASSERTX(0 && "This shall not be reached"); 911 } 912 913 /* NOTREACHED */ 914 FORKEE_ASSERTX(0 && "This shall not be reached"); 915 } 916 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 917 918 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 919 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 920 921 validate_status_signaled(status, sig, 1); 922 923 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 924 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 925} 926 927#define TRACEME_VFORK_CRASH(test, sig) \ 928ATF_TC(test); \ 929ATF_TC_HEAD(test, tc) \ 930{ \ 931 atf_tc_set_md_var(tc, "descr", \ 932 "Verify PT_TRACE_ME followed by a crash signal " #sig " in a " \ 933 "vfork(2)ed child"); \ 934} \ 935 \ 936ATF_TC_BODY(test, tc) \ 937{ \ 938 \ 939 traceme_vfork_crash(sig); \ 940} 941 942TRACEME_VFORK_CRASH(traceme_vfork_crash_trap, SIGTRAP) 943TRACEME_VFORK_CRASH(traceme_vfork_crash_segv, SIGSEGV) 944TRACEME_VFORK_CRASH(traceme_vfork_crash_ill, SIGILL) 945TRACEME_VFORK_CRASH(traceme_vfork_crash_fpe, SIGFPE) 946TRACEME_VFORK_CRASH(traceme_vfork_crash_bus, SIGBUS) 947 948/// ---------------------------------------------------------------------------- 949 950ATF_TC(traceme_vfork_exec); 951ATF_TC_HEAD(traceme_vfork_exec, tc) 952{ 953 atf_tc_set_md_var(tc, "descr", 954 "Verify PT_TRACE_ME followed by exec(3) in a vfork(2)ed child"); 955} 956 957ATF_TC_BODY(traceme_vfork_exec, tc) 958{ 959 const int sigval = SIGTRAP; 960 pid_t child, wpid; 961#if defined(TWAIT_HAVE_STATUS) 962 int status; 963#endif 964 struct ptrace_siginfo info; 965 966 memset(&info, 0, sizeof(info)); 967 968 DPRINTF("Before forking process PID=%d\n", getpid()); 969 SYSCALL_REQUIRE((child = vfork()) != -1); 970 if (child == 0) { 971 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 972 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 973 974 DPRINTF("Before calling execve(2) from child\n"); 975 execlp("/bin/echo", "/bin/echo", NULL); 976 977 /* NOTREACHED */ 978 FORKEE_ASSERTX(0 && "Not reached"); 979 } 980 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 981 982 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 983 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 984 985 validate_status_stopped(status, sigval); 986 987 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 988 SYSCALL_REQUIRE( 989 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 990 991 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 992 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 993 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 994 info.psi_siginfo.si_errno); 995 996 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 997 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_EXEC); 998 999 DPRINTF("Before resuming the child process where it left off and " 1000 "without signal to be sent\n"); 1001 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 1002 1003 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1004 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1005 1006 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1007 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1008} 1009 1010/// ---------------------------------------------------------------------------- 1011 1012#if defined(TWAIT_HAVE_PID) 1013static void 1014unrelated_tracer_sees_crash(int sig) 1015{ 1016 struct msg_fds parent_tracee, parent_tracer; 1017 const int exitval = 10; 1018 pid_t tracee, tracer, wpid; 1019 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1020#if defined(TWAIT_HAVE_STATUS) 1021 int status; 1022#endif 1023 struct ptrace_siginfo info; 1024 1025#ifndef PTRACE_ILLEGAL_ASM 1026 if (sig == SIGILL) 1027 atf_tc_skip("PTRACE_ILLEGAL_ASM not defined"); 1028#endif 1029 1030 memset(&info, 0, sizeof(info)); 1031 1032 DPRINTF("Spawn tracee\n"); 1033 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 1034 tracee = atf_utils_fork(); 1035 if (tracee == 0) { 1036 // Wait for parent to let us crash 1037 CHILD_FROM_PARENT("exit tracee", parent_tracee, msg); 1038 1039 DPRINTF("Before executing a trap\n"); 1040 switch (sig) { 1041 case SIGTRAP: 1042 trigger_trap(); 1043 break; 1044 case SIGSEGV: 1045 trigger_segv(); 1046 break; 1047 case SIGILL: 1048 trigger_ill(); 1049 break; 1050 case SIGFPE: 1051 trigger_fpe(); 1052 break; 1053 case SIGBUS: 1054 trigger_bus(); 1055 break; 1056 default: 1057 /* NOTREACHED */ 1058 FORKEE_ASSERTX(0 && "This shall not be reached"); 1059 } 1060 1061 /* NOTREACHED */ 1062 FORKEE_ASSERTX(0 && "This shall not be reached"); 1063 } 1064 1065 DPRINTF("Spawn debugger\n"); 1066 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 1067 tracer = atf_utils_fork(); 1068 if (tracer == 0) { 1069 /* Fork again and drop parent to reattach to PID 1 */ 1070 tracer = atf_utils_fork(); 1071 if (tracer != 0) 1072 _exit(exitval); 1073 1074 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 1075 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 1076 1077 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 1078 FORKEE_REQUIRE_SUCCESS( 1079 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1080 1081 forkee_status_stopped(status, SIGSTOP); 1082 1083 /* Resume tracee with PT_CONTINUE */ 1084 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 1085 1086 /* Inform parent that tracer has attached to tracee */ 1087 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 1088 1089 /* Wait for parent to tell use that tracee should have exited */ 1090 CHILD_FROM_PARENT("wait for tracee exit", parent_tracer, msg); 1091 1092 /* Wait for tracee and assert that it exited */ 1093 FORKEE_REQUIRE_SUCCESS( 1094 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1095 1096 validate_status_stopped(status, sig); 1097 1098 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for the " 1099 "traced process\n"); 1100 SYSCALL_REQUIRE( 1101 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 1102 1103 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 1104 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 1105 "si_errno=%#x\n", info.psi_siginfo.si_signo, 1106 info.psi_siginfo.si_code, info.psi_siginfo.si_errno); 1107 1108 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sig); 1109 switch (sig) { 1110 case SIGTRAP: 1111 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_BRKPT); 1112 break; 1113 case SIGSEGV: 1114 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SEGV_MAPERR); 1115 break; 1116 case SIGILL: 1117 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, ILL_PRVOPC); 1118 break; 1119 case SIGFPE: 1120 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, FPE_INTDIV); 1121 break; 1122 case SIGBUS: 1123 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, BUS_ADRERR); 1124 break; 1125 } 1126 1127 FORKEE_ASSERT(ptrace(PT_KILL, tracee, NULL, 0) != -1); 1128 DPRINTF("Before calling %s() for the tracee\n", TWAIT_FNAME); 1129 TWAIT_REQUIRE_SUCCESS( 1130 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1131 1132 validate_status_signaled(status, SIGKILL, 0); 1133 1134 DPRINTF("Before calling %s() for tracee\n", TWAIT_FNAME); 1135 TWAIT_REQUIRE_FAILURE(ECHILD, 1136 wpid = TWAIT_GENERIC(tracee, &status, 0)); 1137 1138 /* Inform parent that tracer is exiting normally */ 1139 CHILD_TO_PARENT("tracer done", parent_tracer, msg); 1140 1141 DPRINTF("Before exiting of the tracer process\n"); 1142 _exit(0 /* collect by initproc */); 1143 } 1144 1145 DPRINTF("Wait for the tracer process (direct child) to exit " 1146 "calling %s()\n", TWAIT_FNAME); 1147 TWAIT_REQUIRE_SUCCESS( 1148 wpid = TWAIT_GENERIC(tracer, &status, 0), tracer); 1149 1150 validate_status_exited(status, exitval); 1151 1152 DPRINTF("Wait for the non-exited tracee process with %s()\n", 1153 TWAIT_FNAME); 1154 TWAIT_REQUIRE_SUCCESS( 1155 wpid = TWAIT_GENERIC(tracee, NULL, WNOHANG), 0); 1156 1157 DPRINTF("Wait for the tracer to attach to the tracee\n"); 1158 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 1159 1160 DPRINTF("Resume the tracee and let it crash\n"); 1161 PARENT_TO_CHILD("exit tracee", parent_tracee, msg); 1162 1163 DPRINTF("Resume the tracer and let it detect crashed tracee\n"); 1164 PARENT_TO_CHILD("Message 2", parent_tracer, msg); 1165 1166 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 1167 TWAIT_FNAME); 1168 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1169 1170 validate_status_signaled(status, SIGKILL, 0); 1171 1172 DPRINTF("Await normal exit of tracer\n"); 1173 PARENT_FROM_CHILD("tracer done", parent_tracer, msg); 1174 1175 msg_close(&parent_tracer); 1176 msg_close(&parent_tracee); 1177} 1178 1179#define UNRELATED_TRACER_SEES_CRASH(test, sig) \ 1180ATF_TC(test); \ 1181ATF_TC_HEAD(test, tc) \ 1182{ \ 1183 atf_tc_set_md_var(tc, "descr", \ 1184 "Assert that an unrelated tracer sees crash signal from the " \ 1185 "debuggee"); \ 1186} \ 1187 \ 1188ATF_TC_BODY(test, tc) \ 1189{ \ 1190 \ 1191 unrelated_tracer_sees_crash(sig); \ 1192} 1193 1194UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_trap, SIGTRAP) 1195UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_segv, SIGSEGV) 1196UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_ill, SIGILL) 1197UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_fpe, SIGFPE) 1198UNRELATED_TRACER_SEES_CRASH(unrelated_tracer_sees_crash_bus, SIGBUS) 1199#endif 1200 1201/// ---------------------------------------------------------------------------- 1202 1203#if defined(TWAIT_HAVE_PID) 1204static void 1205tracer_sees_terminaton_before_the_parent_raw(bool notimeout, bool unrelated, 1206 bool stopped) 1207{ 1208 /* 1209 * notimeout - disable timeout in await zombie function 1210 * unrelated - attach from unrelated tracer reparented to initproc 1211 * stopped - attach to a stopped process 1212 */ 1213 1214 struct msg_fds parent_tracee, parent_tracer; 1215 const int exitval_tracee = 5; 1216 const int exitval_tracer = 10; 1217 pid_t tracee, tracer, wpid; 1218 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1219#if defined(TWAIT_HAVE_STATUS) 1220 int status; 1221#endif 1222 1223 /* 1224 * Only a subset of options are supported. 1225 */ 1226 ATF_REQUIRE((!notimeout && !unrelated && !stopped) || 1227 (!notimeout && unrelated && !stopped) || 1228 (notimeout && !unrelated && !stopped) || 1229 (!notimeout && unrelated && stopped)); 1230 1231 DPRINTF("Spawn tracee\n"); 1232 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 1233 tracee = atf_utils_fork(); 1234 if (tracee == 0) { 1235 if (stopped) { 1236 DPRINTF("Stop self PID %d\n", getpid()); 1237 raise(SIGSTOP); 1238 } 1239 1240 // Wait for parent to let us exit 1241 CHILD_FROM_PARENT("exit tracee", parent_tracee, msg); 1242 _exit(exitval_tracee); 1243 } 1244 1245 DPRINTF("Spawn debugger\n"); 1246 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 1247 tracer = atf_utils_fork(); 1248 if (tracer == 0) { 1249 if(unrelated) { 1250 /* Fork again and drop parent to reattach to PID 1 */ 1251 tracer = atf_utils_fork(); 1252 if (tracer != 0) 1253 _exit(exitval_tracer); 1254 } 1255 1256 if (stopped) { 1257 DPRINTF("Await for a stopped parent PID %d\n", tracee); 1258 await_stopped(tracee); 1259 } 1260 1261 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 1262 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 1263 1264 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 1265 FORKEE_REQUIRE_SUCCESS( 1266 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1267 1268 forkee_status_stopped(status, SIGSTOP); 1269 1270 /* Resume tracee with PT_CONTINUE */ 1271 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 1272 1273 /* Inform parent that tracer has attached to tracee */ 1274 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 1275 1276 /* Wait for parent to tell use that tracee should have exited */ 1277 CHILD_FROM_PARENT("wait for tracee exit", parent_tracer, msg); 1278 1279 /* Wait for tracee and assert that it exited */ 1280 FORKEE_REQUIRE_SUCCESS( 1281 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1282 1283 forkee_status_exited(status, exitval_tracee); 1284 DPRINTF("Tracee %d exited with %d\n", tracee, exitval_tracee); 1285 1286 DPRINTF("Before exiting of the tracer process\n"); 1287 _exit(unrelated ? 0 /* collect by initproc */ : exitval_tracer); 1288 } 1289 1290 if (unrelated) { 1291 DPRINTF("Wait for the tracer process (direct child) to exit " 1292 "calling %s()\n", TWAIT_FNAME); 1293 TWAIT_REQUIRE_SUCCESS( 1294 wpid = TWAIT_GENERIC(tracer, &status, 0), tracer); 1295 1296 validate_status_exited(status, exitval_tracer); 1297 1298 DPRINTF("Wait for the non-exited tracee process with %s()\n", 1299 TWAIT_FNAME); 1300 TWAIT_REQUIRE_SUCCESS( 1301 wpid = TWAIT_GENERIC(tracee, NULL, WNOHANG), 0); 1302 } 1303 1304 DPRINTF("Wait for the tracer to attach to the tracee\n"); 1305 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 1306 1307 DPRINTF("Resume the tracee and let it exit\n"); 1308 PARENT_TO_CHILD("exit tracee", parent_tracee, msg); 1309 1310 DPRINTF("Detect that tracee is zombie\n"); 1311 if (notimeout) 1312 await_zombie_raw(tracee, 0); 1313 else 1314 await_zombie(tracee); 1315 1316 DPRINTF("Assert that there is no status about tracee %d - " 1317 "Tracer must detect zombie first - calling %s()\n", tracee, 1318 TWAIT_FNAME); 1319 TWAIT_REQUIRE_SUCCESS( 1320 wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 0); 1321 1322 if (unrelated) { 1323 DPRINTF("Resume the tracer and let it detect exited tracee\n"); 1324 PARENT_TO_CHILD("Message 2", parent_tracer, msg); 1325 } else { 1326 DPRINTF("Tell the tracer child should have exited\n"); 1327 PARENT_TO_CHILD("wait for tracee exit", parent_tracer, msg); 1328 DPRINTF("Wait for tracer to finish its job and exit - calling " 1329 "%s()\n", TWAIT_FNAME); 1330 1331 DPRINTF("Wait from tracer child to complete waiting for " 1332 "tracee\n"); 1333 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracer, &status, 0), 1334 tracer); 1335 1336 validate_status_exited(status, exitval_tracer); 1337 } 1338 1339 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 1340 TWAIT_FNAME); 1341 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1342 1343 validate_status_exited(status, exitval_tracee); 1344 1345 msg_close(&parent_tracer); 1346 msg_close(&parent_tracee); 1347} 1348 1349ATF_TC(tracer_sees_terminaton_before_the_parent); 1350ATF_TC_HEAD(tracer_sees_terminaton_before_the_parent, tc) 1351{ 1352 atf_tc_set_md_var(tc, "descr", 1353 "Assert that tracer sees process termination before the parent"); 1354} 1355 1356ATF_TC_BODY(tracer_sees_terminaton_before_the_parent, tc) 1357{ 1358 1359 tracer_sees_terminaton_before_the_parent_raw(false, false, false); 1360} 1361 1362ATF_TC(tracer_sysctl_lookup_without_duplicates); 1363ATF_TC_HEAD(tracer_sysctl_lookup_without_duplicates, tc) 1364{ 1365 atf_tc_set_md_var(tc, "descr", 1366 "Assert that await_zombie() in attach1 always finds a single " 1367 "process and no other error is reported"); 1368} 1369 1370ATF_TC_BODY(tracer_sysctl_lookup_without_duplicates, tc) 1371{ 1372 time_t start, end; 1373 double diff; 1374 unsigned long N = 0; 1375 1376 /* 1377 * Reuse this test with tracer_sees_terminaton_before_the_parent_raw(). 1378 * This test body isn't specific to this race, however it's just good 1379 * enough for this purposes, no need to invent a dedicated code flow. 1380 */ 1381 1382 start = time(NULL); 1383 while (true) { 1384 DPRINTF("Step: %lu\n", N); 1385 tracer_sees_terminaton_before_the_parent_raw(true, false, 1386 false); 1387 end = time(NULL); 1388 diff = difftime(end, start); 1389 if (diff >= 5.0) 1390 break; 1391 ++N; 1392 } 1393 DPRINTF("Iterations: %lu\n", N); 1394} 1395 1396ATF_TC(unrelated_tracer_sees_terminaton_before_the_parent); 1397ATF_TC_HEAD(unrelated_tracer_sees_terminaton_before_the_parent, tc) 1398{ 1399 atf_tc_set_md_var(tc, "descr", 1400 "Assert that tracer sees process termination before the parent"); 1401} 1402 1403ATF_TC_BODY(unrelated_tracer_sees_terminaton_before_the_parent, tc) 1404{ 1405 1406 tracer_sees_terminaton_before_the_parent_raw(false, true, false); 1407} 1408 1409ATF_TC(tracer_attach_to_unrelated_stopped_process); 1410ATF_TC_HEAD(tracer_attach_to_unrelated_stopped_process, tc) 1411{ 1412 atf_tc_set_md_var(tc, "descr", 1413 "Assert that tracer can attach to an unrelated stopped process"); 1414} 1415 1416ATF_TC_BODY(tracer_attach_to_unrelated_stopped_process, tc) 1417{ 1418 1419 tracer_sees_terminaton_before_the_parent_raw(false, true, true); 1420} 1421#endif 1422 1423/// ---------------------------------------------------------------------------- 1424 1425static void 1426parent_attach_to_its_child(bool stopped) 1427{ 1428 struct msg_fds parent_tracee; 1429 const int exitval_tracee = 5; 1430 pid_t tracee, wpid; 1431 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1432#if defined(TWAIT_HAVE_STATUS) 1433 int status; 1434#endif 1435 1436 DPRINTF("Spawn tracee\n"); 1437 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 1438 tracee = atf_utils_fork(); 1439 if (tracee == 0) { 1440 CHILD_FROM_PARENT("Message 1", parent_tracee, msg); 1441 DPRINTF("Parent should now attach to tracee\n"); 1442 1443 if (stopped) { 1444 DPRINTF("Stop self PID %d\n", getpid()); 1445 SYSCALL_REQUIRE(raise(SIGSTOP) != -1); 1446 } 1447 1448 CHILD_FROM_PARENT("Message 2", parent_tracee, msg); 1449 /* Wait for message from the parent */ 1450 _exit(exitval_tracee); 1451 } 1452 PARENT_TO_CHILD("Message 1", parent_tracee, msg); 1453 1454 if (stopped) { 1455 DPRINTF("Await for a stopped tracee PID %d\n", tracee); 1456 await_stopped(tracee); 1457 } 1458 1459 DPRINTF("Before calling PT_ATTACH for tracee %d\n", tracee); 1460 SYSCALL_REQUIRE(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 1461 1462 DPRINTF("Wait for the stopped tracee process with %s()\n", 1463 TWAIT_FNAME); 1464 TWAIT_REQUIRE_SUCCESS( 1465 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1466 1467 validate_status_stopped(status, SIGSTOP); 1468 1469 DPRINTF("Resume tracee with PT_CONTINUE\n"); 1470 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 1471 1472 DPRINTF("Let the tracee exit now\n"); 1473 PARENT_TO_CHILD("Message 2", parent_tracee, msg); 1474 1475 DPRINTF("Wait for tracee to exit with %s()\n", TWAIT_FNAME); 1476 TWAIT_REQUIRE_SUCCESS( 1477 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1478 1479 validate_status_exited(status, exitval_tracee); 1480 1481 DPRINTF("Before calling %s() for tracee\n", TWAIT_FNAME); 1482 TWAIT_REQUIRE_FAILURE(ECHILD, 1483 wpid = TWAIT_GENERIC(tracee, &status, 0)); 1484 1485 msg_close(&parent_tracee); 1486} 1487 1488ATF_TC(parent_attach_to_its_child); 1489ATF_TC_HEAD(parent_attach_to_its_child, tc) 1490{ 1491 atf_tc_set_md_var(tc, "descr", 1492 "Assert that tracer parent can PT_ATTACH to its child"); 1493} 1494 1495ATF_TC_BODY(parent_attach_to_its_child, tc) 1496{ 1497 1498 parent_attach_to_its_child(false); 1499} 1500 1501ATF_TC(parent_attach_to_its_stopped_child); 1502ATF_TC_HEAD(parent_attach_to_its_stopped_child, tc) 1503{ 1504 atf_tc_set_md_var(tc, "descr", 1505 "Assert that tracer parent can PT_ATTACH to its stopped child"); 1506} 1507 1508ATF_TC_BODY(parent_attach_to_its_stopped_child, tc) 1509{ 1510 1511 parent_attach_to_its_child(true); 1512} 1513 1514/// ---------------------------------------------------------------------------- 1515 1516static void 1517child_attach_to_its_parent(bool stopped) 1518{ 1519 struct msg_fds parent_tracee; 1520 const int exitval_tracer = 5; 1521 pid_t tracer, wpid; 1522 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1523#if defined(TWAIT_HAVE_STATUS) 1524 int status; 1525#endif 1526 1527 DPRINTF("Spawn tracer\n"); 1528 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 1529 tracer = atf_utils_fork(); 1530 if (tracer == 0) { 1531 /* Wait for message from the parent */ 1532 CHILD_FROM_PARENT("Message 1", parent_tracee, msg); 1533 1534 if (stopped) { 1535 DPRINTF("Await for a stopped parent PID %d\n", 1536 getppid()); 1537 await_stopped(getppid()); 1538 } 1539 1540 DPRINTF("Attach to parent PID %d with PT_ATTACH from child\n", 1541 getppid()); 1542 FORKEE_ASSERT(ptrace(PT_ATTACH, getppid(), NULL, 0) != -1); 1543 1544 DPRINTF("Wait for the stopped parent process with %s()\n", 1545 TWAIT_FNAME); 1546 FORKEE_REQUIRE_SUCCESS( 1547 wpid = TWAIT_GENERIC(getppid(), &status, 0), getppid()); 1548 1549 forkee_status_stopped(status, SIGSTOP); 1550 1551 DPRINTF("Resume parent with PT_DETACH\n"); 1552 FORKEE_ASSERT(ptrace(PT_DETACH, getppid(), (void *)1, 0) 1553 != -1); 1554 1555 /* Tell parent we are ready */ 1556 CHILD_TO_PARENT("Message 1", parent_tracee, msg); 1557 1558 _exit(exitval_tracer); 1559 } 1560 1561 DPRINTF("Wait for the tracer to become ready\n"); 1562 PARENT_TO_CHILD("Message 1", parent_tracee, msg); 1563 1564 if (stopped) { 1565 DPRINTF("Stop self PID %d\n", getpid()); 1566 SYSCALL_REQUIRE(raise(SIGSTOP) != -1); 1567 } 1568 1569 DPRINTF("Allow the tracer to exit now\n"); 1570 PARENT_FROM_CHILD("Message 1", parent_tracee, msg); 1571 1572 DPRINTF("Wait for tracer to exit with %s()\n", TWAIT_FNAME); 1573 TWAIT_REQUIRE_SUCCESS( 1574 wpid = TWAIT_GENERIC(tracer, &status, 0), tracer); 1575 1576 validate_status_exited(status, exitval_tracer); 1577 1578 DPRINTF("Before calling %s() for tracer\n", TWAIT_FNAME); 1579 TWAIT_REQUIRE_FAILURE(ECHILD, 1580 wpid = TWAIT_GENERIC(tracer, &status, 0)); 1581 1582 msg_close(&parent_tracee); 1583} 1584 1585ATF_TC(child_attach_to_its_parent); 1586ATF_TC_HEAD(child_attach_to_its_parent, tc) 1587{ 1588 atf_tc_set_md_var(tc, "descr", 1589 "Assert that tracer child can PT_ATTACH to its parent"); 1590} 1591 1592ATF_TC_BODY(child_attach_to_its_parent, tc) 1593{ 1594 1595 child_attach_to_its_parent(false); 1596} 1597 1598ATF_TC(child_attach_to_its_stopped_parent); 1599ATF_TC_HEAD(child_attach_to_its_stopped_parent, tc) 1600{ 1601 atf_tc_set_md_var(tc, "descr", 1602 "Assert that tracer child can PT_ATTACH to its stopped parent"); 1603} 1604 1605ATF_TC_BODY(child_attach_to_its_stopped_parent, tc) 1606{ 1607 /* 1608 * The ATF framework (atf-run) does not tolerate raise(SIGSTOP), as 1609 * this causes a pipe (established from atf-run) to be broken. 1610 * atf-run uses this mechanism to monitor whether a test is alive. 1611 * 1612 * As a workaround spawn this test as a subprocess. 1613 */ 1614 1615 const int exitval = 15; 1616 pid_t child, wpid; 1617#if defined(TWAIT_HAVE_STATUS) 1618 int status; 1619#endif 1620 1621 SYSCALL_REQUIRE((child = fork()) != -1); 1622 if (child == 0) { 1623 child_attach_to_its_parent(true); 1624 _exit(exitval); 1625 } else { 1626 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1627 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1628 1629 validate_status_exited(status, exitval); 1630 1631 DPRINTF("Before calling %s() for the exited child\n", TWAIT_FNAME); 1632 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1633 } 1634} 1635 1636/// ---------------------------------------------------------------------------- 1637 1638#if defined(TWAIT_HAVE_PID) 1639 1640enum tracee_sees_its_original_parent_type { 1641 TRACEE_SEES_ITS_ORIGINAL_PARENT_GETPPID, 1642 TRACEE_SEES_ITS_ORIGINAL_PARENT_SYSCTL_KINFO_PROC2, 1643 TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS 1644}; 1645 1646static void 1647tracee_sees_its_original_parent(enum tracee_sees_its_original_parent_type type) 1648{ 1649 struct msg_fds parent_tracer, parent_tracee; 1650 const int exitval_tracee = 5; 1651 const int exitval_tracer = 10; 1652 pid_t parent, tracee, tracer, wpid; 1653 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 1654#if defined(TWAIT_HAVE_STATUS) 1655 int status; 1656#endif 1657 /* sysctl(3) - kinfo_proc2 */ 1658 int name[CTL_MAXNAME]; 1659 struct kinfo_proc2 kp; 1660 size_t len = sizeof(kp); 1661 unsigned int namelen; 1662 1663 /* procfs - status */ 1664 FILE *fp; 1665 struct stat st; 1666 const char *fname = "/proc/curproc/status"; 1667 char s_executable[MAXPATHLEN]; 1668 int s_pid, s_ppid; 1669 int rv; 1670 1671 if (type == TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS) { 1672 SYSCALL_REQUIRE( 1673 (rv = stat(fname, &st)) == 0 || (errno == ENOENT)); 1674 if (rv != 0) 1675 atf_tc_skip("/proc/curproc/status not found"); 1676 } 1677 1678 DPRINTF("Spawn tracee\n"); 1679 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 1680 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 1681 tracee = atf_utils_fork(); 1682 if (tracee == 0) { 1683 parent = getppid(); 1684 1685 /* Emit message to the parent */ 1686 CHILD_TO_PARENT("tracee ready", parent_tracee, msg); 1687 CHILD_FROM_PARENT("exit tracee", parent_tracee, msg); 1688 1689 switch (type) { 1690 case TRACEE_SEES_ITS_ORIGINAL_PARENT_GETPPID: 1691 FORKEE_ASSERT_EQ(parent, getppid()); 1692 break; 1693 case TRACEE_SEES_ITS_ORIGINAL_PARENT_SYSCTL_KINFO_PROC2: 1694 namelen = 0; 1695 name[namelen++] = CTL_KERN; 1696 name[namelen++] = KERN_PROC2; 1697 name[namelen++] = KERN_PROC_PID; 1698 name[namelen++] = getpid(); 1699 name[namelen++] = len; 1700 name[namelen++] = 1; 1701 1702 FORKEE_ASSERT_EQ( 1703 sysctl(name, namelen, &kp, &len, NULL, 0), 0); 1704 FORKEE_ASSERT_EQ(parent, kp.p_ppid); 1705 break; 1706 case TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS: 1707 /* 1708 * Format: 1709 * EXECUTABLE PID PPID ... 1710 */ 1711 FORKEE_ASSERT((fp = fopen(fname, "r")) != NULL); 1712 fscanf(fp, "%s %d %d", s_executable, &s_pid, &s_ppid); 1713 FORKEE_ASSERT_EQ(fclose(fp), 0); 1714 FORKEE_ASSERT_EQ(parent, s_ppid); 1715 break; 1716 } 1717 1718 _exit(exitval_tracee); 1719 } 1720 DPRINTF("Wait for child to record its parent identifier (pid)\n"); 1721 PARENT_FROM_CHILD("tracee ready", parent_tracee, msg); 1722 1723 DPRINTF("Spawn debugger\n"); 1724 tracer = atf_utils_fork(); 1725 if (tracer == 0) { 1726 /* No IPC to communicate with the child */ 1727 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 1728 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 1729 1730 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 1731 FORKEE_REQUIRE_SUCCESS( 1732 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1733 1734 forkee_status_stopped(status, SIGSTOP); 1735 1736 /* Resume tracee with PT_CONTINUE */ 1737 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 1738 1739 /* Inform parent that tracer has attached to tracee */ 1740 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 1741 1742 /* Wait for parent to tell use that tracee should have exited */ 1743 CHILD_FROM_PARENT("wait for tracee exit", parent_tracer, msg); 1744 1745 /* Wait for tracee and assert that it exited */ 1746 FORKEE_REQUIRE_SUCCESS( 1747 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 1748 1749 forkee_status_exited(status, exitval_tracee); 1750 1751 DPRINTF("Before exiting of the tracer process\n"); 1752 _exit(exitval_tracer); 1753 } 1754 1755 DPRINTF("Wait for the tracer to attach to the tracee\n"); 1756 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 1757 1758 DPRINTF("Resume the tracee and let it exit\n"); 1759 PARENT_TO_CHILD("exit tracee", parent_tracee, msg); 1760 1761 DPRINTF("Detect that tracee is zombie\n"); 1762 await_zombie(tracee); 1763 1764 DPRINTF("Assert that there is no status about tracee - " 1765 "Tracer must detect zombie first - calling %s()\n", TWAIT_FNAME); 1766 TWAIT_REQUIRE_SUCCESS( 1767 wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 0); 1768 1769 DPRINTF("Tell the tracer child should have exited\n"); 1770 PARENT_TO_CHILD("wait for tracee exit", parent_tracer, msg); 1771 1772 DPRINTF("Wait from tracer child to complete waiting for tracee\n"); 1773 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracer, &status, 0), 1774 tracer); 1775 1776 validate_status_exited(status, exitval_tracer); 1777 1778 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 1779 TWAIT_FNAME); 1780 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 1781 tracee); 1782 1783 validate_status_exited(status, exitval_tracee); 1784 1785 msg_close(&parent_tracer); 1786 msg_close(&parent_tracee); 1787} 1788 1789#define TRACEE_SEES_ITS_ORIGINAL_PARENT(test, type, descr) \ 1790ATF_TC(test); \ 1791ATF_TC_HEAD(test, tc) \ 1792{ \ 1793 atf_tc_set_md_var(tc, "descr", \ 1794 "Assert that tracee sees its original parent when being traced " \ 1795 "(check " descr ")"); \ 1796} \ 1797 \ 1798ATF_TC_BODY(test, tc) \ 1799{ \ 1800 \ 1801 tracee_sees_its_original_parent(type); \ 1802} 1803 1804TRACEE_SEES_ITS_ORIGINAL_PARENT( 1805 tracee_sees_its_original_parent_getppid, 1806 TRACEE_SEES_ITS_ORIGINAL_PARENT_GETPPID, 1807 "getppid(2)"); 1808TRACEE_SEES_ITS_ORIGINAL_PARENT( 1809 tracee_sees_its_original_parent_sysctl_kinfo_proc2, 1810 TRACEE_SEES_ITS_ORIGINAL_PARENT_SYSCTL_KINFO_PROC2, 1811 "sysctl(3) and kinfo_proc2"); 1812TRACEE_SEES_ITS_ORIGINAL_PARENT( 1813 tracee_sees_its_original_parent_procfs_status, 1814 TRACEE_SEES_ITS_ORIGINAL_PARENT_PROCFS_STATUS, 1815 "the status file in procfs"); 1816#endif 1817 1818/// ---------------------------------------------------------------------------- 1819 1820static void 1821eventmask_preserved(int event) 1822{ 1823 const int exitval = 5; 1824 const int sigval = SIGSTOP; 1825 pid_t child, wpid; 1826#if defined(TWAIT_HAVE_STATUS) 1827 int status; 1828#endif 1829 ptrace_event_t set_event, get_event; 1830 const int len = sizeof(ptrace_event_t); 1831 1832 DPRINTF("Before forking process PID=%d\n", getpid()); 1833 SYSCALL_REQUIRE((child = fork()) != -1); 1834 if (child == 0) { 1835 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1836 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1837 1838 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1839 FORKEE_ASSERT(raise(sigval) == 0); 1840 1841 DPRINTF("Before exiting of the child process\n"); 1842 _exit(exitval); 1843 } 1844 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1845 1846 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1847 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1848 1849 validate_status_stopped(status, sigval); 1850 1851 set_event.pe_set_event = event; 1852 SYSCALL_REQUIRE( 1853 ptrace(PT_SET_EVENT_MASK, child, &set_event, len) != -1); 1854 SYSCALL_REQUIRE( 1855 ptrace(PT_GET_EVENT_MASK, child, &get_event, len) != -1); 1856 ATF_REQUIRE(memcmp(&set_event, &get_event, len) == 0); 1857 1858 DPRINTF("Before resuming the child process where it left off and " 1859 "without signal to be sent\n"); 1860 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 1861 1862 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1863 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1864 1865 validate_status_exited(status, exitval); 1866 1867 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1868 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 1869} 1870 1871#define EVENTMASK_PRESERVED(test, event) \ 1872ATF_TC(test); \ 1873ATF_TC_HEAD(test, tc) \ 1874{ \ 1875 atf_tc_set_md_var(tc, "descr", \ 1876 "Verify that eventmask " #event " is preserved"); \ 1877} \ 1878 \ 1879ATF_TC_BODY(test, tc) \ 1880{ \ 1881 \ 1882 eventmask_preserved(event); \ 1883} 1884 1885EVENTMASK_PRESERVED(eventmask_preserved_empty, 0) 1886EVENTMASK_PRESERVED(eventmask_preserved_fork, PTRACE_FORK) 1887EVENTMASK_PRESERVED(eventmask_preserved_vfork, PTRACE_VFORK) 1888EVENTMASK_PRESERVED(eventmask_preserved_vfork_done, PTRACE_VFORK_DONE) 1889EVENTMASK_PRESERVED(eventmask_preserved_lwp_create, PTRACE_LWP_CREATE) 1890EVENTMASK_PRESERVED(eventmask_preserved_lwp_exit, PTRACE_LWP_EXIT) 1891 1892/// ---------------------------------------------------------------------------- 1893 1894static void 1895fork_body(pid_t (*fn)(void), bool trackfork, bool trackvfork, 1896 bool trackvforkdone, bool detachchild, bool detachparent) 1897{ 1898 const int exitval = 5; 1899 const int exitval2 = 15; 1900 const int sigval = SIGSTOP; 1901 pid_t child, child2 = 0, wpid; 1902#if defined(TWAIT_HAVE_STATUS) 1903 int status; 1904#endif 1905 ptrace_state_t state; 1906 const int slen = sizeof(state); 1907 ptrace_event_t event; 1908 const int elen = sizeof(event); 1909 1910 DPRINTF("Before forking process PID=%d\n", getpid()); 1911 SYSCALL_REQUIRE((child = fork()) != -1); 1912 if (child == 0) { 1913 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 1914 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 1915 1916 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 1917 FORKEE_ASSERT(raise(sigval) == 0); 1918 1919 FORKEE_ASSERT((child2 = (fn)()) != -1); 1920 1921 if (child2 == 0) 1922 _exit(exitval2); 1923 1924 FORKEE_REQUIRE_SUCCESS 1925 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 1926 1927 forkee_status_exited(status, exitval2); 1928 1929 DPRINTF("Before exiting of the child process\n"); 1930 _exit(exitval); 1931 } 1932 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 1933 1934 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 1935 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 1936 1937 validate_status_stopped(status, sigval); 1938 1939 DPRINTF("Set 0%s%s%s in EVENT_MASK for the child %d\n", 1940 trackfork ? "|PTRACE_FORK" : "", 1941 trackvfork ? "|PTRACE_VFORK" : "", 1942 trackvforkdone ? "|PTRACE_VFORK_DONE" : "", child); 1943 event.pe_set_event = 0; 1944 if (trackfork) 1945 event.pe_set_event |= PTRACE_FORK; 1946 if (trackvfork) 1947 event.pe_set_event |= PTRACE_VFORK; 1948 if (trackvforkdone) 1949 event.pe_set_event |= PTRACE_VFORK_DONE; 1950 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 1951 1952 DPRINTF("Before resuming the child process where it left off and " 1953 "without signal to be sent\n"); 1954 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 1955 1956#if defined(TWAIT_HAVE_PID) 1957 if ((trackfork && fn == fork) || (trackvfork && fn == vfork)) { 1958 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 1959 child); 1960 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 1961 child); 1962 1963 validate_status_stopped(status, SIGTRAP); 1964 1965 SYSCALL_REQUIRE( 1966 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 1967 if (trackfork && fn == fork) { 1968 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 1969 PTRACE_FORK); 1970 } 1971 if (trackvfork && fn == vfork) { 1972 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 1973 PTRACE_VFORK); 1974 } 1975 1976 child2 = state.pe_other_pid; 1977 DPRINTF("Reported ptrace event with forkee %d\n", child2); 1978 1979 DPRINTF("Before calling %s() for the forkee %d of the child " 1980 "%d\n", TWAIT_FNAME, child2, child); 1981 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 1982 child2); 1983 1984 validate_status_stopped(status, SIGTRAP); 1985 1986 SYSCALL_REQUIRE( 1987 ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 1988 if (trackfork && fn == fork) { 1989 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK, 1990 PTRACE_FORK); 1991 } 1992 if (trackvfork && fn == vfork) { 1993 ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK, 1994 PTRACE_VFORK); 1995 } 1996 1997 ATF_REQUIRE_EQ(state.pe_other_pid, child); 1998 1999 DPRINTF("Before resuming the forkee process where it left off " 2000 "and without signal to be sent\n"); 2001 SYSCALL_REQUIRE( 2002 ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 2003 2004 DPRINTF("Before resuming the child process where it left off " 2005 "and without signal to be sent\n"); 2006 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2007 } 2008#endif 2009 2010 if (trackvforkdone && fn == vfork) { 2011 DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME, 2012 child); 2013 TWAIT_REQUIRE_SUCCESS( 2014 wpid = TWAIT_GENERIC(child, &status, 0), child); 2015 2016 validate_status_stopped(status, SIGTRAP); 2017 2018 SYSCALL_REQUIRE( 2019 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 2020 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE); 2021 2022 child2 = state.pe_other_pid; 2023 DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n", 2024 child2); 2025 2026 DPRINTF("Before resuming the child process where it left off " 2027 "and without signal to be sent\n"); 2028 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2029 } 2030 2031#if defined(TWAIT_HAVE_PID) 2032 if ((trackfork && fn == fork) || (trackvfork && fn == vfork)) { 2033 DPRINTF("Before calling %s() for the forkee - expected exited" 2034 "\n", TWAIT_FNAME); 2035 TWAIT_REQUIRE_SUCCESS( 2036 wpid = TWAIT_GENERIC(child2, &status, 0), child2); 2037 2038 validate_status_exited(status, exitval2); 2039 2040 DPRINTF("Before calling %s() for the forkee - expected no " 2041 "process\n", TWAIT_FNAME); 2042 TWAIT_REQUIRE_FAILURE(ECHILD, 2043 wpid = TWAIT_GENERIC(child2, &status, 0)); 2044 } 2045#endif 2046 2047 DPRINTF("Before calling %s() for the child - expected stopped " 2048 "SIGCHLD\n", TWAIT_FNAME); 2049 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2050 2051 validate_status_stopped(status, SIGCHLD); 2052 2053 DPRINTF("Before resuming the child process where it left off and " 2054 "without signal to be sent\n"); 2055 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2056 2057 DPRINTF("Before calling %s() for the child - expected exited\n", 2058 TWAIT_FNAME); 2059 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2060 2061 validate_status_exited(status, exitval); 2062 2063 DPRINTF("Before calling %s() for the child - expected no process\n", 2064 TWAIT_FNAME); 2065 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2066} 2067 2068#define FORK_TEST(name,descr,fun,tfork,tvfork,tvforkdone,detchild,detparent) \ 2069ATF_TC(name); \ 2070ATF_TC_HEAD(name, tc) \ 2071{ \ 2072 atf_tc_set_md_var(tc, "descr", descr); \ 2073} \ 2074 \ 2075ATF_TC_BODY(name, tc) \ 2076{ \ 2077 \ 2078 fork_body(fun, tfork, tvfork, tvforkdone, detchild, detparent); \ 2079} 2080 2081#define F false 2082#define T true 2083 2084#define F_IF__0(x) 2085#define F_IF__1(x) x 2086#define F_IF__(x,y) F_IF__ ## x (y) 2087#define F_IF_(x,y) F_IF__(x,y) 2088#define F_IF(x,y) F_IF_(x,y) 2089 2090#define DSCR(function,forkbit,vforkbit,vforkdonebit,dchildbit,dparentbit) \ 2091 "Verify " #function "(2) called with 0" \ 2092 F_IF(forkbit,"|PTRACE_FORK") \ 2093 F_IF(vforkbit,"|PTRACE_VFORK") \ 2094 F_IF(vforkdonebit,"|PTRACE_VFORK_DONE") \ 2095 " in EVENT_MASK." \ 2096 F_IF(dchildbit," Detach child in this test.") \ 2097 F_IF(dparentbit," Detach parent in this test.") 2098 2099FORK_TEST(fork1, DSCR(fork,0,0,0,0,0), fork, F, F, F, F, F) 2100#if defined(TWAIT_HAVE_PID) 2101FORK_TEST(fork2, DSCR(fork,1,0,0,0,0), fork, T, F, F, F, F) 2102FORK_TEST(fork3, DSCR(fork,0,1,0,0,0), fork, F, T, F, F, F) 2103FORK_TEST(fork4, DSCR(fork,1,1,0,0,0), fork, T, T, F, F, F) 2104#endif 2105FORK_TEST(fork5, DSCR(fork,0,0,1,0,0), fork, F, F, T, F, F) 2106#if defined(TWAIT_HAVE_PID) 2107FORK_TEST(fork6, DSCR(fork,1,0,1,0,0), fork, T, F, T, F, F) 2108FORK_TEST(fork7, DSCR(fork,0,1,1,0,0), fork, F, T, T, F, F) 2109FORK_TEST(fork8, DSCR(fork,1,1,1,0,0), fork, T, T, T, F, F) 2110#endif 2111 2112FORK_TEST(vfork1, DSCR(vfork,0,0,0,0,0), vfork, F, F, F, F, F) 2113#if defined(TWAIT_HAVE_PID) 2114FORK_TEST(vfork2, DSCR(vfork,1,0,0,0,0), vfork, T, F, F, F, F) 2115FORK_TEST(vfork3, DSCR(vfork,0,1,0,0,0), vfork, F, T, F, F, F) 2116FORK_TEST(vfork4, DSCR(vfork,1,1,0,0,0), vfork, T, T, F, F, F) 2117#endif 2118FORK_TEST(vfork5, DSCR(vfork,0,0,1,0,0), vfork, F, F, T, F, F) 2119#if defined(TWAIT_HAVE_PID) 2120FORK_TEST(vfork6, DSCR(vfork,1,0,1,0,0), vfork, T, F, T, F, F) 2121FORK_TEST(vfork7, DSCR(vfork,0,1,1,0,0), vfork, F, T, T, F, F) 2122FORK_TEST(vfork8, DSCR(vfork,1,1,1,0,0), vfork, T, T, T, F, F) 2123#endif 2124 2125/// ---------------------------------------------------------------------------- 2126 2127enum bytes_transfer_type { 2128 BYTES_TRANSFER_DATA, 2129 BYTES_TRANSFER_DATAIO, 2130 BYTES_TRANSFER_TEXT, 2131 BYTES_TRANSFER_TEXTIO, 2132 BYTES_TRANSFER_AUXV 2133}; 2134 2135static int __used 2136bytes_transfer_dummy(int a, int b, int c, int d) 2137{ 2138 int e, f, g, h; 2139 2140 a *= 4; 2141 b += 3; 2142 c -= 2; 2143 d /= 1; 2144 2145 e = strtol("10", NULL, 10); 2146 f = strtol("20", NULL, 10); 2147 g = strtol("30", NULL, 10); 2148 h = strtol("40", NULL, 10); 2149 2150 return (a + b * c - d) + (e * f - g / h); 2151} 2152 2153static void 2154bytes_transfer(int operation, size_t size, enum bytes_transfer_type type) 2155{ 2156 const int exitval = 5; 2157 const int sigval = SIGSTOP; 2158 pid_t child, wpid; 2159 bool skip = false; 2160 2161 int lookup_me = 0; 2162 uint8_t lookup_me8 = 0; 2163 uint16_t lookup_me16 = 0; 2164 uint32_t lookup_me32 = 0; 2165 uint64_t lookup_me64 = 0; 2166 2167 int magic = 0x13579246; 2168 uint8_t magic8 = 0xab; 2169 uint16_t magic16 = 0x1234; 2170 uint32_t magic32 = 0x98765432; 2171 uint64_t magic64 = 0xabcdef0123456789; 2172 2173 struct ptrace_io_desc io; 2174#if defined(TWAIT_HAVE_STATUS) 2175 int status; 2176#endif 2177 /* 513 is just enough, for the purposes of ATF it's good enough */ 2178 AuxInfo ai[513], *aip; 2179 2180 ATF_REQUIRE(size < sizeof(ai)); 2181 2182 /* Prepare variables for .TEXT transfers */ 2183 switch (type) { 2184 case BYTES_TRANSFER_TEXT: 2185 memcpy(&magic, bytes_transfer_dummy, sizeof(magic)); 2186 break; 2187 case BYTES_TRANSFER_TEXTIO: 2188 switch (size) { 2189 case 8: 2190 memcpy(&magic8, bytes_transfer_dummy, sizeof(magic8)); 2191 break; 2192 case 16: 2193 memcpy(&magic16, bytes_transfer_dummy, sizeof(magic16)); 2194 break; 2195 case 32: 2196 memcpy(&magic32, bytes_transfer_dummy, sizeof(magic32)); 2197 break; 2198 case 64: 2199 memcpy(&magic64, bytes_transfer_dummy, sizeof(magic64)); 2200 break; 2201 } 2202 break; 2203 default: 2204 break; 2205 } 2206 2207 /* Prepare variables for PIOD and AUXV transfers */ 2208 switch (type) { 2209 case BYTES_TRANSFER_TEXTIO: 2210 case BYTES_TRANSFER_DATAIO: 2211 io.piod_op = operation; 2212 switch (size) { 2213 case 8: 2214 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 2215 (void *)bytes_transfer_dummy : 2216 &lookup_me8; 2217 io.piod_addr = &lookup_me8; 2218 io.piod_len = sizeof(lookup_me8); 2219 break; 2220 case 16: 2221 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 2222 (void *)bytes_transfer_dummy : 2223 &lookup_me16; 2224 io.piod_addr = &lookup_me16; 2225 io.piod_len = sizeof(lookup_me16); 2226 break; 2227 case 32: 2228 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 2229 (void *)bytes_transfer_dummy : 2230 &lookup_me32; 2231 io.piod_addr = &lookup_me32; 2232 io.piod_len = sizeof(lookup_me32); 2233 break; 2234 case 64: 2235 io.piod_offs = (type == BYTES_TRANSFER_TEXTIO) ? 2236 (void *)bytes_transfer_dummy : 2237 &lookup_me64; 2238 io.piod_addr = &lookup_me64; 2239 io.piod_len = sizeof(lookup_me64); 2240 break; 2241 default: 2242 break; 2243 } 2244 break; 2245 case BYTES_TRANSFER_AUXV: 2246 io.piod_op = operation; 2247 io.piod_offs = 0; 2248 io.piod_addr = ai; 2249 io.piod_len = size; 2250 break; 2251 default: 2252 break; 2253 } 2254 2255 DPRINTF("Before forking process PID=%d\n", getpid()); 2256 SYSCALL_REQUIRE((child = fork()) != -1); 2257 if (child == 0) { 2258 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2259 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2260 2261 switch (type) { 2262 case BYTES_TRANSFER_DATA: 2263 switch (operation) { 2264 case PT_READ_D: 2265 case PT_READ_I: 2266 lookup_me = magic; 2267 break; 2268 default: 2269 break; 2270 } 2271 break; 2272 case BYTES_TRANSFER_DATAIO: 2273 switch (operation) { 2274 case PIOD_READ_D: 2275 case PIOD_READ_I: 2276 switch (size) { 2277 case 8: 2278 lookup_me8 = magic8; 2279 break; 2280 case 16: 2281 lookup_me16 = magic16; 2282 break; 2283 case 32: 2284 lookup_me32 = magic32; 2285 break; 2286 case 64: 2287 lookup_me64 = magic64; 2288 break; 2289 default: 2290 break; 2291 } 2292 break; 2293 default: 2294 break; 2295 } 2296 default: 2297 break; 2298 } 2299 2300 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2301 FORKEE_ASSERT(raise(sigval) == 0); 2302 2303 /* Handle PIOD and PT separately as operation values overlap */ 2304 switch (type) { 2305 case BYTES_TRANSFER_DATA: 2306 switch (operation) { 2307 case PT_WRITE_D: 2308 case PT_WRITE_I: 2309 FORKEE_ASSERT_EQ(lookup_me, magic); 2310 break; 2311 default: 2312 break; 2313 } 2314 break; 2315 case BYTES_TRANSFER_DATAIO: 2316 switch (operation) { 2317 case PIOD_WRITE_D: 2318 case PIOD_WRITE_I: 2319 switch (size) { 2320 case 8: 2321 FORKEE_ASSERT_EQ(lookup_me8, magic8); 2322 break; 2323 case 16: 2324 FORKEE_ASSERT_EQ(lookup_me16, magic16); 2325 break; 2326 case 32: 2327 FORKEE_ASSERT_EQ(lookup_me32, magic32); 2328 break; 2329 case 64: 2330 FORKEE_ASSERT_EQ(lookup_me64, magic64); 2331 break; 2332 default: 2333 break; 2334 } 2335 break; 2336 default: 2337 break; 2338 } 2339 break; 2340 case BYTES_TRANSFER_TEXT: 2341 FORKEE_ASSERT(memcmp(&magic, bytes_transfer_dummy, 2342 sizeof(magic)) == 0); 2343 break; 2344 case BYTES_TRANSFER_TEXTIO: 2345 switch (size) { 2346 case 8: 2347 FORKEE_ASSERT(memcmp(&magic8, 2348 bytes_transfer_dummy, 2349 sizeof(magic8)) == 0); 2350 break; 2351 case 16: 2352 FORKEE_ASSERT(memcmp(&magic16, 2353 bytes_transfer_dummy, 2354 sizeof(magic16)) == 0); 2355 break; 2356 case 32: 2357 FORKEE_ASSERT(memcmp(&magic32, 2358 bytes_transfer_dummy, 2359 sizeof(magic32)) == 0); 2360 break; 2361 case 64: 2362 FORKEE_ASSERT(memcmp(&magic64, 2363 bytes_transfer_dummy, 2364 sizeof(magic64)) == 0); 2365 break; 2366 } 2367 break; 2368 default: 2369 break; 2370 } 2371 2372 DPRINTF("Before exiting of the child process\n"); 2373 _exit(exitval); 2374 } 2375 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2376 2377 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2378 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2379 2380 validate_status_stopped(status, sigval); 2381 2382 /* Check PaX MPROTECT */ 2383 if (!can_we_write_to_text(child)) { 2384 switch (type) { 2385 case BYTES_TRANSFER_TEXTIO: 2386 switch (operation) { 2387 case PIOD_WRITE_D: 2388 case PIOD_WRITE_I: 2389 skip = true; 2390 break; 2391 default: 2392 break; 2393 } 2394 break; 2395 case BYTES_TRANSFER_TEXT: 2396 switch (operation) { 2397 case PT_WRITE_D: 2398 case PT_WRITE_I: 2399 skip = true; 2400 break; 2401 default: 2402 break; 2403 } 2404 break; 2405 default: 2406 break; 2407 } 2408 } 2409 2410 /* Bailout cleanly killing the child process */ 2411 if (skip) { 2412 SYSCALL_REQUIRE(ptrace(PT_KILL, child, (void *)1, 0) != -1); 2413 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2414 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 2415 child); 2416 2417 validate_status_signaled(status, SIGKILL, 0); 2418 2419 atf_tc_skip("PaX MPROTECT setup prevents writes to .text"); 2420 } 2421 2422 DPRINTF("Calling operation to transfer bytes between child=%d and " 2423 "parent=%d\n", child, getpid()); 2424 2425 switch (type) { 2426 case BYTES_TRANSFER_TEXTIO: 2427 case BYTES_TRANSFER_DATAIO: 2428 case BYTES_TRANSFER_AUXV: 2429 switch (operation) { 2430 case PIOD_WRITE_D: 2431 case PIOD_WRITE_I: 2432 switch (size) { 2433 case 8: 2434 lookup_me8 = magic8; 2435 break; 2436 case 16: 2437 lookup_me16 = magic16; 2438 break; 2439 case 32: 2440 lookup_me32 = magic32; 2441 break; 2442 case 64: 2443 lookup_me64 = magic64; 2444 break; 2445 default: 2446 break; 2447 } 2448 break; 2449 default: 2450 break; 2451 } 2452 SYSCALL_REQUIRE(ptrace(PT_IO, child, &io, 0) != -1); 2453 switch (operation) { 2454 case PIOD_READ_D: 2455 case PIOD_READ_I: 2456 switch (size) { 2457 case 8: 2458 ATF_REQUIRE_EQ(lookup_me8, magic8); 2459 break; 2460 case 16: 2461 ATF_REQUIRE_EQ(lookup_me16, magic16); 2462 break; 2463 case 32: 2464 ATF_REQUIRE_EQ(lookup_me32, magic32); 2465 break; 2466 case 64: 2467 ATF_REQUIRE_EQ(lookup_me64, magic64); 2468 break; 2469 default: 2470 break; 2471 } 2472 break; 2473 case PIOD_READ_AUXV: 2474 DPRINTF("Asserting that AUXV length (%zu) is > 0\n", 2475 io.piod_len); 2476 ATF_REQUIRE(io.piod_len > 0); 2477 for (aip = ai; aip->a_type != AT_NULL; aip++) 2478 DPRINTF("a_type=%#llx a_v=%#llx\n", 2479 (long long int)aip->a_type, 2480 (long long int)aip->a_v); 2481 break; 2482 default: 2483 break; 2484 } 2485 break; 2486 case BYTES_TRANSFER_TEXT: 2487 switch (operation) { 2488 case PT_READ_D: 2489 case PT_READ_I: 2490 errno = 0; 2491 lookup_me = ptrace(operation, child, 2492 bytes_transfer_dummy, 0); 2493 ATF_REQUIRE_EQ(lookup_me, magic); 2494 SYSCALL_REQUIRE_ERRNO(errno, 0); 2495 break; 2496 case PT_WRITE_D: 2497 case PT_WRITE_I: 2498 SYSCALL_REQUIRE(ptrace(operation, child, 2499 bytes_transfer_dummy, magic) 2500 != -1); 2501 break; 2502 default: 2503 break; 2504 } 2505 break; 2506 case BYTES_TRANSFER_DATA: 2507 switch (operation) { 2508 case PT_READ_D: 2509 case PT_READ_I: 2510 errno = 0; 2511 lookup_me = ptrace(operation, child, &lookup_me, 0); 2512 ATF_REQUIRE_EQ(lookup_me, magic); 2513 SYSCALL_REQUIRE_ERRNO(errno, 0); 2514 break; 2515 case PT_WRITE_D: 2516 case PT_WRITE_I: 2517 lookup_me = magic; 2518 SYSCALL_REQUIRE(ptrace(operation, child, &lookup_me, 2519 magic) != -1); 2520 break; 2521 default: 2522 break; 2523 } 2524 break; 2525 default: 2526 break; 2527 } 2528 2529 DPRINTF("Before resuming the child process where it left off and " 2530 "without signal to be sent\n"); 2531 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2532 2533 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2534 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2535 2536 validate_status_exited(status, exitval); 2537 2538 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2539 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2540} 2541 2542#define BYTES_TRANSFER(test, operation, size, type) \ 2543ATF_TC(test); \ 2544ATF_TC_HEAD(test, tc) \ 2545{ \ 2546 atf_tc_set_md_var(tc, "descr", \ 2547 "Verify bytes transfer operation" #operation " and size " #size \ 2548 " of type " #type); \ 2549} \ 2550 \ 2551ATF_TC_BODY(test, tc) \ 2552{ \ 2553 \ 2554 bytes_transfer(operation, size, BYTES_TRANSFER_##type); \ 2555} 2556 2557// DATA 2558 2559BYTES_TRANSFER(bytes_transfer_piod_read_d_8, PIOD_READ_D, 8, DATAIO) 2560BYTES_TRANSFER(bytes_transfer_piod_read_d_16, PIOD_READ_D, 16, DATAIO) 2561BYTES_TRANSFER(bytes_transfer_piod_read_d_32, PIOD_READ_D, 32, DATAIO) 2562BYTES_TRANSFER(bytes_transfer_piod_read_d_64, PIOD_READ_D, 64, DATAIO) 2563 2564BYTES_TRANSFER(bytes_transfer_piod_read_i_8, PIOD_READ_I, 8, DATAIO) 2565BYTES_TRANSFER(bytes_transfer_piod_read_i_16, PIOD_READ_I, 16, DATAIO) 2566BYTES_TRANSFER(bytes_transfer_piod_read_i_32, PIOD_READ_I, 32, DATAIO) 2567BYTES_TRANSFER(bytes_transfer_piod_read_i_64, PIOD_READ_I, 64, DATAIO) 2568 2569BYTES_TRANSFER(bytes_transfer_piod_write_d_8, PIOD_WRITE_D, 8, DATAIO) 2570BYTES_TRANSFER(bytes_transfer_piod_write_d_16, PIOD_WRITE_D, 16, DATAIO) 2571BYTES_TRANSFER(bytes_transfer_piod_write_d_32, PIOD_WRITE_D, 32, DATAIO) 2572BYTES_TRANSFER(bytes_transfer_piod_write_d_64, PIOD_WRITE_D, 64, DATAIO) 2573 2574BYTES_TRANSFER(bytes_transfer_piod_write_i_8, PIOD_WRITE_I, 8, DATAIO) 2575BYTES_TRANSFER(bytes_transfer_piod_write_i_16, PIOD_WRITE_I, 16, DATAIO) 2576BYTES_TRANSFER(bytes_transfer_piod_write_i_32, PIOD_WRITE_I, 32, DATAIO) 2577BYTES_TRANSFER(bytes_transfer_piod_write_i_64, PIOD_WRITE_I, 64, DATAIO) 2578 2579BYTES_TRANSFER(bytes_transfer_read_d, PT_READ_D, 32, DATA) 2580BYTES_TRANSFER(bytes_transfer_read_i, PT_READ_I, 32, DATA) 2581BYTES_TRANSFER(bytes_transfer_write_d, PT_WRITE_D, 32, DATA) 2582BYTES_TRANSFER(bytes_transfer_write_i, PT_WRITE_I, 32, DATA) 2583 2584// TEXT 2585 2586BYTES_TRANSFER(bytes_transfer_piod_read_d_8_text, PIOD_READ_D, 8, TEXTIO) 2587BYTES_TRANSFER(bytes_transfer_piod_read_d_16_text, PIOD_READ_D, 16, TEXTIO) 2588BYTES_TRANSFER(bytes_transfer_piod_read_d_32_text, PIOD_READ_D, 32, TEXTIO) 2589BYTES_TRANSFER(bytes_transfer_piod_read_d_64_text, PIOD_READ_D, 64, TEXTIO) 2590 2591BYTES_TRANSFER(bytes_transfer_piod_read_i_8_text, PIOD_READ_I, 8, TEXTIO) 2592BYTES_TRANSFER(bytes_transfer_piod_read_i_16_text, PIOD_READ_I, 16, TEXTIO) 2593BYTES_TRANSFER(bytes_transfer_piod_read_i_32_text, PIOD_READ_I, 32, TEXTIO) 2594BYTES_TRANSFER(bytes_transfer_piod_read_i_64_text, PIOD_READ_I, 64, TEXTIO) 2595 2596BYTES_TRANSFER(bytes_transfer_piod_write_d_8_text, PIOD_WRITE_D, 8, TEXTIO) 2597BYTES_TRANSFER(bytes_transfer_piod_write_d_16_text, PIOD_WRITE_D, 16, TEXTIO) 2598BYTES_TRANSFER(bytes_transfer_piod_write_d_32_text, PIOD_WRITE_D, 32, TEXTIO) 2599BYTES_TRANSFER(bytes_transfer_piod_write_d_64_text, PIOD_WRITE_D, 64, TEXTIO) 2600 2601BYTES_TRANSFER(bytes_transfer_piod_write_i_8_text, PIOD_WRITE_I, 8, TEXTIO) 2602BYTES_TRANSFER(bytes_transfer_piod_write_i_16_text, PIOD_WRITE_I, 16, TEXTIO) 2603BYTES_TRANSFER(bytes_transfer_piod_write_i_32_text, PIOD_WRITE_I, 32, TEXTIO) 2604BYTES_TRANSFER(bytes_transfer_piod_write_i_64_text, PIOD_WRITE_I, 64, TEXTIO) 2605 2606BYTES_TRANSFER(bytes_transfer_read_d_text, PT_READ_D, 32, TEXT) 2607BYTES_TRANSFER(bytes_transfer_read_i_text, PT_READ_I, 32, TEXT) 2608BYTES_TRANSFER(bytes_transfer_write_d_text, PT_WRITE_D, 32, TEXT) 2609BYTES_TRANSFER(bytes_transfer_write_i_text, PT_WRITE_I, 32, TEXT) 2610 2611// AUXV 2612 2613BYTES_TRANSFER(bytes_transfer_piod_read_auxv, PIOD_READ_AUXV, 4096, AUXV) 2614 2615/// ---------------------------------------------------------------------------- 2616 2617#if defined(HAVE_GPREGS) || defined(HAVE_FPREGS) 2618static void 2619access_regs(const char *regset, const char *aux) 2620{ 2621 const int exitval = 5; 2622 const int sigval = SIGSTOP; 2623 pid_t child, wpid; 2624#if defined(TWAIT_HAVE_STATUS) 2625 int status; 2626#endif 2627#if defined(HAVE_GPREGS) 2628 struct reg gpr; 2629 register_t rgstr; 2630#endif 2631#if defined(HAVE_FPREGS) 2632 struct fpreg fpr; 2633#endif 2634 2635#if !defined(HAVE_GPREGS) 2636 if (strcmp(regset, "regs") == 0) 2637 atf_tc_fail("Impossible test scenario!"); 2638#endif 2639 2640#if !defined(HAVE_FPREGS) 2641 if (strcmp(regset, "fpregs") == 0) 2642 atf_tc_fail("Impossible test scenario!"); 2643#endif 2644 2645 DPRINTF("Before forking process PID=%d\n", getpid()); 2646 SYSCALL_REQUIRE((child = fork()) != -1); 2647 if (child == 0) { 2648 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2649 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2650 2651 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2652 FORKEE_ASSERT(raise(sigval) == 0); 2653 2654 DPRINTF("Before exiting of the child process\n"); 2655 _exit(exitval); 2656 } 2657 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2658 2659 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2660 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2661 2662 validate_status_stopped(status, sigval); 2663 2664#if defined(HAVE_GPREGS) 2665 if (strcmp(regset, "regs") == 0) { 2666 DPRINTF("Call GETREGS for the child process\n"); 2667 SYSCALL_REQUIRE(ptrace(PT_GETREGS, child, &gpr, 0) != -1); 2668 2669 if (strcmp(aux, "none") == 0) { 2670 DPRINTF("Retrieved registers\n"); 2671 } else if (strcmp(aux, "pc") == 0) { 2672 rgstr = PTRACE_REG_PC(&gpr); 2673 DPRINTF("Retrieved %" PRIxREGISTER "\n", rgstr); 2674 } else if (strcmp(aux, "set_pc") == 0) { 2675 rgstr = PTRACE_REG_PC(&gpr); 2676 PTRACE_REG_SET_PC(&gpr, rgstr); 2677 } else if (strcmp(aux, "sp") == 0) { 2678 rgstr = PTRACE_REG_SP(&gpr); 2679 DPRINTF("Retrieved %" PRIxREGISTER "\n", rgstr); 2680 } else if (strcmp(aux, "intrv") == 0) { 2681 rgstr = PTRACE_REG_INTRV(&gpr); 2682 DPRINTF("Retrieved %" PRIxREGISTER "\n", rgstr); 2683 } else if (strcmp(aux, "setregs") == 0) { 2684 DPRINTF("Call SETREGS for the child process\n"); 2685 SYSCALL_REQUIRE( 2686 ptrace(PT_GETREGS, child, &gpr, 0) != -1); 2687 } 2688 } 2689#endif 2690 2691#if defined(HAVE_FPREGS) 2692 if (strcmp(regset, "fpregs") == 0) { 2693 DPRINTF("Call GETFPREGS for the child process\n"); 2694 SYSCALL_REQUIRE(ptrace(PT_GETFPREGS, child, &fpr, 0) != -1); 2695 2696 if (strcmp(aux, "getfpregs") == 0) { 2697 DPRINTF("Retrieved FP registers\n"); 2698 } else if (strcmp(aux, "setfpregs") == 0) { 2699 DPRINTF("Call SETFPREGS for the child\n"); 2700 SYSCALL_REQUIRE( 2701 ptrace(PT_SETFPREGS, child, &fpr, 0) != -1); 2702 } 2703 } 2704#endif 2705 2706 DPRINTF("Before resuming the child process where it left off and " 2707 "without signal to be sent\n"); 2708 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2709 2710 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2711 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2712 2713 validate_status_exited(status, exitval); 2714 2715 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2716 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2717} 2718 2719#define ACCESS_REGS(test, regset, aux) \ 2720ATF_TC(test); \ 2721ATF_TC_HEAD(test, tc) \ 2722{ \ 2723 atf_tc_set_md_var(tc, "descr", \ 2724 "Verify " regset " with auxiliary operation: " aux); \ 2725} \ 2726 \ 2727ATF_TC_BODY(test, tc) \ 2728{ \ 2729 \ 2730 access_regs(regset, aux); \ 2731} 2732#endif 2733 2734#if defined(HAVE_GPREGS) 2735ACCESS_REGS(access_regs1, "regs", "none") 2736ACCESS_REGS(access_regs2, "regs", "pc") 2737ACCESS_REGS(access_regs3, "regs", "set_pc") 2738ACCESS_REGS(access_regs4, "regs", "sp") 2739ACCESS_REGS(access_regs5, "regs", "intrv") 2740ACCESS_REGS(access_regs6, "regs", "setregs") 2741#endif 2742#if defined(HAVE_FPREGS) 2743ACCESS_REGS(access_fpregs1, "fpregs", "getfpregs") 2744ACCESS_REGS(access_fpregs2, "fpregs", "setfpregs") 2745#endif 2746 2747/// ---------------------------------------------------------------------------- 2748 2749#if defined(PT_STEP) 2750static void 2751ptrace_step(int N, int setstep) 2752{ 2753 const int exitval = 5; 2754 const int sigval = SIGSTOP; 2755 pid_t child, wpid; 2756#if defined(TWAIT_HAVE_STATUS) 2757 int status; 2758#endif 2759 int happy; 2760 2761#if defined(__arm__) 2762 /* PT_STEP not supported on arm 32-bit */ 2763 atf_tc_expect_fail("PR kern/52119"); 2764#endif 2765 2766 DPRINTF("Before forking process PID=%d\n", getpid()); 2767 SYSCALL_REQUIRE((child = fork()) != -1); 2768 if (child == 0) { 2769 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2770 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2771 2772 happy = check_happy(999); 2773 2774 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2775 FORKEE_ASSERT(raise(sigval) == 0); 2776 2777 FORKEE_ASSERT_EQ(happy, check_happy(999)); 2778 2779 DPRINTF("Before exiting of the child process\n"); 2780 _exit(exitval); 2781 } 2782 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2783 2784 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2785 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2786 2787 validate_status_stopped(status, sigval); 2788 2789 while (N --> 0) { 2790 if (setstep) { 2791 DPRINTF("Before resuming the child process where it " 2792 "left off and without signal to be sent (use " 2793 "PT_SETSTEP and PT_CONTINUE)\n"); 2794 SYSCALL_REQUIRE(ptrace(PT_SETSTEP, child, 0, 0) != -1); 2795 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) 2796 != -1); 2797 } else { 2798 DPRINTF("Before resuming the child process where it " 2799 "left off and without signal to be sent (use " 2800 "PT_STEP)\n"); 2801 SYSCALL_REQUIRE(ptrace(PT_STEP, child, (void *)1, 0) 2802 != -1); 2803 } 2804 2805 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2806 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), 2807 child); 2808 2809 validate_status_stopped(status, SIGTRAP); 2810 2811 if (setstep) { 2812 SYSCALL_REQUIRE(ptrace(PT_CLEARSTEP, child, 0, 0) != -1); 2813 } 2814 } 2815 2816 DPRINTF("Before resuming the child process where it left off and " 2817 "without signal to be sent\n"); 2818 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 2819 2820 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2821 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2822 2823 validate_status_exited(status, exitval); 2824 2825 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2826 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2827} 2828 2829#define PTRACE_STEP(test, N, setstep) \ 2830ATF_TC(test); \ 2831ATF_TC_HEAD(test, tc) \ 2832{ \ 2833 atf_tc_set_md_var(tc, "descr", \ 2834 "Verify " #N " (PT_SETSTEP set to: " #setstep ")"); \ 2835} \ 2836 \ 2837ATF_TC_BODY(test, tc) \ 2838{ \ 2839 \ 2840 ptrace_step(N, setstep); \ 2841} 2842 2843PTRACE_STEP(step1, 1, 0) 2844PTRACE_STEP(step2, 2, 0) 2845PTRACE_STEP(step3, 3, 0) 2846PTRACE_STEP(step4, 4, 0) 2847PTRACE_STEP(setstep1, 1, 1) 2848PTRACE_STEP(setstep2, 2, 1) 2849PTRACE_STEP(setstep3, 3, 1) 2850PTRACE_STEP(setstep4, 4, 1) 2851#endif 2852 2853/// ---------------------------------------------------------------------------- 2854 2855static void 2856ptrace_kill(const char *type) 2857{ 2858 const int sigval = SIGSTOP; 2859 pid_t child, wpid; 2860#if defined(TWAIT_HAVE_STATUS) 2861 int status; 2862#endif 2863 2864 DPRINTF("Before forking process PID=%d\n", getpid()); 2865 SYSCALL_REQUIRE((child = fork()) != -1); 2866 if (child == 0) { 2867 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2868 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2869 2870 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2871 FORKEE_ASSERT(raise(sigval) == 0); 2872 2873 /* NOTREACHED */ 2874 FORKEE_ASSERTX(0 && 2875 "Child should be terminated by a signal from its parent"); 2876 } 2877 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2878 2879 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2880 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2881 2882 validate_status_stopped(status, sigval); 2883 2884 DPRINTF("Before killing the child process with %s\n", type); 2885 if (strcmp(type, "ptrace(PT_KILL)") == 0) { 2886 SYSCALL_REQUIRE(ptrace(PT_KILL, child, (void*)1, 0) != -1); 2887 } else if (strcmp(type, "kill(SIGKILL)") == 0) { 2888 kill(child, SIGKILL); 2889 } else if (strcmp(type, "killpg(SIGKILL)") == 0) { 2890 setpgid(child, 0); 2891 killpg(getpgid(child), SIGKILL); 2892 } 2893 2894 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2895 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2896 2897 validate_status_signaled(status, SIGKILL, 0); 2898 2899 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2900 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 2901} 2902 2903#define PTRACE_KILL(test, type) \ 2904ATF_TC(test); \ 2905ATF_TC_HEAD(test, tc) \ 2906{ \ 2907 atf_tc_set_md_var(tc, "descr", \ 2908 "Verify killing the child with " type); \ 2909} \ 2910 \ 2911ATF_TC_BODY(test, tc) \ 2912{ \ 2913 \ 2914 ptrace_kill(type); \ 2915} 2916 2917// PT_CONTINUE with SIGKILL is covered by traceme_sendsignal_simple1 2918PTRACE_KILL(kill1, "ptrace(PT_KILL)") 2919PTRACE_KILL(kill2, "kill(SIGKILL)") 2920PTRACE_KILL(kill3, "killpg(SIGKILL)") 2921 2922/// ---------------------------------------------------------------------------- 2923 2924static void 2925traceme_lwpinfo(const int threads) 2926{ 2927 const int sigval = SIGSTOP; 2928 const int sigval2 = SIGINT; 2929 pid_t child, wpid; 2930#if defined(TWAIT_HAVE_STATUS) 2931 int status; 2932#endif 2933 struct ptrace_lwpinfo lwp = {0, 0}; 2934 struct ptrace_siginfo info; 2935 2936 /* Maximum number of supported threads in this test */ 2937 pthread_t t[3]; 2938 int n, rv; 2939 2940 ATF_REQUIRE((int)__arraycount(t) >= threads); 2941 2942 DPRINTF("Before forking process PID=%d\n", getpid()); 2943 SYSCALL_REQUIRE((child = fork()) != -1); 2944 if (child == 0) { 2945 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 2946 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 2947 2948 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 2949 FORKEE_ASSERT(raise(sigval) == 0); 2950 2951 for (n = 0; n < threads; n++) { 2952 rv = pthread_create(&t[n], NULL, infinite_thread, NULL); 2953 FORKEE_ASSERT(rv == 0); 2954 } 2955 2956 DPRINTF("Before raising %s from child\n", strsignal(sigval2)); 2957 FORKEE_ASSERT(raise(sigval2) == 0); 2958 2959 /* NOTREACHED */ 2960 FORKEE_ASSERTX(0 && "Not reached"); 2961 } 2962 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 2963 2964 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 2965 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 2966 2967 validate_status_stopped(status, sigval); 2968 2969 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 2970 SYSCALL_REQUIRE( 2971 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 2972 2973 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 2974 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 2975 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 2976 info.psi_siginfo.si_errno); 2977 2978 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 2979 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 2980 2981 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 2982 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 2983 2984 DPRINTF("Assert that there exists a single thread only\n"); 2985 ATF_REQUIRE(lwp.pl_lwpid > 0); 2986 2987 DPRINTF("Assert that lwp thread %d received event PL_EVENT_SIGNAL\n", 2988 lwp.pl_lwpid); 2989 FORKEE_ASSERT_EQ(lwp.pl_event, PL_EVENT_SIGNAL); 2990 2991 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 2992 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 2993 2994 DPRINTF("Assert that there exists a single thread only\n"); 2995 ATF_REQUIRE_EQ(lwp.pl_lwpid, 0); 2996 2997 DPRINTF("Before resuming the child process where it left off and " 2998 "without signal to be sent\n"); 2999 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3000 3001 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3002 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3003 3004 validate_status_stopped(status, sigval2); 3005 3006 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child"); 3007 SYSCALL_REQUIRE( 3008 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 3009 3010 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 3011 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 3012 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 3013 info.psi_siginfo.si_errno); 3014 3015 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval2); 3016 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 3017 3018 memset(&lwp, 0, sizeof(lwp)); 3019 3020 for (n = 0; n <= threads; n++) { 3021 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 3022 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 3023 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 3024 3025 DPRINTF("Assert that the thread exists\n"); 3026 ATF_REQUIRE(lwp.pl_lwpid > 0); 3027 3028 DPRINTF("Assert that lwp thread %d received expected event\n", 3029 lwp.pl_lwpid); 3030 FORKEE_ASSERT_EQ(lwp.pl_event, info.psi_lwpid == lwp.pl_lwpid ? 3031 PL_EVENT_SIGNAL : PL_EVENT_NONE); 3032 } 3033 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 3034 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &lwp, sizeof(lwp)) != -1); 3035 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 3036 3037 DPRINTF("Assert that there are no more threads\n"); 3038 ATF_REQUIRE_EQ(lwp.pl_lwpid, 0); 3039 3040 DPRINTF("Before resuming the child process where it left off and " 3041 "without signal to be sent\n"); 3042 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, SIGKILL) != -1); 3043 3044 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3045 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3046 3047 validate_status_signaled(status, SIGKILL, 0); 3048 3049 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3050 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3051} 3052 3053#define TRACEME_LWPINFO(test, threads) \ 3054ATF_TC(test); \ 3055ATF_TC_HEAD(test, tc) \ 3056{ \ 3057 atf_tc_set_md_var(tc, "descr", \ 3058 "Verify LWPINFO with the child with " #threads \ 3059 " spawned extra threads"); \ 3060} \ 3061 \ 3062ATF_TC_BODY(test, tc) \ 3063{ \ 3064 \ 3065 traceme_lwpinfo(threads); \ 3066} 3067 3068TRACEME_LWPINFO(traceme_lwpinfo0, 0) 3069TRACEME_LWPINFO(traceme_lwpinfo1, 1) 3070TRACEME_LWPINFO(traceme_lwpinfo2, 2) 3071TRACEME_LWPINFO(traceme_lwpinfo3, 3) 3072 3073/// ---------------------------------------------------------------------------- 3074 3075#if defined(TWAIT_HAVE_PID) 3076static void 3077attach_lwpinfo(const int threads) 3078{ 3079 const int sigval = SIGINT; 3080 struct msg_fds parent_tracee, parent_tracer; 3081 const int exitval_tracer = 10; 3082 pid_t tracee, tracer, wpid; 3083 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 3084#if defined(TWAIT_HAVE_STATUS) 3085 int status; 3086#endif 3087 struct ptrace_lwpinfo lwp = {0, 0}; 3088 struct ptrace_siginfo info; 3089 3090 /* Maximum number of supported threads in this test */ 3091 pthread_t t[3]; 3092 int n, rv; 3093 3094 DPRINTF("Spawn tracee\n"); 3095 SYSCALL_REQUIRE(msg_open(&parent_tracee) == 0); 3096 SYSCALL_REQUIRE(msg_open(&parent_tracer) == 0); 3097 tracee = atf_utils_fork(); 3098 if (tracee == 0) { 3099 /* Wait for message from the parent */ 3100 CHILD_TO_PARENT("tracee ready", parent_tracee, msg); 3101 3102 CHILD_FROM_PARENT("spawn threads", parent_tracee, msg); 3103 3104 for (n = 0; n < threads; n++) { 3105 rv = pthread_create(&t[n], NULL, infinite_thread, NULL); 3106 FORKEE_ASSERT(rv == 0); 3107 } 3108 3109 CHILD_TO_PARENT("tracee exit", parent_tracee, msg); 3110 3111 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3112 FORKEE_ASSERT(raise(sigval) == 0); 3113 3114 /* NOTREACHED */ 3115 FORKEE_ASSERTX(0 && "Not reached"); 3116 } 3117 PARENT_FROM_CHILD("tracee ready", parent_tracee, msg); 3118 3119 DPRINTF("Spawn debugger\n"); 3120 tracer = atf_utils_fork(); 3121 if (tracer == 0) { 3122 /* No IPC to communicate with the child */ 3123 DPRINTF("Before calling PT_ATTACH from tracee %d\n", getpid()); 3124 FORKEE_ASSERT(ptrace(PT_ATTACH, tracee, NULL, 0) != -1); 3125 3126 /* Wait for tracee and assert that it was stopped w/ SIGSTOP */ 3127 FORKEE_REQUIRE_SUCCESS( 3128 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 3129 3130 forkee_status_stopped(status, SIGSTOP); 3131 3132 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 3133 "tracee"); 3134 FORKEE_ASSERT( 3135 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 3136 3137 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 3138 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 3139 "si_errno=%#x\n", 3140 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 3141 info.psi_siginfo.si_errno); 3142 3143 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, SIGSTOP); 3144 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SI_USER); 3145 3146 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for child\n"); 3147 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, sizeof(lwp)) 3148 != -1); 3149 3150 DPRINTF("Assert that there exists a thread\n"); 3151 FORKEE_ASSERTX(lwp.pl_lwpid > 0); 3152 3153 DPRINTF("Assert that lwp thread %d received event " 3154 "PL_EVENT_SIGNAL\n", lwp.pl_lwpid); 3155 FORKEE_ASSERT_EQ(lwp.pl_event, PL_EVENT_SIGNAL); 3156 3157 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for " 3158 "tracee\n"); 3159 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, sizeof(lwp)) 3160 != -1); 3161 3162 DPRINTF("Assert that there are no more lwp threads in " 3163 "tracee\n"); 3164 FORKEE_ASSERT_EQ(lwp.pl_lwpid, 0); 3165 3166 /* Resume tracee with PT_CONTINUE */ 3167 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, 0) != -1); 3168 3169 /* Inform parent that tracer has attached to tracee */ 3170 CHILD_TO_PARENT("tracer ready", parent_tracer, msg); 3171 3172 /* Wait for parent */ 3173 CHILD_FROM_PARENT("tracer wait", parent_tracer, msg); 3174 3175 /* Wait for tracee and assert that it raised a signal */ 3176 FORKEE_REQUIRE_SUCCESS( 3177 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 3178 3179 forkee_status_stopped(status, SIGINT); 3180 3181 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 3182 "child"); 3183 FORKEE_ASSERT( 3184 ptrace(PT_GET_SIGINFO, tracee, &info, sizeof(info)) != -1); 3185 3186 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 3187 DPRINTF("Signal properties: si_signo=%#x si_code=%#x " 3188 "si_errno=%#x\n", 3189 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 3190 info.psi_siginfo.si_errno); 3191 3192 FORKEE_ASSERT_EQ(info.psi_siginfo.si_signo, sigval); 3193 FORKEE_ASSERT_EQ(info.psi_siginfo.si_code, SI_LWP); 3194 3195 memset(&lwp, 0, sizeof(lwp)); 3196 3197 for (n = 0; n <= threads; n++) { 3198 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for " 3199 "child\n"); 3200 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, 3201 sizeof(lwp)) != -1); 3202 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 3203 3204 DPRINTF("Assert that the thread exists\n"); 3205 FORKEE_ASSERT(lwp.pl_lwpid > 0); 3206 3207 DPRINTF("Assert that lwp thread %d received expected " 3208 "event\n", lwp.pl_lwpid); 3209 FORKEE_ASSERT_EQ(lwp.pl_event, 3210 info.psi_lwpid == lwp.pl_lwpid ? 3211 PL_EVENT_SIGNAL : PL_EVENT_NONE); 3212 } 3213 DPRINTF("Before calling ptrace(2) with PT_LWPINFO for " 3214 "tracee\n"); 3215 FORKEE_ASSERT(ptrace(PT_LWPINFO, tracee, &lwp, sizeof(lwp)) 3216 != -1); 3217 DPRINTF("LWP=%d\n", lwp.pl_lwpid); 3218 3219 DPRINTF("Assert that there are no more threads\n"); 3220 FORKEE_ASSERT_EQ(lwp.pl_lwpid, 0); 3221 3222 DPRINTF("Before resuming the child process where it left off " 3223 "and without signal to be sent\n"); 3224 FORKEE_ASSERT(ptrace(PT_CONTINUE, tracee, (void *)1, SIGKILL) 3225 != -1); 3226 3227 /* Wait for tracee and assert that it exited */ 3228 FORKEE_REQUIRE_SUCCESS( 3229 wpid = TWAIT_GENERIC(tracee, &status, 0), tracee); 3230 3231 forkee_status_signaled(status, SIGKILL, 0); 3232 3233 DPRINTF("Before exiting of the tracer process\n"); 3234 _exit(exitval_tracer); 3235 } 3236 3237 DPRINTF("Wait for the tracer to attach to the tracee\n"); 3238 PARENT_FROM_CHILD("tracer ready", parent_tracer, msg); 3239 3240 DPRINTF("Resume the tracee and spawn threads\n"); 3241 PARENT_TO_CHILD("spawn threads", parent_tracee, msg); 3242 3243 DPRINTF("Resume the tracee and let it exit\n"); 3244 PARENT_FROM_CHILD("tracee exit", parent_tracee, msg); 3245 3246 DPRINTF("Resume the tracer and let it detect multiple threads\n"); 3247 PARENT_TO_CHILD("tracer wait", parent_tracer, msg); 3248 3249 DPRINTF("Wait for tracer to finish its job and exit - calling %s()\n", 3250 TWAIT_FNAME); 3251 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracer, &status, 0), 3252 tracer); 3253 3254 validate_status_exited(status, exitval_tracer); 3255 3256 DPRINTF("Wait for tracee to finish its job and exit - calling %s()\n", 3257 TWAIT_FNAME); 3258 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(tracee, &status, WNOHANG), 3259 tracee); 3260 3261 validate_status_signaled(status, SIGKILL, 0); 3262 3263 msg_close(&parent_tracer); 3264 msg_close(&parent_tracee); 3265} 3266 3267#define ATTACH_LWPINFO(test, threads) \ 3268ATF_TC(test); \ 3269ATF_TC_HEAD(test, tc) \ 3270{ \ 3271 atf_tc_set_md_var(tc, "descr", \ 3272 "Verify LWPINFO with the child with " #threads \ 3273 " spawned extra threads (tracer is not the original " \ 3274 "parent)"); \ 3275} \ 3276 \ 3277ATF_TC_BODY(test, tc) \ 3278{ \ 3279 \ 3280 attach_lwpinfo(threads); \ 3281} 3282 3283ATTACH_LWPINFO(attach_lwpinfo0, 0) 3284ATTACH_LWPINFO(attach_lwpinfo1, 1) 3285ATTACH_LWPINFO(attach_lwpinfo2, 2) 3286ATTACH_LWPINFO(attach_lwpinfo3, 3) 3287#endif 3288 3289/// ---------------------------------------------------------------------------- 3290 3291static void 3292ptrace_siginfo(bool faked, void (*sah)(int a, siginfo_t *b, void *c), int *signal_caught) 3293{ 3294 const int exitval = 5; 3295 const int sigval = SIGINT; 3296 const int sigfaked = SIGTRAP; 3297 const int sicodefaked = TRAP_BRKPT; 3298 pid_t child, wpid; 3299 struct sigaction sa; 3300#if defined(TWAIT_HAVE_STATUS) 3301 int status; 3302#endif 3303 struct ptrace_siginfo info; 3304 memset(&info, 0, sizeof(info)); 3305 3306 DPRINTF("Before forking process PID=%d\n", getpid()); 3307 SYSCALL_REQUIRE((child = fork()) != -1); 3308 if (child == 0) { 3309 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3310 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3311 3312 sa.sa_sigaction = sah; 3313 sa.sa_flags = SA_SIGINFO; 3314 sigemptyset(&sa.sa_mask); 3315 3316 FORKEE_ASSERT(sigaction(faked ? sigfaked : sigval, &sa, NULL) 3317 != -1); 3318 3319 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3320 FORKEE_ASSERT(raise(sigval) == 0); 3321 3322 FORKEE_ASSERT_EQ(*signal_caught, 1); 3323 3324 DPRINTF("Before exiting of the child process\n"); 3325 _exit(exitval); 3326 } 3327 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3328 3329 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3330 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3331 3332 validate_status_stopped(status, sigval); 3333 3334 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 3335 SYSCALL_REQUIRE( 3336 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 3337 3338 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 3339 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 3340 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 3341 info.psi_siginfo.si_errno); 3342 3343 if (faked) { 3344 DPRINTF("Before setting new faked signal to signo=%d " 3345 "si_code=%d\n", sigfaked, sicodefaked); 3346 info.psi_siginfo.si_signo = sigfaked; 3347 info.psi_siginfo.si_code = sicodefaked; 3348 } 3349 3350 DPRINTF("Before calling ptrace(2) with PT_SET_SIGINFO for child\n"); 3351 SYSCALL_REQUIRE( 3352 ptrace(PT_SET_SIGINFO, child, &info, sizeof(info)) != -1); 3353 3354 if (faked) { 3355 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for " 3356 "child\n"); 3357 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, 3358 sizeof(info)) != -1); 3359 3360 DPRINTF("Before checking siginfo_t\n"); 3361 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigfaked); 3362 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, sicodefaked); 3363 } 3364 3365 DPRINTF("Before resuming the child process where it left off and " 3366 "without signal to be sent\n"); 3367 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 3368 faked ? sigfaked : sigval) != -1); 3369 3370 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3371 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3372 3373 validate_status_exited(status, exitval); 3374 3375 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3376 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3377} 3378 3379#define PTRACE_SIGINFO(test, faked) \ 3380ATF_TC(test); \ 3381ATF_TC_HEAD(test, tc) \ 3382{ \ 3383 atf_tc_set_md_var(tc, "descr", \ 3384 "Verify basic PT_GET_SIGINFO and PT_SET_SIGINFO calls" \ 3385 "with%s setting signal to new value", faked ? "" : "out"); \ 3386} \ 3387 \ 3388static int test##_caught = 0; \ 3389 \ 3390static void \ 3391test##_sighandler(int sig, siginfo_t *info, void *ctx) \ 3392{ \ 3393 if (faked) { \ 3394 FORKEE_ASSERT_EQ(sig, SIGTRAP); \ 3395 FORKEE_ASSERT_EQ(info->si_signo, SIGTRAP); \ 3396 FORKEE_ASSERT_EQ(info->si_code, TRAP_BRKPT); \ 3397 } else { \ 3398 FORKEE_ASSERT_EQ(sig, SIGINT); \ 3399 FORKEE_ASSERT_EQ(info->si_signo, SIGINT); \ 3400 FORKEE_ASSERT_EQ(info->si_code, SI_LWP); \ 3401 } \ 3402 \ 3403 ++ test##_caught; \ 3404} \ 3405 \ 3406ATF_TC_BODY(test, tc) \ 3407{ \ 3408 \ 3409 ptrace_siginfo(faked, test##_sighandler, & test##_caught); \ 3410} 3411 3412PTRACE_SIGINFO(siginfo_set_unmodified, false) 3413PTRACE_SIGINFO(siginfo_set_faked, true) 3414 3415/// ---------------------------------------------------------------------------- 3416 3417ATF_TC(siginfo4); 3418ATF_TC_HEAD(siginfo4, tc) 3419{ 3420 atf_tc_set_md_var(tc, "descr", 3421 "Detect SIGTRAP TRAP_EXEC from tracee"); 3422} 3423 3424ATF_TC_BODY(siginfo4, tc) 3425{ 3426 const int sigval = SIGTRAP; 3427 pid_t child, wpid; 3428#if defined(TWAIT_HAVE_STATUS) 3429 int status; 3430#endif 3431 3432 struct ptrace_siginfo info; 3433 memset(&info, 0, sizeof(info)); 3434 3435 DPRINTF("Before forking process PID=%d\n", getpid()); 3436 SYSCALL_REQUIRE((child = fork()) != -1); 3437 if (child == 0) { 3438 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3439 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3440 3441 DPRINTF("Before calling execve(2) from child\n"); 3442 execlp("/bin/echo", "/bin/echo", NULL); 3443 3444 FORKEE_ASSERT(0 && "Not reached"); 3445 } 3446 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3447 3448 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3449 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3450 3451 validate_status_stopped(status, sigval); 3452 3453 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 3454 SYSCALL_REQUIRE( 3455 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 3456 3457 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 3458 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 3459 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 3460 info.psi_siginfo.si_errno); 3461 3462 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 3463 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_EXEC); 3464 3465 DPRINTF("Before resuming the child process where it left off and " 3466 "without signal to be sent\n"); 3467 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3468 3469 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3470 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3471 3472 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3473 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3474} 3475 3476#if defined(PT_STEP) 3477ATF_TC(siginfo6); 3478ATF_TC_HEAD(siginfo6, tc) 3479{ 3480 atf_tc_set_md_var(tc, "descr", 3481 "Verify single PT_STEP call with signal information check"); 3482} 3483 3484ATF_TC_BODY(siginfo6, tc) 3485{ 3486 const int exitval = 5; 3487 const int sigval = SIGSTOP; 3488 pid_t child, wpid; 3489#if defined(TWAIT_HAVE_STATUS) 3490 int status; 3491#endif 3492 int happy; 3493 struct ptrace_siginfo info; 3494 3495#if defined(__arm__) 3496 /* PT_STEP not supported on arm 32-bit */ 3497 atf_tc_expect_fail("PR kern/52119"); 3498#endif 3499 3500 memset(&info, 0, sizeof(info)); 3501 3502 DPRINTF("Before forking process PID=%d\n", getpid()); 3503 SYSCALL_REQUIRE((child = fork()) != -1); 3504 if (child == 0) { 3505 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3506 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3507 3508 happy = check_happy(100); 3509 3510 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3511 FORKEE_ASSERT(raise(sigval) == 0); 3512 3513 FORKEE_ASSERT_EQ(happy, check_happy(100)); 3514 3515 DPRINTF("Before exiting of the child process\n"); 3516 _exit(exitval); 3517 } 3518 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3519 3520 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3521 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3522 3523 validate_status_stopped(status, sigval); 3524 3525 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 3526 SYSCALL_REQUIRE( 3527 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 3528 3529 DPRINTF("Before checking siginfo_t\n"); 3530 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval); 3531 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP); 3532 3533 DPRINTF("Before resuming the child process where it left off and " 3534 "without signal to be sent (use PT_STEP)\n"); 3535 SYSCALL_REQUIRE(ptrace(PT_STEP, child, (void *)1, 0) != -1); 3536 3537 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3538 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3539 3540 validate_status_stopped(status, SIGTRAP); 3541 3542 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 3543 SYSCALL_REQUIRE( 3544 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 3545 3546 DPRINTF("Before checking siginfo_t\n"); 3547 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 3548 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_TRACE); 3549 3550 DPRINTF("Before resuming the child process where it left off and " 3551 "without signal to be sent\n"); 3552 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3553 3554 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3555 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3556 3557 validate_status_exited(status, exitval); 3558 3559 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3560 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3561} 3562#endif 3563 3564volatile lwpid_t the_lwp_id = 0; 3565 3566static void 3567lwp_main_func(void *arg) 3568{ 3569 the_lwp_id = _lwp_self(); 3570 _lwp_exit(); 3571} 3572 3573ATF_TC(lwp_create1); 3574ATF_TC_HEAD(lwp_create1, tc) 3575{ 3576 atf_tc_set_md_var(tc, "descr", 3577 "Verify that 1 LWP creation is intercepted by ptrace(2) with " 3578 "EVENT_MASK set to PTRACE_LWP_CREATE"); 3579} 3580 3581ATF_TC_BODY(lwp_create1, tc) 3582{ 3583 const int exitval = 5; 3584 const int sigval = SIGSTOP; 3585 pid_t child, wpid; 3586#if defined(TWAIT_HAVE_STATUS) 3587 int status; 3588#endif 3589 ptrace_state_t state; 3590 const int slen = sizeof(state); 3591 ptrace_event_t event; 3592 const int elen = sizeof(event); 3593 ucontext_t uc; 3594 lwpid_t lid; 3595 static const size_t ssize = 16*1024; 3596 void *stack; 3597 3598 DPRINTF("Before forking process PID=%d\n", getpid()); 3599 SYSCALL_REQUIRE((child = fork()) != -1); 3600 if (child == 0) { 3601 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3602 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3603 3604 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3605 FORKEE_ASSERT(raise(sigval) == 0); 3606 3607 DPRINTF("Before allocating memory for stack in child\n"); 3608 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 3609 3610 DPRINTF("Before making context for new lwp in child\n"); 3611 _lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize); 3612 3613 DPRINTF("Before creating new in child\n"); 3614 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 3615 3616 DPRINTF("Before waiting for lwp %d to exit\n", lid); 3617 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 3618 3619 DPRINTF("Before verifying that reported %d and running lid %d " 3620 "are the same\n", lid, the_lwp_id); 3621 FORKEE_ASSERT_EQ(lid, the_lwp_id); 3622 3623 DPRINTF("Before exiting of the child process\n"); 3624 _exit(exitval); 3625 } 3626 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3627 3628 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3629 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3630 3631 validate_status_stopped(status, sigval); 3632 3633 DPRINTF("Set empty EVENT_MASK for the child %d\n", child); 3634 event.pe_set_event = PTRACE_LWP_CREATE; 3635 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 3636 3637 DPRINTF("Before resuming the child process where it left off and " 3638 "without signal to be sent\n"); 3639 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3640 3641 DPRINTF("Before calling %s() for the child - expected stopped " 3642 "SIGTRAP\n", TWAIT_FNAME); 3643 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3644 3645 validate_status_stopped(status, SIGTRAP); 3646 3647 SYSCALL_REQUIRE( 3648 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 3649 3650 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_CREATE); 3651 3652 lid = state.pe_lwp; 3653 DPRINTF("Reported PTRACE_LWP_CREATE event with lid %d\n", lid); 3654 3655 DPRINTF("Before resuming the child process where it left off and " 3656 "without signal to be sent\n"); 3657 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3658 3659 DPRINTF("Before calling %s() for the child - expected exited\n", 3660 TWAIT_FNAME); 3661 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3662 3663 validate_status_exited(status, exitval); 3664 3665 DPRINTF("Before calling %s() for the child - expected no process\n", 3666 TWAIT_FNAME); 3667 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3668} 3669 3670ATF_TC(lwp_exit1); 3671ATF_TC_HEAD(lwp_exit1, tc) 3672{ 3673 atf_tc_set_md_var(tc, "descr", 3674 "Verify that 1 LWP creation is intercepted by ptrace(2) with " 3675 "EVENT_MASK set to PTRACE_LWP_EXIT"); 3676} 3677 3678ATF_TC_BODY(lwp_exit1, tc) 3679{ 3680 const int exitval = 5; 3681 const int sigval = SIGSTOP; 3682 pid_t child, wpid; 3683#if defined(TWAIT_HAVE_STATUS) 3684 int status; 3685#endif 3686 ptrace_state_t state; 3687 const int slen = sizeof(state); 3688 ptrace_event_t event; 3689 const int elen = sizeof(event); 3690 ucontext_t uc; 3691 lwpid_t lid; 3692 static const size_t ssize = 16*1024; 3693 void *stack; 3694 3695 DPRINTF("Before forking process PID=%d\n", getpid()); 3696 SYSCALL_REQUIRE((child = fork()) != -1); 3697 if (child == 0) { 3698 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3699 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3700 3701 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3702 FORKEE_ASSERT(raise(sigval) == 0); 3703 3704 DPRINTF("Before allocating memory for stack in child\n"); 3705 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 3706 3707 DPRINTF("Before making context for new lwp in child\n"); 3708 _lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize); 3709 3710 DPRINTF("Before creating new in child\n"); 3711 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 3712 3713 DPRINTF("Before waiting for lwp %d to exit\n", lid); 3714 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 3715 3716 DPRINTF("Before verifying that reported %d and running lid %d " 3717 "are the same\n", lid, the_lwp_id); 3718 FORKEE_ASSERT_EQ(lid, the_lwp_id); 3719 3720 DPRINTF("Before exiting of the child process\n"); 3721 _exit(exitval); 3722 } 3723 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3724 3725 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3726 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3727 3728 validate_status_stopped(status, sigval); 3729 3730 DPRINTF("Set empty EVENT_MASK for the child %d\n", child); 3731 event.pe_set_event = PTRACE_LWP_EXIT; 3732 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 3733 3734 DPRINTF("Before resuming the child process where it left off and " 3735 "without signal to be sent\n"); 3736 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3737 3738 DPRINTF("Before calling %s() for the child - expected stopped " 3739 "SIGTRAP\n", TWAIT_FNAME); 3740 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3741 3742 validate_status_stopped(status, SIGTRAP); 3743 3744 SYSCALL_REQUIRE( 3745 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 3746 3747 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_EXIT); 3748 3749 lid = state.pe_lwp; 3750 DPRINTF("Reported PTRACE_LWP_EXIT event with lid %d\n", lid); 3751 3752 DPRINTF("Before resuming the child process where it left off and " 3753 "without signal to be sent\n"); 3754 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3755 3756 DPRINTF("Before calling %s() for the child - expected exited\n", 3757 TWAIT_FNAME); 3758 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3759 3760 validate_status_exited(status, exitval); 3761 3762 DPRINTF("Before calling %s() for the child - expected no process\n", 3763 TWAIT_FNAME); 3764 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3765} 3766 3767ATF_TC(signal1); 3768ATF_TC_HEAD(signal1, tc) 3769{ 3770 atf_tc_set_md_var(tc, "descr", 3771 "Verify that masking single unrelated signal does not stop tracer " 3772 "from catching other signals"); 3773} 3774 3775ATF_TC_BODY(signal1, tc) 3776{ 3777 const int exitval = 5; 3778 const int sigval = SIGSTOP; 3779 const int sigmasked = SIGTRAP; 3780 const int signotmasked = SIGINT; 3781 pid_t child, wpid; 3782#if defined(TWAIT_HAVE_STATUS) 3783 int status; 3784#endif 3785 sigset_t intmask; 3786 3787 DPRINTF("Before forking process PID=%d\n", getpid()); 3788 SYSCALL_REQUIRE((child = fork()) != -1); 3789 if (child == 0) { 3790 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3791 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3792 3793 sigemptyset(&intmask); 3794 sigaddset(&intmask, sigmasked); 3795 sigprocmask(SIG_BLOCK, &intmask, NULL); 3796 3797 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3798 FORKEE_ASSERT(raise(sigval) == 0); 3799 3800 DPRINTF("Before raising %s from child\n", 3801 strsignal(signotmasked)); 3802 FORKEE_ASSERT(raise(signotmasked) == 0); 3803 3804 DPRINTF("Before exiting of the child process\n"); 3805 _exit(exitval); 3806 } 3807 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3808 3809 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3810 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3811 3812 validate_status_stopped(status, sigval); 3813 3814 DPRINTF("Before resuming the child process where it left off and " 3815 "without signal to be sent\n"); 3816 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3817 3818 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3819 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3820 3821 validate_status_stopped(status, signotmasked); 3822 3823 DPRINTF("Before resuming the child process where it left off and " 3824 "without signal to be sent\n"); 3825 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3826 3827 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3828 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3829 3830 validate_status_exited(status, exitval); 3831 3832 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3833 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3834} 3835 3836ATF_TC(signal2); 3837ATF_TC_HEAD(signal2, tc) 3838{ 3839 atf_tc_set_md_var(tc, "descr", 3840 "Verify that masking SIGTRAP in tracee stops tracer from " 3841 "catching this raised signal"); 3842} 3843 3844ATF_TC_BODY(signal2, tc) 3845{ 3846 const int exitval = 5; 3847 const int sigval = SIGSTOP; 3848 const int sigmasked = SIGTRAP; 3849 pid_t child, wpid; 3850#if defined(TWAIT_HAVE_STATUS) 3851 int status; 3852#endif 3853 sigset_t intmask; 3854 3855 DPRINTF("Before forking process PID=%d\n", getpid()); 3856 SYSCALL_REQUIRE((child = fork()) != -1); 3857 if (child == 0) { 3858 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3859 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3860 3861 sigemptyset(&intmask); 3862 sigaddset(&intmask, sigmasked); 3863 sigprocmask(SIG_BLOCK, &intmask, NULL); 3864 3865 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3866 FORKEE_ASSERT(raise(sigval) == 0); 3867 3868 DPRINTF("Before raising %s breakpoint from child\n", 3869 strsignal(sigmasked)); 3870 FORKEE_ASSERT(raise(sigmasked) == 0); 3871 3872 DPRINTF("Before exiting of the child process\n"); 3873 _exit(exitval); 3874 } 3875 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3876 3877 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3878 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3879 3880 validate_status_stopped(status, sigval); 3881 3882 DPRINTF("Before resuming the child process where it left off and " 3883 "without signal to be sent\n"); 3884 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3885 3886 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3887 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3888 3889 validate_status_exited(status, exitval); 3890 3891 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3892 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3893} 3894 3895ATF_TC(signal3); 3896ATF_TC_HEAD(signal3, tc) 3897{ 3898 atf_tc_set_md_var(tc, "timeout", "5"); 3899 atf_tc_set_md_var(tc, "descr", 3900 "Verify that masking SIGTRAP in tracee does not stop tracer from " 3901 "catching software breakpoints"); 3902} 3903 3904ATF_TC_BODY(signal3, tc) 3905{ 3906 const int exitval = 5; 3907 const int sigval = SIGSTOP; 3908 const int sigmasked = SIGTRAP; 3909 pid_t child, wpid; 3910#if defined(TWAIT_HAVE_STATUS) 3911 int status; 3912#endif 3913 sigset_t intmask; 3914 3915 DPRINTF("Before forking process PID=%d\n", getpid()); 3916 SYSCALL_REQUIRE((child = fork()) != -1); 3917 if (child == 0) { 3918 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3919 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3920 3921 sigemptyset(&intmask); 3922 sigaddset(&intmask, sigmasked); 3923 sigprocmask(SIG_BLOCK, &intmask, NULL); 3924 3925 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 3926 FORKEE_ASSERT(raise(sigval) == 0); 3927 3928 DPRINTF("Before raising software breakpoint from child\n"); 3929 trigger_trap(); 3930 3931 DPRINTF("Before exiting of the child process\n"); 3932 _exit(exitval); 3933 } 3934 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 3935 3936 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3937 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3938 3939 validate_status_stopped(status, sigval); 3940 3941 DPRINTF("Before resuming the child process where it left off and " 3942 "without signal to be sent\n"); 3943 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 3944 3945 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3946 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3947 3948 validate_status_stopped(status, sigmasked); 3949 3950 DPRINTF("Before resuming the child process where it left off and " 3951 "without signal to be sent\n"); 3952 SYSCALL_REQUIRE(ptrace(PT_KILL, child, NULL, 0) != -1); 3953 3954 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3955 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 3956 3957 validate_status_signaled(status, SIGKILL, 0); 3958 3959 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 3960 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 3961} 3962 3963#if defined(PT_STEP) 3964ATF_TC(signal4); 3965ATF_TC_HEAD(signal4, tc) 3966{ 3967 atf_tc_set_md_var(tc, "descr", 3968 "Verify that masking SIGTRAP in tracee does not stop tracer from " 3969 "catching single step trap"); 3970} 3971 3972ATF_TC_BODY(signal4, tc) 3973{ 3974 const int exitval = 5; 3975 const int sigval = SIGSTOP; 3976 const int sigmasked = SIGTRAP; 3977 pid_t child, wpid; 3978#if defined(TWAIT_HAVE_STATUS) 3979 int status; 3980#endif 3981 sigset_t intmask; 3982 int happy; 3983 3984#if defined(__arm__) 3985 /* PT_STEP not supported on arm 32-bit */ 3986 atf_tc_expect_fail("PR kern/51918 PR kern/52119"); 3987#endif 3988 3989 DPRINTF("Before forking process PID=%d\n", getpid()); 3990 SYSCALL_REQUIRE((child = fork()) != -1); 3991 if (child == 0) { 3992 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 3993 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 3994 3995 happy = check_happy(100); 3996 3997 sigemptyset(&intmask); 3998 sigaddset(&intmask, sigmasked); 3999 sigprocmask(SIG_BLOCK, &intmask, NULL); 4000 4001 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4002 FORKEE_ASSERT(raise(sigval) == 0); 4003 4004 FORKEE_ASSERT_EQ(happy, check_happy(100)); 4005 4006 DPRINTF("Before exiting of the child process\n"); 4007 _exit(exitval); 4008 } 4009 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4010 4011 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4012 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4013 4014 validate_status_stopped(status, sigval); 4015 4016 DPRINTF("Before resuming the child process where it left off and " 4017 "without signal to be sent\n"); 4018 SYSCALL_REQUIRE(ptrace(PT_STEP, child, (void *)1, 0) != -1); 4019 4020 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4021 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4022 4023 validate_status_stopped(status, sigmasked); 4024 4025 DPRINTF("Before resuming the child process where it left off and " 4026 "without signal to be sent\n"); 4027 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4028 4029 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4030 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4031 4032 validate_status_exited(status, exitval); 4033 4034 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4035 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4036} 4037#endif 4038 4039ATF_TC(signal5); 4040ATF_TC_HEAD(signal5, tc) 4041{ 4042 atf_tc_set_md_var(tc, "descr", 4043 "Verify that masking SIGTRAP in tracee does not stop tracer from " 4044 "catching exec() breakpoint"); 4045} 4046 4047ATF_TC_BODY(signal5, tc) 4048{ 4049 const int sigval = SIGSTOP; 4050 const int sigmasked = SIGTRAP; 4051 pid_t child, wpid; 4052#if defined(TWAIT_HAVE_STATUS) 4053 int status; 4054#endif 4055 struct ptrace_siginfo info; 4056 sigset_t intmask; 4057 4058 memset(&info, 0, sizeof(info)); 4059 4060 DPRINTF("Before forking process PID=%d\n", getpid()); 4061 SYSCALL_REQUIRE((child = fork()) != -1); 4062 if (child == 0) { 4063 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4064 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4065 4066 sigemptyset(&intmask); 4067 sigaddset(&intmask, sigmasked); 4068 sigprocmask(SIG_BLOCK, &intmask, NULL); 4069 4070 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4071 FORKEE_ASSERT(raise(sigval) == 0); 4072 4073 DPRINTF("Before calling execve(2) from child\n"); 4074 execlp("/bin/echo", "/bin/echo", NULL); 4075 4076 /* NOTREACHED */ 4077 FORKEE_ASSERTX(0 && "Not reached"); 4078 } 4079 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4080 4081 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4082 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4083 4084 validate_status_stopped(status, sigval); 4085 4086 DPRINTF("Before resuming the child process where it left off and " 4087 "without signal to be sent\n"); 4088 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4089 4090 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4091 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4092 4093 validate_status_stopped(status, sigmasked); 4094 4095 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 4096 SYSCALL_REQUIRE( 4097 ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 4098 4099 DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid); 4100 DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n", 4101 info.psi_siginfo.si_signo, info.psi_siginfo.si_code, 4102 info.psi_siginfo.si_errno); 4103 4104 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigmasked); 4105 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_EXEC); 4106 4107 DPRINTF("Before resuming the child process where it left off and " 4108 "without signal to be sent\n"); 4109 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4110 4111 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4112 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4113 4114 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4115 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4116} 4117 4118#if defined(TWAIT_HAVE_PID) 4119ATF_TC(signal6); 4120ATF_TC_HEAD(signal6, tc) 4121{ 4122 atf_tc_set_md_var(tc, "timeout", "5"); 4123 atf_tc_set_md_var(tc, "descr", 4124 "Verify that masking SIGTRAP in tracee does not stop tracer from " 4125 "catching PTRACE_FORK breakpoint"); 4126} 4127 4128ATF_TC_BODY(signal6, tc) 4129{ 4130 const int exitval = 5; 4131 const int exitval2 = 15; 4132 const int sigval = SIGSTOP; 4133 const int sigmasked = SIGTRAP; 4134 pid_t child, child2, wpid; 4135#if defined(TWAIT_HAVE_STATUS) 4136 int status; 4137#endif 4138 sigset_t intmask; 4139 ptrace_state_t state; 4140 const int slen = sizeof(state); 4141 ptrace_event_t event; 4142 const int elen = sizeof(event); 4143 4144 atf_tc_expect_fail("PR kern/51918"); 4145 4146 DPRINTF("Before forking process PID=%d\n", getpid()); 4147 SYSCALL_REQUIRE((child = fork()) != -1); 4148 if (child == 0) { 4149 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4150 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4151 4152 sigemptyset(&intmask); 4153 sigaddset(&intmask, sigmasked); 4154 sigprocmask(SIG_BLOCK, &intmask, NULL); 4155 4156 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4157 FORKEE_ASSERT(raise(sigval) == 0); 4158 4159 FORKEE_ASSERT((child2 = fork()) != -1); 4160 4161 if (child2 == 0) 4162 _exit(exitval2); 4163 4164 FORKEE_REQUIRE_SUCCESS 4165 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 4166 4167 forkee_status_exited(status, exitval2); 4168 4169 DPRINTF("Before exiting of the child process\n"); 4170 _exit(exitval); 4171 } 4172 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4173 4174 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4175 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4176 4177 validate_status_stopped(status, sigval); 4178 4179 DPRINTF("Enable PTRACE_FORK in EVENT_MASK for the child %d\n", child); 4180 event.pe_set_event = PTRACE_FORK; 4181 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 4182 4183 DPRINTF("Before resuming the child process where it left off and " 4184 "without signal to be sent\n"); 4185 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4186 4187 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4188 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4189 4190 validate_status_stopped(status, sigmasked); 4191 4192 SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 4193 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_FORK); 4194 4195 child2 = state.pe_other_pid; 4196 DPRINTF("Reported PTRACE_FORK event with forkee %d\n", child2); 4197 4198 DPRINTF("Before calling %s() for the child2\n", TWAIT_FNAME); 4199 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 4200 child2); 4201 4202 validate_status_stopped(status, SIGTRAP); 4203 4204 SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 4205 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_FORK); 4206 ATF_REQUIRE_EQ(state.pe_other_pid, child); 4207 4208 DPRINTF("Before resuming the forkee process where it left off and " 4209 "without signal to be sent\n"); 4210 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 4211 4212 DPRINTF("Before resuming the child process where it left off and " 4213 "without signal to be sent\n"); 4214 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4215 4216 DPRINTF("Before calling %s() for the forkee - expected exited\n", 4217 TWAIT_FNAME); 4218 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 4219 child2); 4220 4221 validate_status_exited(status, exitval2); 4222 4223 DPRINTF("Before calling %s() for the forkee - expected no process\n", 4224 TWAIT_FNAME); 4225 TWAIT_REQUIRE_FAILURE(ECHILD, 4226 wpid = TWAIT_GENERIC(child2, &status, 0)); 4227 4228 DPRINTF("Before calling %s() for the child - expected stopped " 4229 "SIGCHLD\n", TWAIT_FNAME); 4230 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4231 4232 validate_status_stopped(status, SIGCHLD); 4233 4234 DPRINTF("Before resuming the child process where it left off and " 4235 "without signal to be sent\n"); 4236 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4237 4238 DPRINTF("Before calling %s() for the child - expected exited\n", 4239 TWAIT_FNAME); 4240 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4241 4242 validate_status_exited(status, exitval); 4243 4244 DPRINTF("Before calling %s() for the child - expected no process\n", 4245 TWAIT_FNAME); 4246 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4247} 4248#endif 4249 4250#if defined(TWAIT_HAVE_PID) 4251ATF_TC(signal7); 4252ATF_TC_HEAD(signal7, tc) 4253{ 4254 atf_tc_set_md_var(tc, "descr", 4255 "Verify that masking SIGTRAP in tracee does not stop tracer from " 4256 "catching PTRACE_VFORK breakpoint"); 4257} 4258 4259ATF_TC_BODY(signal7, tc) 4260{ 4261 const int exitval = 5; 4262 const int exitval2 = 15; 4263 const int sigval = SIGSTOP; 4264 const int sigmasked = SIGTRAP; 4265 pid_t child, child2, wpid; 4266#if defined(TWAIT_HAVE_STATUS) 4267 int status; 4268#endif 4269 sigset_t intmask; 4270 ptrace_state_t state; 4271 const int slen = sizeof(state); 4272 ptrace_event_t event; 4273 const int elen = sizeof(event); 4274 4275 atf_tc_expect_fail("PR kern/51918"); 4276 4277 DPRINTF("Before forking process PID=%d\n", getpid()); 4278 SYSCALL_REQUIRE((child = fork()) != -1); 4279 if (child == 0) { 4280 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4281 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4282 4283 sigemptyset(&intmask); 4284 sigaddset(&intmask, sigmasked); 4285 sigprocmask(SIG_BLOCK, &intmask, NULL); 4286 4287 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4288 FORKEE_ASSERT(raise(sigval) == 0); 4289 4290 FORKEE_ASSERT((child2 = fork()) != -1); 4291 4292 if (child2 == 0) 4293 _exit(exitval2); 4294 4295 FORKEE_REQUIRE_SUCCESS 4296 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 4297 4298 forkee_status_exited(status, exitval2); 4299 4300 DPRINTF("Before exiting of the child process\n"); 4301 _exit(exitval); 4302 } 4303 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4304 4305 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4306 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4307 4308 validate_status_stopped(status, sigval); 4309 4310 DPRINTF("Enable PTRACE_VFORK in EVENT_MASK for the child %d\n", child); 4311 event.pe_set_event = PTRACE_VFORK; 4312 SYSCALL_REQUIRE( 4313 ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1 || 4314 errno == ENOTSUP); 4315 4316 DPRINTF("Before resuming the child process where it left off and " 4317 "without signal to be sent\n"); 4318 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4319 4320 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4321 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4322 4323 validate_status_stopped(status, sigmasked); 4324 4325 SYSCALL_REQUIRE( 4326 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 4327 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK); 4328 4329 child2 = state.pe_other_pid; 4330 DPRINTF("Reported PTRACE_VFORK event with forkee %d\n", child2); 4331 4332 DPRINTF("Before calling %s() for the child2\n", TWAIT_FNAME); 4333 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 4334 child2); 4335 4336 validate_status_stopped(status, SIGTRAP); 4337 4338 SYSCALL_REQUIRE( 4339 ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1); 4340 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK); 4341 ATF_REQUIRE_EQ(state.pe_other_pid, child); 4342 4343 DPRINTF("Before resuming the forkee process where it left off and " 4344 "without signal to be sent\n"); 4345 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1); 4346 4347 DPRINTF("Before resuming the child process where it left off and " 4348 "without signal to be sent\n"); 4349 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4350 4351 DPRINTF("Before calling %s() for the forkee - expected exited\n", 4352 TWAIT_FNAME); 4353 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0), 4354 child2); 4355 4356 validate_status_exited(status, exitval2); 4357 4358 DPRINTF("Before calling %s() for the forkee - expected no process\n", 4359 TWAIT_FNAME); 4360 TWAIT_REQUIRE_FAILURE(ECHILD, 4361 wpid = TWAIT_GENERIC(child2, &status, 0)); 4362 4363 DPRINTF("Before calling %s() for the child - expected stopped " 4364 "SIGCHLD\n", TWAIT_FNAME); 4365 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4366 4367 validate_status_stopped(status, SIGCHLD); 4368 4369 DPRINTF("Before resuming the child process where it left off and " 4370 "without signal to be sent\n"); 4371 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4372 4373 DPRINTF("Before calling %s() for the child - expected exited\n", 4374 TWAIT_FNAME); 4375 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4376 4377 validate_status_exited(status, exitval); 4378 4379 DPRINTF("Before calling %s() for the child - expected no process\n", 4380 TWAIT_FNAME); 4381 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4382} 4383#endif 4384 4385ATF_TC(signal8); 4386ATF_TC_HEAD(signal8, tc) 4387{ 4388 atf_tc_set_md_var(tc, "descr", 4389 "Verify that masking SIGTRAP in tracee does not stop tracer from " 4390 "catching PTRACE_VFORK_DONE breakpoint"); 4391} 4392 4393ATF_TC_BODY(signal8, tc) 4394{ 4395 const int exitval = 5; 4396 const int exitval2 = 15; 4397 const int sigval = SIGSTOP; 4398 const int sigmasked = SIGTRAP; 4399 pid_t child, child2, wpid; 4400#if defined(TWAIT_HAVE_STATUS) 4401 int status; 4402#endif 4403 sigset_t intmask; 4404 ptrace_state_t state; 4405 const int slen = sizeof(state); 4406 ptrace_event_t event; 4407 const int elen = sizeof(event); 4408 4409 atf_tc_expect_fail("PR kern/51918"); 4410 4411 DPRINTF("Before forking process PID=%d\n", getpid()); 4412 SYSCALL_REQUIRE((child = fork()) != -1); 4413 if (child == 0) { 4414 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4415 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4416 4417 sigemptyset(&intmask); 4418 sigaddset(&intmask, sigmasked); 4419 sigprocmask(SIG_BLOCK, &intmask, NULL); 4420 4421 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4422 FORKEE_ASSERT(raise(sigval) == 0); 4423 4424 FORKEE_ASSERT((child2 = vfork()) != -1); 4425 4426 if (child2 == 0) 4427 _exit(exitval2); 4428 4429 FORKEE_REQUIRE_SUCCESS 4430 (wpid = TWAIT_GENERIC(child2, &status, 0), child2); 4431 4432 forkee_status_exited(status, exitval2); 4433 4434 DPRINTF("Before exiting of the child process\n"); 4435 _exit(exitval); 4436 } 4437 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4438 4439 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4440 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4441 4442 validate_status_stopped(status, sigval); 4443 4444 DPRINTF("Enable PTRACE_VFORK_DONE in EVENT_MASK for the child %d\n", 4445 child); 4446 event.pe_set_event = PTRACE_VFORK_DONE; 4447 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 4448 4449 DPRINTF("Before resuming the child process where it left off and " 4450 "without signal to be sent\n"); 4451 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4452 4453 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4454 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4455 4456 validate_status_stopped(status, sigmasked); 4457 4458 SYSCALL_REQUIRE( 4459 ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 4460 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE); 4461 4462 child2 = state.pe_other_pid; 4463 DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n", child2); 4464 4465 DPRINTF("Before resuming the child process where it left off and " 4466 "without signal to be sent\n"); 4467 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4468 4469 DPRINTF("Before calling %s() for the child - expected stopped " 4470 "SIGCHLD\n", TWAIT_FNAME); 4471 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4472 4473 validate_status_stopped(status, SIGCHLD); 4474 4475 DPRINTF("Before resuming the child process where it left off and " 4476 "without signal to be sent\n"); 4477 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4478 4479 DPRINTF("Before calling %s() for the child - expected exited\n", 4480 TWAIT_FNAME); 4481 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4482 4483 validate_status_exited(status, exitval); 4484 4485 DPRINTF("Before calling %s() for the child - expected no process\n", 4486 TWAIT_FNAME); 4487 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4488} 4489 4490ATF_TC(signal9); 4491ATF_TC_HEAD(signal9, tc) 4492{ 4493 atf_tc_set_md_var(tc, "descr", 4494 "Verify that masking SIGTRAP in tracee does not stop tracer from " 4495 "catching PTRACE_LWP_CREATE breakpoint"); 4496} 4497 4498ATF_TC_BODY(signal9, tc) 4499{ 4500 const int exitval = 5; 4501 const int sigval = SIGSTOP; 4502 const int sigmasked = SIGTRAP; 4503 pid_t child, wpid; 4504#if defined(TWAIT_HAVE_STATUS) 4505 int status; 4506#endif 4507 sigset_t intmask; 4508 ptrace_state_t state; 4509 const int slen = sizeof(state); 4510 ptrace_event_t event; 4511 const int elen = sizeof(event); 4512 ucontext_t uc; 4513 lwpid_t lid; 4514 static const size_t ssize = 16*1024; 4515 void *stack; 4516 4517 atf_tc_expect_fail("PR kern/51918"); 4518 4519 DPRINTF("Before forking process PID=%d\n", getpid()); 4520 SYSCALL_REQUIRE((child = fork()) != -1); 4521 if (child == 0) { 4522 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4523 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4524 4525 sigemptyset(&intmask); 4526 sigaddset(&intmask, sigmasked); 4527 sigprocmask(SIG_BLOCK, &intmask, NULL); 4528 4529 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4530 FORKEE_ASSERT(raise(sigval) == 0); 4531 4532 DPRINTF("Before allocating memory for stack in child\n"); 4533 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 4534 4535 DPRINTF("Before making context for new lwp in child\n"); 4536 _lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize); 4537 4538 DPRINTF("Before creating new in child\n"); 4539 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 4540 4541 DPRINTF("Before waiting for lwp %d to exit\n", lid); 4542 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 4543 4544 DPRINTF("Before verifying that reported %d and running lid %d " 4545 "are the same\n", lid, the_lwp_id); 4546 FORKEE_ASSERT_EQ(lid, the_lwp_id); 4547 4548 DPRINTF("Before exiting of the child process\n"); 4549 _exit(exitval); 4550 } 4551 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4552 4553 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4554 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4555 4556 validate_status_stopped(status, sigval); 4557 4558 DPRINTF("Set empty EVENT_MASK for the child %d\n", child); 4559 event.pe_set_event = PTRACE_LWP_CREATE; 4560 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 4561 4562 DPRINTF("Before resuming the child process where it left off and " 4563 "without signal to be sent\n"); 4564 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4565 4566 DPRINTF("Before calling %s() for the child - expected stopped " 4567 "SIGTRAP\n", TWAIT_FNAME); 4568 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4569 4570 validate_status_stopped(status, sigmasked); 4571 4572 SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 4573 4574 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_CREATE); 4575 4576 lid = state.pe_lwp; 4577 DPRINTF("Reported PTRACE_LWP_CREATE event with lid %d\n", lid); 4578 4579 DPRINTF("Before resuming the child process where it left off and " 4580 "without signal to be sent\n"); 4581 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4582 4583 DPRINTF("Before calling %s() for the child - expected exited\n", 4584 TWAIT_FNAME); 4585 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4586 4587 validate_status_exited(status, exitval); 4588 4589 DPRINTF("Before calling %s() for the child - expected no process\n", 4590 TWAIT_FNAME); 4591 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4592} 4593 4594ATF_TC(signal10); 4595ATF_TC_HEAD(signal10, tc) 4596{ 4597 atf_tc_set_md_var(tc, "descr", 4598 "Verify that masking SIGTRAP in tracee does not stop tracer from " 4599 "catching PTRACE_LWP_EXIT breakpoint"); 4600} 4601 4602ATF_TC_BODY(signal10, tc) 4603{ 4604 const int exitval = 5; 4605 const int sigval = SIGSTOP; 4606 const int sigmasked = SIGTRAP; 4607 pid_t child, wpid; 4608#if defined(TWAIT_HAVE_STATUS) 4609 int status; 4610#endif 4611 sigset_t intmask; 4612 ptrace_state_t state; 4613 const int slen = sizeof(state); 4614 ptrace_event_t event; 4615 const int elen = sizeof(event); 4616 ucontext_t uc; 4617 lwpid_t lid; 4618 static const size_t ssize = 16*1024; 4619 void *stack; 4620 4621 atf_tc_expect_fail("PR kern/51918"); 4622 4623 DPRINTF("Before forking process PID=%d\n", getpid()); 4624 SYSCALL_REQUIRE((child = fork()) != -1); 4625 if (child == 0) { 4626 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4627 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4628 4629 sigemptyset(&intmask); 4630 sigaddset(&intmask, sigmasked); 4631 sigprocmask(SIG_BLOCK, &intmask, NULL); 4632 4633 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4634 FORKEE_ASSERT(raise(sigval) == 0); 4635 4636 DPRINTF("Before allocating memory for stack in child\n"); 4637 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 4638 4639 DPRINTF("Before making context for new lwp in child\n"); 4640 _lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize); 4641 4642 DPRINTF("Before creating new in child\n"); 4643 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 4644 4645 DPRINTF("Before waiting for lwp %d to exit\n", lid); 4646 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 4647 4648 DPRINTF("Before verifying that reported %d and running lid %d " 4649 "are the same\n", lid, the_lwp_id); 4650 FORKEE_ASSERT_EQ(lid, the_lwp_id); 4651 4652 DPRINTF("Before exiting of the child process\n"); 4653 _exit(exitval); 4654 } 4655 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4656 4657 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4658 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4659 4660 validate_status_stopped(status, sigval); 4661 4662 DPRINTF("Set empty EVENT_MASK for the child %d\n", child); 4663 event.pe_set_event = PTRACE_LWP_EXIT; 4664 SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1); 4665 4666 DPRINTF("Before resuming the child process where it left off and " 4667 "without signal to be sent\n"); 4668 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4669 4670 DPRINTF("Before calling %s() for the child - expected stopped " 4671 "SIGTRAP\n", TWAIT_FNAME); 4672 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4673 4674 validate_status_stopped(status, sigmasked); 4675 4676 SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1); 4677 4678 ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_EXIT); 4679 4680 lid = state.pe_lwp; 4681 DPRINTF("Reported PTRACE_LWP_EXIT event with lid %d\n", lid); 4682 4683 DPRINTF("Before resuming the child process where it left off and " 4684 "without signal to be sent\n"); 4685 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4686 4687 DPRINTF("Before calling %s() for the child - expected exited\n", 4688 TWAIT_FNAME); 4689 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4690 4691 validate_status_exited(status, exitval); 4692 4693 DPRINTF("Before calling %s() for the child - expected no process\n", 4694 TWAIT_FNAME); 4695 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4696} 4697 4698static void 4699lwp_main_stop(void *arg) 4700{ 4701 the_lwp_id = _lwp_self(); 4702 4703 raise(SIGTRAP); 4704 4705 _lwp_exit(); 4706} 4707 4708ATF_TC(suspend1); 4709ATF_TC_HEAD(suspend1, tc) 4710{ 4711 atf_tc_set_md_var(tc, "descr", 4712 "Verify that a thread can be suspended by a debugger and later " 4713 "resumed by a tracee"); 4714} 4715 4716ATF_TC_BODY(suspend1, tc) 4717{ 4718 const int exitval = 5; 4719 const int sigval = SIGSTOP; 4720 pid_t child, wpid; 4721#if defined(TWAIT_HAVE_STATUS) 4722 int status; 4723#endif 4724 ucontext_t uc; 4725 lwpid_t lid; 4726 static const size_t ssize = 16*1024; 4727 void *stack; 4728 struct ptrace_lwpinfo pl; 4729 struct ptrace_siginfo psi; 4730 volatile int go = 0; 4731 4732 // Feature pending for refactoring 4733 atf_tc_expect_fail("PR kern/51995"); 4734 4735 // Hangs with qemu 4736 ATF_REQUIRE(0 && "In order to get reliable failure, abort"); 4737 4738 DPRINTF("Before forking process PID=%d\n", getpid()); 4739 SYSCALL_REQUIRE((child = fork()) != -1); 4740 if (child == 0) { 4741 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4742 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4743 4744 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4745 FORKEE_ASSERT(raise(sigval) == 0); 4746 4747 DPRINTF("Before allocating memory for stack in child\n"); 4748 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 4749 4750 DPRINTF("Before making context for new lwp in child\n"); 4751 _lwp_makecontext(&uc, lwp_main_stop, NULL, NULL, stack, ssize); 4752 4753 DPRINTF("Before creating new in child\n"); 4754 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 4755 4756 while (go == 0) 4757 continue; 4758 4759 raise(SIGINT); 4760 4761 FORKEE_ASSERT(_lwp_continue(lid) == 0); 4762 4763 DPRINTF("Before waiting for lwp %d to exit\n", lid); 4764 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 4765 4766 DPRINTF("Before verifying that reported %d and running lid %d " 4767 "are the same\n", lid, the_lwp_id); 4768 FORKEE_ASSERT_EQ(lid, the_lwp_id); 4769 4770 DPRINTF("Before exiting of the child process\n"); 4771 _exit(exitval); 4772 } 4773 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 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_stopped(status, sigval); 4779 4780 DPRINTF("Before resuming the child process where it left off and " 4781 "without signal to be sent\n"); 4782 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4783 4784 DPRINTF("Before calling %s() for the child - expected stopped " 4785 "SIGTRAP\n", TWAIT_FNAME); 4786 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4787 4788 validate_status_stopped(status, SIGTRAP); 4789 4790 DPRINTF("Before reading siginfo and lwpid_t\n"); 4791 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1); 4792 4793 DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid); 4794 SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1); 4795 4796 DPRINTF("Write new go to tracee (PID=%d) from tracer (PID=%d)\n", 4797 child, getpid()); 4798 SYSCALL_REQUIRE(ptrace(PT_WRITE_D, child, __UNVOLATILE(&go), 1) != -1); 4799 4800 DPRINTF("Before resuming the child process where it left off and " 4801 "without signal to be sent\n"); 4802 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4803 4804 DPRINTF("Before calling %s() for the child - expected stopped " 4805 "SIGINT\n", TWAIT_FNAME); 4806 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4807 4808 validate_status_stopped(status, SIGINT); 4809 4810 pl.pl_lwpid = 0; 4811 4812 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 4813 while (pl.pl_lwpid != 0) { 4814 4815 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 4816 switch (pl.pl_lwpid) { 4817 case 1: 4818 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SIGNAL); 4819 break; 4820 case 2: 4821 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SUSPENDED); 4822 break; 4823 } 4824 } 4825 4826 DPRINTF("Before resuming the child process where it left off and " 4827 "without signal to be sent\n"); 4828 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4829 4830 DPRINTF("Before calling %s() for the child - expected exited\n", 4831 TWAIT_FNAME); 4832 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4833 4834 validate_status_exited(status, exitval); 4835 4836 DPRINTF("Before calling %s() for the child - expected no process\n", 4837 TWAIT_FNAME); 4838 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4839} 4840 4841ATF_TC(suspend2); 4842ATF_TC_HEAD(suspend2, tc) 4843{ 4844 atf_tc_set_md_var(tc, "descr", 4845 "Verify that the while the only thread within a process is " 4846 "suspended, the whole process cannot be unstopped"); 4847} 4848 4849ATF_TC_BODY(suspend2, tc) 4850{ 4851 const int exitval = 5; 4852 const int sigval = SIGSTOP; 4853 pid_t child, wpid; 4854#if defined(TWAIT_HAVE_STATUS) 4855 int status; 4856#endif 4857 struct ptrace_siginfo psi; 4858 4859 // Feature pending for refactoring 4860 atf_tc_expect_fail("PR kern/51995"); 4861 4862 // Hangs with qemu 4863 ATF_REQUIRE(0 && "In order to get reliable failure, abort"); 4864 4865 DPRINTF("Before forking process PID=%d\n", getpid()); 4866 SYSCALL_REQUIRE((child = fork()) != -1); 4867 if (child == 0) { 4868 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4869 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4870 4871 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4872 FORKEE_ASSERT(raise(sigval) == 0); 4873 4874 DPRINTF("Before exiting of the child process\n"); 4875 _exit(exitval); 4876 } 4877 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4878 4879 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4880 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4881 4882 validate_status_stopped(status, sigval); 4883 4884 DPRINTF("Before reading siginfo and lwpid_t\n"); 4885 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1); 4886 4887 DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid); 4888 SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1); 4889 4890 DPRINTF("Before resuming the child process where it left off and " 4891 "without signal to be sent\n"); 4892 ATF_REQUIRE_ERRNO(EDEADLK, 4893 ptrace(PT_CONTINUE, child, (void *)1, 0) == -1); 4894 4895 DPRINTF("Before resuming LWP %d\n", psi.psi_lwpid); 4896 SYSCALL_REQUIRE(ptrace(PT_RESUME, child, NULL, psi.psi_lwpid) != -1); 4897 4898 DPRINTF("Before resuming the child process where it left off and " 4899 "without signal to be sent\n"); 4900 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4901 4902 DPRINTF("Before calling %s() for the child - expected exited\n", 4903 TWAIT_FNAME); 4904 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4905 4906 validate_status_exited(status, exitval); 4907 4908 DPRINTF("Before calling %s() for the child - expected no process\n", 4909 TWAIT_FNAME); 4910 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 4911} 4912 4913ATF_TC(resume1); 4914ATF_TC_HEAD(resume1, tc) 4915{ 4916 atf_tc_set_md_var(tc, "timeout", "5"); 4917 atf_tc_set_md_var(tc, "descr", 4918 "Verify that a thread can be suspended by a debugger and later " 4919 "resumed by the debugger"); 4920} 4921 4922ATF_TC_BODY(resume1, tc) 4923{ 4924 struct msg_fds fds; 4925 const int exitval = 5; 4926 const int sigval = SIGSTOP; 4927 pid_t child, wpid; 4928 uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */ 4929#if defined(TWAIT_HAVE_STATUS) 4930 int status; 4931#endif 4932 ucontext_t uc; 4933 lwpid_t lid; 4934 static const size_t ssize = 16*1024; 4935 void *stack; 4936 struct ptrace_lwpinfo pl; 4937 struct ptrace_siginfo psi; 4938 4939 // Feature pending for refactoring 4940 atf_tc_expect_fail("PR kern/51995"); 4941 4942 // Hangs with qemu 4943 ATF_REQUIRE(0 && "In order to get reliable failure, abort"); 4944 4945 SYSCALL_REQUIRE(msg_open(&fds) == 0); 4946 4947 DPRINTF("Before forking process PID=%d\n", getpid()); 4948 SYSCALL_REQUIRE((child = fork()) != -1); 4949 if (child == 0) { 4950 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 4951 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 4952 4953 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 4954 FORKEE_ASSERT(raise(sigval) == 0); 4955 4956 DPRINTF("Before allocating memory for stack in child\n"); 4957 FORKEE_ASSERT((stack = malloc(ssize)) != NULL); 4958 4959 DPRINTF("Before making context for new lwp in child\n"); 4960 _lwp_makecontext(&uc, lwp_main_stop, NULL, NULL, stack, ssize); 4961 4962 DPRINTF("Before creating new in child\n"); 4963 FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0); 4964 4965 CHILD_TO_PARENT("Message", fds, msg); 4966 4967 raise(SIGINT); 4968 4969 DPRINTF("Before waiting for lwp %d to exit\n", lid); 4970 FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0); 4971 4972 DPRINTF("Before verifying that reported %d and running lid %d " 4973 "are the same\n", lid, the_lwp_id); 4974 FORKEE_ASSERT_EQ(lid, the_lwp_id); 4975 4976 DPRINTF("Before exiting of the child process\n"); 4977 _exit(exitval); 4978 } 4979 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 4980 4981 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 4982 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4983 4984 validate_status_stopped(status, sigval); 4985 4986 DPRINTF("Before resuming the child process where it left off and " 4987 "without signal to be sent\n"); 4988 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 4989 4990 DPRINTF("Before calling %s() for the child - expected stopped " 4991 "SIGTRAP\n", TWAIT_FNAME); 4992 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 4993 4994 validate_status_stopped(status, SIGTRAP); 4995 4996 DPRINTF("Before reading siginfo and lwpid_t\n"); 4997 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1); 4998 4999 DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid); 5000 SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1); 5001 5002 PARENT_FROM_CHILD("Message", fds, msg); 5003 5004 DPRINTF("Before resuming the child process where it left off and " 5005 "without signal to be sent\n"); 5006 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5007 5008 DPRINTF("Before calling %s() for the child - expected stopped " 5009 "SIGINT\n", TWAIT_FNAME); 5010 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5011 5012 validate_status_stopped(status, SIGINT); 5013 5014 pl.pl_lwpid = 0; 5015 5016 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 5017 while (pl.pl_lwpid != 0) { 5018 SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1); 5019 switch (pl.pl_lwpid) { 5020 case 1: 5021 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SIGNAL); 5022 break; 5023 case 2: 5024 ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SUSPENDED); 5025 break; 5026 } 5027 } 5028 5029 DPRINTF("Before resuming LWP %d\n", psi.psi_lwpid); 5030 SYSCALL_REQUIRE(ptrace(PT_RESUME, child, NULL, psi.psi_lwpid) != -1); 5031 5032 DPRINTF("Before resuming the child process where it left off and " 5033 "without signal to be sent\n"); 5034 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5035 5036 DPRINTF("Before calling %s() for the child - expected exited\n", 5037 TWAIT_FNAME); 5038 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5039 5040 validate_status_exited(status, exitval); 5041 5042 DPRINTF("Before calling %s() for the child - expected no process\n", 5043 TWAIT_FNAME); 5044 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5045 5046 msg_close(&fds); 5047 5048 DPRINTF("XXX: Test worked this time but for consistency timeout it\n"); 5049 sleep(10); 5050} 5051 5052ATF_TC(syscall1); 5053ATF_TC_HEAD(syscall1, tc) 5054{ 5055 atf_tc_set_md_var(tc, "descr", 5056 "Verify that getpid(2) can be traced with PT_SYSCALL"); 5057} 5058 5059ATF_TC_BODY(syscall1, tc) 5060{ 5061 const int exitval = 5; 5062 const int sigval = SIGSTOP; 5063 pid_t child, wpid; 5064#if defined(TWAIT_HAVE_STATUS) 5065 int status; 5066#endif 5067 struct ptrace_siginfo info; 5068 memset(&info, 0, sizeof(info)); 5069 5070 DPRINTF("Before forking process PID=%d\n", getpid()); 5071 SYSCALL_REQUIRE((child = fork()) != -1); 5072 if (child == 0) { 5073 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5074 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5075 5076 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5077 FORKEE_ASSERT(raise(sigval) == 0); 5078 5079 syscall(SYS_getpid); 5080 5081 DPRINTF("Before exiting of the child process\n"); 5082 _exit(exitval); 5083 } 5084 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5085 5086 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5087 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5088 5089 validate_status_stopped(status, sigval); 5090 5091 DPRINTF("Before resuming the child process where it left off and " 5092 "without signal to be sent\n"); 5093 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 5094 5095 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5096 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5097 5098 validate_status_stopped(status, SIGTRAP); 5099 5100 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 5101 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 5102 5103 DPRINTF("Before checking siginfo_t and lwpid\n"); 5104 ATF_REQUIRE_EQ(info.psi_lwpid, 1); 5105 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 5106 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_SCE); 5107 5108 DPRINTF("Before resuming the child process where it left off and " 5109 "without signal to be sent\n"); 5110 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 5111 5112 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5113 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5114 5115 validate_status_stopped(status, SIGTRAP); 5116 5117 DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n"); 5118 SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1); 5119 5120 DPRINTF("Before checking siginfo_t and lwpid\n"); 5121 ATF_REQUIRE_EQ(info.psi_lwpid, 1); 5122 ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP); 5123 ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_SCX); 5124 5125 DPRINTF("Before resuming the child process where it left off and " 5126 "without signal to be sent\n"); 5127 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5128 5129 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5130 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5131 5132 validate_status_exited(status, exitval); 5133 5134 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5135 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5136} 5137 5138ATF_TC(syscallemu1); 5139ATF_TC_HEAD(syscallemu1, tc) 5140{ 5141 atf_tc_set_md_var(tc, "descr", 5142 "Verify that exit(2) can be intercepted with PT_SYSCALLEMU"); 5143} 5144 5145ATF_TC_BODY(syscallemu1, tc) 5146{ 5147 const int exitval = 5; 5148 const int sigval = SIGSTOP; 5149 pid_t child, wpid; 5150#if defined(TWAIT_HAVE_STATUS) 5151 int status; 5152#endif 5153 5154#if defined(__sparc__) && !defined(__sparc64__) 5155 /* syscallemu does not work on sparc (32-bit) */ 5156 atf_tc_expect_fail("PR kern/52166"); 5157#endif 5158 5159 DPRINTF("Before forking process PID=%d\n", getpid()); 5160 SYSCALL_REQUIRE((child = fork()) != -1); 5161 if (child == 0) { 5162 DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid()); 5163 FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1); 5164 5165 DPRINTF("Before raising %s from child\n", strsignal(sigval)); 5166 FORKEE_ASSERT(raise(sigval) == 0); 5167 5168 syscall(SYS_exit, 100); 5169 5170 DPRINTF("Before exiting of the child process\n"); 5171 _exit(exitval); 5172 } 5173 DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child); 5174 5175 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5176 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5177 5178 validate_status_stopped(status, sigval); 5179 5180 DPRINTF("Before resuming the child process where it left off and " 5181 "without signal to be sent\n"); 5182 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 5183 5184 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5185 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5186 5187 validate_status_stopped(status, SIGTRAP); 5188 5189 DPRINTF("Set SYSCALLEMU for intercepted syscall\n"); 5190 SYSCALL_REQUIRE(ptrace(PT_SYSCALLEMU, child, (void *)1, 0) != -1); 5191 5192 DPRINTF("Before resuming the child process where it left off and " 5193 "without signal to be sent\n"); 5194 SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1); 5195 5196 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5197 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5198 5199 validate_status_stopped(status, SIGTRAP); 5200 5201 DPRINTF("Before resuming the child process where it left off and " 5202 "without signal to be sent\n"); 5203 SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1); 5204 5205 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5206 TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child); 5207 5208 validate_status_exited(status, exitval); 5209 5210 DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME); 5211 TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0)); 5212} 5213 5214#include "t_ptrace_amd64_wait.h" 5215#include "t_ptrace_i386_wait.h" 5216#include "t_ptrace_x86_wait.h" 5217 5218ATF_TP_ADD_TCS(tp) 5219{ 5220 setvbuf(stdout, NULL, _IONBF, 0); 5221 setvbuf(stderr, NULL, _IONBF, 0); 5222 5223 ATF_TP_ADD_TC(tp, traceme_raise1); 5224 ATF_TP_ADD_TC(tp, traceme_raise2); 5225 ATF_TP_ADD_TC(tp, traceme_raise3); 5226 ATF_TP_ADD_TC(tp, traceme_raise4); 5227 ATF_TP_ADD_TC(tp, traceme_raise5); 5228 5229 ATF_TP_ADD_TC(tp, traceme_crash_trap); 5230 ATF_TP_ADD_TC(tp, traceme_crash_segv); 5231 ATF_TP_ADD_TC(tp, traceme_crash_ill); 5232 ATF_TP_ADD_TC(tp, traceme_crash_fpe); 5233 ATF_TP_ADD_TC(tp, traceme_crash_bus); 5234 5235 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle1); 5236 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle2); 5237 ATF_TP_ADD_TC(tp, traceme_sendsignal_handle3); 5238 5239 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked1); 5240 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked2); 5241 ATF_TP_ADD_TC(tp, traceme_sendsignal_masked3); 5242 5243 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored1); 5244 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored2); 5245 ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored3); 5246 5247 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple1); 5248 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple2); 5249 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple3); 5250 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple4); 5251 ATF_TP_ADD_TC(tp, traceme_sendsignal_simple5); 5252 5253 ATF_TP_ADD_TC(tp, traceme_pid1_parent); 5254 5255 ATF_TP_ADD_TC(tp, traceme_vfork_raise1); 5256 ATF_TP_ADD_TC(tp, traceme_vfork_raise2); 5257 ATF_TP_ADD_TC(tp, traceme_vfork_raise3); 5258 ATF_TP_ADD_TC(tp, traceme_vfork_raise4); 5259 ATF_TP_ADD_TC(tp, traceme_vfork_raise5); 5260 ATF_TP_ADD_TC(tp, traceme_vfork_raise6); 5261 ATF_TP_ADD_TC(tp, traceme_vfork_raise7); 5262 ATF_TP_ADD_TC(tp, traceme_vfork_raise8); 5263 5264 ATF_TP_ADD_TC(tp, traceme_vfork_crash_trap); 5265 ATF_TP_ADD_TC(tp, traceme_vfork_crash_segv); 5266 ATF_TP_ADD_TC(tp, traceme_vfork_crash_ill); 5267 ATF_TP_ADD_TC(tp, traceme_vfork_crash_fpe); 5268 ATF_TP_ADD_TC(tp, traceme_vfork_crash_bus); 5269 5270 ATF_TP_ADD_TC(tp, traceme_vfork_exec); 5271 5272 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_trap); 5273 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_segv); 5274 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_ill); 5275 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_fpe); 5276 ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_bus); 5277 5278 ATF_TP_ADD_TC_HAVE_PID(tp, tracer_sees_terminaton_before_the_parent); 5279 ATF_TP_ADD_TC_HAVE_PID(tp, tracer_sysctl_lookup_without_duplicates); 5280 ATF_TP_ADD_TC_HAVE_PID(tp, 5281 unrelated_tracer_sees_terminaton_before_the_parent); 5282 ATF_TP_ADD_TC_HAVE_PID(tp, tracer_attach_to_unrelated_stopped_process); 5283 5284 ATF_TP_ADD_TC(tp, parent_attach_to_its_child); 5285 ATF_TP_ADD_TC(tp, parent_attach_to_its_stopped_child); 5286 5287 ATF_TP_ADD_TC(tp, child_attach_to_its_parent); 5288 ATF_TP_ADD_TC(tp, child_attach_to_its_stopped_parent); 5289 5290 ATF_TP_ADD_TC_HAVE_PID(tp, 5291 tracee_sees_its_original_parent_getppid); 5292 ATF_TP_ADD_TC_HAVE_PID(tp, 5293 tracee_sees_its_original_parent_sysctl_kinfo_proc2); 5294 ATF_TP_ADD_TC_HAVE_PID(tp, 5295 tracee_sees_its_original_parent_procfs_status); 5296 5297 ATF_TP_ADD_TC(tp, eventmask_preserved_empty); 5298 ATF_TP_ADD_TC(tp, eventmask_preserved_fork); 5299 ATF_TP_ADD_TC(tp, eventmask_preserved_vfork); 5300 ATF_TP_ADD_TC(tp, eventmask_preserved_vfork_done); 5301 ATF_TP_ADD_TC(tp, eventmask_preserved_lwp_create); 5302 ATF_TP_ADD_TC(tp, eventmask_preserved_lwp_exit); 5303 5304 ATF_TP_ADD_TC(tp, fork1); 5305 ATF_TP_ADD_TC_HAVE_PID(tp, fork2); 5306 ATF_TP_ADD_TC_HAVE_PID(tp, fork3); 5307 ATF_TP_ADD_TC_HAVE_PID(tp, fork4); 5308 ATF_TP_ADD_TC(tp, fork5); 5309 ATF_TP_ADD_TC_HAVE_PID(tp, fork6); 5310 ATF_TP_ADD_TC_HAVE_PID(tp, fork7); 5311 ATF_TP_ADD_TC_HAVE_PID(tp, fork8); 5312 5313 ATF_TP_ADD_TC(tp, vfork1); 5314 ATF_TP_ADD_TC_HAVE_PID(tp, vfork2); 5315 ATF_TP_ADD_TC_HAVE_PID(tp, vfork3); 5316 ATF_TP_ADD_TC_HAVE_PID(tp, vfork4); 5317 ATF_TP_ADD_TC(tp, vfork5); 5318 ATF_TP_ADD_TC_HAVE_PID(tp, vfork6); 5319// thes tests hang on SMP machines, disable them for now 5320// ATF_TP_ADD_TC_HAVE_PID(tp, vfork7); 5321// ATF_TP_ADD_TC_HAVE_PID(tp, vfork8); 5322 5323 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_8); 5324 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_16); 5325 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_32); 5326 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_64); 5327 5328 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_8); 5329 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_16); 5330 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_32); 5331 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_64); 5332 5333 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_8); 5334 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_16); 5335 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_32); 5336 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_64); 5337 5338 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_8); 5339 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_16); 5340 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_32); 5341 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_64); 5342 5343 ATF_TP_ADD_TC(tp, bytes_transfer_read_d); 5344 ATF_TP_ADD_TC(tp, bytes_transfer_read_i); 5345 ATF_TP_ADD_TC(tp, bytes_transfer_write_d); 5346 ATF_TP_ADD_TC(tp, bytes_transfer_write_i); 5347 5348 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_8_text); 5349 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_16_text); 5350 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_32_text); 5351 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_64_text); 5352 5353 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_8_text); 5354 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_16_text); 5355 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_32_text); 5356 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_64_text); 5357 5358 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_8_text); 5359 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_16_text); 5360 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_32_text); 5361 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_64_text); 5362 5363 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_8_text); 5364 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_16_text); 5365 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_32_text); 5366 ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_64_text); 5367 5368 ATF_TP_ADD_TC(tp, bytes_transfer_read_d_text); 5369 ATF_TP_ADD_TC(tp, bytes_transfer_read_i_text); 5370 ATF_TP_ADD_TC(tp, bytes_transfer_write_d_text); 5371 ATF_TP_ADD_TC(tp, bytes_transfer_write_i_text); 5372 5373 ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_auxv); 5374 5375 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs1); 5376 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs2); 5377 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs3); 5378 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs4); 5379 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs5); 5380 ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs6); 5381 5382 ATF_TP_ADD_TC_HAVE_FPREGS(tp, access_fpregs1); 5383 ATF_TP_ADD_TC_HAVE_FPREGS(tp, access_fpregs2); 5384 5385 ATF_TP_ADD_TC_PT_STEP(tp, step1); 5386 ATF_TP_ADD_TC_PT_STEP(tp, step2); 5387 ATF_TP_ADD_TC_PT_STEP(tp, step3); 5388 ATF_TP_ADD_TC_PT_STEP(tp, step4); 5389 5390 ATF_TP_ADD_TC_PT_STEP(tp, setstep1); 5391 ATF_TP_ADD_TC_PT_STEP(tp, setstep2); 5392 ATF_TP_ADD_TC_PT_STEP(tp, setstep3); 5393 ATF_TP_ADD_TC_PT_STEP(tp, setstep4); 5394 5395 ATF_TP_ADD_TC(tp, kill1); 5396 ATF_TP_ADD_TC(tp, kill2); 5397 ATF_TP_ADD_TC(tp, kill3); 5398 5399 ATF_TP_ADD_TC(tp, traceme_lwpinfo0); 5400 ATF_TP_ADD_TC(tp, traceme_lwpinfo1); 5401 ATF_TP_ADD_TC(tp, traceme_lwpinfo2); 5402 ATF_TP_ADD_TC(tp, traceme_lwpinfo3); 5403 5404 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo0); 5405 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo1); 5406 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo2); 5407 ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo3); 5408 5409 ATF_TP_ADD_TC(tp, siginfo_set_unmodified); 5410 ATF_TP_ADD_TC(tp, siginfo_set_faked); 5411 5412 ATF_TP_ADD_TC(tp, siginfo4); 5413 ATF_TP_ADD_TC_PT_STEP(tp, siginfo6); 5414 5415 ATF_TP_ADD_TC(tp, lwp_create1); 5416 5417 ATF_TP_ADD_TC(tp, lwp_exit1); 5418 5419 ATF_TP_ADD_TC(tp, signal1); 5420 ATF_TP_ADD_TC(tp, signal2); 5421 ATF_TP_ADD_TC(tp, signal3); 5422 ATF_TP_ADD_TC_PT_STEP(tp, signal4); 5423 ATF_TP_ADD_TC(tp, signal5); 5424 ATF_TP_ADD_TC_HAVE_PID(tp, signal6); 5425 ATF_TP_ADD_TC_HAVE_PID(tp, signal7); 5426 ATF_TP_ADD_TC(tp, signal8); 5427 ATF_TP_ADD_TC(tp, signal9); 5428 ATF_TP_ADD_TC(tp, signal10); 5429 5430 ATF_TP_ADD_TC(tp, suspend1); 5431 ATF_TP_ADD_TC(tp, suspend2); 5432 5433 ATF_TP_ADD_TC(tp, resume1); 5434 5435 ATF_TP_ADD_TC(tp, syscall1); 5436 5437 ATF_TP_ADD_TC(tp, syscallemu1); 5438 5439 ATF_TP_ADD_TCS_PTRACE_WAIT_AMD64(); 5440 ATF_TP_ADD_TCS_PTRACE_WAIT_I386(); 5441 ATF_TP_ADD_TCS_PTRACE_WAIT_X86(); 5442 5443 return atf_no_error(); 5444} 5445