diff options
Diffstat (limited to 'sys/kern')
-rw-r--r-- | sys/kern/kern_fork.c | 3 | ||||
-rw-r--r-- | sys/kern/kern_sig.c | 2 | ||||
-rw-r--r-- | sys/kern/subr_syscall.c | 8 | ||||
-rw-r--r-- | sys/kern/sys_process.c | 17 | ||||
-rw-r--r-- | sys/kern/vfs_aio.c | 7 | ||||
-rw-r--r-- | sys/kern/vfs_default.c | 1 |
6 files changed, 23 insertions, 15 deletions
diff --git a/sys/kern/kern_fork.c b/sys/kern/kern_fork.c index 4d96840..8fa6bcd 100644 --- a/sys/kern/kern_fork.c +++ b/sys/kern/kern_fork.c @@ -728,6 +728,7 @@ do_fork(struct thread *td, int flags, struct proc *p2, struct thread *td2, if (flags & RFPPWAIT) { td->td_pflags |= TDP_RFPPWAIT; td->td_rfppwait_p = p2; + td->td_dbgflags |= TDB_VFORK; } PROC_UNLOCK(p2); if ((flags & RFSTOPPED) == 0) { @@ -1063,7 +1064,7 @@ fork_return(struct thread *td, struct trapframe *frame) * parent's children, do it now. */ dbg = p->p_pptr->p_pptr; - proc_set_traced(p); + proc_set_traced(p, true); CTR2(KTR_PTRACE, "fork_return: attaching to new child pid %d: oppid %d", p->p_pid, p->p_oppid); diff --git a/sys/kern/kern_sig.c b/sys/kern/kern_sig.c index 2c37d76..75121b5 100644 --- a/sys/kern/kern_sig.c +++ b/sys/kern/kern_sig.c @@ -2510,7 +2510,7 @@ ptracestop(struct thread *td, int sig) * a chance to report itself upon the next iteration. */ if ((td->td_dbgflags & TDB_FSTP) != 0 || - ((p->p_flag & P2_PTRACE_FSTP) == 0 && + ((p->p_flag2 & P2_PTRACE_FSTP) == 0 && p->p_xthread == NULL)) { p->p_xstat = sig; p->p_xthread = td; diff --git a/sys/kern/subr_syscall.c b/sys/kern/subr_syscall.c index f2b83f0..201d876 100644 --- a/sys/kern/subr_syscall.c +++ b/sys/kern/subr_syscall.c @@ -249,5 +249,13 @@ again: cv_timedwait(&p2->p_pwait, &p2->p_mtx, hz); } PROC_UNLOCK(p2); + + if (td->td_dbgflags & TDB_VFORK) { + PROC_LOCK(p); + if (p->p_ptevents & PTRACE_VFORK) + ptracestop(td, SIGTRAP); + td->td_dbgflags &= ~TDB_VFORK; + PROC_UNLOCK(p); + } } } diff --git a/sys/kern/sys_process.c b/sys/kern/sys_process.c index c4533ce..b2dbf72 100644 --- a/sys/kern/sys_process.c +++ b/sys/kern/sys_process.c @@ -649,12 +649,13 @@ sys_ptrace(struct thread *td, struct ptrace_args *uap) #endif void -proc_set_traced(struct proc *p) +proc_set_traced(struct proc *p, bool stop) { PROC_LOCK_ASSERT(p, MA_OWNED); p->p_flag |= P_TRACED; - p->p_flag2 |= P2_PTRACE_FSTP; + if (stop) + p->p_flag2 |= P2_PTRACE_FSTP; p->p_ptevents = PTRACE_DEFAULT; p->p_oppid = p->p_pptr->p_pid; } @@ -867,7 +868,7 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data) switch (req) { case PT_TRACE_ME: /* set my trace flag and "owner" so it can read/write me */ - proc_set_traced(p); + proc_set_traced(p, false); if (p->p_flag & P_PPWAIT) p->p_flag |= P_PPTRACE; CTR1(KTR_PTRACE, "PT_TRACE_ME: pid %d", p->p_pid); @@ -884,7 +885,7 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data) * The old parent is remembered so we can put things back * on a "detach". */ - proc_set_traced(p); + proc_set_traced(p, true); if (p->p_pptr != td->td_proc) { proc_reparent(p, td->td_proc); } @@ -957,7 +958,7 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data) } tmp = *(int *)addr; if ((tmp & ~(PTRACE_EXEC | PTRACE_SCE | PTRACE_SCX | - PTRACE_FORK | PTRACE_LWP)) != 0) { + PTRACE_FORK | PTRACE_LWP | PTRACE_VFORK)) != 0) { error = EINVAL; break; } @@ -1296,7 +1297,11 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data) if (td2->td_dbgflags & TDB_FORK) { pl->pl_flags |= PL_FLAG_FORKED; pl->pl_child_pid = td2->td_dbg_forked; - } + if (td2->td_dbgflags & TDB_VFORK) + pl->pl_flags |= PL_FLAG_VFORKED; + } else if ((td2->td_dbgflags & (TDB_SCX | TDB_VFORK)) == + TDB_VFORK) + pl->pl_flags |= PL_FLAG_VFORK_DONE; if (td2->td_dbgflags & TDB_CHILD) pl->pl_flags |= PL_FLAG_CHILD; if (td2->td_dbgflags & TDB_BORN) diff --git a/sys/kern/vfs_aio.c b/sys/kern/vfs_aio.c index 89b7a00..0fa87f9 100644 --- a/sys/kern/vfs_aio.c +++ b/sys/kern/vfs_aio.c @@ -1582,7 +1582,7 @@ static struct aiocb_ops aiocb_ops_osigevent = { */ int aio_aqueue(struct thread *td, struct aiocb *job, struct aioliojob *lj, - int type, struct aiocb_ops *ops) + int type, struct aiocb_ops *ops) { struct proc *p = td->td_proc; cap_rights_t rights; @@ -2568,14 +2568,9 @@ static int kern_aio_fsync(struct thread *td, int op, struct aiocb *aiocbp, struct aiocb_ops *ops) { - struct proc *p = td->td_proc; - struct kaioinfo *ki; if (op != O_SYNC) /* XXX lack of O_DSYNC */ return (EINVAL); - ki = p->p_aioinfo; - if (ki == NULL) - aio_init_aioinfo(p); return (aio_aqueue(td, aiocbp, NULL, LIO_SYNC, ops)); } diff --git a/sys/kern/vfs_default.c b/sys/kern/vfs_default.c index 94b8149..166ed65 100644 --- a/sys/kern/vfs_default.c +++ b/sys/kern/vfs_default.c @@ -635,7 +635,6 @@ int vop_stdfsync(ap) struct vop_fsync_args /* { struct vnode *a_vp; - struct ucred *a_cred; int a_waitfor; struct thread *a_td; } */ *ap; |