aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--procps/Config.src10
-rw-r--r--procps/ps.c103
2 files changed, 94 insertions, 19 deletions
diff --git a/procps/Config.src b/procps/Config.src
index 570b026da..5cd47c84f 100644
--- a/procps/Config.src
+++ b/procps/Config.src
@@ -90,12 +90,20 @@ config PS
90config FEATURE_PS_WIDE 90config FEATURE_PS_WIDE
91 bool "Enable wide output option (-w)" 91 bool "Enable wide output option (-w)"
92 default y 92 default y
93 depends on PS 93 depends on PS && !DESKTOP
94 help 94 help
95 Support argument 'w' for wide output. 95 Support argument 'w' for wide output.
96 If given once, 132 chars are printed, and if given more 96 If given once, 132 chars are printed, and if given more
97 than once, the length is unlimited. 97 than once, the length is unlimited.
98 98
99config FEATURE_PS_LONG
100 bool "Enable long output option (-l)"
101 default y
102 depends on PS && !DESKTOP
103 help
104 Support argument 'l' for long output.
105 Adds fields PPID, RSS, START, TIME & TTY
106
99config FEATURE_PS_TIME 107config FEATURE_PS_TIME
100 bool "Enable time and elapsed time output" 108 bool "Enable time and elapsed time output"
101 default y 109 default y
diff --git a/procps/ps.c b/procps/ps.c
index dcc0f7bd4..c98384d71 100644
--- a/procps/ps.c
+++ b/procps/ps.c
@@ -39,6 +39,12 @@
39//usage: IF_FEATURE_PS_WIDE( 39//usage: IF_FEATURE_PS_WIDE(
40//usage: "\n w Wide output" 40//usage: "\n w Wide output"
41//usage: ) 41//usage: )
42//usage: IF_FEATURE_PS_LONG(
43//usage: "\n l Long output"
44//usage: )
45//usage: IF_FEATURE_SHOW_THREADS(
46//usage: "\n T Show threads"
47//usage: )
42//usage: 48//usage:
43//usage:#endif /* ENABLE_DESKTOP */ 49//usage:#endif /* ENABLE_DESKTOP */
44//usage: 50//usage:
@@ -56,15 +62,15 @@
56//usage: " 2990 andersen andersen R ps\n" 62//usage: " 2990 andersen andersen R ps\n"
57 63
58#include "libbb.h" 64#include "libbb.h"
65#ifdef __linux__
66# include <sys/sysinfo.h>
67#endif
59 68
60/* Absolute maximum on output line length */ 69/* Absolute maximum on output line length */
61enum { MAX_WIDTH = 2*1024 }; 70enum { MAX_WIDTH = 2*1024 };
62 71
63#if ENABLE_DESKTOP 72#if ENABLE_DESKTOP
64 73
65#ifdef __linux__
66# include <sys/sysinfo.h>
67#endif
68#include <sys/times.h> /* for times() */ 74#include <sys/times.h> /* for times() */
69#ifndef AT_CLKTCK 75#ifndef AT_CLKTCK
70# define AT_CLKTCK 17 76# define AT_CLKTCK 17
@@ -625,15 +631,21 @@ int ps_main(int argc UNUSED_PARAM, char **argv UNUSED_PARAM)
625 enum { 631 enum {
626 OPT_Z = (1 << 0) * ENABLE_SELINUX, 632 OPT_Z = (1 << 0) * ENABLE_SELINUX,
627 OPT_T = (1 << ENABLE_SELINUX) * ENABLE_FEATURE_SHOW_THREADS, 633 OPT_T = (1 << ENABLE_SELINUX) * ENABLE_FEATURE_SHOW_THREADS,
634 OPT_l = (1 << ENABLE_SELINUX) * (1 << ENABLE_FEATURE_SHOW_THREADS) * ENABLE_FEATURE_PS_LONG,
628 }; 635 };
636#if ENABLE_FEATURE_PS_LONG
637 time_t now = now;
638 struct sysinfo info;
639#endif
629 int opts = 0; 640 int opts = 0;
630 /* If we support any options, parse argv */ 641 /* If we support any options, parse argv */
631#if ENABLE_SELINUX || ENABLE_FEATURE_SHOW_THREADS || ENABLE_FEATURE_PS_WIDE 642#if ENABLE_SELINUX || ENABLE_FEATURE_SHOW_THREADS || ENABLE_FEATURE_PS_WIDE || ENABLE_FEATURE_PS_LONG
632# if ENABLE_FEATURE_PS_WIDE 643# if ENABLE_FEATURE_PS_WIDE
633 /* -w is a bit complicated */ 644 /* -w is a bit complicated */
634 int w_count = 0; 645 int w_count = 0;
635 opt_complementary = "-:ww"; 646 opt_complementary = "-:ww";
636 opts = getopt32(argv, IF_SELINUX("Z")IF_FEATURE_SHOW_THREADS("T")"w", &w_count); 647 opts = getopt32(argv, IF_SELINUX("Z")IF_FEATURE_SHOW_THREADS("T")IF_FEATURE_PS_LONG("l")
648 "w", &w_count);
637 /* if w is given once, GNU ps sets the width to 132, 649 /* if w is given once, GNU ps sets the width to 132,
638 * if w is given more than once, it is "unlimited" 650 * if w is given more than once, it is "unlimited"
639 */ 651 */
@@ -648,23 +660,47 @@ int ps_main(int argc UNUSED_PARAM, char **argv UNUSED_PARAM)
648# else 660# else
649 /* -w is not supported, only -Z and/or -T */ 661 /* -w is not supported, only -Z and/or -T */
650 opt_complementary = "-"; 662 opt_complementary = "-";
651 opts = getopt32(argv, IF_SELINUX("Z")IF_FEATURE_SHOW_THREADS("T")); 663 opts = getopt32(argv, IF_SELINUX("Z")IF_FEATURE_SHOW_THREADS("T")IF_FEATURE_PS_LONG("l"));
652# endif 664# endif
653#endif
654 665
655#if ENABLE_SELINUX 666# if ENABLE_SELINUX
656 if ((opts & OPT_Z) && is_selinux_enabled()) { 667 if ((opts & OPT_Z) && is_selinux_enabled()) {
657 psscan_flags = PSSCAN_PID | PSSCAN_CONTEXT 668 psscan_flags = PSSCAN_PID | PSSCAN_CONTEXT
658 | PSSCAN_STATE | PSSCAN_COMM; 669 | PSSCAN_STATE | PSSCAN_COMM;
659 puts(" PID CONTEXT STAT COMMAND"); 670 puts(" PID CONTEXT STAT COMMAND");
660 } else 671 } else
661#endif 672# endif
662 { 673 if (opts & OPT_l) {
674 psscan_flags = PSSCAN_STATE | PSSCAN_UIDGID | PSSCAN_PID | PSSCAN_PPID
675 | PSSCAN_TTY | PSSCAN_STIME | PSSCAN_UTIME | PSSCAN_COMM
676 | PSSCAN_VSZ | PSSCAN_RSS;
677/* http://pubs.opengroup.org/onlinepubs/9699919799/utilities/ps.html
678 * mandates for -l:
679 * -F Flags associated with the process (?)
680 * S The state of the process
681 * UID,PID,PPID
682 * -C Processor utilization for scheduling
683 * -PRI The priority of the process; higher numbers mean lower priority
684 * -NI Nice value; used in priority computation
685 * -ADDR The address of the process
686 * SZ The size in blocks of the core image of the process
687 * -WCHAN The event for which the process is waiting or sleeping
688 * TTY
689 * TIME The cumulative execution time for the process
690 * CMD
691 * We don't show fileds marked with '-'. We show VSZ and RSS instead of SZ
692 */
693 puts("S UID PID PPID VSZ RSS TTY TIME CMD");
694 now = time(NULL);
695 sysinfo(&info);
696 }
697 else {
663 puts(" PID USER VSZ STAT COMMAND"); 698 puts(" PID USER VSZ STAT COMMAND");
664 } 699 }
665 if (opts & OPT_T) { 700 if (opts & OPT_T) {
666 psscan_flags |= PSSCAN_TASKS; 701 psscan_flags |= PSSCAN_TASKS;
667 } 702 }
703#endif
668 704
669 p = NULL; 705 p = NULL;
670 while ((p = procps_scan(p, psscan_flags)) != NULL) { 706 while ((p = procps_scan(p, psscan_flags)) != NULL) {
@@ -678,15 +714,46 @@ int ps_main(int argc UNUSED_PARAM, char **argv UNUSED_PARAM)
678 } else 714 } else
679#endif 715#endif
680 { 716 {
681 const char *user = get_cached_username(p->uid); 717 char buf6[6];
682 //if (p->vsz == 0) 718 smart_ulltoa5(p->vsz, buf6, " mgtpezy");
683 // len = printf("%5u %-8.8s %s ", 719 buf6[5] = '\0';
684 // p->pid, user, p->state); 720#if ENABLE_FEATURE_PS_LONG
685 //else 721 if (opts & OPT_l) {
722 char bufr[6], strt[6];
723 char tty[2 * sizeof(int)*3 + 2];
724 char *endp;
725 unsigned sut = (p->stime + p->utime) / 100;
726 unsigned elapsed = info.uptime - (p->start_time / 100);
727 time_t start = now - elapsed;
728 struct tm *tm = localtime(&start);
729
730 smart_ulltoa5(p->rss, bufr, " mgtpezy");
731 bufr[5] = '\0';
732
733 if (p->tty_major == 136)
734 endp = stpcpy(tty, "pts/");
735 else
736 if (p->tty_major == 4) {
737 endp = stpcpy(tty, "tty");
738 if (p->tty_minor >= 64) {
739 p->tty_minor -= 64;
740 *endp++ = 'S';
741 }
742 }
743 else
744 endp = tty + sprintf(tty, "%d:", p->tty_major);
745 strcpy(endp, utoa(p->tty_minor));
746
747 strftime(strt, 6, (elapsed >= (24 * 60 * 60)) ? "%b%d" : "%H:%M", tm);
748 strt[5] = '\0';
749 // S UID PID PPID VSZ RSS TTY TIME CMD
750 len = printf("%c %5u %5u %5u %5s %5s %-5s %02u:%02u:%02u ",
751 p->state[0], p->uid, p->pid, p->ppid, buf6, bufr, tty,
752 sut / 3600, (sut % 3600) / 60, sut % 60);
753 } else
754#endif
686 { 755 {
687 char buf6[6]; 756 const char *user = get_cached_username(p->uid);
688 smart_ulltoa5(p->vsz, buf6, " mgtpezy");
689 buf6[5] = '\0';
690 len = printf("%5u %-8.8s %s %s ", 757 len = printf("%5u %-8.8s %s %s ",
691 p->pid, user, buf6, p->state); 758 p->pid, user, buf6, p->state);
692 } 759 }