t_ptrace_wait.c revision 1.137
1/*	$NetBSD: t_ptrace_wait.c,v 1.137 2019/10/13 09:42:15 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.137 2019/10/13 09:42:15 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 1
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
5458#define TRACE_THREADS_NUM 100
5459
5460static volatile int done;
5461pthread_mutex_t trace_threads_mtx = PTHREAD_MUTEX_INITIALIZER;
5462
5463static void *
5464trace_threads_cb(void *arg __unused)
5465{
5466
5467	pthread_mutex_lock(&trace_threads_mtx);
5468	done++;
5469	pthread_mutex_unlock(&trace_threads_mtx);
5470
5471	while (done < TRACE_THREADS_NUM)
5472		sched_yield();
5473
5474	return NULL;
5475}
5476
5477static void
5478trace_threads(bool trace_create, bool trace_exit)
5479{
5480	const int sigval = SIGSTOP;
5481	pid_t child, wpid;
5482#if defined(TWAIT_HAVE_STATUS)
5483	int status;
5484#endif
5485	ptrace_state_t state;
5486	const int slen = sizeof(state);
5487	ptrace_event_t event;
5488	const int elen = sizeof(event);
5489	struct ptrace_siginfo info;
5490
5491	pthread_t t[TRACE_THREADS_NUM];
5492	int rv;
5493	size_t n;
5494	lwpid_t lid;
5495
5496	/* Track created and exited threads */
5497	bool traced_lwps[__arraycount(t)];
5498
5499#if !TEST_LWP_ENABLED
5500	if (trace_create || trace_exit)
5501		atf_tc_skip("PR kern/51995");
5502#endif
5503
5504	DPRINTF("Before forking process PID=%d\n", getpid());
5505	SYSCALL_REQUIRE((child = fork()) != -1);
5506	if (child == 0) {
5507		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
5508		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
5509
5510		DPRINTF("Before raising %s from child\n", strsignal(sigval));
5511		FORKEE_ASSERT(raise(sigval) == 0);
5512
5513		for (n = 0; n < __arraycount(t); n++) {
5514			rv = pthread_create(&t[n], NULL, trace_threads_cb,
5515			    NULL);
5516			FORKEE_ASSERT(rv == 0);
5517		}
5518
5519		for (n = 0; n < __arraycount(t); n++) {
5520			rv = pthread_join(t[n], NULL);
5521			FORKEE_ASSERT(rv == 0);
5522		}
5523
5524		/*
5525		 * There is race between _exit() and pthread_join() detaching
5526		 * a thread. For simplicity kill the process after detecting
5527		 * LWP events.
5528		 */
5529		while (true)
5530			continue;
5531
5532		FORKEE_ASSERT(0 && "Not reached");
5533	}
5534	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
5535
5536	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
5537	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
5538
5539	validate_status_stopped(status, sigval);
5540
5541	DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n");
5542	SYSCALL_REQUIRE(
5543	    ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
5544
5545	DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid);
5546	DPRINTF("Signal properties: si_signo=%#x si_code=%#x si_errno=%#x\n",
5547	    info.psi_siginfo.si_signo, info.psi_siginfo.si_code,
5548	    info.psi_siginfo.si_errno);
5549
5550	ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval);
5551	ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP);
5552
5553	DPRINTF("Set LWP event mask for the child %d\n", child);
5554	memset(&event, 0, sizeof(event));
5555	if (trace_create)
5556		event.pe_set_event |= PTRACE_LWP_CREATE;
5557	if (trace_exit)
5558		event.pe_set_event |= PTRACE_LWP_EXIT;
5559	SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1);
5560
5561	DPRINTF("Before resuming the child process where it left off and "
5562	    "without signal to be sent\n");
5563	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
5564
5565	memset(traced_lwps, 0, sizeof(traced_lwps));
5566
5567	for (n = 0; n < (trace_create ? __arraycount(t) : 0); n++) {
5568		DPRINTF("Before calling %s() for the child - expected stopped "
5569		    "SIGTRAP\n", TWAIT_FNAME);
5570		TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0),
5571		    child);
5572
5573		validate_status_stopped(status, SIGTRAP);
5574
5575		DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for "
5576		    "child\n");
5577		SYSCALL_REQUIRE(
5578		    ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
5579
5580		DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid);
5581		DPRINTF("Signal properties: si_signo=%#x si_code=%#x "
5582		    "si_errno=%#x\n",
5583		    info.psi_siginfo.si_signo, info.psi_siginfo.si_code,
5584		    info.psi_siginfo.si_errno);
5585
5586		ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP);
5587		ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_LWP);
5588
5589		SYSCALL_REQUIRE(
5590		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
5591
5592		ATF_REQUIRE_EQ_MSG(state.pe_report_event, PTRACE_LWP_CREATE,
5593		    "%d != %d", state.pe_report_event, PTRACE_LWP_CREATE);
5594
5595		lid = state.pe_lwp;
5596		DPRINTF("Reported PTRACE_LWP_CREATE event with lid %d\n", lid);
5597
5598		traced_lwps[lid - 1] = true;
5599
5600		DPRINTF("Before resuming the child process where it left off "
5601		    "and without signal to be sent\n");
5602		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
5603	}
5604
5605	for (n = 0; n < (trace_exit ? __arraycount(t) : 0); n++) {
5606		DPRINTF("Before calling %s() for the child - expected stopped "
5607		    "SIGTRAP\n", TWAIT_FNAME);
5608		TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0),
5609		    child);
5610
5611		validate_status_stopped(status, SIGTRAP);
5612
5613		DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for "
5614		    "child\n");
5615		SYSCALL_REQUIRE(
5616		    ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
5617
5618		DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid);
5619		DPRINTF("Signal properties: si_signo=%#x si_code=%#x "
5620		    "si_errno=%#x\n",
5621		    info.psi_siginfo.si_signo, info.psi_siginfo.si_code,
5622		    info.psi_siginfo.si_errno);
5623
5624		ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP);
5625		ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_LWP);
5626
5627		SYSCALL_REQUIRE(
5628		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
5629
5630		ATF_REQUIRE_EQ_MSG(state.pe_report_event, PTRACE_LWP_EXIT,
5631		    "%d != %d", state.pe_report_event, PTRACE_LWP_EXIT);
5632
5633		lid = state.pe_lwp;
5634		DPRINTF("Reported PTRACE_LWP_EXIT event with lid %d\n", lid);
5635
5636		if (trace_create) {
5637			ATF_REQUIRE(traced_lwps[lid - 1] == true);
5638			traced_lwps[lid - 1] = false;
5639		}
5640
5641		DPRINTF("Before resuming the child process where it left off "
5642		    "and without signal to be sent\n");
5643		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
5644	}
5645
5646	kill(child, SIGKILL);
5647
5648	DPRINTF("Before calling %s() for the child - expected exited\n",
5649	    TWAIT_FNAME);
5650	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
5651
5652	validate_status_signaled(status, SIGKILL, 0);
5653
5654	DPRINTF("Before calling %s() for the child - expected no process\n",
5655	    TWAIT_FNAME);
5656	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
5657}
5658
5659#define TRACE_THREADS(test, trace_create, trace_exit)			\
5660ATF_TC(test);								\
5661ATF_TC_HEAD(test, tc)							\
5662{									\
5663        atf_tc_set_md_var(tc, "descr",					\
5664            "Verify spawning threads with%s tracing LWP create and"	\
5665	    "with%s tracing LWP exit", trace_create ? "" : "out",	\
5666	    trace_exit ? "" : "out");					\
5667}									\
5668									\
5669ATF_TC_BODY(test, tc)							\
5670{									\
5671									\
5672        trace_threads(trace_create, trace_exit);			\
5673}
5674
5675TRACE_THREADS(trace_thread_nolwpevents, false, false)
5676TRACE_THREADS(trace_thread_lwpexit, false, true)
5677TRACE_THREADS(trace_thread_lwpcreate, true, false)
5678TRACE_THREADS(trace_thread_lwpcreate_and_exit, true, true)
5679
5680/// ----------------------------------------------------------------------------
5681
5682ATF_TC(signal_mask_unrelated);
5683ATF_TC_HEAD(signal_mask_unrelated, tc)
5684{
5685	atf_tc_set_md_var(tc, "descr",
5686	    "Verify that masking single unrelated signal does not stop tracer "
5687	    "from catching other signals");
5688}
5689
5690ATF_TC_BODY(signal_mask_unrelated, tc)
5691{
5692	const int exitval = 5;
5693	const int sigval = SIGSTOP;
5694	const int sigmasked = SIGTRAP;
5695	const int signotmasked = SIGINT;
5696	pid_t child, wpid;
5697#if defined(TWAIT_HAVE_STATUS)
5698	int status;
5699#endif
5700	sigset_t intmask;
5701
5702	DPRINTF("Before forking process PID=%d\n", getpid());
5703	SYSCALL_REQUIRE((child = fork()) != -1);
5704	if (child == 0) {
5705		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
5706		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
5707
5708		sigemptyset(&intmask);
5709		sigaddset(&intmask, sigmasked);
5710		sigprocmask(SIG_BLOCK, &intmask, NULL);
5711
5712		DPRINTF("Before raising %s from child\n", strsignal(sigval));
5713		FORKEE_ASSERT(raise(sigval) == 0);
5714
5715		DPRINTF("Before raising %s from child\n",
5716		    strsignal(signotmasked));
5717		FORKEE_ASSERT(raise(signotmasked) == 0);
5718
5719		DPRINTF("Before exiting of the child process\n");
5720		_exit(exitval);
5721	}
5722	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
5723
5724	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
5725	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
5726
5727	validate_status_stopped(status, sigval);
5728
5729	DPRINTF("Before resuming the child process where it left off and "
5730	    "without signal to be sent\n");
5731	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
5732
5733	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
5734	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
5735
5736	validate_status_stopped(status, signotmasked);
5737
5738	DPRINTF("Before resuming the child process where it left off and "
5739	    "without signal to be sent\n");
5740	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
5741
5742	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
5743	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
5744
5745	validate_status_exited(status, exitval);
5746
5747	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
5748	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
5749}
5750
5751/// ----------------------------------------------------------------------------
5752
5753#if defined(TWAIT_HAVE_PID)
5754static void
5755fork2_body(const char *fn, bool masked, bool ignored)
5756{
5757	const int exitval = 5;
5758	const int exitval2 = 0; /* Match exit status from /bin/echo */
5759	const int sigval = SIGSTOP;
5760	pid_t child, child2 = 0, wpid;
5761#if defined(TWAIT_HAVE_STATUS)
5762	int status;
5763#endif
5764	ptrace_state_t state;
5765	const int slen = sizeof(state);
5766	ptrace_event_t event;
5767	const int elen = sizeof(event);
5768	struct sigaction sa;
5769	struct ptrace_siginfo info;
5770	sigset_t intmask;
5771	struct kinfo_proc2 kp;
5772	size_t len = sizeof(kp);
5773
5774	int name[6];
5775	const size_t namelen = __arraycount(name);
5776	ki_sigset_t kp_sigmask;
5777	ki_sigset_t kp_sigignore;
5778
5779	char * const arg[] = { __UNCONST("/bin/echo"), NULL };
5780
5781	DPRINTF("Before forking process PID=%d\n", getpid());
5782	SYSCALL_REQUIRE((child = fork()) != -1);
5783	if (child == 0) {
5784		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
5785		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
5786
5787		if (masked) {
5788			sigemptyset(&intmask);
5789			sigaddset(&intmask, SIGTRAP);
5790			sigprocmask(SIG_BLOCK, &intmask, NULL);
5791		}
5792
5793		if (ignored) {
5794			memset(&sa, 0, sizeof(sa));
5795			sa.sa_handler = SIG_IGN;
5796			sigemptyset(&sa.sa_mask);
5797			FORKEE_ASSERT(sigaction(SIGTRAP, &sa, NULL) != -1);
5798		}
5799
5800		DPRINTF("Before raising %s from child\n", strsignal(sigval));
5801		FORKEE_ASSERT(raise(sigval) == 0);
5802
5803		if (strcmp(fn, "spawn") == 0) {
5804			FORKEE_ASSERT_EQ(posix_spawn(&child2,
5805			    arg[0], NULL, NULL, arg, NULL), 0);
5806		} else  {
5807			if (strcmp(fn, "fork") == 0) {
5808				FORKEE_ASSERT((child2 = fork()) != -1);
5809			} else {
5810				FORKEE_ASSERT((child2 = vfork()) != -1);
5811			}
5812			if (child2 == 0)
5813				_exit(exitval2);
5814		}
5815
5816		FORKEE_REQUIRE_SUCCESS
5817		    (wpid = TWAIT_GENERIC(child2, &status, 0), child2);
5818
5819		forkee_status_exited(status, exitval2);
5820
5821		DPRINTF("Before exiting of the child process\n");
5822		_exit(exitval);
5823	}
5824	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
5825
5826	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
5827	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
5828
5829	validate_status_stopped(status, sigval);
5830
5831	DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n");
5832	SYSCALL_REQUIRE(
5833	    ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
5834
5835	DPRINTF("Before checking siginfo_t\n");
5836	ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval);
5837	ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP);
5838
5839	name[0] = CTL_KERN,
5840	name[1] = KERN_PROC2,
5841	name[2] = KERN_PROC_PID;
5842	name[3] = child;
5843	name[4] = sizeof(kp);
5844	name[5] = 1;
5845
5846	FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
5847
5848	if (masked)
5849		kp_sigmask = kp.p_sigmask;
5850
5851	if (ignored)
5852		kp_sigignore = kp.p_sigignore;
5853
5854	DPRINTF("Set 0%s%s%s%s in EVENT_MASK for the child %d\n",
5855	    strcmp(fn, "spawn") == 0 ? "|PTRACE_POSIX_SPAWN" : "",
5856	    strcmp(fn, "fork") == 0 ? "|PTRACE_FORK" : "",
5857	    strcmp(fn, "vfork") == 0 ? "|PTRACE_VFORK" : "",
5858	    strcmp(fn, "vforkdone") == 0 ? "|PTRACE_VFORK_DONE" : "", child);
5859	event.pe_set_event = 0;
5860	if (strcmp(fn, "spawn") == 0)
5861		event.pe_set_event |= PTRACE_POSIX_SPAWN;
5862	if (strcmp(fn, "fork") == 0)
5863		event.pe_set_event |= PTRACE_FORK;
5864	if (strcmp(fn, "vfork") == 0)
5865		event.pe_set_event |= PTRACE_VFORK;
5866	if (strcmp(fn, "vforkdone") == 0)
5867		event.pe_set_event |= PTRACE_VFORK_DONE;
5868	SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1);
5869
5870	DPRINTF("Before resuming the child process where it left off and "
5871	    "without signal to be sent\n");
5872	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
5873
5874	if (strcmp(fn, "spawn") == 0 || strcmp(fn, "fork") == 0 ||
5875	    strcmp(fn, "vfork") == 0) {
5876		DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME,
5877		    child);
5878		TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0),
5879		    child);
5880
5881		validate_status_stopped(status, SIGTRAP);
5882
5883		ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
5884
5885		if (masked) {
5886			DPRINTF("kp_sigmask="
5887			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5888			    PRIx32 "\n",
5889			    kp_sigmask.__bits[0], kp_sigmask.__bits[1],
5890			    kp_sigmask.__bits[2], kp_sigmask.__bits[3]);
5891
5892			DPRINTF("kp.p_sigmask="
5893			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5894			    PRIx32 "\n",
5895			    kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1],
5896			    kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]);
5897
5898			ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask,
5899			    sizeof(kp_sigmask)));
5900		}
5901
5902		if (ignored) {
5903			DPRINTF("kp_sigignore="
5904			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5905			    PRIx32 "\n",
5906			    kp_sigignore.__bits[0], kp_sigignore.__bits[1],
5907			    kp_sigignore.__bits[2], kp_sigignore.__bits[3]);
5908
5909			DPRINTF("kp.p_sigignore="
5910			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5911			    PRIx32 "\n",
5912			    kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1],
5913			    kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]);
5914
5915			ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore,
5916			    sizeof(kp_sigignore)));
5917		}
5918
5919		SYSCALL_REQUIRE(
5920		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
5921		if (strcmp(fn, "spawn") == 0) {
5922			ATF_REQUIRE_EQ(
5923			    state.pe_report_event & PTRACE_POSIX_SPAWN,
5924			       PTRACE_POSIX_SPAWN);
5925		}
5926		if (strcmp(fn, "fork") == 0) {
5927			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK,
5928			       PTRACE_FORK);
5929		}
5930		if (strcmp(fn, "vfork") == 0) {
5931			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK,
5932			       PTRACE_VFORK);
5933		}
5934
5935		child2 = state.pe_other_pid;
5936		DPRINTF("Reported ptrace event with forkee %d\n", child2);
5937
5938		DPRINTF("Before calling %s() for the forkee %d of the child "
5939		    "%d\n", TWAIT_FNAME, child2, child);
5940		TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0),
5941		    child2);
5942
5943		validate_status_stopped(status, SIGTRAP);
5944
5945		name[3] = child2;
5946		ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
5947
5948		if (masked) {
5949			DPRINTF("kp_sigmask="
5950			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5951			    PRIx32 "\n",
5952			    kp_sigmask.__bits[0], kp_sigmask.__bits[1],
5953			    kp_sigmask.__bits[2], kp_sigmask.__bits[3]);
5954
5955			DPRINTF("kp.p_sigmask="
5956			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5957			    PRIx32 "\n",
5958			    kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1],
5959			    kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]);
5960
5961			ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask,
5962			    sizeof(kp_sigmask)));
5963		}
5964
5965		if (ignored) {
5966			DPRINTF("kp_sigignore="
5967			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5968			    PRIx32 "\n",
5969			    kp_sigignore.__bits[0], kp_sigignore.__bits[1],
5970			    kp_sigignore.__bits[2], kp_sigignore.__bits[3]);
5971
5972			DPRINTF("kp.p_sigignore="
5973			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
5974			    PRIx32 "\n",
5975			    kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1],
5976			    kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]);
5977
5978			ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore,
5979			    sizeof(kp_sigignore)));
5980		}
5981
5982		SYSCALL_REQUIRE(
5983		    ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1);
5984		if (strcmp(fn, "spawn") == 0) {
5985			ATF_REQUIRE_EQ(
5986			    state.pe_report_event & PTRACE_POSIX_SPAWN,
5987			       PTRACE_POSIX_SPAWN);
5988		}
5989		if (strcmp(fn, "fork") == 0) {
5990			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK,
5991			       PTRACE_FORK);
5992		}
5993		if (strcmp(fn, "vfork") == 0) {
5994			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK,
5995			       PTRACE_VFORK);
5996		}
5997
5998		ATF_REQUIRE_EQ(state.pe_other_pid, child);
5999
6000		DPRINTF("Before resuming the forkee process where it left off "
6001		    "and without signal to be sent\n");
6002		SYSCALL_REQUIRE(
6003		    ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1);
6004
6005		DPRINTF("Before resuming the child process where it left off "
6006		    "and without signal to be sent\n");
6007		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6008	}
6009
6010	if (strcmp(fn, "vforkdone") == 0) {
6011		DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME,
6012		    child);
6013		TWAIT_REQUIRE_SUCCESS(
6014		    wpid = TWAIT_GENERIC(child, &status, 0), child);
6015
6016		validate_status_stopped(status, SIGTRAP);
6017
6018		name[3] = child;
6019		ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
6020
6021		/*
6022		 * SIGCHLD is now pending in the signal queue and
6023		 * the kernel presents it to userland as a masked signal.
6024		 */
6025		sigdelset((sigset_t *)&kp.p_sigmask, SIGCHLD);
6026
6027		if (masked) {
6028			DPRINTF("kp_sigmask="
6029			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
6030			    PRIx32 "\n",
6031			    kp_sigmask.__bits[0], kp_sigmask.__bits[1],
6032			    kp_sigmask.__bits[2], kp_sigmask.__bits[3]);
6033
6034			DPRINTF("kp.p_sigmask="
6035			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
6036			    PRIx32 "\n",
6037			    kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1],
6038			    kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]);
6039
6040			ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask,
6041			    sizeof(kp_sigmask)));
6042		}
6043
6044		if (ignored) {
6045			DPRINTF("kp_sigignore="
6046			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
6047			    PRIx32 "\n",
6048			    kp_sigignore.__bits[0], kp_sigignore.__bits[1],
6049			    kp_sigignore.__bits[2], kp_sigignore.__bits[3]);
6050
6051			DPRINTF("kp.p_sigignore="
6052			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
6053			    PRIx32 "\n",
6054			    kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1],
6055			    kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]);
6056
6057			ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore,
6058			    sizeof(kp_sigignore)));
6059		}
6060
6061		SYSCALL_REQUIRE(
6062		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
6063		ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE);
6064
6065		child2 = state.pe_other_pid;
6066		DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n",
6067		    child2);
6068
6069		DPRINTF("Before resuming the child process where it left off "
6070		    "and without signal to be sent\n");
6071		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6072	}
6073
6074	if (strcmp(fn, "spawn") == 0 || strcmp(fn, "fork") == 0 ||
6075	    strcmp(fn, "vfork") == 0) {
6076		DPRINTF("Before calling %s() for the forkee - expected exited"
6077		    "\n", TWAIT_FNAME);
6078		TWAIT_REQUIRE_SUCCESS(
6079		    wpid = TWAIT_GENERIC(child2, &status, 0), child2);
6080
6081		validate_status_exited(status, exitval2);
6082
6083		DPRINTF("Before calling %s() for the forkee - expected no "
6084		    "process\n", TWAIT_FNAME);
6085		TWAIT_REQUIRE_FAILURE(ECHILD,
6086		    wpid = TWAIT_GENERIC(child2, &status, 0));
6087	}
6088
6089	DPRINTF("Before calling %s() for the child - expected stopped "
6090	    "SIGCHLD\n", TWAIT_FNAME);
6091	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6092
6093	validate_status_stopped(status, SIGCHLD);
6094
6095	DPRINTF("Before resuming the child process where it left off and "
6096	    "without signal to be sent\n");
6097	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6098
6099	DPRINTF("Before calling %s() for the child - expected exited\n",
6100	    TWAIT_FNAME);
6101	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6102
6103	validate_status_exited(status, exitval);
6104
6105	DPRINTF("Before calling %s() for the child - expected no process\n",
6106	    TWAIT_FNAME);
6107	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6108}
6109
6110#define FORK2_TEST(name,fn,masked,ignored)				\
6111ATF_TC(name);								\
6112ATF_TC_HEAD(name, tc)							\
6113{									\
6114	atf_tc_set_md_var(tc, "descr", "Verify that " fn " is caught "	\
6115	    "regardless of signal %s%s", 				\
6116	    masked ? "masked" : "", ignored ? "ignored" : "");		\
6117}									\
6118									\
6119ATF_TC_BODY(name, tc)							\
6120{									\
6121									\
6122	fork2_body(fn, masked, ignored);				\
6123}
6124
6125FORK2_TEST(posix_spawn_singalmasked, "spawn", true, false)
6126FORK2_TEST(posix_spawn_singalignored, "spawn", false, true)
6127FORK2_TEST(fork_singalmasked, "fork", true, false)
6128FORK2_TEST(fork_singalignored, "fork", false, true)
6129#if TEST_VFORK_ENABLED
6130FORK2_TEST(vfork_singalmasked, "vfork", true, false)
6131FORK2_TEST(vfork_singalignored, "vfork", false, true)
6132FORK2_TEST(vforkdone_singalmasked, "vforkdone", true, false)
6133FORK2_TEST(vforkdone_singalignored, "vforkdone", false, true)
6134#endif
6135#endif
6136
6137/// ----------------------------------------------------------------------------
6138
6139volatile lwpid_t the_lwp_id = 0;
6140
6141static void
6142lwp_main_func(void *arg)
6143{
6144	the_lwp_id = _lwp_self();
6145	_lwp_exit();
6146}
6147
6148ATF_TC(signal9);
6149ATF_TC_HEAD(signal9, tc)
6150{
6151	atf_tc_set_md_var(tc, "descr",
6152	    "Verify that masking SIGTRAP in tracee does not stop tracer from "
6153	    "catching PTRACE_LWP_CREATE breakpoint");
6154}
6155
6156ATF_TC_BODY(signal9, tc)
6157{
6158	const int exitval = 5;
6159	const int sigval = SIGSTOP;
6160	const int sigmasked = SIGTRAP;
6161	pid_t child, wpid;
6162#if defined(TWAIT_HAVE_STATUS)
6163	int status;
6164#endif
6165	sigset_t intmask;
6166	ptrace_state_t state;
6167	const int slen = sizeof(state);
6168	ptrace_event_t event;
6169	const int elen = sizeof(event);
6170	ucontext_t uc;
6171	lwpid_t lid;
6172	static const size_t ssize = 16*1024;
6173	void *stack;
6174
6175	DPRINTF("Before forking process PID=%d\n", getpid());
6176	SYSCALL_REQUIRE((child = fork()) != -1);
6177	if (child == 0) {
6178		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6179		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6180
6181		sigemptyset(&intmask);
6182		sigaddset(&intmask, sigmasked);
6183		sigprocmask(SIG_BLOCK, &intmask, NULL);
6184
6185		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6186		FORKEE_ASSERT(raise(sigval) == 0);
6187
6188		DPRINTF("Before allocating memory for stack in child\n");
6189		FORKEE_ASSERT((stack = malloc(ssize)) != NULL);
6190
6191		DPRINTF("Before making context for new lwp in child\n");
6192		_lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize);
6193
6194		DPRINTF("Before creating new in child\n");
6195		FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0);
6196
6197		DPRINTF("Before waiting for lwp %d to exit\n", lid);
6198		FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0);
6199
6200		DPRINTF("Before verifying that reported %d and running lid %d "
6201		    "are the same\n", lid, the_lwp_id);
6202		FORKEE_ASSERT_EQ(lid, the_lwp_id);
6203
6204		DPRINTF("Before exiting of the child process\n");
6205		_exit(exitval);
6206	}
6207	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6208
6209	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6210	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6211
6212	validate_status_stopped(status, sigval);
6213
6214	DPRINTF("Set empty EVENT_MASK for the child %d\n", child);
6215	event.pe_set_event = PTRACE_LWP_CREATE;
6216	SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1);
6217
6218	DPRINTF("Before resuming the child process where it left off and "
6219	    "without signal to be sent\n");
6220	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6221
6222	DPRINTF("Before calling %s() for the child - expected stopped "
6223	    "SIGTRAP\n", TWAIT_FNAME);
6224	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6225
6226	validate_status_stopped(status, sigmasked);
6227
6228	SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
6229
6230	ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_CREATE);
6231
6232	lid = state.pe_lwp;
6233	DPRINTF("Reported PTRACE_LWP_CREATE event with lid %d\n", lid);
6234
6235	DPRINTF("Before resuming the child process where it left off and "
6236	    "without signal to be sent\n");
6237	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6238
6239	DPRINTF("Before calling %s() for the child - expected exited\n",
6240	    TWAIT_FNAME);
6241	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6242
6243	validate_status_exited(status, exitval);
6244
6245	DPRINTF("Before calling %s() for the child - expected no process\n",
6246	    TWAIT_FNAME);
6247	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6248}
6249
6250ATF_TC(signal10);
6251ATF_TC_HEAD(signal10, tc)
6252{
6253	atf_tc_set_md_var(tc, "descr",
6254	    "Verify that masking SIGTRAP in tracee does not stop tracer from "
6255	    "catching PTRACE_LWP_EXIT breakpoint");
6256}
6257
6258ATF_TC_BODY(signal10, tc)
6259{
6260	const int exitval = 5;
6261	const int sigval = SIGSTOP;
6262	const int sigmasked = SIGTRAP;
6263	pid_t child, wpid;
6264#if defined(TWAIT_HAVE_STATUS)
6265	int status;
6266#endif
6267	sigset_t intmask;
6268	ptrace_state_t state;
6269	const int slen = sizeof(state);
6270	ptrace_event_t event;
6271	const int elen = sizeof(event);
6272	ucontext_t uc;
6273	lwpid_t lid;
6274	static const size_t ssize = 16*1024;
6275	void *stack;
6276
6277	DPRINTF("Before forking process PID=%d\n", getpid());
6278	SYSCALL_REQUIRE((child = fork()) != -1);
6279	if (child == 0) {
6280		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6281		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6282
6283		sigemptyset(&intmask);
6284		sigaddset(&intmask, sigmasked);
6285		sigprocmask(SIG_BLOCK, &intmask, NULL);
6286
6287		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6288		FORKEE_ASSERT(raise(sigval) == 0);
6289
6290		DPRINTF("Before allocating memory for stack in child\n");
6291		FORKEE_ASSERT((stack = malloc(ssize)) != NULL);
6292
6293		DPRINTF("Before making context for new lwp in child\n");
6294		_lwp_makecontext(&uc, lwp_main_func, NULL, NULL, stack, ssize);
6295
6296		DPRINTF("Before creating new in child\n");
6297		FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0);
6298
6299		DPRINTF("Before waiting for lwp %d to exit\n", lid);
6300		FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0);
6301
6302		DPRINTF("Before verifying that reported %d and running lid %d "
6303		    "are the same\n", lid, the_lwp_id);
6304		FORKEE_ASSERT_EQ(lid, the_lwp_id);
6305
6306		DPRINTF("Before exiting of the child process\n");
6307		_exit(exitval);
6308	}
6309	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6310
6311	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6312	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6313
6314	validate_status_stopped(status, sigval);
6315
6316	DPRINTF("Set empty EVENT_MASK for the child %d\n", child);
6317	event.pe_set_event = PTRACE_LWP_EXIT;
6318	SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1);
6319
6320	DPRINTF("Before resuming the child process where it left off and "
6321	    "without signal to be sent\n");
6322	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6323
6324	DPRINTF("Before calling %s() for the child - expected stopped "
6325	    "SIGTRAP\n", TWAIT_FNAME);
6326	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6327
6328	validate_status_stopped(status, sigmasked);
6329
6330	SYSCALL_REQUIRE(ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
6331
6332	ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_LWP_EXIT);
6333
6334	lid = state.pe_lwp;
6335	DPRINTF("Reported PTRACE_LWP_EXIT event with lid %d\n", lid);
6336
6337	DPRINTF("Before resuming the child process where it left off and "
6338	    "without signal to be sent\n");
6339	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6340
6341	DPRINTF("Before calling %s() for the child - expected exited\n",
6342	    TWAIT_FNAME);
6343	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6344
6345	validate_status_exited(status, exitval);
6346
6347	DPRINTF("Before calling %s() for the child - expected no process\n",
6348	    TWAIT_FNAME);
6349	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6350}
6351
6352static void
6353lwp_main_stop(void *arg)
6354{
6355	the_lwp_id = _lwp_self();
6356
6357	raise(SIGTRAP);
6358
6359	_lwp_exit();
6360}
6361
6362ATF_TC(suspend2);
6363ATF_TC_HEAD(suspend2, tc)
6364{
6365	atf_tc_set_md_var(tc, "descr",
6366	    "Verify that the while the only thread within a process is "
6367	    "suspended, the whole process cannot be unstopped");
6368}
6369
6370ATF_TC_BODY(suspend2, tc)
6371{
6372	const int exitval = 5;
6373	const int sigval = SIGSTOP;
6374	pid_t child, wpid;
6375#if defined(TWAIT_HAVE_STATUS)
6376	int status;
6377#endif
6378	struct ptrace_siginfo psi;
6379
6380	DPRINTF("Before forking process PID=%d\n", getpid());
6381	SYSCALL_REQUIRE((child = fork()) != -1);
6382	if (child == 0) {
6383		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6384		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6385
6386		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6387		FORKEE_ASSERT(raise(sigval) == 0);
6388
6389		DPRINTF("Before exiting of the child process\n");
6390		_exit(exitval);
6391	}
6392	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6393
6394	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6395	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6396
6397	validate_status_stopped(status, sigval);
6398
6399	DPRINTF("Before reading siginfo and lwpid_t\n");
6400	SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1);
6401
6402	DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid);
6403	SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1);
6404
6405	DPRINTF("Before resuming the child process where it left off and "
6406	    "without signal to be sent\n");
6407	ATF_REQUIRE_ERRNO(EDEADLK,
6408	    ptrace(PT_CONTINUE, child, (void *)1, 0) == -1);
6409
6410	DPRINTF("Before resuming LWP %d\n", psi.psi_lwpid);
6411	SYSCALL_REQUIRE(ptrace(PT_RESUME, child, NULL, psi.psi_lwpid) != -1);
6412
6413	DPRINTF("Before resuming the child process where it left off and "
6414	    "without signal to be sent\n");
6415	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6416
6417	DPRINTF("Before calling %s() for the child - expected exited\n",
6418	    TWAIT_FNAME);
6419	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6420
6421	validate_status_exited(status, exitval);
6422
6423	DPRINTF("Before calling %s() for the child - expected no process\n",
6424	    TWAIT_FNAME);
6425	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6426}
6427
6428ATF_TC(resume1);
6429ATF_TC_HEAD(resume1, tc)
6430{
6431	atf_tc_set_md_var(tc, "descr",
6432	    "Verify that a thread can be suspended by a debugger and later "
6433	    "resumed by the debugger");
6434}
6435
6436ATF_TC_BODY(resume1, tc)
6437{
6438	struct msg_fds fds;
6439	const int exitval = 5;
6440	const int sigval = SIGSTOP;
6441	pid_t child, wpid;
6442	uint8_t msg = 0xde; /* dummy message for IPC based on pipe(2) */
6443#if defined(TWAIT_HAVE_STATUS)
6444	int status;
6445#endif
6446	ucontext_t uc;
6447	lwpid_t lid;
6448	static const size_t ssize = 16*1024;
6449	void *stack;
6450	struct ptrace_lwpinfo pl;
6451	struct ptrace_siginfo psi;
6452
6453	SYSCALL_REQUIRE(msg_open(&fds) == 0);
6454
6455	DPRINTF("Before forking process PID=%d\n", getpid());
6456	SYSCALL_REQUIRE((child = fork()) != -1);
6457	if (child == 0) {
6458		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6459		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6460
6461		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6462		FORKEE_ASSERT(raise(sigval) == 0);
6463
6464		DPRINTF("Before allocating memory for stack in child\n");
6465		FORKEE_ASSERT((stack = malloc(ssize)) != NULL);
6466
6467		DPRINTF("Before making context for new lwp in child\n");
6468		_lwp_makecontext(&uc, lwp_main_stop, NULL, NULL, stack, ssize);
6469
6470		DPRINTF("Before creating new in child\n");
6471		FORKEE_ASSERT(_lwp_create(&uc, 0, &lid) == 0);
6472
6473		CHILD_TO_PARENT("Message", fds, msg);
6474
6475		raise(SIGINT);
6476
6477		DPRINTF("Before waiting for lwp %d to exit\n", lid);
6478		FORKEE_ASSERT(_lwp_wait(lid, NULL) == 0);
6479
6480		DPRINTF("Before verifying that reported %d and running lid %d "
6481		    "are the same\n", lid, the_lwp_id);
6482		FORKEE_ASSERT_EQ(lid, the_lwp_id);
6483
6484		DPRINTF("Before exiting of the child process\n");
6485		_exit(exitval);
6486	}
6487	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6488
6489	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6490	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6491
6492	validate_status_stopped(status, sigval);
6493
6494	DPRINTF("Before resuming the child process where it left off and "
6495	    "without signal to be sent\n");
6496	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6497
6498	DPRINTF("Before calling %s() for the child - expected stopped "
6499	    "SIGTRAP\n", TWAIT_FNAME);
6500	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6501
6502	validate_status_stopped(status, SIGTRAP);
6503
6504	DPRINTF("Before reading siginfo and lwpid_t\n");
6505	SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &psi, sizeof(psi)) != -1);
6506
6507	DPRINTF("Before suspending LWP %d\n", psi.psi_lwpid);
6508	SYSCALL_REQUIRE(ptrace(PT_SUSPEND, child, NULL, psi.psi_lwpid) != -1);
6509
6510	PARENT_FROM_CHILD("Message", fds, msg);
6511
6512	DPRINTF("Before resuming the child process where it left off and "
6513	    "without signal to be sent\n");
6514	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6515
6516	DPRINTF("Before calling %s() for the child - expected stopped "
6517	    "SIGINT\n", TWAIT_FNAME);
6518	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6519
6520	validate_status_stopped(status, SIGINT);
6521
6522	pl.pl_lwpid = 0;
6523
6524	SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1);
6525	while (pl.pl_lwpid != 0) {
6526		SYSCALL_REQUIRE(ptrace(PT_LWPINFO, child, &pl, sizeof(pl)) != -1);
6527		switch (pl.pl_lwpid) {
6528		case 1:
6529			ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SIGNAL);
6530			break;
6531		case 2:
6532			ATF_REQUIRE_EQ(pl.pl_event, PL_EVENT_SUSPENDED);
6533			break;
6534		}
6535	}
6536
6537	DPRINTF("Before resuming LWP %d\n", psi.psi_lwpid);
6538	SYSCALL_REQUIRE(ptrace(PT_RESUME, child, NULL, psi.psi_lwpid) != -1);
6539
6540	DPRINTF("Before resuming the child process where it left off and "
6541	    "without signal to be sent\n");
6542	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6543
6544	DPRINTF("Before calling %s() for the child - expected exited\n",
6545	    TWAIT_FNAME);
6546	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6547
6548	validate_status_exited(status, exitval);
6549
6550	DPRINTF("Before calling %s() for the child - expected no process\n",
6551	    TWAIT_FNAME);
6552	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6553
6554	msg_close(&fds);
6555}
6556
6557ATF_TC(syscall1);
6558ATF_TC_HEAD(syscall1, tc)
6559{
6560	atf_tc_set_md_var(tc, "descr",
6561	    "Verify that getpid(2) can be traced with PT_SYSCALL");
6562}
6563
6564ATF_TC_BODY(syscall1, tc)
6565{
6566	const int exitval = 5;
6567	const int sigval = SIGSTOP;
6568	pid_t child, wpid;
6569#if defined(TWAIT_HAVE_STATUS)
6570	int status;
6571#endif
6572	struct ptrace_siginfo info;
6573	memset(&info, 0, sizeof(info));
6574
6575	DPRINTF("Before forking process PID=%d\n", getpid());
6576	SYSCALL_REQUIRE((child = fork()) != -1);
6577	if (child == 0) {
6578		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6579		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6580
6581		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6582		FORKEE_ASSERT(raise(sigval) == 0);
6583
6584		syscall(SYS_getpid);
6585
6586		DPRINTF("Before exiting of the child process\n");
6587		_exit(exitval);
6588	}
6589	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6590
6591	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6592	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6593
6594	validate_status_stopped(status, sigval);
6595
6596	DPRINTF("Before resuming the child process where it left off and "
6597	    "without signal to be sent\n");
6598	SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1);
6599
6600	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6601	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6602
6603	validate_status_stopped(status, SIGTRAP);
6604
6605	DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n");
6606	SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
6607
6608	DPRINTF("Before checking siginfo_t and lwpid\n");
6609	ATF_REQUIRE_EQ(info.psi_lwpid, 1);
6610	ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP);
6611	ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_SCE);
6612
6613	DPRINTF("Before resuming the child process where it left off and "
6614	    "without signal to be sent\n");
6615	SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1);
6616
6617	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6618	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6619
6620	validate_status_stopped(status, SIGTRAP);
6621
6622	DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n");
6623	SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
6624
6625	DPRINTF("Before checking siginfo_t and lwpid\n");
6626	ATF_REQUIRE_EQ(info.psi_lwpid, 1);
6627	ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, SIGTRAP);
6628	ATF_REQUIRE_EQ(info.psi_siginfo.si_code, TRAP_SCX);
6629
6630	DPRINTF("Before resuming the child process where it left off and "
6631	    "without signal to be sent\n");
6632	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6633
6634	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6635	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6636
6637	validate_status_exited(status, exitval);
6638
6639	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6640	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6641}
6642
6643ATF_TC(syscallemu1);
6644ATF_TC_HEAD(syscallemu1, tc)
6645{
6646	atf_tc_set_md_var(tc, "descr",
6647	    "Verify that exit(2) can be intercepted with PT_SYSCALLEMU");
6648}
6649
6650ATF_TC_BODY(syscallemu1, tc)
6651{
6652	const int exitval = 5;
6653	const int sigval = SIGSTOP;
6654	pid_t child, wpid;
6655#if defined(TWAIT_HAVE_STATUS)
6656	int status;
6657#endif
6658
6659#if defined(__sparc__) && !defined(__sparc64__)
6660	/* syscallemu does not work on sparc (32-bit) */
6661	atf_tc_expect_fail("PR kern/52166");
6662#endif
6663
6664	DPRINTF("Before forking process PID=%d\n", getpid());
6665	SYSCALL_REQUIRE((child = fork()) != -1);
6666	if (child == 0) {
6667		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6668		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6669
6670		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6671		FORKEE_ASSERT(raise(sigval) == 0);
6672
6673		syscall(SYS_exit, 100);
6674
6675		DPRINTF("Before exiting of the child process\n");
6676		_exit(exitval);
6677	}
6678	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6679
6680	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6681	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6682
6683	validate_status_stopped(status, sigval);
6684
6685	DPRINTF("Before resuming the child process where it left off and "
6686	    "without signal to be sent\n");
6687	SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1);
6688
6689	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6690	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6691
6692	validate_status_stopped(status, SIGTRAP);
6693
6694	DPRINTF("Set SYSCALLEMU for intercepted syscall\n");
6695	SYSCALL_REQUIRE(ptrace(PT_SYSCALLEMU, child, (void *)1, 0) != -1);
6696
6697	DPRINTF("Before resuming the child process where it left off and "
6698	    "without signal to be sent\n");
6699	SYSCALL_REQUIRE(ptrace(PT_SYSCALL, child, (void *)1, 0) != -1);
6700
6701	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6702	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6703
6704	validate_status_stopped(status, SIGTRAP);
6705
6706	DPRINTF("Before resuming the child process where it left off and "
6707	    "without signal to be sent\n");
6708	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6709
6710	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6711	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6712
6713	validate_status_exited(status, exitval);
6714
6715	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6716	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6717}
6718
6719/// ----------------------------------------------------------------------------
6720
6721static void
6722clone_body(int flags, bool trackfork, bool trackvfork,
6723    bool trackvforkdone)
6724{
6725	const int exitval = 5;
6726	const int exitval2 = 15;
6727	const int sigval = SIGSTOP;
6728	pid_t child, child2 = 0, wpid;
6729#if defined(TWAIT_HAVE_STATUS)
6730	int status;
6731#endif
6732	ptrace_state_t state;
6733	const int slen = sizeof(state);
6734	ptrace_event_t event;
6735	const int elen = sizeof(event);
6736
6737	const size_t stack_size = 1024 * 1024;
6738	void *stack, *stack_base;
6739
6740	stack = malloc(stack_size);
6741	ATF_REQUIRE(stack != NULL);
6742
6743#ifdef __MACHINE_STACK_GROWS_UP
6744	stack_base = stack;
6745#else
6746	stack_base = (char *)stack + stack_size;
6747#endif
6748
6749	DPRINTF("Before forking process PID=%d\n", getpid());
6750	SYSCALL_REQUIRE((child = fork()) != -1);
6751	if (child == 0) {
6752		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
6753		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
6754
6755		DPRINTF("Before raising %s from child\n", strsignal(sigval));
6756		FORKEE_ASSERT(raise(sigval) == 0);
6757
6758		SYSCALL_REQUIRE((child2 = __clone(clone_func, stack_base,
6759		    flags|SIGCHLD, (void *)(intptr_t)exitval2)) != -1);
6760
6761		DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(),
6762		    child2);
6763
6764		// XXX WALLSIG?
6765		FORKEE_REQUIRE_SUCCESS
6766		    (wpid = TWAIT_GENERIC(child2, &status, WALLSIG), child2);
6767
6768		forkee_status_exited(status, exitval2);
6769
6770		DPRINTF("Before exiting of the child process\n");
6771		_exit(exitval);
6772	}
6773	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
6774
6775	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
6776	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6777
6778	validate_status_stopped(status, sigval);
6779
6780	DPRINTF("Set 0%s%s%s in EVENT_MASK for the child %d\n",
6781	    trackfork ? "|PTRACE_FORK" : "",
6782	    trackvfork ? "|PTRACE_VFORK" : "",
6783	    trackvforkdone ? "|PTRACE_VFORK_DONE" : "", child);
6784	event.pe_set_event = 0;
6785	if (trackfork)
6786		event.pe_set_event |= PTRACE_FORK;
6787	if (trackvfork)
6788		event.pe_set_event |= PTRACE_VFORK;
6789	if (trackvforkdone)
6790		event.pe_set_event |= PTRACE_VFORK_DONE;
6791	SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1);
6792
6793	DPRINTF("Before resuming the child process where it left off and "
6794	    "without signal to be sent\n");
6795	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6796
6797#if defined(TWAIT_HAVE_PID)
6798	if ((trackfork && !(flags & CLONE_VFORK)) ||
6799	    (trackvfork && (flags & CLONE_VFORK))) {
6800		DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME,
6801		    child);
6802		TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0),
6803		    child);
6804
6805		validate_status_stopped(status, SIGTRAP);
6806
6807		SYSCALL_REQUIRE(
6808		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
6809		if (trackfork && !(flags & CLONE_VFORK)) {
6810			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK,
6811			       PTRACE_FORK);
6812		}
6813		if (trackvfork && (flags & CLONE_VFORK)) {
6814			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK,
6815			       PTRACE_VFORK);
6816		}
6817
6818		child2 = state.pe_other_pid;
6819		DPRINTF("Reported ptrace event with forkee %d\n", child2);
6820
6821		DPRINTF("Before calling %s() for the forkee %d of the child "
6822		    "%d\n", TWAIT_FNAME, child2, child);
6823		TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0),
6824		    child2);
6825
6826		validate_status_stopped(status, SIGTRAP);
6827
6828		SYSCALL_REQUIRE(
6829		    ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1);
6830		if (trackfork && !(flags & CLONE_VFORK)) {
6831			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK,
6832			       PTRACE_FORK);
6833		}
6834		if (trackvfork && (flags & CLONE_VFORK)) {
6835			ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK,
6836			       PTRACE_VFORK);
6837		}
6838
6839		ATF_REQUIRE_EQ(state.pe_other_pid, child);
6840
6841		DPRINTF("Before resuming the forkee process where it left off "
6842		    "and without signal to be sent\n");
6843		SYSCALL_REQUIRE(
6844		    ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1);
6845
6846		DPRINTF("Before resuming the child process where it left off "
6847		    "and without signal to be sent\n");
6848		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6849	}
6850#endif
6851
6852	if (trackvforkdone && (flags & CLONE_VFORK)) {
6853		DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME,
6854		    child);
6855		TWAIT_REQUIRE_SUCCESS(
6856		    wpid = TWAIT_GENERIC(child, &status, 0), child);
6857
6858		validate_status_stopped(status, SIGTRAP);
6859
6860		SYSCALL_REQUIRE(
6861		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
6862		ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE);
6863
6864		child2 = state.pe_other_pid;
6865		DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n",
6866		    child2);
6867
6868		DPRINTF("Before resuming the child process where it left off "
6869		    "and without signal to be sent\n");
6870		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6871	}
6872
6873#if defined(TWAIT_HAVE_PID)
6874	if ((trackfork && !(flags & CLONE_VFORK)) ||
6875	    (trackvfork && (flags & CLONE_VFORK))) {
6876		DPRINTF("Before calling %s() for the forkee - expected exited"
6877		    "\n", TWAIT_FNAME);
6878		TWAIT_REQUIRE_SUCCESS(
6879		    wpid = TWAIT_GENERIC(child2, &status, 0), child2);
6880
6881		validate_status_exited(status, exitval2);
6882
6883		DPRINTF("Before calling %s() for the forkee - expected no "
6884		    "process\n", TWAIT_FNAME);
6885		TWAIT_REQUIRE_FAILURE(ECHILD,
6886		    wpid = TWAIT_GENERIC(child2, &status, 0));
6887	}
6888#endif
6889
6890	DPRINTF("Before calling %s() for the child - expected stopped "
6891	    "SIGCHLD\n", TWAIT_FNAME);
6892	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6893
6894	validate_status_stopped(status, SIGCHLD);
6895
6896	DPRINTF("Before resuming the child process where it left off and "
6897	    "without signal to be sent\n");
6898	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
6899
6900	DPRINTF("Before calling %s() for the child - expected exited\n",
6901	    TWAIT_FNAME);
6902	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
6903
6904	validate_status_exited(status, exitval);
6905
6906	DPRINTF("Before calling %s() for the child - expected no process\n",
6907	    TWAIT_FNAME);
6908	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
6909}
6910
6911#define CLONE_TEST(name,flags,tfork,tvfork,tvforkdone)			\
6912ATF_TC(name);								\
6913ATF_TC_HEAD(name, tc)							\
6914{									\
6915	atf_tc_set_md_var(tc, "descr", "Verify clone(%s) "		\
6916	    "called with 0%s%s%s in EVENT_MASK",			\
6917	    #flags,							\
6918	    tfork ? "|PTRACE_FORK" : "",				\
6919	    tvfork ? "|PTRACE_VFORK" : "",				\
6920	    tvforkdone ? "|PTRACE_VFORK_DONE" : "");			\
6921}									\
6922									\
6923ATF_TC_BODY(name, tc)							\
6924{									\
6925									\
6926	clone_body(flags, tfork, tvfork, tvforkdone);			\
6927}
6928
6929CLONE_TEST(clone1, 0, false, false, false)
6930#if defined(TWAIT_HAVE_PID)
6931CLONE_TEST(clone2, 0, true, false, false)
6932CLONE_TEST(clone3, 0, false, true, false)
6933CLONE_TEST(clone4, 0, true, true, false)
6934#endif
6935CLONE_TEST(clone5, 0, false, false, true)
6936#if defined(TWAIT_HAVE_PID)
6937CLONE_TEST(clone6, 0, true, false, true)
6938CLONE_TEST(clone7, 0, false, true, true)
6939CLONE_TEST(clone8, 0, true, true, true)
6940#endif
6941
6942CLONE_TEST(clone_vm1, CLONE_VM, false, false, false)
6943#if defined(TWAIT_HAVE_PID)
6944CLONE_TEST(clone_vm2, CLONE_VM, true, false, false)
6945CLONE_TEST(clone_vm3, CLONE_VM, false, true, false)
6946CLONE_TEST(clone_vm4, CLONE_VM, true, true, false)
6947#endif
6948CLONE_TEST(clone_vm5, CLONE_VM, false, false, true)
6949#if defined(TWAIT_HAVE_PID)
6950CLONE_TEST(clone_vm6, CLONE_VM, true, false, true)
6951CLONE_TEST(clone_vm7, CLONE_VM, false, true, true)
6952CLONE_TEST(clone_vm8, CLONE_VM, true, true, true)
6953#endif
6954
6955CLONE_TEST(clone_fs1, CLONE_FS, false, false, false)
6956#if defined(TWAIT_HAVE_PID)
6957CLONE_TEST(clone_fs2, CLONE_FS, true, false, false)
6958CLONE_TEST(clone_fs3, CLONE_FS, false, true, false)
6959CLONE_TEST(clone_fs4, CLONE_FS, true, true, false)
6960#endif
6961CLONE_TEST(clone_fs5, CLONE_FS, false, false, true)
6962#if defined(TWAIT_HAVE_PID)
6963CLONE_TEST(clone_fs6, CLONE_FS, true, false, true)
6964CLONE_TEST(clone_fs7, CLONE_FS, false, true, true)
6965CLONE_TEST(clone_fs8, CLONE_FS, true, true, true)
6966#endif
6967
6968CLONE_TEST(clone_files1, CLONE_FILES, false, false, false)
6969#if defined(TWAIT_HAVE_PID)
6970CLONE_TEST(clone_files2, CLONE_FILES, true, false, false)
6971CLONE_TEST(clone_files3, CLONE_FILES, false, true, false)
6972CLONE_TEST(clone_files4, CLONE_FILES, true, true, false)
6973#endif
6974CLONE_TEST(clone_files5, CLONE_FILES, false, false, true)
6975#if defined(TWAIT_HAVE_PID)
6976CLONE_TEST(clone_files6, CLONE_FILES, true, false, true)
6977CLONE_TEST(clone_files7, CLONE_FILES, false, true, true)
6978CLONE_TEST(clone_files8, CLONE_FILES, true, true, true)
6979#endif
6980
6981//CLONE_TEST(clone_sighand1, CLONE_SIGHAND, false, false, false)
6982#if defined(TWAIT_HAVE_PID)
6983//CLONE_TEST(clone_sighand2, CLONE_SIGHAND, true, false, false)
6984//CLONE_TEST(clone_sighand3, CLONE_SIGHAND, false, true, false)
6985//CLONE_TEST(clone_sighand4, CLONE_SIGHAND, true, true, false)
6986#endif
6987//CLONE_TEST(clone_sighand5, CLONE_SIGHAND, false, false, true)
6988#if defined(TWAIT_HAVE_PID)
6989//CLONE_TEST(clone_sighand6, CLONE_SIGHAND, true, false, true)
6990//CLONE_TEST(clone_sighand7, CLONE_SIGHAND, false, true, true)
6991//CLONE_TEST(clone_sighand8, CLONE_SIGHAND, true, true, true)
6992#endif
6993
6994#if TEST_VFORK_ENABLED
6995CLONE_TEST(clone_vfork1, CLONE_VFORK, false, false, false)
6996#if defined(TWAIT_HAVE_PID)
6997CLONE_TEST(clone_vfork2, CLONE_VFORK, true, false, false)
6998CLONE_TEST(clone_vfork3, CLONE_VFORK, false, true, false)
6999CLONE_TEST(clone_vfork4, CLONE_VFORK, true, true, false)
7000#endif
7001CLONE_TEST(clone_vfork5, CLONE_VFORK, false, false, true)
7002#if defined(TWAIT_HAVE_PID)
7003CLONE_TEST(clone_vfork6, CLONE_VFORK, true, false, true)
7004CLONE_TEST(clone_vfork7, CLONE_VFORK, false, true, true)
7005CLONE_TEST(clone_vfork8, CLONE_VFORK, true, true, true)
7006#endif
7007#endif
7008
7009/// ----------------------------------------------------------------------------
7010
7011#if defined(TWAIT_HAVE_PID)
7012static void
7013clone_body2(int flags, bool masked, bool ignored)
7014{
7015	const int exitval = 5;
7016	const int exitval2 = 15;
7017	const int sigval = SIGSTOP;
7018	pid_t child, child2 = 0, wpid;
7019#if defined(TWAIT_HAVE_STATUS)
7020	int status;
7021#endif
7022	ptrace_state_t state;
7023	const int slen = sizeof(state);
7024	ptrace_event_t event;
7025	const int elen = sizeof(event);
7026	struct sigaction sa;
7027	struct ptrace_siginfo info;
7028	sigset_t intmask;
7029	struct kinfo_proc2 kp;
7030	size_t len = sizeof(kp);
7031
7032	int name[6];
7033	const size_t namelen = __arraycount(name);
7034	ki_sigset_t kp_sigmask;
7035	ki_sigset_t kp_sigignore;
7036
7037	const size_t stack_size = 1024 * 1024;
7038	void *stack, *stack_base;
7039
7040	stack = malloc(stack_size);
7041	ATF_REQUIRE(stack != NULL);
7042
7043#ifdef __MACHINE_STACK_GROWS_UP
7044	stack_base = stack;
7045#else
7046	stack_base = (char *)stack + stack_size;
7047#endif
7048
7049	SYSCALL_REQUIRE((child = fork()) != -1);
7050	if (child == 0) {
7051		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
7052		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
7053
7054		if (masked) {
7055			sigemptyset(&intmask);
7056			sigaddset(&intmask, SIGTRAP);
7057			sigprocmask(SIG_BLOCK, &intmask, NULL);
7058		}
7059
7060		if (ignored) {
7061			memset(&sa, 0, sizeof(sa));
7062			sa.sa_handler = SIG_IGN;
7063			sigemptyset(&sa.sa_mask);
7064			FORKEE_ASSERT(sigaction(SIGTRAP, &sa, NULL) != -1);
7065		}
7066		DPRINTF("Before raising %s from child\n", strsignal(sigval));
7067		FORKEE_ASSERT(raise(sigval) == 0);
7068
7069		DPRINTF("Before forking process PID=%d flags=%#x\n", getpid(),
7070		    flags);
7071		SYSCALL_REQUIRE((child2 = __clone(clone_func, stack_base,
7072		    flags|SIGCHLD, (void *)(intptr_t)exitval2)) != -1);
7073
7074		DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(),
7075		    child2);
7076
7077		// XXX WALLSIG?
7078		FORKEE_REQUIRE_SUCCESS
7079		    (wpid = TWAIT_GENERIC(child2, &status, WALLSIG), child2);
7080
7081		forkee_status_exited(status, exitval2);
7082
7083		DPRINTF("Before exiting of the child process\n");
7084		_exit(exitval);
7085	}
7086	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
7087
7088	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7089	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7090
7091	validate_status_stopped(status, sigval);
7092
7093	DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for child\n");
7094	SYSCALL_REQUIRE(
7095	    ptrace(PT_GET_SIGINFO, child, &info, sizeof(info)) != -1);
7096
7097	DPRINTF("Before checking siginfo_t\n");
7098	ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval);
7099	ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP);
7100
7101	name[0] = CTL_KERN,
7102	name[1] = KERN_PROC2,
7103	name[2] = KERN_PROC_PID;
7104	name[3] = child;
7105	name[4] = sizeof(kp);
7106	name[5] = 1;
7107
7108	FORKEE_ASSERT_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
7109
7110	if (masked)
7111		kp_sigmask = kp.p_sigmask;
7112
7113	if (ignored)
7114		kp_sigignore = kp.p_sigignore;
7115
7116	DPRINTF("Set PTRACE_FORK | PTRACE_VFORK | PTRACE_VFORK_DONE in "
7117	    "EVENT_MASK for the child %d\n", child);
7118	event.pe_set_event = PTRACE_FORK | PTRACE_VFORK | PTRACE_VFORK_DONE;
7119	SYSCALL_REQUIRE(ptrace(PT_SET_EVENT_MASK, child, &event, elen) != -1);
7120
7121	DPRINTF("Before resuming the child process where it left off and "
7122	    "without signal to be sent\n");
7123	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
7124
7125	DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME,
7126	    child);
7127	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0),
7128	    child);
7129
7130	validate_status_stopped(status, SIGTRAP);
7131
7132	ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
7133
7134	if (masked) {
7135		DPRINTF("kp_sigmask="
7136		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7137		    PRIx32 "\n",
7138		    kp_sigmask.__bits[0], kp_sigmask.__bits[1],
7139		    kp_sigmask.__bits[2], kp_sigmask.__bits[3]);
7140
7141		DPRINTF("kp.p_sigmask="
7142		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7143		    PRIx32 "\n",
7144		    kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1],
7145		    kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]);
7146
7147		ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask,
7148		    sizeof(kp_sigmask)));
7149	}
7150
7151	if (ignored) {
7152		DPRINTF("kp_sigignore="
7153		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7154		    PRIx32 "\n",
7155		    kp_sigignore.__bits[0], kp_sigignore.__bits[1],
7156		    kp_sigignore.__bits[2], kp_sigignore.__bits[3]);
7157
7158		DPRINTF("kp.p_sigignore="
7159		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7160		    PRIx32 "\n",
7161		    kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1],
7162		    kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]);
7163
7164		ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore,
7165		    sizeof(kp_sigignore)));
7166	}
7167
7168	SYSCALL_REQUIRE(
7169	    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
7170	DPRINTF("state.pe_report_event=%#x pid=%d\n", state.pe_report_event,
7171	    child2);
7172	if (!(flags & CLONE_VFORK)) {
7173		ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK,
7174		       PTRACE_FORK);
7175	} else {
7176		ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK,
7177		       PTRACE_VFORK);
7178	}
7179
7180	child2 = state.pe_other_pid;
7181	DPRINTF("Reported ptrace event with forkee %d\n", child2);
7182
7183	DPRINTF("Before calling %s() for the forkee %d of the child "
7184	    "%d\n", TWAIT_FNAME, child2, child);
7185	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child2, &status, 0),
7186	    child2);
7187
7188	validate_status_stopped(status, SIGTRAP);
7189
7190	name[3] = child2;
7191	ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
7192
7193	if (masked) {
7194		DPRINTF("kp_sigmask="
7195		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7196		    PRIx32 "\n",
7197		    kp_sigmask.__bits[0], kp_sigmask.__bits[1],
7198		    kp_sigmask.__bits[2], kp_sigmask.__bits[3]);
7199
7200		DPRINTF("kp.p_sigmask="
7201		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7202		    PRIx32 "\n",
7203		    kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1],
7204		    kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]);
7205
7206		ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask,
7207		    sizeof(kp_sigmask)));
7208	}
7209
7210	if (ignored) {
7211		DPRINTF("kp_sigignore="
7212		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7213		    PRIx32 "\n",
7214		    kp_sigignore.__bits[0], kp_sigignore.__bits[1],
7215		    kp_sigignore.__bits[2], kp_sigignore.__bits[3]);
7216
7217		DPRINTF("kp.p_sigignore="
7218		    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7219		    PRIx32 "\n",
7220		    kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1],
7221		    kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]);
7222
7223		ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore,
7224		    sizeof(kp_sigignore)));
7225	}
7226
7227	SYSCALL_REQUIRE(
7228	    ptrace(PT_GET_PROCESS_STATE, child2, &state, slen) != -1);
7229	if (!(flags & CLONE_VFORK)) {
7230		ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_FORK,
7231		       PTRACE_FORK);
7232	} else {
7233		ATF_REQUIRE_EQ(state.pe_report_event & PTRACE_VFORK,
7234		       PTRACE_VFORK);
7235	}
7236
7237	ATF_REQUIRE_EQ(state.pe_other_pid, child);
7238
7239	DPRINTF("Before resuming the forkee process where it left off "
7240	    "and without signal to be sent\n");
7241	SYSCALL_REQUIRE(
7242	    ptrace(PT_CONTINUE, child2, (void *)1, 0) != -1);
7243
7244	DPRINTF("Before resuming the child process where it left off "
7245	    "and without signal to be sent\n");
7246	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
7247
7248	if (flags & CLONE_VFORK) {
7249		DPRINTF("Before calling %s() for the child %d\n", TWAIT_FNAME,
7250		    child);
7251		TWAIT_REQUIRE_SUCCESS(
7252		    wpid = TWAIT_GENERIC(child, &status, 0), child);
7253
7254		validate_status_stopped(status, SIGTRAP);
7255
7256		name[3] = child;
7257		ATF_REQUIRE_EQ(sysctl(name, namelen, &kp, &len, NULL, 0), 0);
7258
7259		/*
7260		 * SIGCHLD is now pending in the signal queue and
7261		 * the kernel presents it to userland as a masked signal.
7262		 */
7263		sigdelset((sigset_t *)&kp.p_sigmask, SIGCHLD);
7264
7265		if (masked) {
7266			DPRINTF("kp_sigmask="
7267			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7268			    PRIx32 "\n",
7269			    kp_sigmask.__bits[0], kp_sigmask.__bits[1],
7270			    kp_sigmask.__bits[2], kp_sigmask.__bits[3]);
7271
7272			DPRINTF("kp.p_sigmask="
7273			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7274			    PRIx32 "\n",
7275			    kp.p_sigmask.__bits[0], kp.p_sigmask.__bits[1],
7276			    kp.p_sigmask.__bits[2], kp.p_sigmask.__bits[3]);
7277
7278			ATF_REQUIRE(!memcmp(&kp_sigmask, &kp.p_sigmask,
7279			    sizeof(kp_sigmask)));
7280		}
7281
7282		if (ignored) {
7283			DPRINTF("kp_sigignore="
7284			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7285			    PRIx32 "\n",
7286			    kp_sigignore.__bits[0], kp_sigignore.__bits[1],
7287			    kp_sigignore.__bits[2], kp_sigignore.__bits[3]);
7288
7289			DPRINTF("kp.p_sigignore="
7290			    "%#02" PRIx32 "%02" PRIx32 "%02" PRIx32 "%02"
7291			    PRIx32 "\n",
7292			    kp.p_sigignore.__bits[0], kp.p_sigignore.__bits[1],
7293			    kp.p_sigignore.__bits[2], kp.p_sigignore.__bits[3]);
7294
7295			ATF_REQUIRE(!memcmp(&kp_sigignore, &kp.p_sigignore,
7296			    sizeof(kp_sigignore)));
7297		}
7298
7299		SYSCALL_REQUIRE(
7300		    ptrace(PT_GET_PROCESS_STATE, child, &state, slen) != -1);
7301		ATF_REQUIRE_EQ(state.pe_report_event, PTRACE_VFORK_DONE);
7302
7303		child2 = state.pe_other_pid;
7304		DPRINTF("Reported PTRACE_VFORK_DONE event with forkee %d\n",
7305		    child2);
7306
7307		DPRINTF("Before resuming the child process where it left off "
7308		    "and without signal to be sent\n");
7309		SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
7310	}
7311
7312	DPRINTF("Before calling %s() for the forkee - expected exited"
7313	    "\n", TWAIT_FNAME);
7314	TWAIT_REQUIRE_SUCCESS(
7315	    wpid = TWAIT_GENERIC(child2, &status, 0), child2);
7316
7317	validate_status_exited(status, exitval2);
7318
7319	DPRINTF("Before calling %s() for the forkee - expected no "
7320	    "process\n", TWAIT_FNAME);
7321	TWAIT_REQUIRE_FAILURE(ECHILD,
7322	    wpid = TWAIT_GENERIC(child2, &status, 0));
7323
7324	DPRINTF("Before calling %s() for the child - expected stopped "
7325	    "SIGCHLD\n", TWAIT_FNAME);
7326	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7327
7328	validate_status_stopped(status, SIGCHLD);
7329
7330	DPRINTF("Before resuming the child process where it left off and "
7331	    "without signal to be sent\n");
7332	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
7333
7334	DPRINTF("Before calling %s() for the child - expected exited\n",
7335	    TWAIT_FNAME);
7336	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7337
7338	validate_status_exited(status, exitval);
7339
7340	DPRINTF("Before calling %s() for the child - expected no process\n",
7341	    TWAIT_FNAME);
7342	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
7343}
7344
7345#define CLONE_TEST2(name,flags,masked,ignored)				\
7346ATF_TC(name);								\
7347ATF_TC_HEAD(name, tc)							\
7348{									\
7349	atf_tc_set_md_var(tc, "descr", "Verify that clone(%s) is caught"\
7350	    " regardless of signal %s%s", 				\
7351	    #flags, masked ? "masked" : "", ignored ? "ignored" : "");	\
7352}									\
7353									\
7354ATF_TC_BODY(name, tc)							\
7355{									\
7356									\
7357	clone_body2(flags, masked, ignored);				\
7358}
7359
7360CLONE_TEST2(clone_signalignored, 0, true, false)
7361CLONE_TEST2(clone_signalmasked, 0, false, true)
7362CLONE_TEST2(clone_vm_signalignored, CLONE_VM, true, false)
7363CLONE_TEST2(clone_vm_signalmasked, CLONE_VM, false, true)
7364CLONE_TEST2(clone_fs_signalignored, CLONE_FS, true, false)
7365CLONE_TEST2(clone_fs_signalmasked, CLONE_FS, false, true)
7366CLONE_TEST2(clone_files_signalignored, CLONE_FILES, true, false)
7367CLONE_TEST2(clone_files_signalmasked, CLONE_FILES, false, true)
7368//CLONE_TEST2(clone_sighand_signalignored, CLONE_SIGHAND, true, false) // XXX
7369//CLONE_TEST2(clone_sighand_signalmasked, CLONE_SIGHAND, false, true)  // XXX
7370#if TEST_VFORK_ENABLED
7371CLONE_TEST2(clone_vfork_signalignored, CLONE_VFORK, true, false)
7372CLONE_TEST2(clone_vfork_signalmasked, CLONE_VFORK, false, true)
7373#endif
7374#endif
7375
7376/// ----------------------------------------------------------------------------
7377
7378#if TEST_VFORK_ENABLED
7379#if defined(TWAIT_HAVE_PID)
7380static void
7381traceme_vfork_clone_body(int flags)
7382{
7383	const int exitval = 5;
7384	const int exitval2 = 15;
7385	pid_t child, child2 = 0, wpid;
7386#if defined(TWAIT_HAVE_STATUS)
7387	int status;
7388#endif
7389
7390	const size_t stack_size = 1024 * 1024;
7391	void *stack, *stack_base;
7392
7393	stack = malloc(stack_size);
7394	ATF_REQUIRE(stack != NULL);
7395
7396#ifdef __MACHINE_STACK_GROWS_UP
7397	stack_base = stack;
7398#else
7399	stack_base = (char *)stack + stack_size;
7400#endif
7401
7402	SYSCALL_REQUIRE((child = vfork()) != -1);
7403	if (child == 0) {
7404		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
7405		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
7406
7407		DPRINTF("Before forking process PID=%d flags=%#x\n", getpid(),
7408		    flags);
7409		SYSCALL_REQUIRE((child2 = __clone(clone_func, stack_base,
7410		    flags|SIGCHLD, (void *)(intptr_t)exitval2)) != -1);
7411
7412		DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(),
7413		    child2);
7414
7415		// XXX WALLSIG?
7416		FORKEE_REQUIRE_SUCCESS
7417		    (wpid = TWAIT_GENERIC(child2, &status, WALLSIG), child2);
7418
7419		forkee_status_exited(status, exitval2);
7420
7421		DPRINTF("Before exiting of the child process\n");
7422		_exit(exitval);
7423	}
7424	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
7425
7426	DPRINTF("Before calling %s() for the child - expected exited\n",
7427	    TWAIT_FNAME);
7428	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7429
7430	validate_status_exited(status, exitval);
7431
7432	DPRINTF("Before calling %s() for the child - expected no process\n",
7433	    TWAIT_FNAME);
7434	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
7435}
7436
7437#define TRACEME_VFORK_CLONE_TEST(name,flags)				\
7438ATF_TC(name);								\
7439ATF_TC_HEAD(name, tc)							\
7440{									\
7441	atf_tc_set_md_var(tc, "descr", "Verify that clone(%s) is "	\
7442	    "handled correctly with vfork(2)ed tracer", 		\
7443	    #flags);							\
7444}									\
7445									\
7446ATF_TC_BODY(name, tc)							\
7447{									\
7448									\
7449	traceme_vfork_clone_body(flags);				\
7450}
7451
7452TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone, 0)
7453TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_vm, CLONE_VM)
7454TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_fs, CLONE_FS)
7455TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_files, CLONE_FILES)
7456//TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_sighand, CLONE_SIGHAND)  // XXX
7457TRACEME_VFORK_CLONE_TEST(traceme_vfork_clone_vfork, CLONE_VFORK)
7458#endif
7459#endif
7460
7461/// ----------------------------------------------------------------------------
7462
7463static void
7464user_va0_disable(int operation)
7465{
7466	pid_t child, wpid;
7467#if defined(TWAIT_HAVE_STATUS)
7468	int status;
7469#endif
7470	const int sigval = SIGSTOP;
7471	int rv;
7472
7473	struct ptrace_siginfo info;
7474
7475	if (get_user_va0_disable() == 0)
7476		atf_tc_skip("vm.user_va0_disable is set to 0");
7477
7478	memset(&info, 0, sizeof(info));
7479
7480	DPRINTF("Before forking process PID=%d\n", getpid());
7481	SYSCALL_REQUIRE((child = fork()) != -1);
7482	if (child == 0) {
7483		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
7484		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
7485
7486		DPRINTF("Before raising %s from child\n", strsignal(sigval));
7487		FORKEE_ASSERT(raise(sigval) == 0);
7488
7489		/* NOTREACHED */
7490		FORKEE_ASSERTX(0 && "This shall not be reached");
7491		__unreachable();
7492	}
7493	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
7494
7495	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7496	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7497
7498	validate_status_stopped(status, sigval);
7499
7500	DPRINTF("Before calling ptrace(2) with PT_GET_SIGINFO for "
7501		"child\n");
7502	SYSCALL_REQUIRE(ptrace(PT_GET_SIGINFO, child, &info,
7503		sizeof(info)) != -1);
7504
7505	DPRINTF("Signal traced to lwpid=%d\n", info.psi_lwpid);
7506	DPRINTF("Signal properties: si_signo=%#x si_code=%#x "
7507		"si_errno=%#x\n",
7508		info.psi_siginfo.si_signo, info.psi_siginfo.si_code,
7509		info.psi_siginfo.si_errno);
7510
7511	ATF_REQUIRE_EQ(info.psi_siginfo.si_signo, sigval);
7512	ATF_REQUIRE_EQ(info.psi_siginfo.si_code, SI_LWP);
7513
7514	DPRINTF("Before resuming the child process in PC=0x0 "
7515	    "and without signal to be sent\n");
7516	errno = 0;
7517	rv = ptrace(operation, child, (void *)0, 0);
7518	ATF_REQUIRE_EQ(errno, EINVAL);
7519	ATF_REQUIRE_EQ(rv, -1);
7520
7521	SYSCALL_REQUIRE(ptrace(PT_KILL, child, NULL, 0) != -1);
7522
7523	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7524	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7525	validate_status_signaled(status, SIGKILL, 0);
7526
7527	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7528	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
7529}
7530
7531#define USER_VA0_DISABLE(test, operation)				\
7532ATF_TC(test);								\
7533ATF_TC_HEAD(test, tc)							\
7534{									\
7535	atf_tc_set_md_var(tc, "descr",					\
7536	    "Verify behavior of " #operation " with PC set to 0x0");	\
7537}									\
7538									\
7539ATF_TC_BODY(test, tc)							\
7540{									\
7541									\
7542	user_va0_disable(operation);					\
7543}
7544
7545USER_VA0_DISABLE(user_va0_disable_pt_continue, PT_CONTINUE)
7546USER_VA0_DISABLE(user_va0_disable_pt_syscall, PT_SYSCALL)
7547USER_VA0_DISABLE(user_va0_disable_pt_detach, PT_DETACH)
7548
7549/// ----------------------------------------------------------------------------
7550
7551/*
7552 * Parse the core file and find the requested note.  If the reading or parsing
7553 * fails, the test is failed.  If the note is found, it is read onto buf, up to
7554 * buf_len.  The actual length of the note is returned (which can be greater
7555 * than buf_len, indicating that it has been truncated).  If the note is not
7556 * found, -1 is returned.
7557 */
7558static ssize_t core_find_note(const char *core_path,
7559    const char *note_name, uint64_t note_type, void *buf, size_t buf_len)
7560{
7561	int core_fd;
7562	Elf *core_elf;
7563	size_t core_numhdr, i;
7564	ssize_t ret = -1;
7565	/* note: we assume note name will be null-terminated */
7566	size_t name_len = strlen(note_name) + 1;
7567
7568	SYSCALL_REQUIRE((core_fd = open(core_path, O_RDONLY)) != -1);
7569	SYSCALL_REQUIRE(elf_version(EV_CURRENT) != EV_NONE);
7570	SYSCALL_REQUIRE((core_elf = elf_begin(core_fd, ELF_C_READ, NULL)));
7571
7572	SYSCALL_REQUIRE(elf_getphnum(core_elf, &core_numhdr) != 0);
7573	for (i = 0; i < core_numhdr && ret == -1; i++) {
7574		GElf_Phdr core_hdr;
7575		size_t offset;
7576		SYSCALL_REQUIRE(gelf_getphdr(core_elf, i, &core_hdr));
7577		if (core_hdr.p_type != PT_NOTE)
7578		    continue;
7579
7580		for (offset = core_hdr.p_offset;
7581		    offset < core_hdr.p_offset + core_hdr.p_filesz;) {
7582			Elf64_Nhdr note_hdr;
7583			char name_buf[64];
7584
7585			switch (gelf_getclass(core_elf)) {
7586			case ELFCLASS64:
7587				SYSCALL_REQUIRE(pread(core_fd, &note_hdr,
7588				    sizeof(note_hdr), offset)
7589				    == sizeof(note_hdr));
7590				offset += sizeof(note_hdr);
7591				break;
7592			case ELFCLASS32:
7593				{
7594				Elf32_Nhdr tmp_hdr;
7595				SYSCALL_REQUIRE(pread(core_fd, &tmp_hdr,
7596				    sizeof(tmp_hdr), offset)
7597				    == sizeof(tmp_hdr));
7598				offset += sizeof(tmp_hdr);
7599				note_hdr.n_namesz = tmp_hdr.n_namesz;
7600				note_hdr.n_descsz = tmp_hdr.n_descsz;
7601				note_hdr.n_type = tmp_hdr.n_type;
7602				}
7603				break;
7604			}
7605
7606			/* indicates end of notes */
7607			if (note_hdr.n_namesz == 0 || note_hdr.n_descsz == 0)
7608				break;
7609			if (note_hdr.n_namesz == name_len &&
7610			    note_hdr.n_namesz <= sizeof(name_buf)) {
7611				SYSCALL_REQUIRE(pread(core_fd, name_buf,
7612				    note_hdr.n_namesz, offset)
7613				    == (ssize_t)(size_t)note_hdr.n_namesz);
7614
7615				if (!strncmp(note_name, name_buf, name_len) &&
7616				    note_hdr.n_type == note_type)
7617					ret = note_hdr.n_descsz;
7618			}
7619
7620			offset += note_hdr.n_namesz;
7621			/* fix to alignment */
7622			offset = ((offset + core_hdr.p_align - 1)
7623			    / core_hdr.p_align) * core_hdr.p_align;
7624
7625			/* if name & type matched above */
7626			if (ret != -1) {
7627				ssize_t read_len = MIN(buf_len,
7628				    note_hdr.n_descsz);
7629				SYSCALL_REQUIRE(pread(core_fd, buf,
7630				    read_len, offset) == read_len);
7631				break;
7632			}
7633
7634			offset += note_hdr.n_descsz;
7635		}
7636	}
7637
7638	elf_end(core_elf);
7639	close(core_fd);
7640
7641	return ret;
7642}
7643
7644ATF_TC(core_dump_procinfo);
7645ATF_TC_HEAD(core_dump_procinfo, tc)
7646{
7647	atf_tc_set_md_var(tc, "descr",
7648		"Trigger a core dump and verify its contents.");
7649}
7650
7651ATF_TC_BODY(core_dump_procinfo, tc)
7652{
7653	const int exitval = 5;
7654	pid_t child, wpid;
7655#if defined(TWAIT_HAVE_STATUS)
7656	const int sigval = SIGTRAP;
7657	int status;
7658#endif
7659	char core_path[] = "/tmp/core.XXXXXX";
7660	int core_fd;
7661	struct netbsd_elfcore_procinfo procinfo;
7662
7663	DPRINTF("Before forking process PID=%d\n", getpid());
7664	SYSCALL_REQUIRE((child = fork()) != -1);
7665	if (child == 0) {
7666		DPRINTF("Before calling PT_TRACE_ME from child %d\n", getpid());
7667		FORKEE_ASSERT(ptrace(PT_TRACE_ME, 0, NULL, 0) != -1);
7668
7669		DPRINTF("Before triggering SIGTRAP\n");
7670		trigger_trap();
7671
7672		DPRINTF("Before exiting of the child process\n");
7673		_exit(exitval);
7674	}
7675	DPRINTF("Parent process PID=%d, child's PID=%d\n", getpid(), child);
7676
7677	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7678	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7679
7680	validate_status_stopped(status, sigval);
7681
7682	SYSCALL_REQUIRE((core_fd = mkstemp(core_path)) != -1);
7683	close(core_fd);
7684
7685	DPRINTF("Call DUMPCORE for the child process\n");
7686	SYSCALL_REQUIRE(ptrace(PT_DUMPCORE, child, core_path, strlen(core_path))
7687	    != -1);
7688
7689	DPRINTF("Read core file\n");
7690	ATF_REQUIRE_EQ(core_find_note(core_path, "NetBSD-CORE",
7691	    ELF_NOTE_NETBSD_CORE_PROCINFO, &procinfo, sizeof(procinfo)),
7692	    sizeof(procinfo));
7693
7694	ATF_CHECK_EQ(procinfo.cpi_version, 1);
7695	ATF_CHECK_EQ(procinfo.cpi_cpisize, sizeof(procinfo));
7696	ATF_CHECK_EQ(procinfo.cpi_signo, SIGTRAP);
7697	ATF_CHECK_EQ(procinfo.cpi_pid, child);
7698	ATF_CHECK_EQ(procinfo.cpi_ppid, getpid());
7699	ATF_CHECK_EQ(procinfo.cpi_pgrp, getpgid(child));
7700	ATF_CHECK_EQ(procinfo.cpi_sid, getsid(child));
7701	ATF_CHECK_EQ(procinfo.cpi_ruid, getuid());
7702	ATF_CHECK_EQ(procinfo.cpi_euid, geteuid());
7703	ATF_CHECK_EQ(procinfo.cpi_rgid, getgid());
7704	ATF_CHECK_EQ(procinfo.cpi_egid, getegid());
7705	ATF_CHECK_EQ(procinfo.cpi_nlwps, 1);
7706	ATF_CHECK_EQ(procinfo.cpi_siglwp, 1);
7707
7708	unlink(core_path);
7709
7710	DPRINTF("Before resuming the child process where it left off and "
7711	    "without signal to be sent\n");
7712	SYSCALL_REQUIRE(ptrace(PT_CONTINUE, child, (void *)1, 0) != -1);
7713
7714	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7715	TWAIT_REQUIRE_SUCCESS(wpid = TWAIT_GENERIC(child, &status, 0), child);
7716
7717	validate_status_exited(status, exitval);
7718
7719	DPRINTF("Before calling %s() for the child\n", TWAIT_FNAME);
7720	TWAIT_REQUIRE_FAILURE(ECHILD, wpid = TWAIT_GENERIC(child, &status, 0));
7721}
7722
7723/// ----------------------------------------------------------------------------
7724
7725#include "t_ptrace_amd64_wait.h"
7726#include "t_ptrace_i386_wait.h"
7727#include "t_ptrace_x86_wait.h"
7728
7729ATF_TP_ADD_TCS(tp)
7730{
7731	setvbuf(stdout, NULL, _IONBF, 0);
7732	setvbuf(stderr, NULL, _IONBF, 0);
7733
7734	ATF_TP_ADD_TC(tp, traceme_raise1);
7735	ATF_TP_ADD_TC(tp, traceme_raise2);
7736	ATF_TP_ADD_TC(tp, traceme_raise3);
7737	ATF_TP_ADD_TC(tp, traceme_raise4);
7738	ATF_TP_ADD_TC(tp, traceme_raise5);
7739	ATF_TP_ADD_TC(tp, traceme_raise6);
7740	ATF_TP_ADD_TC(tp, traceme_raise7);
7741	ATF_TP_ADD_TC(tp, traceme_raise8);
7742	ATF_TP_ADD_TC(tp, traceme_raise9);
7743	ATF_TP_ADD_TC(tp, traceme_raise10);
7744
7745	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored1);
7746	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored2);
7747	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored3);
7748	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored4);
7749	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored5);
7750	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored6);
7751	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored7);
7752	ATF_TP_ADD_TC(tp, traceme_raisesignal_ignored8);
7753
7754	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked1);
7755	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked2);
7756	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked3);
7757	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked4);
7758	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked5);
7759	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked6);
7760	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked7);
7761	ATF_TP_ADD_TC(tp, traceme_raisesignal_masked8);
7762
7763	ATF_TP_ADD_TC(tp, traceme_crash_trap);
7764	ATF_TP_ADD_TC(tp, traceme_crash_segv);
7765	ATF_TP_ADD_TC(tp, traceme_crash_ill);
7766	ATF_TP_ADD_TC(tp, traceme_crash_fpe);
7767	ATF_TP_ADD_TC(tp, traceme_crash_bus);
7768
7769	ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_trap);
7770	ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_segv);
7771	ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_ill);
7772	ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_fpe);
7773	ATF_TP_ADD_TC(tp, traceme_signalmasked_crash_bus);
7774
7775	ATF_TP_ADD_TC(tp, traceme_signalignored_crash_trap);
7776	ATF_TP_ADD_TC(tp, traceme_signalignored_crash_segv);
7777	ATF_TP_ADD_TC(tp, traceme_signalignored_crash_ill);
7778	ATF_TP_ADD_TC(tp, traceme_signalignored_crash_fpe);
7779	ATF_TP_ADD_TC(tp, traceme_signalignored_crash_bus);
7780
7781	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle1);
7782	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle2);
7783	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle3);
7784	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle4);
7785	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle5);
7786	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle6);
7787	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle7);
7788	ATF_TP_ADD_TC(tp, traceme_sendsignal_handle8);
7789
7790	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked1);
7791	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked2);
7792	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked3);
7793	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked4);
7794	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked5);
7795	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked6);
7796	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked7);
7797	ATF_TP_ADD_TC(tp, traceme_sendsignal_masked8);
7798
7799	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored1);
7800	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored2);
7801	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored3);
7802	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored4);
7803	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored5);
7804	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored6);
7805	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored7);
7806	ATF_TP_ADD_TC(tp, traceme_sendsignal_ignored8);
7807
7808	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple1);
7809	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple2);
7810	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple3);
7811	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple4);
7812	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple5);
7813	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple6);
7814	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple7);
7815	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple8);
7816	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple9);
7817	ATF_TP_ADD_TC(tp, traceme_sendsignal_simple10);
7818
7819	ATF_TP_ADD_TC(tp, traceme_pid1_parent);
7820
7821	ATF_TP_ADD_TC(tp, traceme_vfork_raise1);
7822	ATF_TP_ADD_TC(tp, traceme_vfork_raise2);
7823	ATF_TP_ADD_TC(tp, traceme_vfork_raise3);
7824	ATF_TP_ADD_TC(tp, traceme_vfork_raise4);
7825	ATF_TP_ADD_TC(tp, traceme_vfork_raise5);
7826	ATF_TP_ADD_TC(tp, traceme_vfork_raise6);
7827	ATF_TP_ADD_TC(tp, traceme_vfork_raise7);
7828	ATF_TP_ADD_TC(tp, traceme_vfork_raise8);
7829	ATF_TP_ADD_TC(tp, traceme_vfork_raise9);
7830	ATF_TP_ADD_TC(tp, traceme_vfork_raise10);
7831	ATF_TP_ADD_TC(tp, traceme_vfork_raise11);
7832	ATF_TP_ADD_TC(tp, traceme_vfork_raise12);
7833	ATF_TP_ADD_TC(tp, traceme_vfork_raise13);
7834
7835	ATF_TP_ADD_TC(tp, traceme_vfork_crash_trap);
7836	ATF_TP_ADD_TC(tp, traceme_vfork_crash_segv);
7837	ATF_TP_ADD_TC(tp, traceme_vfork_crash_ill);
7838	ATF_TP_ADD_TC(tp, traceme_vfork_crash_fpe);
7839	ATF_TP_ADD_TC(tp, traceme_vfork_crash_bus);
7840
7841	ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_trap);
7842	ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_segv);
7843	ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_ill);
7844	ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_fpe);
7845	ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_crash_bus);
7846
7847	ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_trap);
7848	ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_segv);
7849	ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_ill);
7850	ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_fpe);
7851	ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_crash_bus);
7852
7853	ATF_TP_ADD_TC(tp, traceme_vfork_exec);
7854	ATF_TP_ADD_TC(tp, traceme_vfork_signalmasked_exec);
7855	ATF_TP_ADD_TC(tp, traceme_vfork_signalignored_exec);
7856
7857	ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_trap);
7858	ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_segv);
7859	ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_ill);
7860	ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_fpe);
7861	ATF_TP_ADD_TC_HAVE_PID(tp, unrelated_tracer_sees_crash_bus);
7862
7863	ATF_TP_ADD_TC_HAVE_PID(tp,
7864	    unrelated_tracer_sees_signalmasked_crash_trap);
7865	ATF_TP_ADD_TC_HAVE_PID(tp,
7866	    unrelated_tracer_sees_signalmasked_crash_segv);
7867	ATF_TP_ADD_TC_HAVE_PID(tp,
7868	    unrelated_tracer_sees_signalmasked_crash_ill);
7869	ATF_TP_ADD_TC_HAVE_PID(tp,
7870	    unrelated_tracer_sees_signalmasked_crash_fpe);
7871	ATF_TP_ADD_TC_HAVE_PID(tp,
7872	    unrelated_tracer_sees_signalmasked_crash_bus);
7873
7874	ATF_TP_ADD_TC_HAVE_PID(tp,
7875	    unrelated_tracer_sees_signalignored_crash_trap);
7876	ATF_TP_ADD_TC_HAVE_PID(tp,
7877	    unrelated_tracer_sees_signalignored_crash_segv);
7878	ATF_TP_ADD_TC_HAVE_PID(tp,
7879	    unrelated_tracer_sees_signalignored_crash_ill);
7880	ATF_TP_ADD_TC_HAVE_PID(tp,
7881	    unrelated_tracer_sees_signalignored_crash_fpe);
7882	ATF_TP_ADD_TC_HAVE_PID(tp,
7883	    unrelated_tracer_sees_signalignored_crash_bus);
7884
7885	ATF_TP_ADD_TC_HAVE_PID(tp, tracer_sees_terminaton_before_the_parent);
7886	ATF_TP_ADD_TC_HAVE_PID(tp, tracer_sysctl_lookup_without_duplicates);
7887	ATF_TP_ADD_TC_HAVE_PID(tp,
7888		unrelated_tracer_sees_terminaton_before_the_parent);
7889	ATF_TP_ADD_TC_HAVE_PID(tp, tracer_attach_to_unrelated_stopped_process);
7890
7891	ATF_TP_ADD_TC(tp, parent_attach_to_its_child);
7892	ATF_TP_ADD_TC(tp, parent_attach_to_its_stopped_child);
7893
7894	ATF_TP_ADD_TC(tp, child_attach_to_its_parent);
7895	ATF_TP_ADD_TC(tp, child_attach_to_its_stopped_parent);
7896
7897	ATF_TP_ADD_TC_HAVE_PID(tp,
7898		tracee_sees_its_original_parent_getppid);
7899	ATF_TP_ADD_TC_HAVE_PID(tp,
7900		tracee_sees_its_original_parent_sysctl_kinfo_proc2);
7901	ATF_TP_ADD_TC_HAVE_PID(tp,
7902		tracee_sees_its_original_parent_procfs_status);
7903
7904	ATF_TP_ADD_TC(tp, eventmask_preserved_empty);
7905	ATF_TP_ADD_TC(tp, eventmask_preserved_fork);
7906	ATF_TP_ADD_TC(tp, eventmask_preserved_vfork);
7907	ATF_TP_ADD_TC(tp, eventmask_preserved_vfork_done);
7908	ATF_TP_ADD_TC(tp, eventmask_preserved_lwp_create);
7909	ATF_TP_ADD_TC(tp, eventmask_preserved_lwp_exit);
7910	ATF_TP_ADD_TC(tp, eventmask_preserved_posix_spawn);
7911
7912	ATF_TP_ADD_TC(tp, fork1);
7913	ATF_TP_ADD_TC_HAVE_PID(tp, fork2);
7914	ATF_TP_ADD_TC_HAVE_PID(tp, fork3);
7915	ATF_TP_ADD_TC_HAVE_PID(tp, fork4);
7916	ATF_TP_ADD_TC(tp, fork5);
7917	ATF_TP_ADD_TC_HAVE_PID(tp, fork6);
7918	ATF_TP_ADD_TC_HAVE_PID(tp, fork7);
7919	ATF_TP_ADD_TC_HAVE_PID(tp, fork8);
7920	ATF_TP_ADD_TC(tp, fork9);
7921	ATF_TP_ADD_TC_HAVE_PID(tp, fork10);
7922	ATF_TP_ADD_TC_HAVE_PID(tp, fork11);
7923	ATF_TP_ADD_TC_HAVE_PID(tp, fork12);
7924	ATF_TP_ADD_TC(tp, fork13);
7925	ATF_TP_ADD_TC_HAVE_PID(tp, fork14);
7926	ATF_TP_ADD_TC_HAVE_PID(tp, fork15);
7927	ATF_TP_ADD_TC_HAVE_PID(tp, fork16);
7928
7929#if TEST_VFORK_ENABLED
7930	ATF_TP_ADD_TC(tp, vfork1);
7931	ATF_TP_ADD_TC_HAVE_PID(tp, vfork2);
7932	ATF_TP_ADD_TC_HAVE_PID(tp, vfork3);
7933	ATF_TP_ADD_TC_HAVE_PID(tp, vfork4);
7934	ATF_TP_ADD_TC(tp, vfork5);
7935	ATF_TP_ADD_TC_HAVE_PID(tp, vfork6);
7936	ATF_TP_ADD_TC_HAVE_PID(tp, vfork7);
7937	ATF_TP_ADD_TC_HAVE_PID(tp, vfork8);
7938	ATF_TP_ADD_TC(tp, vfork9);
7939	ATF_TP_ADD_TC_HAVE_PID(tp, vfork10);
7940	ATF_TP_ADD_TC_HAVE_PID(tp, vfork11);
7941	ATF_TP_ADD_TC_HAVE_PID(tp, vfork12);
7942	ATF_TP_ADD_TC(tp, vfork13);
7943	ATF_TP_ADD_TC_HAVE_PID(tp, vfork14);
7944	ATF_TP_ADD_TC_HAVE_PID(tp, vfork15);
7945	ATF_TP_ADD_TC_HAVE_PID(tp, vfork16);
7946#endif
7947
7948	ATF_TP_ADD_TC(tp, posix_spawn1);
7949	ATF_TP_ADD_TC(tp, posix_spawn2);
7950	ATF_TP_ADD_TC(tp, posix_spawn3);
7951	ATF_TP_ADD_TC(tp, posix_spawn4);
7952	ATF_TP_ADD_TC(tp, posix_spawn5);
7953	ATF_TP_ADD_TC(tp, posix_spawn6);
7954	ATF_TP_ADD_TC(tp, posix_spawn7);
7955	ATF_TP_ADD_TC(tp, posix_spawn8);
7956	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn9);
7957	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn10);
7958	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn11);
7959	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn12);
7960	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn13);
7961	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn14);
7962	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn15);
7963	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn16);
7964
7965	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn_detach_spawner);
7966	ATF_TP_ADD_TC_HAVE_PID(tp, fork_detach_forker);
7967#if TEST_VFORK_ENABLED
7968	ATF_TP_ADD_TC_HAVE_PID(tp, vfork_detach_vforker);
7969	ATF_TP_ADD_TC_HAVE_PID(tp, vfork_detach_vforkerdone);
7970#endif
7971
7972	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn_kill_spawner);
7973	ATF_TP_ADD_TC_HAVE_PID(tp, fork_kill_forker);
7974#if TEST_VFORK_ENABLED
7975	ATF_TP_ADD_TC_HAVE_PID(tp, vfork_kill_vforker);
7976	ATF_TP_ADD_TC_HAVE_PID(tp, vfork_kill_vforkerdone);
7977#endif
7978
7979#if TEST_VFORK_ENABLED
7980	ATF_TP_ADD_TC(tp, traceme_vfork_fork);
7981	ATF_TP_ADD_TC(tp, traceme_vfork_vfork);
7982#endif
7983
7984	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_8);
7985	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_16);
7986	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_32);
7987	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_64);
7988
7989	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_8);
7990	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_16);
7991	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_32);
7992	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_64);
7993
7994	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_8);
7995	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_16);
7996	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_32);
7997	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_64);
7998
7999	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_8);
8000	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_16);
8001	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_32);
8002	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_64);
8003
8004	ATF_TP_ADD_TC(tp, bytes_transfer_read_d);
8005	ATF_TP_ADD_TC(tp, bytes_transfer_read_i);
8006	ATF_TP_ADD_TC(tp, bytes_transfer_write_d);
8007	ATF_TP_ADD_TC(tp, bytes_transfer_write_i);
8008
8009	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_8_text);
8010	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_16_text);
8011	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_32_text);
8012	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_d_64_text);
8013
8014	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_8_text);
8015	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_16_text);
8016	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_32_text);
8017	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_i_64_text);
8018
8019	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_8_text);
8020	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_16_text);
8021	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_32_text);
8022	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_d_64_text);
8023
8024	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_8_text);
8025	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_16_text);
8026	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_32_text);
8027	ATF_TP_ADD_TC(tp, bytes_transfer_piod_write_i_64_text);
8028
8029	ATF_TP_ADD_TC(tp, bytes_transfer_read_d_text);
8030	ATF_TP_ADD_TC(tp, bytes_transfer_read_i_text);
8031	ATF_TP_ADD_TC(tp, bytes_transfer_write_d_text);
8032	ATF_TP_ADD_TC(tp, bytes_transfer_write_i_text);
8033
8034	ATF_TP_ADD_TC(tp, bytes_transfer_piod_read_auxv);
8035
8036	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_read_i);
8037	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_read_d);
8038	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_write_i);
8039	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_pt_write_d);
8040
8041	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_read_i);
8042	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_read_d);
8043	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_write_i);
8044	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_write_d);
8045
8046	ATF_TP_ADD_TC(tp, bytes_transfer_alignment_piod_read_auxv);
8047
8048	ATF_TP_ADD_TC(tp, bytes_transfer_eof_pt_read_i);
8049	ATF_TP_ADD_TC(tp, bytes_transfer_eof_pt_read_d);
8050	ATF_TP_ADD_TC(tp, bytes_transfer_eof_pt_write_i);
8051	ATF_TP_ADD_TC(tp, bytes_transfer_eof_pt_write_d);
8052
8053	ATF_TP_ADD_TC(tp, bytes_transfer_eof_piod_read_i);
8054	ATF_TP_ADD_TC(tp, bytes_transfer_eof_piod_read_d);
8055	ATF_TP_ADD_TC(tp, bytes_transfer_eof_piod_write_i);
8056	ATF_TP_ADD_TC(tp, bytes_transfer_eof_piod_write_d);
8057
8058	ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs1);
8059	ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs2);
8060	ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs3);
8061	ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs4);
8062	ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs5);
8063	ATF_TP_ADD_TC_HAVE_GPREGS(tp, access_regs6);
8064
8065	ATF_TP_ADD_TC_HAVE_FPREGS(tp, access_fpregs1);
8066	ATF_TP_ADD_TC_HAVE_FPREGS(tp, access_fpregs2);
8067
8068	ATF_TP_ADD_TC_PT_STEP(tp, step1);
8069	ATF_TP_ADD_TC_PT_STEP(tp, step2);
8070	ATF_TP_ADD_TC_PT_STEP(tp, step3);
8071	ATF_TP_ADD_TC_PT_STEP(tp, step4);
8072
8073	ATF_TP_ADD_TC_PT_STEP(tp, setstep1);
8074	ATF_TP_ADD_TC_PT_STEP(tp, setstep2);
8075	ATF_TP_ADD_TC_PT_STEP(tp, setstep3);
8076	ATF_TP_ADD_TC_PT_STEP(tp, setstep4);
8077
8078	ATF_TP_ADD_TC_PT_STEP(tp, step_signalmasked);
8079	ATF_TP_ADD_TC_PT_STEP(tp, step_signalignored);
8080
8081	ATF_TP_ADD_TC(tp, kill1);
8082	ATF_TP_ADD_TC(tp, kill2);
8083	ATF_TP_ADD_TC(tp, kill3);
8084
8085	ATF_TP_ADD_TC(tp, traceme_lwpinfo0);
8086	ATF_TP_ADD_TC(tp, traceme_lwpinfo1);
8087	ATF_TP_ADD_TC(tp, traceme_lwpinfo2);
8088	ATF_TP_ADD_TC(tp, traceme_lwpinfo3);
8089
8090	ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo0);
8091	ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo1);
8092	ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo2);
8093	ATF_TP_ADD_TC_HAVE_PID(tp, attach_lwpinfo3);
8094
8095	ATF_TP_ADD_TC(tp, siginfo_set_unmodified);
8096	ATF_TP_ADD_TC(tp, siginfo_set_faked);
8097
8098	ATF_TP_ADD_TC(tp, traceme_exec);
8099	ATF_TP_ADD_TC(tp, traceme_signalmasked_exec);
8100	ATF_TP_ADD_TC(tp, traceme_signalignored_exec);
8101
8102	ATF_TP_ADD_TC(tp, trace_thread_nolwpevents);
8103	ATF_TP_ADD_TC(tp, trace_thread_lwpexit);
8104	ATF_TP_ADD_TC(tp, trace_thread_lwpcreate);
8105	ATF_TP_ADD_TC(tp, trace_thread_lwpcreate_and_exit);
8106
8107	ATF_TP_ADD_TC(tp, signal_mask_unrelated);
8108
8109	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn_singalmasked);
8110	ATF_TP_ADD_TC_HAVE_PID(tp, posix_spawn_singalignored);
8111	ATF_TP_ADD_TC_HAVE_PID(tp, fork_singalmasked);
8112	ATF_TP_ADD_TC_HAVE_PID(tp, fork_singalignored);
8113#if TEST_VFORK_ENABLED
8114	ATF_TP_ADD_TC_HAVE_PID(tp, vfork_singalmasked);
8115	ATF_TP_ADD_TC_HAVE_PID(tp, vfork_singalignored);
8116	ATF_TP_ADD_TC_HAVE_PID(tp, vforkdone_singalmasked);
8117	ATF_TP_ADD_TC_HAVE_PID(tp, vforkdone_singalignored);
8118#endif
8119
8120	ATF_TP_ADD_TC(tp, signal9);
8121	ATF_TP_ADD_TC(tp, signal10);
8122
8123	ATF_TP_ADD_TC(tp, suspend2);
8124
8125	ATF_TP_ADD_TC(tp, resume1);
8126
8127	ATF_TP_ADD_TC(tp, syscall1);
8128
8129	ATF_TP_ADD_TC(tp, syscallemu1);
8130
8131	ATF_TP_ADD_TC(tp, clone1);
8132	ATF_TP_ADD_TC_HAVE_PID(tp, clone2);
8133	ATF_TP_ADD_TC_HAVE_PID(tp, clone3);
8134	ATF_TP_ADD_TC_HAVE_PID(tp, clone4);
8135	ATF_TP_ADD_TC(tp, clone5);
8136	ATF_TP_ADD_TC_HAVE_PID(tp, clone6);
8137	ATF_TP_ADD_TC_HAVE_PID(tp, clone7);
8138	ATF_TP_ADD_TC_HAVE_PID(tp, clone8);
8139
8140	ATF_TP_ADD_TC(tp, clone_vm1);
8141	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm2);
8142	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm3);
8143	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm4);
8144	ATF_TP_ADD_TC(tp, clone_vm5);
8145	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm6);
8146	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm7);
8147	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm8);
8148
8149	ATF_TP_ADD_TC(tp, clone_fs1);
8150	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs2);
8151	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs3);
8152	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs4);
8153	ATF_TP_ADD_TC(tp, clone_fs5);
8154	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs6);
8155	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs7);
8156	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs8);
8157
8158	ATF_TP_ADD_TC(tp, clone_files1);
8159	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files2);
8160	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files3);
8161	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files4);
8162	ATF_TP_ADD_TC(tp, clone_files5);
8163	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files6);
8164	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files7);
8165	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files8);
8166
8167//	ATF_TP_ADD_TC(tp, clone_sighand1); // XXX
8168//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand2); // XXX
8169//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand3); // XXX
8170//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand4); // XXX
8171//	ATF_TP_ADD_TC(tp, clone_sighand5); // XXX
8172//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand6); // XXX
8173//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand7); // XXX
8174//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand8); // XXX
8175
8176#if TEST_VFORK_ENABLED
8177	ATF_TP_ADD_TC(tp, clone_vfork1);
8178	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork2);
8179	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork3);
8180	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork4);
8181	ATF_TP_ADD_TC(tp, clone_vfork5);
8182	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork6);
8183	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork7);
8184	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork8);
8185#endif
8186
8187	ATF_TP_ADD_TC_HAVE_PID(tp, clone_signalignored);
8188	ATF_TP_ADD_TC_HAVE_PID(tp, clone_signalmasked);
8189	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm_signalignored);
8190	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vm_signalmasked);
8191	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs_signalignored);
8192	ATF_TP_ADD_TC_HAVE_PID(tp, clone_fs_signalmasked);
8193	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files_signalignored);
8194	ATF_TP_ADD_TC_HAVE_PID(tp, clone_files_signalmasked);
8195//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand_signalignored); // XXX
8196//	ATF_TP_ADD_TC_HAVE_PID(tp, clone_sighand_signalmasked); // XXX
8197#if TEST_VFORK_ENABLED
8198	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork_signalignored);
8199	ATF_TP_ADD_TC_HAVE_PID(tp, clone_vfork_signalmasked);
8200#endif
8201
8202#if TEST_VFORK_ENABLED
8203	ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone);
8204	ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_vm);
8205	ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_fs);
8206	ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_files);
8207//	ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_sighand); // XXX
8208	ATF_TP_ADD_TC_HAVE_PID(tp, traceme_vfork_clone_vfork);
8209#endif
8210
8211	ATF_TP_ADD_TC(tp, user_va0_disable_pt_continue);
8212	ATF_TP_ADD_TC(tp, user_va0_disable_pt_syscall);
8213	ATF_TP_ADD_TC(tp, user_va0_disable_pt_detach);
8214
8215	ATF_TP_ADD_TC(tp, core_dump_procinfo);
8216
8217	ATF_TP_ADD_TCS_PTRACE_WAIT_AMD64();
8218	ATF_TP_ADD_TCS_PTRACE_WAIT_I386();
8219	ATF_TP_ADD_TCS_PTRACE_WAIT_X86();
8220
8221	return atf_no_error();
8222}
8223