sys_ptrace_common.c revision 1.7 1 /* $NetBSD: sys_ptrace_common.c,v 1.7 2016/12/15 12:04:18 kamil Exp $ */
2
3 /*-
4 * Copyright (c) 2008, 2009 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Andrew Doran.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 /*-
33 * Copyright (c) 1982, 1986, 1989, 1993
34 * The Regents of the University of California. All rights reserved.
35 * (c) UNIX System Laboratories, Inc.
36 * All or some portions of this file are derived from material licensed
37 * to the University of California by American Telephone and Telegraph
38 * Co. or Unix System Laboratories, Inc. and are reproduced herein with
39 * the permission of UNIX System Laboratories, Inc.
40 *
41 * This code is derived from software contributed to Berkeley by
42 * Jan-Simon Pendry.
43 *
44 * Redistribution and use in source and binary forms, with or without
45 * modification, are permitted provided that the following conditions
46 * are met:
47 * 1. Redistributions of source code must retain the above copyright
48 * notice, this list of conditions and the following disclaimer.
49 * 2. Redistributions in binary form must reproduce the above copyright
50 * notice, this list of conditions and the following disclaimer in the
51 * documentation and/or other materials provided with the distribution.
52 * 3. Neither the name of the University nor the names of its contributors
53 * may be used to endorse or promote products derived from this software
54 * without specific prior written permission.
55 *
56 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
57 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
58 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
59 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
60 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
61 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
62 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
63 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
64 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
65 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
66 * SUCH DAMAGE.
67 *
68 * from: @(#)sys_process.c 8.1 (Berkeley) 6/10/93
69 */
70
71 /*-
72 * Copyright (c) 1993 Jan-Simon Pendry.
73 * Copyright (c) 1994 Christopher G. Demetriou. All rights reserved.
74 *
75 * This code is derived from software contributed to Berkeley by
76 * Jan-Simon Pendry.
77 *
78 * Redistribution and use in source and binary forms, with or without
79 * modification, are permitted provided that the following conditions
80 * are met:
81 * 1. Redistributions of source code must retain the above copyright
82 * notice, this list of conditions and the following disclaimer.
83 * 2. Redistributions in binary form must reproduce the above copyright
84 * notice, this list of conditions and the following disclaimer in the
85 * documentation and/or other materials provided with the distribution.
86 * 3. All advertising materials mentioning features or use of this software
87 * must display the following acknowledgement:
88 * This product includes software developed by the University of
89 * California, Berkeley and its contributors.
90 * 4. Neither the name of the University nor the names of its contributors
91 * may be used to endorse or promote products derived from this software
92 * without specific prior written permission.
93 *
94 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
95 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
96 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
97 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
98 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
99 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
100 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
101 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
102 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
103 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
104 * SUCH DAMAGE.
105 *
106 * from: @(#)sys_process.c 8.1 (Berkeley) 6/10/93
107 */
108
109 /*
110 * References:
111 * (1) Bach's "The Design of the UNIX Operating System",
112 * (2) sys/miscfs/procfs from UCB's 4.4BSD-Lite distribution,
113 * (3) the "4.4BSD Programmer's Reference Manual" published
114 * by USENIX and O'Reilly & Associates.
115 * The 4.4BSD PRM does a reasonably good job of documenting what the various
116 * ptrace() requests should actually do, and its text is quoted several times
117 * in this file.
118 */
119
120 #include <sys/cdefs.h>
121 __KERNEL_RCSID(0, "$NetBSD: sys_ptrace_common.c,v 1.7 2016/12/15 12:04:18 kamil Exp $");
122
123 #ifdef _KERNEL_OPT
124 #include "opt_ptrace.h"
125 #include "opt_ktrace.h"
126 #include "opt_pax.h"
127 #endif
128
129 #include <sys/param.h>
130 #include <sys/systm.h>
131 #include <sys/proc.h>
132 #include <sys/errno.h>
133 #include <sys/exec.h>
134 #include <sys/pax.h>
135 #include <sys/ptrace.h>
136 #include <sys/uio.h>
137 #include <sys/ras.h>
138 #include <sys/kmem.h>
139 #include <sys/kauth.h>
140 #include <sys/mount.h>
141 #include <sys/syscallargs.h>
142 #include <sys/module.h>
143 #include <sys/condvar.h>
144 #include <sys/mutex.h>
145
146 #include <uvm/uvm_extern.h>
147
148 #include <machine/reg.h>
149
150 #ifdef PTRACE
151
152 # ifdef DEBUG
153 # define DPRINTF(a) uprintf a
154 # else
155 # define DPRINTF(a)
156 # endif
157
158 static kauth_listener_t ptrace_listener;
159 static int process_auxv_offset(struct proc *, struct uio *);
160
161 #if 0
162 static int ptrace_cbref;
163 static kmutex_t ptrace_mtx;
164 static kcondvar_t ptrace_cv;
165 #endif
166
167 static int
168 ptrace_listener_cb(kauth_cred_t cred, kauth_action_t action, void *cookie,
169 void *arg0, void *arg1, void *arg2, void *arg3)
170 {
171 struct proc *p;
172 int result;
173
174 result = KAUTH_RESULT_DEFER;
175 p = arg0;
176
177 #if 0
178 mutex_enter(&ptrace_mtx);
179 ptrace_cbref++;
180 mutex_exit(&ptrace_mtx);
181 #endif
182 if (action != KAUTH_PROCESS_PTRACE)
183 goto out;
184
185 switch ((u_long)arg1) {
186 case PT_TRACE_ME:
187 case PT_ATTACH:
188 case PT_WRITE_I:
189 case PT_WRITE_D:
190 case PT_READ_I:
191 case PT_READ_D:
192 case PT_IO:
193 #ifdef PT_GETREGS
194 case PT_GETREGS:
195 #endif
196 #ifdef PT_SETREGS
197 case PT_SETREGS:
198 #endif
199 #ifdef PT_GETFPREGS
200 case PT_GETFPREGS:
201 #endif
202 #ifdef PT_SETFPREGS
203 case PT_SETFPREGS:
204 #endif
205 #ifdef __HAVE_PTRACE_WATCHPOINTS
206 case PT_READ_WATCHPOINT:
207 case PT_WRITE_WATCHPOINT:
208 case PT_COUNT_WATCHPOINTS:
209 #endif
210 case PT_SET_EVENT_MASK:
211 case PT_GET_EVENT_MASK:
212 case PT_GET_PROCESS_STATE:
213 #ifdef __HAVE_PTRACE_MACHDEP
214 PTRACE_MACHDEP_REQUEST_CASES
215 #endif
216 if (kauth_cred_getuid(cred) != kauth_cred_getuid(p->p_cred) ||
217 ISSET(p->p_flag, PK_SUGID)) {
218 break;
219 }
220
221 result = KAUTH_RESULT_ALLOW;
222
223 break;
224
225 #ifdef PT_STEP
226 case PT_STEP:
227 #endif
228 case PT_CONTINUE:
229 case PT_KILL:
230 case PT_DETACH:
231 case PT_LWPINFO:
232 case PT_SYSCALL:
233 case PT_SYSCALLEMU:
234 case PT_DUMPCORE:
235 result = KAUTH_RESULT_ALLOW;
236 break;
237
238 default:
239 break;
240 }
241
242 out:
243 #if 0
244 mutex_enter(&ptrace_mtx);
245 if (--ptrace_cbref == 0)
246 cv_broadcast(&ptrace_cv);
247 mutex_exit(&ptrace_mtx);
248 #endif
249
250 return result;
251 }
252
253 int
254 ptrace_init(void)
255 {
256
257 #if 0
258 mutex_init(&ptrace_mtx, MUTEX_DEFAULT, IPL_NONE);
259 cv_init(&ptrace_cv, "ptracecb");
260 ptrace_cbref = 0;
261 #endif
262 ptrace_listener = kauth_listen_scope(KAUTH_SCOPE_PROCESS,
263 ptrace_listener_cb, NULL);
264 return 0;
265 }
266
267 int
268 ptrace_fini(void)
269 {
270
271 kauth_unlisten_scope(ptrace_listener);
272
273 #if 0
274 /* Make sure no-one is executing our kauth listener */
275
276 mutex_enter(&ptrace_mtx);
277 while (ptrace_cbref != 0)
278 cv_wait(&ptrace_cv, &ptrace_mtx);
279 mutex_exit(&ptrace_mtx);
280 mutex_destroy(&ptrace_mtx);
281 cv_destroy(&ptrace_cv);
282 #endif
283
284 return 0;
285 }
286
287 int
288 do_ptrace(struct ptrace_methods *ptm, struct lwp *l, int req, pid_t pid,
289 void *addr, int data, register_t *retval)
290 {
291 struct proc *p = l->l_proc;
292 struct lwp *lt;
293 #ifdef PT_STEP
294 struct lwp *lt2;
295 #endif
296 struct proc *t; /* target process */
297 struct uio uio;
298 struct iovec iov;
299 struct ptrace_io_desc piod;
300 struct ptrace_event pe;
301 struct ptrace_state ps;
302 struct ptrace_lwpinfo pl;
303 #ifdef __HAVE_PTRACE_WATCHPOINTS
304 struct ptrace_watchpoint pw;
305 #endif
306 struct vmspace *vm;
307 int error, write, tmp, pheld;
308 int signo = 0;
309 int resume_all;
310 ksiginfo_t ksi;
311 char *path;
312 int len = 0;
313 error = 0;
314
315 /*
316 * If attaching or detaching, we need to get a write hold on the
317 * proclist lock so that we can re-parent the target process.
318 */
319 mutex_enter(proc_lock);
320
321 /* "A foolish consistency..." XXX */
322 if (req == PT_TRACE_ME) {
323 t = p;
324 mutex_enter(t->p_lock);
325 } else {
326 /* Find the process we're supposed to be operating on. */
327 t = proc_find(pid);
328 if (t == NULL) {
329 mutex_exit(proc_lock);
330 return ESRCH;
331 }
332
333 /* XXX-elad */
334 mutex_enter(t->p_lock);
335 error = kauth_authorize_process(l->l_cred, KAUTH_PROCESS_CANSEE,
336 t, KAUTH_ARG(KAUTH_REQ_PROCESS_CANSEE_ENTRY), NULL, NULL);
337 if (error) {
338 mutex_exit(proc_lock);
339 mutex_exit(t->p_lock);
340 return ESRCH;
341 }
342 }
343
344 /*
345 * Grab a reference on the process to prevent it from execing or
346 * exiting.
347 */
348 if (!rw_tryenter(&t->p_reflock, RW_READER)) {
349 mutex_exit(proc_lock);
350 mutex_exit(t->p_lock);
351 return EBUSY;
352 }
353
354 /* Make sure we can operate on it. */
355 switch (req) {
356 case PT_TRACE_ME:
357 /* Saying that you're being traced is always legal. */
358 break;
359
360 case PT_ATTACH:
361 /*
362 * You can't attach to a process if:
363 * (1) it's the process that's doing the attaching,
364 */
365 if (t->p_pid == p->p_pid) {
366 error = EINVAL;
367 break;
368 }
369
370 /*
371 * (2) it's a system process
372 */
373 if (t->p_flag & PK_SYSTEM) {
374 error = EPERM;
375 break;
376 }
377
378 /*
379 * (3) it's already being traced, or
380 */
381 if (ISSET(t->p_slflag, PSL_TRACED)) {
382 error = EBUSY;
383 break;
384 }
385
386 /*
387 * (4) the tracer is chrooted, and its root directory is
388 * not at or above the root directory of the tracee
389 */
390 mutex_exit(t->p_lock); /* XXXSMP */
391 tmp = proc_isunder(t, l);
392 mutex_enter(t->p_lock); /* XXXSMP */
393 if (!tmp) {
394 error = EPERM;
395 break;
396 }
397 break;
398
399 case PT_READ_I:
400 case PT_READ_D:
401 case PT_WRITE_I:
402 case PT_WRITE_D:
403 case PT_IO:
404 #ifdef PT_GETREGS
405 case PT_GETREGS:
406 #endif
407 #ifdef PT_SETREGS
408 case PT_SETREGS:
409 #endif
410 #ifdef PT_GETFPREGS
411 case PT_GETFPREGS:
412 #endif
413 #ifdef PT_SETFPREGS
414 case PT_SETFPREGS:
415 #endif
416 #ifdef __HAVE_PTRACE_WATCHPOINTS
417 case PT_READ_WATCHPOINT:
418 case PT_WRITE_WATCHPOINT:
419 case PT_COUNT_WATCHPOINTS:
420 #endif
421 #ifdef __HAVE_PTRACE_MACHDEP
422 PTRACE_MACHDEP_REQUEST_CASES
423 #endif
424 /*
425 * You can't read/write the memory or registers of a process
426 * if the tracer is chrooted, and its root directory is not at
427 * or above the root directory of the tracee.
428 */
429 mutex_exit(t->p_lock); /* XXXSMP */
430 tmp = proc_isunder(t, l);
431 mutex_enter(t->p_lock); /* XXXSMP */
432 if (!tmp) {
433 error = EPERM;
434 break;
435 }
436 /*FALLTHROUGH*/
437
438 case PT_CONTINUE:
439 case PT_KILL:
440 case PT_DETACH:
441 case PT_LWPINFO:
442 case PT_SYSCALL:
443 case PT_SYSCALLEMU:
444 case PT_DUMPCORE:
445 #ifdef PT_STEP
446 case PT_STEP:
447 #endif
448 case PT_SET_EVENT_MASK:
449 case PT_GET_EVENT_MASK:
450 case PT_GET_PROCESS_STATE:
451 /*
452 * You can't do what you want to the process if:
453 * (1) It's not being traced at all,
454 */
455 if (!ISSET(t->p_slflag, PSL_TRACED)) {
456 error = EPERM;
457 break;
458 }
459
460 /*
461 * (2) it's being traced by procfs (which has
462 * different signal delivery semantics),
463 */
464 if (ISSET(t->p_slflag, PSL_FSTRACE)) {
465 DPRINTF(("file system traced\n"));
466 error = EBUSY;
467 break;
468 }
469
470 /*
471 * (3) it's not being traced by _you_, or
472 */
473 if (t->p_pptr != p) {
474 DPRINTF(("parent %d != %d\n", t->p_pptr->p_pid,
475 p->p_pid));
476 error = EBUSY;
477 break;
478 }
479
480 /*
481 * (4) it's not currently stopped.
482 */
483 if (t->p_stat != SSTOP || !t->p_waited /* XXXSMP */) {
484 DPRINTF(("stat %d flag %d\n", t->p_stat,
485 !t->p_waited));
486 error = EBUSY;
487 break;
488 }
489 break;
490
491 default: /* It was not a legal request. */
492 error = EINVAL;
493 break;
494 }
495
496 if (error == 0) {
497 error = kauth_authorize_process(l->l_cred,
498 KAUTH_PROCESS_PTRACE, t, KAUTH_ARG(req),
499 NULL, NULL);
500 }
501 if (error == 0) {
502 lt = lwp_find_first(t);
503 if (lt == NULL)
504 error = ESRCH;
505 }
506
507 if (error != 0) {
508 mutex_exit(proc_lock);
509 mutex_exit(t->p_lock);
510 rw_exit(&t->p_reflock);
511 return error;
512 }
513
514 /* Do single-step fixup if needed. */
515 FIX_SSTEP(t);
516 KASSERT(lt != NULL);
517 lwp_addref(lt);
518
519 /*
520 * Which locks do we need held? XXX Ugly.
521 */
522 switch (req) {
523 #ifdef PT_STEP
524 case PT_STEP:
525 #endif
526 case PT_CONTINUE:
527 case PT_DETACH:
528 case PT_KILL:
529 case PT_SYSCALL:
530 case PT_SYSCALLEMU:
531 case PT_ATTACH:
532 case PT_TRACE_ME:
533 pheld = 1;
534 break;
535 default:
536 mutex_exit(proc_lock);
537 mutex_exit(t->p_lock);
538 pheld = 0;
539 break;
540 }
541
542 /* Now do the operation. */
543 write = 0;
544 *retval = 0;
545 tmp = 0;
546 resume_all = 1;
547
548 switch (req) {
549 case PT_TRACE_ME:
550 /* Just set the trace flag. */
551 SET(t->p_slflag, PSL_TRACED);
552 t->p_opptr = t->p_pptr;
553 break;
554
555 case PT_WRITE_I: /* XXX no separate I and D spaces */
556 case PT_WRITE_D:
557 #if defined(__HAVE_RAS)
558 /*
559 * Can't write to a RAS
560 */
561 if (ras_lookup(t, addr) != (void *)-1) {
562 error = EACCES;
563 break;
564 }
565 #endif
566 write = 1;
567 tmp = data;
568 /* FALLTHROUGH */
569
570 case PT_READ_I: /* XXX no separate I and D spaces */
571 case PT_READ_D:
572 /* write = 0 done above. */
573 iov.iov_base = (void *)&tmp;
574 iov.iov_len = sizeof(tmp);
575 uio.uio_iov = &iov;
576 uio.uio_iovcnt = 1;
577 uio.uio_offset = (off_t)(unsigned long)addr;
578 uio.uio_resid = sizeof(tmp);
579 uio.uio_rw = write ? UIO_WRITE : UIO_READ;
580 UIO_SETUP_SYSSPACE(&uio);
581
582 error = process_domem(l, lt, &uio);
583 if (!write)
584 *retval = tmp;
585 break;
586
587 case PT_IO:
588 error = ptm->ptm_copyinpiod(&piod, addr);
589 if (error)
590 break;
591
592 iov.iov_base = piod.piod_addr;
593 iov.iov_len = piod.piod_len;
594 uio.uio_iov = &iov;
595 uio.uio_iovcnt = 1;
596 uio.uio_offset = (off_t)(unsigned long)piod.piod_offs;
597 uio.uio_resid = piod.piod_len;
598
599 switch (piod.piod_op) {
600 case PIOD_READ_D:
601 case PIOD_READ_I:
602 uio.uio_rw = UIO_READ;
603 break;
604 case PIOD_WRITE_D:
605 case PIOD_WRITE_I:
606 /*
607 * Can't write to a RAS
608 */
609 if (ras_lookup(t, addr) != (void *)-1) {
610 return EACCES;
611 }
612 uio.uio_rw = UIO_WRITE;
613 break;
614 case PIOD_READ_AUXV:
615 req = PT_READ_D;
616 uio.uio_rw = UIO_READ;
617 tmp = t->p_execsw->es_arglen * PROC_PTRSZ(t);
618 if (uio.uio_offset > tmp)
619 return EIO;
620 if (uio.uio_resid > tmp - uio.uio_offset)
621 uio.uio_resid = tmp - uio.uio_offset;
622 piod.piod_len = iov.iov_len = uio.uio_resid;
623 error = process_auxv_offset(t, &uio);
624 if (error)
625 return error;
626 break;
627 default:
628 error = EINVAL;
629 break;
630 }
631 if (error)
632 break;
633 error = proc_vmspace_getref(l->l_proc, &vm);
634 if (error)
635 break;
636 uio.uio_vmspace = vm;
637
638 error = process_domem(l, lt, &uio);
639 piod.piod_len -= uio.uio_resid;
640 (void) ptm->ptm_copyoutpiod(&piod, addr);
641
642 uvmspace_free(vm);
643 break;
644
645 case PT_DUMPCORE:
646 if ((path = addr) != NULL) {
647 char *dst;
648 len = data;
649
650 if (len < 0 || len >= MAXPATHLEN) {
651 error = EINVAL;
652 break;
653 }
654 dst = kmem_alloc(len + 1, KM_SLEEP);
655 if ((error = copyin(path, dst, len)) != 0) {
656 kmem_free(dst, len + 1);
657 break;
658 }
659 path = dst;
660 path[len] = '\0';
661 }
662 error = (*coredump_vec)(lt, path);
663 if (path)
664 kmem_free(path, len + 1);
665 break;
666
667 #ifdef PT_STEP
668 case PT_STEP:
669 /*
670 * From the 4.4BSD PRM:
671 * "Execution continues as in request PT_CONTINUE; however
672 * as soon as possible after execution of at least one
673 * instruction, execution stops again. [ ... ]"
674 */
675 #endif
676 case PT_CONTINUE:
677 case PT_SYSCALL:
678 case PT_DETACH:
679 if (req == PT_SYSCALL) {
680 if (!ISSET(t->p_slflag, PSL_SYSCALL)) {
681 SET(t->p_slflag, PSL_SYSCALL);
682 #ifdef __HAVE_SYSCALL_INTERN
683 (*t->p_emul->e_syscall_intern)(t);
684 #endif
685 }
686 } else {
687 if (ISSET(t->p_slflag, PSL_SYSCALL)) {
688 CLR(t->p_slflag, PSL_SYSCALL);
689 #ifdef __HAVE_SYSCALL_INTERN
690 (*t->p_emul->e_syscall_intern)(t);
691 #endif
692 }
693 }
694 t->p_trace_enabled = trace_is_enabled(t);
695
696 /*
697 * Pick up the LWPID, if supplied. There are two cases:
698 * data < 0 : step or continue single thread, lwp = -data
699 * data > 0 in PT_STEP : step this thread, continue others
700 * For operations other than PT_STEP, data > 0 means
701 * data is the signo to deliver to the process.
702 */
703 tmp = data;
704 if (tmp >= 0) {
705 #ifdef PT_STEP
706 if (req == PT_STEP)
707 signo = 0;
708 else
709 #endif
710 {
711 signo = tmp;
712 tmp = 0; /* don't search for LWP */
713 }
714 } else
715 tmp = -tmp;
716
717 if (tmp > 0) {
718 if (req == PT_DETACH) {
719 error = EINVAL;
720 break;
721 }
722 lwp_delref2 (lt);
723 lt = lwp_find(t, tmp);
724 if (lt == NULL) {
725 error = ESRCH;
726 break;
727 }
728 lwp_addref(lt);
729 resume_all = 0;
730 signo = 0;
731 }
732
733 /*
734 * From the 4.4BSD PRM:
735 * "The data argument is taken as a signal number and the
736 * child's execution continues at location addr as if it
737 * incurred that signal. Normally the signal number will
738 * be either 0 to indicate that the signal that caused the
739 * stop should be ignored, or that value fetched out of
740 * the process's image indicating which signal caused
741 * the stop. If addr is (int *)1 then execution continues
742 * from where it stopped."
743 */
744
745 /* Check that the data is a valid signal number or zero. */
746 if (signo < 0 || signo >= NSIG) {
747 error = EINVAL;
748 break;
749 }
750
751 /* If the address parameter is not (int *)1, set the pc. */
752 if ((int *)addr != (int *)1) {
753 error = process_set_pc(lt, addr);
754 if (error != 0)
755 break;
756 }
757 #ifdef PT_STEP
758 /*
759 * Arrange for a single-step, if that's requested and possible.
760 * More precisely, set the single step status as requested for
761 * the requested thread, and clear it for other threads.
762 */
763 LIST_FOREACH(lt2, &t->p_lwps, l_sibling) {
764 if (lt != lt2) {
765 lwp_lock(lt2);
766 process_sstep(lt2, 0);
767 lwp_unlock(lt2);
768 }
769 }
770 error = process_sstep(lt, req == PT_STEP);
771 if (error)
772 break;
773 #endif
774 if (req == PT_DETACH) {
775 CLR(t->p_slflag, PSL_TRACED|PSL_FSTRACE|PSL_SYSCALL);
776
777 /* give process back to original parent or init */
778 if (t->p_opptr != t->p_pptr) {
779 struct proc *pp = t->p_opptr;
780 proc_reparent(t, pp ? pp : initproc);
781 }
782
783 /* not being traced any more */
784 t->p_opptr = NULL;
785 }
786 sendsig:
787 t->p_fpid = 0;
788 /* Finally, deliver the requested signal (or none). */
789 if (t->p_stat == SSTOP) {
790 /*
791 * Unstop the process. If it needs to take a
792 * signal, make all efforts to ensure that at
793 * an LWP runs to see it.
794 */
795 t->p_xsig = signo;
796 if (resume_all)
797 proc_unstop(t);
798 else
799 lwp_unstop(lt);
800 } else if (signo != 0) {
801 KSI_INIT_EMPTY(&ksi);
802 ksi.ksi_signo = signo;
803 kpsignal2(t, &ksi);
804 }
805 break;
806
807 case PT_SYSCALLEMU:
808 if (!ISSET(t->p_slflag, PSL_SYSCALL) || t->p_stat != SSTOP) {
809 error = EINVAL;
810 break;
811 }
812 SET(t->p_slflag, PSL_SYSCALLEMU);
813 break;
814
815 case PT_KILL:
816 /* just send the process a KILL signal. */
817 signo = SIGKILL;
818 goto sendsig; /* in PT_CONTINUE, above. */
819
820 case PT_ATTACH:
821 /*
822 * Go ahead and set the trace flag.
823 * Save the old parent (it's reset in
824 * _DETACH, and also in kern_exit.c:wait4()
825 * Reparent the process so that the tracing
826 * proc gets to see all the action.
827 * Stop the target.
828 */
829 proc_changeparent(t, p);
830 signo = SIGSTOP;
831 goto sendsig;
832
833 case PT_GET_EVENT_MASK:
834 if (data != sizeof(pe)) {
835 DPRINTF(("ptrace(%d): %d != %zu\n", req,
836 data, sizeof(pe)));
837 error = EINVAL;
838 break;
839 }
840 memset(&pe, 0, sizeof(pe));
841 pe.pe_set_event = ISSET(t->p_slflag, PSL_TRACEFORK) ?
842 PTRACE_FORK : 0;
843 error = copyout(&pe, addr, sizeof(pe));
844 break;
845
846 case PT_SET_EVENT_MASK:
847 if (data != sizeof(pe)) {
848 DPRINTF(("ptrace(%d): %d != %zu\n", req, data,
849 sizeof(pe)));
850 error = EINVAL;
851 break;
852 }
853 if ((error = copyin(addr, &pe, sizeof(pe))) != 0)
854 return error;
855 if (pe.pe_set_event & PTRACE_FORK)
856 SET(t->p_slflag, PSL_TRACEFORK);
857 else
858 CLR(t->p_slflag, PSL_TRACEFORK);
859 break;
860
861 case PT_GET_PROCESS_STATE:
862 if (data != sizeof(ps)) {
863 DPRINTF(("ptrace(%d): %d != %zu\n", req, data,
864 sizeof(ps)));
865 error = EINVAL;
866 break;
867 }
868 memset(&ps, 0, sizeof(ps));
869 if (t->p_fpid) {
870 ps.pe_report_event = PTRACE_FORK;
871 ps.pe_other_pid = t->p_fpid;
872 }
873 error = copyout(&ps, addr, sizeof(ps));
874 break;
875
876 case PT_LWPINFO:
877 if (data != sizeof(pl)) {
878 DPRINTF(("ptrace(%d): %d != %zu\n", req, data,
879 sizeof(pl)));
880 error = EINVAL;
881 break;
882 }
883 error = copyin(addr, &pl, sizeof(pl));
884 if (error)
885 break;
886 tmp = pl.pl_lwpid;
887 lwp_delref(lt);
888 mutex_enter(t->p_lock);
889 if (tmp == 0)
890 lt = lwp_find_first(t);
891 else {
892 lt = lwp_find(t, tmp);
893 if (lt == NULL) {
894 mutex_exit(t->p_lock);
895 error = ESRCH;
896 break;
897 }
898 lt = LIST_NEXT(lt, l_sibling);
899 }
900 while (lt != NULL && !lwp_alive(lt))
901 lt = LIST_NEXT(lt, l_sibling);
902 pl.pl_lwpid = 0;
903 pl.pl_event = 0;
904 if (lt) {
905 lwp_addref(lt);
906 pl.pl_lwpid = lt->l_lid;
907 /*
908 * If we match the lwp, or it was sent to every lwp,
909 * we set PL_EVENT_SIGNAL.
910 * XXX: ps_lwp == 0 means everyone and noone, so
911 * check ps_signo too.
912 */
913 if (lt->l_lid == t->p_sigctx.ps_lwp
914 || (t->p_sigctx.ps_lwp == 0 && t->p_sigctx.ps_signo))
915 pl.pl_event = PL_EVENT_SIGNAL;
916 }
917 mutex_exit(t->p_lock);
918
919 error = copyout(&pl, addr, sizeof(pl));
920 break;
921
922 #ifdef PT_SETREGS
923 case PT_SETREGS:
924 write = 1;
925 #endif
926 #ifdef PT_GETREGS
927 case PT_GETREGS:
928 /* write = 0 done above. */
929 #endif
930 #if defined(PT_SETREGS) || defined(PT_GETREGS)
931 tmp = data;
932 if (tmp != 0 && t->p_nlwps > 1) {
933 lwp_delref(lt);
934 mutex_enter(t->p_lock);
935 lt = lwp_find(t, tmp);
936 if (lt == NULL) {
937 mutex_exit(t->p_lock);
938 error = ESRCH;
939 break;
940 }
941 lwp_addref(lt);
942 mutex_exit(t->p_lock);
943 }
944 if (!process_validregs(lt))
945 error = EINVAL;
946 else {
947 error = proc_vmspace_getref(p, &vm);
948 if (error)
949 break;
950 iov.iov_base = addr;
951 iov.iov_len = PROC_REGSZ(p);
952 uio.uio_iov = &iov;
953 uio.uio_iovcnt = 1;
954 uio.uio_offset = 0;
955 uio.uio_resid = iov.iov_len;
956 uio.uio_rw = write ? UIO_WRITE : UIO_READ;
957 uio.uio_vmspace = vm;
958
959 error = ptm->ptm_doregs(l, lt, &uio);
960 uvmspace_free(vm);
961 }
962 break;
963 #endif
964
965 #ifdef PT_SETFPREGS
966 case PT_SETFPREGS:
967 write = 1;
968 /*FALLTHROUGH*/
969 #endif
970 #ifdef PT_GETFPREGS
971 case PT_GETFPREGS:
972 /* write = 0 done above. */
973 #endif
974 #if defined(PT_SETFPREGS) || defined(PT_GETFPREGS)
975 tmp = data;
976 if (tmp != 0 && t->p_nlwps > 1) {
977 lwp_delref(lt);
978 mutex_enter(t->p_lock);
979 lt = lwp_find(t, tmp);
980 if (lt == NULL) {
981 mutex_exit(t->p_lock);
982 error = ESRCH;
983 break;
984 }
985 lwp_addref(lt);
986 mutex_exit(t->p_lock);
987 }
988 if (!process_validfpregs(lt))
989 error = EINVAL;
990 else {
991 error = proc_vmspace_getref(p, &vm);
992 if (error)
993 break;
994 iov.iov_base = addr;
995 iov.iov_len = PROC_FPREGSZ(p);
996 uio.uio_iov = &iov;
997 uio.uio_iovcnt = 1;
998 uio.uio_offset = 0;
999 uio.uio_resid = iov.iov_len;
1000 uio.uio_rw = write ? UIO_WRITE : UIO_READ;
1001 uio.uio_vmspace = vm;
1002
1003 error = ptm->ptm_dofpregs(l, lt, &uio);
1004 uvmspace_free(vm);
1005 }
1006 break;
1007 #endif
1008
1009 #ifdef __HAVE_PTRACE_WATCHPOINTS
1010 /*
1011 * The "write" variable is used as type of operation.
1012 * Possible values:
1013 * 0 - return the number of supported hardware watchpoints
1014 * 1 - set new watchpoint value
1015 * 2 - get existing watchpoint image
1016 */
1017 case PT_WRITE_WATCHPOINT:
1018 write = 1;
1019 case PT_READ_WATCHPOINT:
1020 /* write = 0 done above */
1021
1022 if (data != sizeof(pw)) {
1023 DPRINTF(("ptrace(%d): %d != %zu\n", req,
1024 data, sizeof(pe)));
1025 error = EINVAL;
1026 break;
1027 }
1028 error = copyin(addr, &pw, sizeof(pw));
1029 if (error)
1030 break;
1031 tmp = pw.pw_lwpid;
1032 if (tmp != 0 && t->p_nlwps > 1) {
1033 lwp_delref(lt);
1034 mutex_enter(t->p_lock);
1035 lt = lwp_find(t, tmp);
1036 if (lt == NULL) {
1037 mutex_exit(t->p_lock);
1038 error = ESRCH;
1039 break;
1040 }
1041 lwp_addref(lt);
1042 mutex_exit(t->p_lock);
1043 }
1044 ++write;
1045 case PT_COUNT_WATCHPOINTS:
1046 if (!process_validwatchpoint(lt))
1047 error = EINVAL;
1048 else {
1049 lwp_lock(lt);
1050 error = ptm->ptm_dowatchpoint(l, lt, write, &pw, addr,
1051 retval);
1052 lwp_unlock(lt);
1053 }
1054 break;
1055 #endif
1056
1057 #ifdef __HAVE_PTRACE_MACHDEP
1058 PTRACE_MACHDEP_REQUEST_CASES
1059 error = ptrace_machdep_dorequest(l, lt, req, addr, data);
1060 break;
1061 #endif
1062 }
1063
1064 if (pheld) {
1065 mutex_exit(t->p_lock);
1066 mutex_exit(proc_lock);
1067 }
1068 if (lt != NULL)
1069 lwp_delref(lt);
1070 rw_exit(&t->p_reflock);
1071
1072 return error;
1073 }
1074
1075 int
1076 process_doregs(struct lwp *curl /*tracer*/,
1077 struct lwp *l /*traced*/,
1078 struct uio *uio)
1079 {
1080 #if defined(PT_GETREGS) || defined(PT_SETREGS)
1081 int error;
1082 struct reg r;
1083 char *kv;
1084 int kl;
1085
1086 if (uio->uio_offset < 0 || uio->uio_offset > (off_t)sizeof(r))
1087 return EINVAL;
1088
1089 kl = sizeof(r);
1090 kv = (char *)&r;
1091
1092 kv += uio->uio_offset;
1093 kl -= uio->uio_offset;
1094 if ((size_t)kl > uio->uio_resid)
1095 kl = uio->uio_resid;
1096
1097 error = process_read_regs(l, &r);
1098 if (error == 0)
1099 error = uiomove(kv, kl, uio);
1100 if (error == 0 && uio->uio_rw == UIO_WRITE) {
1101 if (l->l_stat != LSSTOP)
1102 error = EBUSY;
1103 else
1104 error = process_write_regs(l, &r);
1105 }
1106
1107 uio->uio_offset = 0;
1108 return error;
1109 #else
1110 return EINVAL;
1111 #endif
1112 }
1113
1114 int
1115 process_validregs(struct lwp *l)
1116 {
1117
1118 #if defined(PT_SETREGS) || defined(PT_GETREGS)
1119 return (l->l_flag & LW_SYSTEM) == 0;
1120 #else
1121 return 0;
1122 #endif
1123 }
1124
1125 int
1126 process_dofpregs(struct lwp *curl /*tracer*/,
1127 struct lwp *l /*traced*/,
1128 struct uio *uio)
1129 {
1130 #if defined(PT_GETFPREGS) || defined(PT_SETFPREGS)
1131 int error;
1132 struct fpreg r;
1133 char *kv;
1134 size_t kl;
1135
1136 if (uio->uio_offset < 0 || uio->uio_offset > (off_t)sizeof(r))
1137 return EINVAL;
1138
1139 kl = sizeof(r);
1140 kv = (char *)&r;
1141
1142 kv += uio->uio_offset;
1143 kl -= uio->uio_offset;
1144 if (kl > uio->uio_resid)
1145 kl = uio->uio_resid;
1146
1147 error = process_read_fpregs(l, &r, &kl);
1148 if (error == 0)
1149 error = uiomove(kv, kl, uio);
1150 if (error == 0 && uio->uio_rw == UIO_WRITE) {
1151 if (l->l_stat != LSSTOP)
1152 error = EBUSY;
1153 else
1154 error = process_write_fpregs(l, &r, kl);
1155 }
1156 uio->uio_offset = 0;
1157 return error;
1158 #else
1159 return EINVAL;
1160 #endif
1161 }
1162
1163 int
1164 process_validfpregs(struct lwp *l)
1165 {
1166
1167 #if defined(PT_SETFPREGS) || defined(PT_GETFPREGS)
1168 return (l->l_flag & LW_SYSTEM) == 0;
1169 #else
1170 return 0;
1171 #endif
1172 }
1173
1174 static int
1175 process_auxv_offset(struct proc *p, struct uio *uio)
1176 {
1177 struct ps_strings pss;
1178 int error;
1179 off_t off = (off_t)p->p_psstrp;
1180
1181 if ((error = copyin_psstrings(p, &pss)) != 0)
1182 return error;
1183
1184 if (pss.ps_envstr == NULL)
1185 return EIO;
1186
1187 uio->uio_offset += (off_t)(vaddr_t)(pss.ps_envstr + pss.ps_nenvstr + 1);
1188 #ifdef __MACHINE_STACK_GROWS_UP
1189 if (uio->uio_offset < off)
1190 return EIO;
1191 #else
1192 if (uio->uio_offset > off)
1193 return EIO;
1194 if ((uio->uio_offset + uio->uio_resid) > off)
1195 uio->uio_resid = off - uio->uio_offset;
1196 #endif
1197 return 0;
1198 }
1199
1200 int
1201 process_dowatchpoint(struct lwp *curl /*tracer*/, struct lwp *l /*traced*/,
1202 int operation, struct ptrace_watchpoint *pw, void *addr,
1203 register_t *retval)
1204 {
1205
1206 #ifdef __HAVE_PTRACE_WATCHPOINTS
1207 int error;
1208
1209 KASSERT(operation >= 0);
1210 KASSERT(operation <= 2);
1211
1212 switch (operation) {
1213 case 0:
1214 return process_count_watchpoints(l, retval);
1215 case 1:
1216 error = process_read_watchpoint(l, pw);
1217 if (error)
1218 return error;
1219 return copyout(pw, addr, sizeof(*pw));
1220 default:
1221 return process_write_watchpoint(l, pw);
1222 }
1223 #else
1224 return EINVAL;
1225 #endif
1226 }
1227
1228 int
1229 process_validwatchpoint(struct lwp *l)
1230 {
1231
1232 #ifdef __HAVE_PTRACE_WATCHPOINTS
1233 return (l->l_flag & LW_SYSTEM) == 0;
1234 #else
1235 return 0;
1236 #endif
1237 }
1238 #endif /* PTRACE */
1239
1240 MODULE(MODULE_CLASS_EXEC, ptrace_common, "");
1241
1242 static int
1243 ptrace_common_modcmd(modcmd_t cmd, void *arg)
1244 {
1245 int error;
1246
1247 switch (cmd) {
1248 case MODULE_CMD_INIT:
1249 error = ptrace_init();
1250 break;
1251 case MODULE_CMD_FINI:
1252 error = ptrace_fini();
1253 break;
1254 default:
1255 ptrace_hooks();
1256 error = ENOTTY;
1257 break;
1258 }
1259 return error;
1260 }
1261