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