bin/65803: ps enhancements (posix syntax, and more)
Cyrille Lefevre
cyrille.lefevre at laposte.net
Wed Apr 21 17:20:22 PDT 2004
The following reply was made to PR bin/65803; it has been noted by GNATS.
From: Cyrille Lefevre <cyrille.lefevre at laposte.net>
To: freebsd gnats <freebsd-gnats-submit at freebsd.org>
Cc:
Subject: Re: bin/65803: ps enhancements (posix syntax, and more)
Date: Thu, 22 Apr 2004 02:15:04 +0200
the original PR describe OpenBSD -k as don't show kernel threads,
which is wrong, OpenBSD -K is FreeBSD -H except that system processes
aren't displayed by default while they are under FreeBSD.
added features :
-t '?' to select process not attached to a terminal (from older bsd).
tsid added in -j format string.
at last, implement KERN_PROC_SESSION in /sys/kern/kern_proc.c as
well as system processes filtering in KERN_PROC_PROC (not sure about
that). both features have not been tested yet, but will be soon.
bugs :
ttys are udev_t, not dev_t (this prevented the -t '?' to work).
pscomp() getpcpu * 100 or always 0.
also, uses typed variables instead of an
integer generic one which is more cleaner.
FYI, here are the ps sizes once compiled w/ -O and stripped :
-current : 38048
this one : 38760
diff -u orig/ps.c ./ps.c
--- orig/ps.c Tue Apr 20 03:31:42 2004
+++ ./ps.c Thu Apr 22 00:52:48 2004
@@ -94,12 +94,13 @@
const char *msg2;
int count;
int noval;
+ int all;
union {
char **cmds;
char *fmt;
gid_t *gids;
pid_t *pids;
- dev_t *ttys;
+ udev_t *ttys;
uid_t *uids;
void *ptr;
} l;
@@ -147,7 +148,7 @@
/* PLEASE KEEP THE TABLE BELOW SORTED ALPHABETICALLY!!! */
static LIST lists[] = {
#define _LIST(t, s, o, k, m1, m2) \
- { t, sizeof(s), KOFF(o), k, m1, m2, 0, 0, { 0 } }
+ { t, sizeof(s), KOFF(o), k, m1, m2, 0, 0, 0, { 0 } }
_LIST(CMD, char *, ki_comm, 0,
"command", NULL), /* nop | -C */
_LIST(FMT, char, ki_sparestrings, 0,
@@ -334,7 +335,7 @@
flag = 0;
if (nselectors == 1) {
for (list = lists; list->type != _LTYPE; list++)
- if (list->count && list->op) {
+ if (list->count && list->op && !list->all) {
what = list->op | showthreads;
flag = (int)((int *)list->l.ptr)[0];
nselectors = 0;
@@ -363,7 +364,7 @@
}
}
#if defined(DEBUG)
-fprintf(stderr, "what:flag:nentries:nkept == %d:%d:%d:%d\n",
+fprintf(stderr, "what:flag:nentries:nkept == %x:%u:%d:%d\n",
what, flag, nentries, nkept);
#endif
sizevars();
@@ -484,7 +485,8 @@
{
static char bsd_opts[] = "AaCcefG:gHhjLlM:mN:nO:o:p:QqrSsTt:U:uvwxXZ";
static char psx_opts[] = "AaC:cdefG:g:jLlMmn:O:o:Pp:Qqs:Tt:u:U:xyz";
- /* internal format syntax:
+ /*
+ * internal format syntax:
* keyword[:flags in reverse polish notation][=header]
* reverse polish notation:
* x by itself, * means any, x! means not x,
@@ -497,38 +499,38 @@
* both modifiers: X if extended.
*/
/*
-Z: prepend label
-d: pid tt state time command
-j: user pid ppid pgid (sid) jobc state tt time command
-l: uid pid ppid cpu pri nice vsz rss mwchan state tt time command
-n: user -> uid, mwchan -> nwchan
-u: user pid %cpu %mem vsz rss tt state start time command
-s: uid pid sig sigmask sigignore sigcatch state tt command
-v: pid (tt) state time sl re pagein vsz rss lim tsiz %cpu %mem command
+ * Z: prepend label
+ * d: pid tt state time command
+ * j: user pid ppid pgid (sid) jobc state tt time command
+ * l: uid pid ppid cpu pri nice vsz rss mwchan state tt time command
+ * n: user -> uid, mwchan -> nwchan
+ * u: user pid %cpu %mem vsz rss tt state start time command
+ * s: uid pid sig sigmask sigignore sigcatch state tt command
+ * v: pid (tt) state time sl re pagein vsz rss lim tsiz %cpu %mem command
*/
static char bsd_fmtstr[] = "\
label:Z user:[ju](n!)& uid:([ju]n&)([ls]([ju]!)&)| pid:2! ppid:[jl] \
-pgid:j sid:jX& tpgid:jX& jobc:j sig:s sigmask:s sigignore:s sigcatch:s \
-cpu:l pri:l nice:l %cpu:u %mem:u vsz:[lu] rss:[lu] mwchan:l(n!)& \
-nwchan:ln& tt:[d2u](vX&)| state:1! tt:[jls]([du]!)& start:u time:1! \
-sl:v re:v pagein:v vsz:v([lu]!)& rss:v([lu]!)& lim:v tsiz:v %cpu:v(u!)& \
-%mem:v(u!)& command:1! \
+pgid:j sid:jX& tpgid:jX& tsid:jX& jobc:j sig:s sigmask:s sigignore:s \
+sigcatch:s cpu:l pri:l nice:l %cpu:u %mem:u vsz:[lu] rss:[lu] \
+mwchan:l(n!)& nwchan:ln& tt:[d2u](vX&)| state:1! tt:[jls]([du]!)& \
+start:u time:1! sl:v re:v pagein:v vsz:v([lu]!)& rss:v([lu]!)& lim:v \
+tsiz:v %cpu:v(u!)& %mem:v(u!)& command:1! \
";
/*
-M: prepend label
-P: add psr
-c: omit nice, c -> cls
-d: pid tty time comm
-f: user pid ppid c stime tty time args
-j: pid ppid pgid sid tty time comm
-l: f s uid pid ppid c pri nice addr sz wchan tty time comm
-y: omit f, addr -> rss
+ * M: prepend label
+ * P: add psr
+ * c: omit nice, c -> cls
+ * d: pid tty time comm
+ * f: user pid ppid c stime tty time args
+ * j: pid ppid pgid sid tty time comm
+ * l: f s uid pid ppid c pri nice addr sz wchan tty time comm
+ * y: omit f, addr -> rss
*/
static char psx_fmtstr[] = "\
label:M f:l(y!)& s:l user:f uid:l(f!)& pid:2! ppid:[fjl] pgid:j \
-sid:j tpgid:jX& c:[fl](c!)& class:[fl]c& psr:P pri:l nice:l(c!)& \
-addr:l(y!)& rss:ly& sz:l wchan:l stime:f tty:1! time:1! comm:[1f]! \
-args:f \
+sid:j tpgid:jX& tsid:jX& c:[fl](c!)& class:[fl]c& psr:P pri:l \
+nice:l(c!)& addr:l(y!)& rss:ly& sz:l wchan:l stime:f tty:1! time:1! \
+comm:[1f]! args:f \
";
int c;
@@ -982,7 +984,7 @@
/* gid_t gid; */
struct group *grp;
pid_t pid;
- /* dev_t tty; */
+ /* udev_t tty; */
struct stat sb;
const char *ttypath;
/* uid_t uid; */
@@ -1132,7 +1134,11 @@
(void)strlcpy(buf, arg, len + 1);
if (strcmp(buf, "co") == 0)
ttypath = _PATH_CONSOLE;
- else if (*buf != '/') {
+ else if (*buf == '?') {
+ ttypath = NULL;
+ sb.st_rdev = (udev_t)-1;
+ list->all = 1;
+ } else if (*buf != '/') {
(void)snprintf(pathbuf,
sizeof(buf), "%s%s",
!strncmp(buf, "tty", 3) ? _PATH_DEV :
@@ -1140,15 +1146,18 @@
ttypath = pathbuf;
} else
ttypath = buf;
- if (stat(ttypath, &sb) == -1) {
- warn("%s", ttypath);
- fatal = 1;
- continue;
- }
- if (!S_ISCHR(sb.st_mode)) {
- warnx("%s: not a %s", ttypath, list->msg);
- fatal = 1;
- continue;
+ if (ttypath) {
+ if (stat(ttypath, &sb) == -1) {
+ warn("%s", ttypath);
+ fatal = 1;
+ continue;
+ }
+ if (!S_ISCHR(sb.st_mode)) {
+ warnx("%s: not a %s", ttypath,
+ list->msg);
+ fatal = 1;
+ continue;
+ }
}
/* tty = sb.st_rdev; */
break;
@@ -1344,18 +1353,19 @@
pscomp(const void *a, const void *b)
{
const KINFO *ka, *kb;
- int i;
+ double d;
+ segsz_t s;
+ udev_t u;
#define VSIZE(k) ((k)->ki_p->ki_dsize + (k)->ki_p->ki_ssize + \
(k)->ki_p->ki_tsize)
ka = a;
kb = b;
/* SORTCPU and SORTMEM are sorted in descending order. */
- if (sortby == SORTCPU && (i = (int)(getpcpu(kb) - getpcpu(ka))) != 0)
- return(i);
- if (sortby == SORTMEM &&
- (i = (int)(VSIZE(kb) - VSIZE(ka))) != 0)
- return(i);
+ if (sortby == SORTCPU && (d = (getpcpu(kb) - getpcpu(ka))) != 0)
+ return((int)(d * 100));
+ if (sortby == SORTMEM && (s = (VSIZE(kb) - VSIZE(ka))) != 0)
+ return((int)s);
/*
* TTY's are sorted in ascending order, except that all NODEV
* processes come before all processes with a device.
@@ -1364,8 +1374,8 @@
return(-1);
if (ka->ki_p->ki_tdev != NODEV && kb->ki_p->ki_tdev == NODEV)
return(1);
- if ((i = (int)(ka->ki_p->ki_tdev - kb->ki_p->ki_tdev)) != 0)
- return(i);
+ if ((u = (ka->ki_p->ki_tdev - kb->ki_p->ki_tdev)) != 0)
+ return((int)u);
/* PID's are sorted in ascending order. */
return((int)(ka->ki_p->ki_pid - kb->ki_p->ki_pid));
}
Index: kern_proc.c
===================================================================
RCS file: /home/ncvs/src/sys/kern/kern_proc.c,v
retrieving revision 1.202
diff -u -I$Id.*$ -I$.+BSD.*$ -r1.202 kern_proc.c
--- kern_proc.c 5 Apr 2004 21:03:34 -0000 1.202
+++ kern_proc.c 21 Apr 2004 23:45:23 -0000
/* could do this by traversing pgrp */
if (p->p_pgrp == NULL ||
p->p_pgrp->pg_id != (pid_t)name[0]) {
+ PROC_UNLOCK(p);
+ continue;
+ }
+ break;
+
+ case KERN_PROC_SESSION:
+ if (p->p_session == NULL ||
+ p->p_session->s_sid != (pid_t)name[0]) {
PROC_UNLOCK(p);
continue;
}
@@ -1018,6 +1030,8 @@
break;
case KERN_PROC_PROC:
+ if (p->flag & P_SYSTEM)
+ continue;
break;
default:
Cyrille Lefevre
--
mailto:cyrille.lefevre at laposte.net
More information about the freebsd-bugs
mailing list