Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 4 May 2014 03:34:32 +0000 (UTC)
From:      Mark Johnston <markj@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r265308 - head/lib/libproc
Message-ID:  <201405040334.s443YWZW042309@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: markj
Date: Sun May  4 03:34:32 2014
New Revision: 265308
URL: http://svnweb.freebsd.org/changeset/base/265308

Log:
  If the traced process stops because it received a signal, libproc needs
  to ensure that the signal is forwarded when proc_continue() is called.
  
  MFC after:	3 weeks

Modified:
  head/lib/libproc/libproc.h
  head/lib/libproc/proc_bkpt.c
  head/lib/libproc/proc_util.c

Modified: head/lib/libproc/libproc.h
==============================================================================
--- head/lib/libproc/libproc.h	Sun May  4 01:33:02 2014	(r265307)
+++ head/lib/libproc/libproc.h	Sun May  4 03:34:32 2014	(r265308)
@@ -102,6 +102,7 @@ typedef struct lwpstatus {
 #define PR_FAULTED	2
 #define PR_SYSENTRY	3
 #define PR_SYSEXIT	4
+#define PR_SIGNALLED	5
 	int pr_what;
 #define FLTBPT		-1
 } lwpstatus_t;

Modified: head/lib/libproc/proc_bkpt.c
==============================================================================
--- head/lib/libproc/proc_bkpt.c	Sun May  4 01:33:02 2014	(r265307)
+++ head/lib/libproc/proc_bkpt.c	Sun May  4 03:34:32 2014	(r265308)
@@ -55,13 +55,6 @@ __FBSDID("$FreeBSD$");
 #error "Add support for your architecture"
 #endif
 
-static void
-proc_cont(struct proc_handle *phdl)
-{
-
-	ptrace(PT_CONTINUE, proc_getpid(phdl), (caddr_t)1, 0);
-}
-
 static int
 proc_stop(struct proc_handle *phdl)
 {
@@ -87,7 +80,7 @@ proc_bkptset(struct proc_handle *phdl, u
 {
 	struct ptrace_io_desc piod;
 	unsigned long paddr, caddr;
-	int ret = 0;
+	int ret = 0, stopped;
 
 	*saved = 0;
 	if (phdl->status == PS_DEAD || phdl->status == PS_UNDEAD ||
@@ -98,9 +91,12 @@ proc_bkptset(struct proc_handle *phdl, u
 
 	DPRINTFX("adding breakpoint at 0x%lx", address);
 
-	if (phdl->status != PS_STOP)
+	stopped = 0;
+	if (phdl->status != PS_STOP) {
 		if (proc_stop(phdl) != 0)
 			return (-1);
+		stopped = 1;
+	}
 
 	/*
 	 * Read the original instruction.
@@ -135,9 +131,9 @@ proc_bkptset(struct proc_handle *phdl, u
 	}
 
 done:
-	if (phdl->status != PS_STOP)
+	if (stopped)
 		/* Restart the process if we had to stop it. */
-		proc_cont(phdl);
+		proc_continue(phdl);
 
 	return (ret);
 }
@@ -148,7 +144,7 @@ proc_bkptdel(struct proc_handle *phdl, u
 {
 	struct ptrace_io_desc piod;
 	unsigned long paddr, caddr;
-	int ret = 0;
+	int ret = 0, stopped;
 
 	if (phdl->status == PS_DEAD || phdl->status == PS_UNDEAD ||
 	    phdl->status == PS_IDLE) {
@@ -158,9 +154,12 @@ proc_bkptdel(struct proc_handle *phdl, u
 
 	DPRINTFX("removing breakpoint at 0x%lx", address);
 
-	if (phdl->status != PS_STOP)
+	stopped = 0;
+	if (phdl->status != PS_STOP) {
 		if (proc_stop(phdl) != 0)
 			return (-1);
+		stopped = 1;
+	}
 
 	/*
 	 * Overwrite the breakpoint instruction that we setup previously.
@@ -177,9 +176,9 @@ proc_bkptdel(struct proc_handle *phdl, u
 		ret = -1;
 	}
 
-	if (phdl->status != PS_STOP)
+	if (stopped)
 		/* Restart the process if we had to stop it. */
-		proc_cont(phdl);
+		proc_continue(phdl);
  
 	return (ret);
 }

Modified: head/lib/libproc/proc_util.c
==============================================================================
--- head/lib/libproc/proc_util.c	Sun May  4 01:33:02 2014	(r265307)
+++ head/lib/libproc/proc_util.c	Sun May  4 03:34:32 2014	(r265308)
@@ -35,10 +35,9 @@
 #include <sys/wait.h>
 #include <err.h>
 #include <errno.h>
-#include <unistd.h>
-#include <stdio.h>
 #include <signal.h>
 #include <string.h>
+#include <unistd.h>
 #include "_libproc.h"
 
 int
@@ -59,11 +58,14 @@ proc_clearflags(struct proc_handle *phdl
 int
 proc_continue(struct proc_handle *phdl)
 {
+	int pending = 0;
 
 	if (phdl == NULL)
 		return (-1);
 
-	if (ptrace(PT_CONTINUE, phdl->pid, (caddr_t)(uintptr_t) 1, 0) != 0)
+	if (phdl->status == PS_STOP && WSTOPSIG(phdl->wstat) != SIGTRAP)
+		pending = WSTOPSIG(phdl->wstat);
+	if (ptrace(PT_CONTINUE, phdl->pid, (caddr_t)(uintptr_t)1, pending) != 0)
 		return (-1);
 
 	phdl->status = PS_RUN;
@@ -208,12 +210,16 @@ proc_getlwpstatus(struct proc_handle *ph
 		return (NULL);
 	siginfo = &lwpinfo.pl_siginfo;
 	if (lwpinfo.pl_event == PL_EVENT_SIGNAL &&
-	    (lwpinfo.pl_flags & PL_FLAG_SI) &&
-	    siginfo->si_signo == SIGTRAP &&
-	    (siginfo->si_code == TRAP_BRKPT ||
-	    siginfo->si_code == TRAP_TRACE)) {
-		psp->pr_why = PR_FAULTED;
-		psp->pr_what = FLTBPT;
+	    (lwpinfo.pl_flags & PL_FLAG_SI) != 0) {
+		if (siginfo->si_signo == SIGTRAP &&
+		    (siginfo->si_code == TRAP_BRKPT ||
+		    siginfo->si_code == TRAP_TRACE)) {
+			psp->pr_why = PR_FAULTED;
+			psp->pr_what = FLTBPT;
+		} else {
+			psp->pr_why = PR_SIGNALLED;
+			psp->pr_what = siginfo->si_signo;
+		}
 	} else if (lwpinfo.pl_flags & PL_FLAG_SCE) {
 		psp->pr_why = PR_SYSENTRY;
 	} else if (lwpinfo.pl_flags & PL_FLAG_SCX) {



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201405040334.s443YWZW042309>