From owner-p4-projects@FreeBSD.ORG Sun Jan 13 03:29:48 2008 Return-Path: Delivered-To: p4-projects@freebsd.org Received: by hub.freebsd.org (Postfix, from userid 32767) id 77CCF16A419; Sun, 13 Jan 2008 03:29:48 +0000 (UTC) Delivered-To: perforce@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 24B8C16A417 for ; Sun, 13 Jan 2008 03:29:48 +0000 (UTC) (envelope-from jb@freebsd.org) Received: from repoman.freebsd.org (repoman.freebsd.org [IPv6:2001:4f8:fff6::29]) by mx1.freebsd.org (Postfix) with ESMTP id 276D313C4F5 for ; Sun, 13 Jan 2008 03:29:48 +0000 (UTC) (envelope-from jb@freebsd.org) Received: from repoman.freebsd.org (localhost [127.0.0.1]) by repoman.freebsd.org (8.14.1/8.14.1) with ESMTP id m0D3TlGu037326 for ; Sun, 13 Jan 2008 03:29:47 GMT (envelope-from jb@freebsd.org) Received: (from perforce@localhost) by repoman.freebsd.org (8.14.1/8.14.1/Submit) id m0D3Tlus037323 for perforce@freebsd.org; Sun, 13 Jan 2008 03:29:47 GMT (envelope-from jb@freebsd.org) Date: Sun, 13 Jan 2008 03:29:47 GMT Message-Id: <200801130329.m0D3Tlus037323@repoman.freebsd.org> X-Authentication-Warning: repoman.freebsd.org: perforce set sender to jb@freebsd.org using -f From: John Birrell To: Perforce Change Reviews Cc: Subject: PERFORCE change 133154 for review X-BeenThere: p4-projects@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: p4 projects tree changes List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 13 Jan 2008 03:29:48 -0000 http://perforce.freebsd.org/chv.cgi?CH=133154 Change 133154 by jb@jb_freebsd1 on 2008/01/13 03:29:46 Implement proc_attach to allocate a handle like proc_create does. Add clear, get and set flags. Move proc_free() into the same file as create/attach. Affected files ... .. //depot/projects/dtrace/src/lib/libproc/Makefile#3 edit .. //depot/projects/dtrace/src/lib/libproc/_libproc.h#3 edit .. //depot/projects/dtrace/src/lib/libproc/libproc.h#2 edit .. //depot/projects/dtrace/src/lib/libproc/proc_create.c#3 edit .. //depot/projects/dtrace/src/lib/libproc/proc_free.c#3 delete .. //depot/projects/dtrace/src/lib/libproc/proc_util.c#2 edit Differences ... ==== //depot/projects/dtrace/src/lib/libproc/Makefile#3 (text+ko) ==== @@ -4,7 +4,6 @@ SRCS= \ proc_create.c \ - proc_free.c \ proc_util.c INCS= libproc.h ==== //depot/projects/dtrace/src/lib/libproc/_libproc.h#3 (text+ko) ==== @@ -37,6 +37,7 @@ struct proc_handle { pid_t pid; /* Process ID. */ int kq; /* Kernel event queue ID. */ + int flags; /* Process flags. */ int status; /* Process status (PS_*). */ }; ==== //depot/projects/dtrace/src/lib/libproc/libproc.h#2 (text+ko) ==== @@ -42,10 +42,13 @@ /* Function prototype definitions. */ __BEGIN_DECLS -int proc_attach(struct proc_handle *); +int proc_attach(pid_t pid, int flags, struct proc_handle **pphdl); int proc_continue(struct proc_handle *); +int proc_clearflags(struct proc_handle *, int); +int proc_create(const char *, char * const *, struct proc_handle **); int proc_detach(struct proc_handle *); -int proc_create(const char *, char * const *, struct proc_handle **); +int proc_getflags(struct proc_handle *); +int proc_setflags(struct proc_handle *, int); int proc_state(struct proc_handle *); int proc_wait(struct proc_handle *); pid_t proc_getpid(struct proc_handle *); ==== //depot/projects/dtrace/src/lib/libproc/proc_create.c#3 (text+ko) ==== @@ -37,11 +37,63 @@ #include int +proc_attach(pid_t pid, int flags, struct proc_handle **pphdl) +{ + struct proc_handle *phdl; + struct kevent kev; + int error = 0; + int status; + + if (pid == 0 || pphdl == NULL) + return (EINVAL); + + /* + * Allocate memory for the process handle, a structure containing + * all things related to the process. + */ + if ((phdl = malloc(sizeof(struct proc_handle))) == NULL) + return (ENOMEM); + + memset(phdl, 0, sizeof(struct proc_handle)); + phdl->pid = pid; + phdl->flags = flags; + phdl->status = PS_RUN; + + EV_SET(&kev, pid, EVFILT_PROC, EV_ADD | EV_ONESHOT, NOTE_EXIT, + 0, NULL); + + if ((phdl->kq = kqueue()) == -1) + err(1, "ERROR: cannot create kernel evet queue"); + + if (kevent(phdl->kq, &kev, 1, NULL, 0, NULL) < 0) + err(2, "ERROR: cannot monitor child process %d", pid); + + if (ptrace(PT_ATTACH, phdl->pid, NULL, 0) != 0) + error = errno; + + /* Wait for the child process to stop. */ + else if (waitpid(pid, &status, WUNTRACED) == -1) + err(3, "ERROR: child process %d didn't stop as expected", pid); + + /* Check for an unexpected status. */ + else if (WIFSTOPPED(status) == 0) + err(4, "ERROR: child process %d status 0x%x", pid, status); + else + phdl->status = PS_STOP; + + if (error) + proc_free(phdl); + else + *pphdl = phdl; + + return (error); +} + +int proc_create(const char *file, char * const *argv, struct proc_handle **pphdl) { struct proc_handle *phdl; struct kevent kev; - char errbuf[_POSIX2_LINE_MAX]; int error = 0; int status; pid_t pid; @@ -99,3 +151,9 @@ return (error); } + +void +proc_free(struct proc_handle *phdl) +{ + free(phdl); +} ==== //depot/projects/dtrace/src/lib/libproc/proc_util.c#2 (text+ko) ==== @@ -34,13 +34,12 @@ #include int -proc_attach(struct proc_handle *phdl) +proc_clearflags(struct proc_handle *phdl, int mask) { if (phdl == NULL) return (EINVAL); - if (ptrace(PT_ATTACH, phdl->pid, NULL, 0) != 0) - return (errno); + phdl->flags &= ~mask; return (0); } @@ -72,6 +71,26 @@ } int +proc_getflags(struct proc_handle *phdl) +{ + if (phdl == NULL) + return (-1); + + return(phdl->flags); +} + +int +proc_setflags(struct proc_handle *phdl, int mask) +{ + if (phdl == NULL) + return (EINVAL); + + phdl->flags |= mask; + + return (0); +} + +int proc_state(struct proc_handle *phdl) { if (phdl == NULL)