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