#include <fcntl.h>
#include <dirent.h>
+
+#define DEV_ENCODE(M,m) ( \
+ ( (M&0xfff) << 8) | ( (m&0xfff00) << 12) | (m&0xff) \
+)
+
+///////////////////////////////////////////////////////
#ifdef __FreeBSD__
#include <sys/param.h>
#include <sys/sysctl.h>
#include <sys/stat.h>
#include <sys/proc.h>
#include <sys/user.h>
+#define NO_TTY_VALUE DEV_ENCODE(-1,-1)
+#define HZ 1 // only bother with seconds
#endif
+///////////////////////////////////////////////////////
#ifdef __linux__
#include <asm/param.h> /* HZ */
#include <asm/page.h> /* PAGE_SIZE */
+#define NO_TTY_VALUE DEV_ENCODE(0,0)
+#ifndef HZ
+#warning HZ not defined, assuming it is 100
+#define HZ 100
+#endif
#endif
-static int P_euid;
-static int P_pid;
+///////////////////////////////////////////////////////////
+
+#ifndef PAGE_SIZE
+#warning PAGE_SIZE not defined, assuming it is 4096
+#define PAGE_SIZE 4096
+#endif
+
+
+
+static char P_tty_text[16];
static char P_cmd[16];
static char P_state;
-static int P_ppid, P_pgrp, P_session, P_tty, P_tpgid;
+static int P_euid;
+static int P_pid;
+static int P_ppid, P_pgrp, P_session, P_tty_num, P_tpgid;
static unsigned long P_flags, P_min_flt, P_cmin_flt, P_maj_flt, P_cmaj_flt, P_utime, P_stime;
static long P_cutime, P_cstime, P_priority, P_nice, P_timeout, P_alarm;
static unsigned long P_start_time, P_vsize;
static unsigned long P_wchan, P_nswap, P_cnswap;
+
#if 0
static int screen_cols = 80;
static int w_count;
static char *flagptr; /* current location in ps_argv[thisarg] */
-#ifndef PAGE_SIZE
-#warning PAGE_SIZE not defined, assuming it is 4096
-#define PAGE_SIZE 4096
-#endif
-
-#ifndef HZ
-#warning HZ not defined, assuming it is 100
-#define HZ 100
-#endif
-
static void usage(void){
&P_euid, &P_euid // don't know which is which
);
/* fprintf(stderr, "stat2proc converted %d fields.\n",num); */
- // convert FreeBSD tty numbers to Linux format :-)
- P_tty = ((tty_min&0xfff00)<<12) | ((tty_maj&0xfff)<<8) | (tty_min&0xff) ;
+
+ snprintf(P_tty_text, sizeof P_tty_text, "%3d,%-3d", tty_maj, tty_min);
+ P_tty_num = DEV_ENCODE(tty_maj,tty_min);
+// tty decode is 224 to 256 bytes on i386
+#if 1
+ tmp = NULL;
+ if (tty_maj == 5) tmp = " ttyp%c ";
+ if (tty_maj == 12) tmp = " ttyv%c ";
+ if (tty_maj == 28) tmp = " ttyd%c ";
+ if (P_tty_num == NO_TTY_VALUE) tmp = " ? ";
+ if (P_tty_num == DEV_ENCODE(0,0)) tmp = "console";
+ if (P_tty_num == DEV_ENCODE(12,255)) tmp = "consolectl";
+ if (tmp) {
+ snprintf(
+ P_tty_text,
+ sizeof P_tty_text,
+ tmp,
+ "0123456789abcdefghijklmnopqrstuvwxyz"[tty_min&31]
+ );
+ }
+#endif
+
if(num < 9) return 0;
if(P_pid != pid) return 0;
return 1;
"%u %u %u %u " /* no use for RT signals */
"%lu %lu %lu",
&P_state,
- &P_ppid, &P_pgrp, &P_session, &P_tty, &P_tpgid,
+ &P_ppid, &P_pgrp, &P_session, &P_tty_num, &P_tpgid,
&P_flags, &P_min_flt, &P_cmin_flt, &P_maj_flt, &P_cmaj_flt, &P_utime, &P_stime,
&P_cutime, &P_cstime, &P_priority, &P_nice, &P_timeout, &P_alarm,
&P_start_time, &P_vsize,
/* fprintf(stderr, "stat2proc converted %d fields.\n",num); */
P_vsize /= 1024;
P_rss *= (PAGE_SIZE/1024);
+
+ memcpy(P_tty_text, " ? ", 8);
+ if (P_tty_num != NO_TTY_VALUE) {
+ int tty_maj = (P_tty_num>>8)&0xfff;
+ int tty_min = (P_tty_num&0xff) | ((P_tty_num>>12)&0xfff00);
+ snprintf(P_tty_text, sizeof P_tty_text, "%3d,%-3d", tty_maj, tty_min);
+ }
+
if(num < 30) return 0;
if(P_pid != pid) return 0;
return 1;
}
static void print_proc(void){
- char tty[16];
- snprintf(tty, sizeof tty, "%3d,%-3d", (P_tty>>8)&0xfff, (P_tty&0xff) | ((P_tty>>12)&0xfff00));
switch(ps_format){
case 0:
- printf("%5d %s %s", P_pid, tty, do_time(P_utime+P_stime));
+ printf("%5d %s %s", P_pid, P_tty_text, do_time(P_utime+P_stime));
break;
case 'o':
printf("%d\n", P_pid);
"%5ld %06x %s %s",
P_state, P_euid, P_pid, P_ppid, do_cpu(0),
(int)P_priority, (int)P_nice, P_vsize/(PAGE_SIZE/1024),
- (unsigned)(P_wchan&0xffffff), tty, do_time(P_utime+P_stime)
+ (unsigned)(P_wchan&0xffffff), P_tty_text, do_time(P_utime+P_stime)
);
break;
case 'f':
printf(
"%8s %5d %5d %s %s %s %s",
- do_user(), P_pid, P_ppid, do_cpu(0), do_stime(), tty, do_time(P_utime+P_stime)
+ do_user(), P_pid, P_ppid, do_cpu(0), do_stime(), P_tty_text, do_time(P_utime+P_stime)
);
break;
case 'j':
printf(
"%5d %5d %5d %s %s",
- P_pid, P_pgrp, P_session, tty, do_time(P_utime+P_stime)
+ P_pid, P_pgrp, P_session, P_tty_text, do_time(P_utime+P_stime)
);
break;
case 'u'|0x80:
printf(
"%8s %5d %s %s %5ld %4ld %s %c %s %s",
- do_user(), P_pid, do_cpu(1), do_mem(1), P_vsize, P_rss, tty, P_state,
+ do_user(), P_pid, do_cpu(1), do_mem(1), P_vsize, P_rss, P_tty_text, P_state,
do_stime(), do_time(P_utime+P_stime)
);
break;
case 'v'|0x80:
printf(
"%5d %s %c %s %6d - - %5d %s",
- P_pid, tty, P_state, do_time(P_utime+P_stime), (int)P_maj_flt,
+ P_pid, P_tty_text, P_state, do_time(P_utime+P_stime), (int)P_maj_flt,
(int)P_rss, do_mem(1)
);
break;
case 'j'|0x80:
printf(
"%5d %5d %5d %5d %s %5d %c %5d %s",
- P_ppid, P_pid, P_pgrp, P_session, tty, P_tpgid, P_state, P_euid, do_time(P_utime+P_stime)
+ P_ppid, P_pid, P_pgrp, P_session, P_tty_text, P_tpgid, P_state, P_euid, do_time(P_utime+P_stime)
);
break;
case 'l'|0x80:
"0 %5d %5d %5d %3d %3d "
"%5ld %4ld %06x %c %s %s",
P_euid, P_pid, P_ppid, (int)P_priority, (int)P_nice,
- P_vsize, P_rss, (unsigned)(P_wchan&0xffffff), P_state, tty, do_time(P_utime+P_stime)
+ P_vsize, P_rss, (unsigned)(P_wchan&0xffffff), P_state, P_tty_text, do_time(P_utime+P_stime)
);
break;
default:
if(want_one_command){
if(strcmp(want_one_command,P_cmd)) continue;
}else{
- if(!select_notty && P_tty==-1) continue;
+ if(!select_notty && P_tty_num==NO_TTY_VALUE) continue;
if(!select_all && P_euid!=ouruid) continue;
}
found_a_proc++;
/* Ought to have debug print stuff like this:
* #define Print(fmt, args...) printf("Debug: " fmt, ## args)
*/
-#ifdef HAVE_CONFIG_H
-#include "config.h"
-#endif
#include <stdlib.h>
#include <stdio.h>
trace("-w wide output.\n");
w_count++;
break;
-#ifdef NOBODY_HAS_BSD_HABITS_ANYMORE
- case 'x': /* Same as -y, but for System V Release 4 MP */
- trace("-x works like Sun Solaris & SCO Unixware -y option\n");
- format_modifiers |= FM_x;
- break;
-#endif
+ case 'x': /* behind personality until "ps -ax" habit is uncommon */
+ if(personality & PER_SVR4_x){
+ // Same as -y, but for System V Release 4 MP
+ trace("-x works like Sun Solaris & SCO Unixware -y option\n");
+ format_modifiers |= FM_y;
+ break;
+ }
+ if(personality & PER_HPUX_x){
+ trace("-x extends the command line\n");
+ w_count += 2;
+ unix_f_option = 1;
+ break;
+ }
+ return "Must set personality to get -x option.";
case 'y': /* Sun's -l hack (also: Irix "lnode" resource control info) */
trace("-y Print lnone info in UID/USER column or do Sun -l hack.\n");
format_modifiers |= FM_y;
#if 0
case 'z': /* alias of Mandatory Access Control level info */
trace("-z shows aliased MAC info\n");
- return "Don't understand MAC on Linux.";
+ return "Don't understand MAC aliases on Linux.";
break;
#endif
case '-':
trace("j job control format\n");
format_flags |= FF_Bj;
break;
-#if 0
- case 'k': // OpenBSD: don't hide "kernel threads" -- like the swapper?
- trace("k Print LWP (thread) info.\n"); // was: Use /vmcore as c-dumpfile\n");
- break;
-#endif
+ case 'k':
+ // OpenBSD: don't hide "kernel threads" -- like the swapper?
+ // trace("k Print LWP (thread) info.\n"); // was: Use /vmcore as c-dumpfile\n");
+
+ // NetBSD, and soon (?) FreeBSD: sort-by-keyword
+ trace("k Specify sorting keywords.\n");
+ arg=get_opt_arg();
+ if(!arg) return "Long sort specification must follow 'k'.";
+ defer_sf_option(arg, SF_G_sort);
+ return NULL; /* can't have any more options */
case 'l':
trace("l Display long format\n");
format_flags |= FF_Bl;
// get seriously confused. Ask yourself if users would freak out
// about "ps -aux" suddenly changing behavior if a user "x" were
// added to the system.
+ //
+ // Also, a "-x" option is coming. It's already there in fact,
+ // for some non-default personalities. So "ps -ax" will parse
+ // as SysV options... and you're screwed if you've been patching
+ // out the friendly warning. Cut-over is likely to be in 2005.
if(!(personality & PER_FORCE_BSD))
fprintf(stderr, "Warning: bad syntax, perhaps a bogus '-'? See http://procps.sf.net/faq.html\n");
// Remember: contact albert@users.sf.net or procps-feedback@lists.sf.net