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