aboutsummaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
Diffstat (limited to 'sys')
-rw-r--r--sys/kern/kern_exit.c1
-rw-r--r--sys/kern/kern_sig.c3
-rw-r--r--sys/kern/sys_process.c19
-rw-r--r--sys/sys/proc.h1
-rw-r--r--sys/sys/ptrace.h9
5 files changed, 33 insertions, 0 deletions
diff --git a/sys/kern/kern_exit.c b/sys/kern/kern_exit.c
index 5d0f4c3c879b..056116d96e83 100644
--- a/sys/kern/kern_exit.c
+++ b/sys/kern/kern_exit.c
@@ -429,6 +429,7 @@ retry:
mtx_lock(&Giant);
PROC_LOCK(p);
p->p_xstat = rv;
+ p->p_xlwpid = td->td_tid;
*p->p_ru = p->p_stats->p_ru;
mtx_lock_spin(&sched_lock);
calcru(p, &p->p_ru->ru_utime, &p->p_ru->ru_stime, NULL);
diff --git a/sys/kern/kern_sig.c b/sys/kern/kern_sig.c
index d17cbe232c54..bbc9e281e6f9 100644
--- a/sys/kern/kern_sig.c
+++ b/sys/kern/kern_sig.c
@@ -1882,6 +1882,7 @@ do_tdsignal(struct thread *td, int sig, sigtarget_t target)
goto out;
p->p_flag |= P_STOPPED_SIG;
p->p_xstat = sig;
+ p->p_xlwpid = td->td_tid;
mtx_lock_spin(&sched_lock);
FOREACH_THREAD_IN_PROC(p, td0) {
if (TD_IS_SLEEPING(td0) &&
@@ -2011,6 +2012,7 @@ ptracestop(struct thread *td, int sig)
&p->p_mtx.mtx_object, "Stopping for traced signal");
p->p_xstat = sig;
+ p->p_xlwpid = td->td_tid;
PROC_LOCK(p->p_pptr);
psignal(p->p_pptr, SIGCHLD);
PROC_UNLOCK(p->p_pptr);
@@ -2154,6 +2156,7 @@ issignal(td)
&p->p_mtx.mtx_object, "Catching SIGSTOP");
p->p_flag |= P_STOPPED_SIG;
p->p_xstat = sig;
+ p->p_xlwpid = td->td_tid;
mtx_lock_spin(&sched_lock);
FOREACH_THREAD_IN_PROC(p, td0) {
if (TD_IS_SLEEPING(td0) &&
diff --git a/sys/kern/sys_process.c b/sys/kern/sys_process.c
index f65b67c75a74..0cae07b970c5 100644
--- a/sys/kern/sys_process.c
+++ b/sys/kern/sys_process.c
@@ -305,6 +305,7 @@ ptrace(struct thread *td, struct ptrace_args *uap)
*/
union {
struct ptrace_io_desc piod;
+ struct ptrace_lwpinfo pl;
struct dbreg dbreg;
struct fpreg fpreg;
struct reg reg;
@@ -317,6 +318,7 @@ ptrace(struct thread *td, struct ptrace_args *uap)
case PT_GETREGS:
case PT_GETFPREGS:
case PT_GETDBREGS:
+ case PT_LWPINFO:
break;
case PT_SETREGS:
error = copyin(uap->addr, &r.reg, sizeof r.reg);
@@ -354,6 +356,9 @@ ptrace(struct thread *td, struct ptrace_args *uap)
case PT_GETDBREGS:
error = copyout(&r.dbreg, uap->addr, sizeof r.dbreg);
break;
+ case PT_LWPINFO:
+ error = copyout(&r.pl, uap->addr, uap->data);
+ break;
}
return (error);
@@ -367,6 +372,7 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data)
struct proc *curp, *p, *pp;
struct thread *td2 = NULL;
struct ptrace_io_desc *piod;
+ struct ptrace_lwpinfo *pl;
int error, write, tmp;
int proctree_locked = 0;
lwpid_t tid = 0;
@@ -606,6 +612,7 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data)
/* deliver or queue signal */
if (P_SHOULDSTOP(p)) {
p->p_xstat = data;
+ p->p_xlwpid = 0;
p->p_flag &= ~(P_STOPPED_TRACE|P_STOPPED_SIG);
mtx_lock_spin(&sched_lock);
thread_unsuspend(p);
@@ -727,6 +734,17 @@ kern_ptrace(struct thread *td, int req, pid_t pid, void *addr, int data)
PROC_UNLOCK(p);
return (error);
+ case PT_LWPINFO:
+ if (data == 0 || data > sizeof(*pl))
+ return (EINVAL);
+ pl = addr;
+ _PHOLD(p);
+ pl->pl_lwpid = p->p_xlwpid;
+ _PRELE(p);
+ PROC_UNLOCK(p);
+ pl->pl_event = PL_EVENT_SIGNAL;
+ return (0);
+
default:
#ifdef __HAVE_PTRACE_MACHDEP
if (req >= PT_FIRSTMACH) {
@@ -764,6 +782,7 @@ stopevent(struct proc *p, unsigned int event, unsigned int val)
p->p_step = 1;
do {
p->p_xstat = val;
+ p->p_xlwpid = 0;
p->p_stype = event; /* Which event caused the stop? */
wakeup(&p->p_stype); /* Wake up any PIOCWAIT'ing procs */
msleep(&p->p_step, &p->p_mtx, PWAIT, "stopevent", 0);
diff --git a/sys/sys/proc.h b/sys/sys/proc.h
index 8246c599fc43..bf3c78846a76 100644
--- a/sys/sys/proc.h
+++ b/sys/sys/proc.h
@@ -602,6 +602,7 @@ struct proc {
#define p_endcopy p_xstat
u_short p_xstat; /* (c) Exit status; also stop sig. */
+ lwpid_t p_xlwpid; /* (c) Thread corresponding p_xstat. */
int p_numthreads; /* (j) Number of threads. */
int p_numksegrps; /* (?) number of ksegrps */
struct mdproc p_md; /* Any machine-dependent fields. */
diff --git a/sys/sys/ptrace.h b/sys/sys/ptrace.h
index c849eb6fc195..03ff33c13ce6 100644
--- a/sys/sys/ptrace.h
+++ b/sys/sys/ptrace.h
@@ -47,6 +47,7 @@
#define PT_ATTACH 10 /* trace some running process */
#define PT_DETACH 11 /* stop tracing a process */
#define PT_IO 12 /* do I/O to/from stopped process. */
+#define PT_LWPINFO 13 /* Info about the LWP that stopped. */
#define PT_TO_SCE 20
#define PT_TO_SCX 21
@@ -77,6 +78,14 @@ struct ptrace_io_desc {
#define PIOD_READ_I 3 /* Read from I space */
#define PIOD_WRITE_I 4 /* Write to I space */
+/* Argument structure for PT_LWPINFO. */
+struct ptrace_lwpinfo {
+ lwpid_t pl_lwpid; /* LWP described. */
+ int pl_event; /* Event that stopped the LWP. */
+#define PL_EVENT_NONE 0
+#define PL_EVENT_SIGNAL 1
+};
+
#ifdef _KERNEL
#define PTRACESTOP_SC(p, td, flag) \